This commit is contained in:
Delucse
2020-12-03 11:17:39 +01:00
parent 4f57e7fd32
commit 5d9bfa97af
7 changed files with 440 additions and 14 deletions
+27 -14
View File
@@ -2,6 +2,7 @@ import React, { Component } from 'react';
import PropTypes from 'prop-types';
import { connect } from 'react-redux';
import { Link } from 'react-router-dom';
import { logout } from '../actions/authActions';
import senseboxLogo from './sensebox_logo.svg';
@@ -20,7 +21,7 @@ import ListItemIcon from '@material-ui/core/ListItemIcon';
import ListItemText from '@material-ui/core/ListItemText';
import LinearProgress from '@material-ui/core/LinearProgress';
import { faBars, faChevronLeft, faLayerGroup, faBuilding, faIdCard, faEnvelope, faCog, faChalkboardTeacher, faFolderPlus, faTools, faLightbulb } from "@fortawesome/free-solid-svg-icons";
import { faBars, faChevronLeft, faLayerGroup, faSignInAlt, faSignOutAlt, faCertificate, faUserCircle, faIdCard, faEnvelope, faCog, faChalkboardTeacher, faFolderPlus, faTools, faLightbulb } from "@fortawesome/free-solid-svg-icons";
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
const styles = (theme) => ({
@@ -102,8 +103,7 @@ class Navbar extends Component {
{[{ text: 'Tutorials', icon: faChalkboardTeacher, link: "/tutorial" },
{ text: 'Tutorial-Builder', icon: faTools, link: "/tutorial/builder" },
{ text: 'Galerie', icon: faLightbulb, link: "/gallery" },
{ text: 'Projekte', icon: faLayerGroup, link: "/project" },
{ text: 'Einstellungen', icon: faCog, link: "/settings" }].map((item, index) => (
{ text: 'Projekte', icon: faLayerGroup, link: "/project" }].map((item, index) => (
<Link to={item.link} key={index} style={{ textDecoration: 'none', color: 'inherit' }}>
<ListItem button onClick={this.toggleDrawer}>
<ListItemIcon><FontAwesomeIcon icon={item.icon} /></ListItemIcon>
@@ -113,14 +113,25 @@ class Navbar extends Component {
))}
</List>
<Divider classes={{ root: this.props.classes.appBarColor }} style={{ marginTop: 'auto' }} />
{/* <List>
{[{ text: 'Über uns', icon: faBuilding }, { text: 'Kontakt', icon: faEnvelope }, { text: 'Impressum', icon: faIdCard }].map((item, index) => (
<ListItem button key={index} onClick={this.toggleDrawer}>
<ListItemIcon><FontAwesomeIcon icon={item.icon} /></ListItemIcon>
<ListItemText primary={item.text} />
</ListItem>
))}
</List> */}
<List>
{[{ text: 'Anmelden', icon: faSignInAlt, link: '/user/login', restriction: !this.props.isAuthenticated },
{ text: 'Konto', icon: faUserCircle, link: '/user', restriction: this.props.isAuthenticated },
{ text: 'MyBadges', icon: faCertificate, link: '/user/badge', restriction: this.props.isAuthenticated },
{ text: 'Abmelden', icon: faSignOutAlt, function: this.props.logout, restriction: this.props.isAuthenticated },
{ text: 'Einstellungen', icon: faCog, link: "/settings" }].map((item, index) => {
if(item.restriction || Object.keys(item).filter(attribute => attribute === 'restriction').length === 0){
return(
<Link to={item.link} key={index} style={{ textDecoration: 'none', color: 'inherit' }}>
<ListItem button onClick={item.function ? () => {item.function(); this.toggleDrawer();} : this.toggleDrawer}>
<ListItemIcon><FontAwesomeIcon icon={item.icon} /></ListItemIcon>
<ListItemText primary={item.text} />
</ListItem>
</Link>
);
}
}
)}
</List>
</Drawer>
{this.props.tutorialIsLoading || this.props.projectIsLoading ?
<LinearProgress style={{marginBottom: '30px', boxShadow: '0px 2px 4px -1px rgba(0,0,0,0.2),0px 4px 5px 0px rgba(0,0,0,0.14),0px 1px 10px 0px rgba(0,0,0,0.12)'}}/>
@@ -132,12 +143,14 @@ class Navbar extends Component {
Navbar.propTypes = {
tutorialIsLoading: PropTypes.bool.isRequired,
projectIsLoading: PropTypes.bool.isRequired
projectIsLoading: PropTypes.bool.isRequired,
isAuthenticated: PropTypes.bool.isRequired
};
const mapStateToProps = state => ({
tutorialIsLoading: state.tutorial.progress,
projectIsLoading: state.project.progress
projectIsLoading: state.project.progress,
isAuthenticated: state.auth.isAuthenticated
});
export default connect(mapStateToProps, null)(withStyles(styles, { withTheme: true })(withRouter(Navbar)));
export default connect(mapStateToProps, { logout })(withStyles(styles, { withTheme: true })(withRouter(Navbar)));
+3
View File
@@ -15,6 +15,7 @@ import Project from './Project/Project';
import Settings from './Settings/Settings';
import Impressum from './Impressum';
import Privacy from './Privacy';
import Login from './User/Login';
class Routes extends Component {
@@ -40,6 +41,8 @@ class Routes extends Component {
// User-Projects
<Route path="/project" exact component={ProjectHome} />
<Route path="/project/:projectId" exact component={Project} />
// User
<Route path="/user/login" exact component={Login} />
// settings
<Route path="/settings" exact component={Settings} />
// privacy
+157
View File
@@ -0,0 +1,157 @@
import React, { Component } from 'react';
import PropTypes from 'prop-types';
import { connect } from 'react-redux';
import { login } from '../../actions/authActions'
import { clearMessages } from '../../actions/messageActions'
import { withRouter } from 'react-router-dom';
import Snackbar from '../Snackbar';
import Breadcrumbs from '../Breadcrumbs';
import Button from '@material-ui/core/Button';
import IconButton from '@material-ui/core/IconButton';
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
import { faEye, faEyeSlash } from "@fortawesome/free-solid-svg-icons";
import TextField from '@material-ui/core/TextField';
import Divider from '@material-ui/core/Divider';
import InputAdornment from '@material-ui/core/InputAdornment';
import CircularProgress from '@material-ui/core/CircularProgress';
import Link from '@material-ui/core/Link';
export class Login extends Component {
constructor(props) {
super(props);
this.state = {
email: '',
password: '',
snackbar: false,
type: '',
key: '',
message: '',
showPassword: false
};
}
componentDidUpdate(props){
const { message } = this.props;
if (message !== props.message) {
if(message.id === 'LOGIN_SUCCESS'){
this.props.history.goBack();
}
// Check for login error
else if(message.id === 'LOGIN_FAIL'){
this.setState({ email: '', password: '', snackbar: true, key: Date.now(), message: 'Der Benutzername oder das Passwort ist nicht korrekt.', type: 'error' });
}
}
}
onChange = e => {
this.setState({ [e.target.name]: e.target.value });
};
onSubmit = e => {
e.preventDefault();
const {email, password} = this.state;
if(email !== '' && password !== ''){
// create user object
const user = {
email,
password
};
this.props.login(user);
} else {
this.setState({ snackbar: true, key: Date.now(), message: 'Gib sowohl ein Benutzername als auch ein Passwort ein.', type: 'error' });
}
};
handleClickShowPassword = () => {
this.setState({ showPassword: !this.state.showPassword });
};
handleMouseDownPassword = (e) => {
e.preventDefault();
};
render(){
return(
<div>
<Breadcrumbs content={[{ link: '/user/login', title: 'Anmelden' }]} />
<div style={{maxWidth: '500px', marginLeft: 'auto', marginRight: 'auto'}}>
<h1>Anmelden</h1>
<Snackbar
open={this.state.snackbar}
message={this.state.message}
type={this.state.type}
key={this.state.key}
/>
<TextField
style={{marginBottom: '10px'}}
// variant='outlined'
type='text'
label='E-Mail oder Nutzername'
name='email'
value={this.state.email}
onChange={this.onChange}
fullWidth={true}
/>
<TextField
// variant='outlined'
type={this.state.showPassword ? 'text' : 'password'}
label='Passwort'
name='password'
value={this.state.password}
InputProps={{
endAdornment:
<InputAdornment
position="end"
>
<IconButton
onClick={this.handleClickShowPassword}
onMouseDown={this.handleMouseDownPassword}
edge="end"
>
<FontAwesomeIcon size='xs' icon={this.state.showPassword ? faEyeSlash : faEye} />
</IconButton>
</InputAdornment>
}}
onChange={this.onChange}
fullWidth={true}
/>
<p>
<Button color="primary" variant='contained' onClick={this.onSubmit} style={{width: '100%'}}>
{this.props.progress ?
<div style={{height: '24.5px'}}><CircularProgress color="inherit" size={20}/></div>
: 'Anmelden'}
</Button>
</p>
<p style={{textAlign: 'center', fontSize: '0.8rem'}}>
<Link rel="noreferrer" target="_blank" href={'https://opensensemap.org/'} color="primary">Passwort vergessen?</Link>
</p>
<Divider variant='fullWidth'/>
<p style={{textAlign: 'center', paddingRight: "34px", paddingLeft: "34px"}}>
Du hast noch kein Konto? <Link rel="noreferrer" target="_blank" href={'https://opensensemap.org/'}>Registrieren</Link>
</p>
</div>
</div>
);
}
}
Login.propTypes = {
message: PropTypes.object.isRequired,
login: PropTypes.func.isRequired,
clearMessages: PropTypes.func.isRequired,
message: PropTypes.object.isRequired,
progress: PropTypes.bool.isRequired
};
const mapStateToProps = state => ({
message: state.message,
progress: state.auth.progress
});
export default connect(mapStateToProps, { login, clearMessages })(withRouter(Login));