adjustment of the tutorial component and all dependencies to the new tutorial.json
This commit is contained in:
parent
33445cf67c
commit
6c3709fde8
@ -1,4 +1,4 @@
|
||||
import { TUTORIAL_SUCCESS, TUTORIAL_ERROR, TUTORIAL_CHANGE, TUTORIAL_XML, TUTORIAL_ID, TUTORIAL_LEVEL } from './types';
|
||||
import { TUTORIAL_SUCCESS, TUTORIAL_ERROR, TUTORIAL_CHANGE, TUTORIAL_XML, TUTORIAL_ID, TUTORIAL_STEP } from './types';
|
||||
|
||||
export const tutorialChange = () => (dispatch) => {
|
||||
dispatch({
|
||||
@ -30,13 +30,6 @@ export const storeTutorialXml = (code) => (dispatch, getState) => {
|
||||
}
|
||||
};
|
||||
|
||||
// level = "instruction" or "assessment"
|
||||
export const setTutorialLevel = (level) => (dispatch) => {
|
||||
dispatch({
|
||||
type: TUTORIAL_LEVEL,
|
||||
payload: level
|
||||
});
|
||||
}
|
||||
|
||||
export const tutorialId = (id) => (dispatch) => {
|
||||
dispatch({
|
||||
@ -44,3 +37,10 @@ export const tutorialId = (id) => (dispatch) => {
|
||||
payload: id
|
||||
});
|
||||
};
|
||||
|
||||
export const tutorialStep = (step) => (dispatch) => {
|
||||
dispatch({
|
||||
type: TUTORIAL_STEP,
|
||||
payload: step
|
||||
});
|
||||
};
|
||||
|
@ -12,4 +12,4 @@ export const TUTORIAL_ERROR = 'TUTORIAL_ERROR';
|
||||
export const TUTORIAL_CHANGE = 'TUTORIAL_CHANGE';
|
||||
export const TUTORIAL_XML = 'TUTORIAL_XML';
|
||||
export const TUTORIAL_ID = 'TUTORIAL_ID';
|
||||
export const TUTORIAL_LEVEL = 'TUTORIAL_LEVEL';
|
||||
export const TUTORIAL_STEP = 'TUTORIAL_STEP';
|
||||
|
@ -26,16 +26,18 @@ class BlocklyWindow extends Component {
|
||||
this.props.onChangeWorkspace(event);
|
||||
Blockly.Events.disableOrphans(event);
|
||||
});
|
||||
Blockly.svgResize(workspace);
|
||||
}
|
||||
|
||||
componentDidUpdate(props) {
|
||||
if(props.initialXml !== this.props.initialXml){
|
||||
// guarantees that the current xml-code (this.props.initialXml) is rendered
|
||||
const workspace = Blockly.getMainWorkspace();
|
||||
workspace.clear();
|
||||
Blockly.Xml.domToWorkspace(Blockly.Xml.textToDom(this.props.initialXml), workspace);
|
||||
}
|
||||
}
|
||||
// componentDidUpdate(props) {
|
||||
// const workspace = Blockly.getMainWorkspace();
|
||||
// if(props.initialXml !== this.props.initialXml){
|
||||
// // guarantees that the current xml-code (this.props.initialXml) is rendered
|
||||
// workspace.clear();
|
||||
// Blockly.Xml.domToWorkspace(Blockly.Xml.textToDom(this.props.initialXml), workspace);
|
||||
// }
|
||||
// Blockly.svgResize(workspace);
|
||||
// }
|
||||
|
||||
render() {
|
||||
return (
|
||||
|
53
src/components/Tutorial/Assessment.js
Normal file
53
src/components/Tutorial/Assessment.js
Normal file
@ -0,0 +1,53 @@
|
||||
import React, { Component } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { connect } from 'react-redux';
|
||||
|
||||
import BlocklyWindow from '../Blockly/BlocklyWindow';
|
||||
import SolutionCheck from './SolutionCheck';
|
||||
import CodeViewer from '../CodeViewer';
|
||||
|
||||
import Grid from '@material-ui/core/Grid';
|
||||
import Card from '@material-ui/core/Card';
|
||||
import Typography from '@material-ui/core/Typography';
|
||||
|
||||
class Assessment extends Component {
|
||||
|
||||
render() {
|
||||
var currentTutorialId = this.props.currentTutorialId;
|
||||
var step = this.props.step
|
||||
return (
|
||||
<div style={{width: '100%'}}>
|
||||
<Typography variant='h4' style={{marginBottom: '5px'}}>{step.headline}</Typography>
|
||||
<Grid container spacing={2}>
|
||||
<Grid item xs={12} md={6} lg={8} style={{ position: 'relative' }}>
|
||||
<SolutionCheck />
|
||||
<BlocklyWindow initialXml={this.props.status[currentTutorialId].xml ? this.props.status[currentTutorialId].xml : null}/>
|
||||
</Grid>
|
||||
<Grid item xs={12} md={6} lg={4}>
|
||||
<Card style={{height: 'calc(50% - 30px)', padding: '10px', marginBottom: '10px'}}>
|
||||
<Typography variant='h5'>Arbeitsauftrag</Typography>
|
||||
<Typography>{step.text1}</Typography>
|
||||
</Card>
|
||||
<div style={{height: '50%'}}>
|
||||
<CodeViewer />
|
||||
</div>
|
||||
</Grid>
|
||||
</Grid>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
}
|
||||
|
||||
Assessment.propTypes = {
|
||||
currentTutorialId: PropTypes.number,
|
||||
status: PropTypes.array.isRequired,
|
||||
change: PropTypes.number.isRequired
|
||||
};
|
||||
|
||||
const mapStateToProps = state => ({
|
||||
change: state.tutorial.change,
|
||||
status: state.tutorial.status,
|
||||
currentTutorialId: state.tutorial.currentId
|
||||
});
|
||||
|
||||
export default connect(mapStateToProps, null)(Assessment);
|
@ -4,36 +4,35 @@ import { connect } from 'react-redux';
|
||||
|
||||
import BlocklyWindow from '../Blockly/BlocklyWindow';
|
||||
|
||||
import { tutorials } from './tutorials';
|
||||
|
||||
import Grid from '@material-ui/core/Grid';
|
||||
|
||||
import Typography from '@material-ui/core/Typography';
|
||||
|
||||
class Instruction extends Component {
|
||||
|
||||
render() {
|
||||
var currentTutorialId = this.props.currentTutorialId;
|
||||
var step = this.props.step;
|
||||
return (
|
||||
tutorials[currentTutorialId].instruction ?
|
||||
<div>
|
||||
<p>{tutorials[currentTutorialId].instruction.description}</p>
|
||||
{tutorials[currentTutorialId].instruction.xml ?
|
||||
<Grid container spacing={2}>
|
||||
<Grid item xs={12}>
|
||||
<BlocklyWindow
|
||||
trashcan={false}
|
||||
readOnly={true}
|
||||
zoomControls={false}
|
||||
grid={false}
|
||||
move={false}
|
||||
blocklyCSS={{minHeight: '300px'}}
|
||||
initialXml={tutorials[this.props.currentTutorialId].instruction.xml}
|
||||
/>
|
||||
</Grid>
|
||||
<div>
|
||||
<Typography variant='h4' style={{marginBottom: '5px'}}>{step.headline}</Typography>
|
||||
<Typography style={{marginBottom: '5px'}}>{step.text1}</Typography>
|
||||
{step.hardware && step.hardware.length > 0 ? 'Hardware: todo' : null}
|
||||
{step.requirements && step.requirements.length > 0 ? 'Voraussetzungen: todo' : null}
|
||||
{step.xml ?
|
||||
<Grid container spacing={2}>
|
||||
<Grid item xs={12}>
|
||||
<BlocklyWindow
|
||||
trashcan={false}
|
||||
readOnly={true}
|
||||
zoomControls={false}
|
||||
grid={false}
|
||||
move={false}
|
||||
blocklyCSS={{minHeight: '300px'}}
|
||||
initialXml={step.xml}
|
||||
/>
|
||||
</Grid>
|
||||
: null }
|
||||
</div>
|
||||
: null
|
||||
</Grid>
|
||||
: null }
|
||||
</div>
|
||||
);
|
||||
};
|
||||
}
|
||||
|
@ -3,11 +3,9 @@ import PropTypes from 'prop-types';
|
||||
import { connect } from 'react-redux';
|
||||
import { tutorialCheck } from '../../actions/tutorialActions';
|
||||
|
||||
import * as Blockly from 'blockly/core';
|
||||
|
||||
import Compile from '../Compile';
|
||||
|
||||
import { tutorials } from './tutorials';
|
||||
import tutorials from './tutorials.json';
|
||||
import { checkXml } from './compareXml';
|
||||
|
||||
import { withStyles } from '@material-ui/core/styles';
|
||||
@ -49,51 +47,50 @@ class SolutionCheck extends Component {
|
||||
}
|
||||
|
||||
check = () => {
|
||||
const workspace = Blockly.getMainWorkspace();
|
||||
var msg = checkXml(tutorials[this.props.currentTutorialId].solution, this.props.xml);
|
||||
const tutorial = tutorials.filter(tutorial => tutorial.id === this.props.currentTutorialId)[0];
|
||||
const step = tutorial.steps[this.props.activeStep];
|
||||
var msg = checkXml(step.xml, this.props.xml);
|
||||
this.props.tutorialCheck(msg.type);
|
||||
this.setState({ msg, open: true });
|
||||
}
|
||||
|
||||
render() {
|
||||
return (
|
||||
tutorials[this.props.currentTutorialId].test ?
|
||||
<div>
|
||||
<Tooltip title='Lösung kontrollieren'>
|
||||
<IconButton
|
||||
className={this.props.classes.compile}
|
||||
style={{width: '40px', height: '40px', position: 'absolute', top: 8, right: 8, zIndex: 21 }}
|
||||
onClick={() => this.check()}
|
||||
>
|
||||
<FontAwesomeIcon icon={faPlay} size="xs"/>
|
||||
</IconButton>
|
||||
</Tooltip>
|
||||
<Dialog fullWidth maxWidth={'sm'} onClose={this.toggleDialog} open={this.state.open} style={{zIndex: 9999999}}>
|
||||
<DialogTitle>{this.state.msg.type === 'error' ? 'Fehler' : 'Erfolg'}</DialogTitle>
|
||||
<DialogContent dividers>
|
||||
{this.state.msg.text}
|
||||
{this.state.msg.type === 'success' ?
|
||||
<div style={{marginTop: '20px', display: 'flex'}}>
|
||||
<Compile />
|
||||
<Button
|
||||
style={{marginLeft: '10px'}}
|
||||
variant="contained"
|
||||
color="primary"
|
||||
onClick={() => {this.toggleDialog(); this.props.history.push(`/tutorial/${this.props.currentTutorialId+2}`)}}
|
||||
>
|
||||
nächstes Tutorial
|
||||
</Button>
|
||||
</div>
|
||||
: null}
|
||||
</DialogContent>
|
||||
<DialogActions>
|
||||
<Button onClick={this.toggleDialog} color="primary">
|
||||
Schließen
|
||||
<div>
|
||||
<Tooltip title='Lösung kontrollieren'>
|
||||
<IconButton
|
||||
className={this.props.classes.compile}
|
||||
style={{width: '40px', height: '40px', position: 'absolute', top: 8, right: 8, zIndex: 21 }}
|
||||
onClick={() => this.check()}
|
||||
>
|
||||
<FontAwesomeIcon icon={faPlay} size="xs"/>
|
||||
</IconButton>
|
||||
</Tooltip>
|
||||
<Dialog fullWidth maxWidth={'sm'} onClose={this.toggleDialog} open={this.state.open} style={{zIndex: 9999999}}>
|
||||
<DialogTitle>{this.state.msg.type === 'error' ? 'Fehler' : 'Erfolg'}</DialogTitle>
|
||||
<DialogContent dividers>
|
||||
{this.state.msg.text}
|
||||
{this.state.msg.type === 'success' ?
|
||||
<div style={{marginTop: '20px', display: 'flex'}}>
|
||||
<Compile />
|
||||
<Button
|
||||
style={{marginLeft: '10px'}}
|
||||
variant="contained"
|
||||
color="primary"
|
||||
onClick={() => {this.toggleDialog(); this.props.history.push(`/tutorial/${this.props.currentTutorialId+2}`)}}
|
||||
>
|
||||
nächstes Tutorial
|
||||
</Button>
|
||||
</DialogActions>
|
||||
</Dialog>
|
||||
</div>
|
||||
: null
|
||||
</div>
|
||||
: null}
|
||||
</DialogContent>
|
||||
<DialogActions>
|
||||
<Button onClick={this.toggleDialog} color="primary">
|
||||
Schließen
|
||||
</Button>
|
||||
</DialogActions>
|
||||
</Dialog>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
}
|
||||
@ -102,11 +99,13 @@ class SolutionCheck extends Component {
|
||||
SolutionCheck.propTypes = {
|
||||
tutorialCheck: PropTypes.func.isRequired,
|
||||
currentTutorialId: PropTypes.number,
|
||||
activeStep: PropTypes.number.isRequired,
|
||||
xml: PropTypes.string.isRequired
|
||||
};
|
||||
|
||||
const mapStateToProps = state => ({
|
||||
currentTutorialId: state.tutorial.currentId,
|
||||
activeStep: state.tutorial.activeStep,
|
||||
xml: state.workspace.code.xml
|
||||
});
|
||||
|
||||
|
@ -6,7 +6,7 @@ import { withRouter } from 'react-router-dom';
|
||||
|
||||
import clsx from 'clsx';
|
||||
|
||||
import { tutorials } from './tutorials';
|
||||
import tutorials from './tutorials.json';
|
||||
|
||||
import { fade } from '@material-ui/core/styles/colorManipulator';
|
||||
import { withStyles } from '@material-ui/core/styles';
|
||||
@ -56,22 +56,22 @@ class StepperHorizontal extends Component {
|
||||
return (
|
||||
<div className={clsx(this.props.classes.stepper, this.props.classes['stepper'+tutorialStatus])}>
|
||||
<Button
|
||||
disabled={tutorialId === 0}
|
||||
onClick={() => {this.props.history.push(`/tutorial/${tutorialId}`)}}
|
||||
disabled={tutorialId === 1}
|
||||
onClick={() => {this.props.history.push(`/tutorial/${tutorialId-1}`)}}
|
||||
>
|
||||
{'<'}
|
||||
</Button>
|
||||
<Stepper activeStep={tutorialId+1} orientation="horizontal"
|
||||
<Stepper activeStep={tutorialId} orientation="horizontal"
|
||||
style={{padding: 0}} classes={{root: this.props.classes.color}}>
|
||||
<Step expanded completed={false}>
|
||||
<StepLabel icon={tutorialStatus !== 'Other' ? <div className={clsx(tutorialStatus === 'Error' ? this.props.classes.iconDivError: this.props.classes.iconDivSuccess)}><FontAwesomeIcon className={this.props.classes.icon} icon={tutorialStatus === 'Success' ? faCheck : faTimes}/></div> : ''}>
|
||||
<h1 style={{margin: 0}}>{tutorials[tutorialId].title}</h1>
|
||||
<h1 style={{margin: 0}}>{tutorials.filter(tutorial => tutorial.id === tutorialId)[0].title}</h1>
|
||||
</StepLabel>
|
||||
</Step>
|
||||
</Stepper>
|
||||
<Button
|
||||
disabled={tutorialId+2 > tutorials.length}
|
||||
onClick={() => {this.props.history.push(`/tutorial/${tutorialId+2}`)}}
|
||||
disabled={tutorialId+1 > tutorials.length}
|
||||
onClick={() => {this.props.history.push(`/tutorial/${tutorialId+1}`)}}
|
||||
>
|
||||
{'>'}
|
||||
</Button>
|
||||
|
@ -1,17 +1,13 @@
|
||||
import React, { Component } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { connect } from 'react-redux';
|
||||
import { tutorialStep } from '../../actions/tutorialActions';
|
||||
|
||||
import { withRouter, Link } from 'react-router-dom';
|
||||
|
||||
import clsx from 'clsx';
|
||||
|
||||
import { tutorials } from './tutorials';
|
||||
|
||||
import { fade } from '@material-ui/core/styles/colorManipulator';
|
||||
import { withStyles } from '@material-ui/core/styles';
|
||||
import withWidth, { isWidthUp } from '@material-ui/core/withWidth';
|
||||
import Button from '@material-ui/core/Button';
|
||||
import Stepper from '@material-ui/core/Stepper';
|
||||
import Step from '@material-ui/core/Step';
|
||||
import StepLabel from '@material-ui/core/StepLabel';
|
||||
@ -26,176 +22,74 @@ const styles = (theme) => ({
|
||||
borderStyle: `solid`,
|
||||
// borderWidth: '2px',
|
||||
borderRadius: '50%',
|
||||
borderColor: theme.palette.secondary.main,
|
||||
width: '12px',
|
||||
height: '12px',
|
||||
margin: '0 auto'
|
||||
},
|
||||
stepIconMedium: {
|
||||
width: '18px',
|
||||
height: '18px',
|
||||
margin: '0 auto',
|
||||
},
|
||||
stepIconLarge: {
|
||||
width: '24px',
|
||||
height: '24px'
|
||||
},
|
||||
stepIconTransparent: {
|
||||
borderColor: `transparent`,
|
||||
cursor: 'default'
|
||||
stepIconActive: {
|
||||
backgroundColor: theme.palette.secondary.main
|
||||
},
|
||||
stepIconSuccess: {
|
||||
borderColor: theme.palette.primary.main,
|
||||
},
|
||||
stepIconError: {
|
||||
borderColor: theme.palette.error.dark,
|
||||
},
|
||||
stepIconOther: {
|
||||
borderColor: theme.palette.secondary.main,
|
||||
},
|
||||
stepIconActiveSuccess: {
|
||||
backgroundColor: fade(theme.palette.primary.main, 0.6)
|
||||
},
|
||||
stepIconActiveError: {
|
||||
backgroundColor: fade(theme.palette.error.dark, 0.6)
|
||||
},
|
||||
stepIconActiveOther: {
|
||||
backgroundColor: fade(theme.palette.secondary.main, 0.6)
|
||||
},
|
||||
progress: {
|
||||
position: 'absolute',
|
||||
top: 0,
|
||||
right: 0,
|
||||
marginRight: '5px',
|
||||
width: '3px',
|
||||
},
|
||||
progressForeground: {
|
||||
backgroundColor: theme.palette.primary.main
|
||||
},
|
||||
progressBackground: {
|
||||
backgroundColor: fade(theme.palette.primary.main, 0.2),
|
||||
height: '100%',
|
||||
borderRadius: '2px'
|
||||
connector: {
|
||||
height: '10px',
|
||||
borderLeft: `3px solid ${theme.palette.primary.main}`,
|
||||
margin: '5px auto'
|
||||
}
|
||||
});
|
||||
|
||||
class StepperVertical extends Component {
|
||||
|
||||
constructor(props){
|
||||
super(props);
|
||||
this.state = {
|
||||
tutorialArray: props.currentTutorialId === 0 ?
|
||||
tutorials.slice(props.currentTutorialId, props.currentTutorialId+5)
|
||||
: props.currentTutorialId === 1 ?
|
||||
tutorials.slice(props.currentTutorialId-1, props.currentTutorialId+4)
|
||||
: props.currentTutorialId === tutorials.length-1 ?
|
||||
tutorials.slice(props.currentTutorialId-4, props.currentTutorialId+5)
|
||||
: props.currentTutorialId === tutorials.length-2 ?
|
||||
tutorials.slice(props.currentTutorialId-3, props.currentTutorialId+4)
|
||||
: tutorials.slice(props.currentTutorialId-2, props.currentTutorialId+3),
|
||||
selectedVerticalTutorialId: props.currentTutorialId
|
||||
};
|
||||
componentDidMount(){
|
||||
this.props.tutorialStep(0);
|
||||
}
|
||||
|
||||
componentDidUpdate(props){
|
||||
if(props.currentTutorialId !== this.props.currentTutorialId){
|
||||
this.setState({
|
||||
tutorialArray: this.props.currentTutorialId === 0 ?
|
||||
tutorials.slice(this.props.currentTutorialId, this.props.currentTutorialId+5)
|
||||
: this.props.currentTutorialId === 1 ?
|
||||
tutorials.slice(this.props.currentTutorialId-1, this.props.currentTutorialId+4)
|
||||
: this.props.currentTutorialId === tutorials.length-1 ?
|
||||
tutorials.slice(this.props.currentTutorialId-4, this.props.currentTutorialId+5)
|
||||
: this.props.currentTutorialId === tutorials.length-2 ?
|
||||
tutorials.slice(this.props.currentTutorialId-3, this.props.currentTutorialId+4)
|
||||
: tutorials.slice(this.props.currentTutorialId-2, this.props.currentTutorialId+3),
|
||||
selectedVerticalTutorialId: this.props.currentTutorialId
|
||||
});
|
||||
if(props.currentTutorialId !== Number(this.props.match.params.tutorialId)){
|
||||
this.props.tutorialStep(0);
|
||||
}
|
||||
}
|
||||
|
||||
verticalStepper = (step) => {
|
||||
var newTutorialId = this.state.selectedVerticalTutorialId + step;
|
||||
var tutorialArray = newTutorialId === 0 ?
|
||||
tutorials.slice(newTutorialId, newTutorialId+5)
|
||||
: newTutorialId === 1 ?
|
||||
tutorials.slice(newTutorialId-1, newTutorialId+4)
|
||||
: newTutorialId === tutorials.length-1 ?
|
||||
tutorials.slice(newTutorialId-4, newTutorialId+5)
|
||||
: newTutorialId === tutorials.length-2 ?
|
||||
tutorials.slice(newTutorialId-3, newTutorialId+4)
|
||||
: tutorials.slice(newTutorialId-2, newTutorialId+3);
|
||||
this.setState({ tutorialArray: tutorialArray, selectedVerticalTutorialId: newTutorialId });
|
||||
}
|
||||
|
||||
render() {
|
||||
var tutorialId = this.props.currentTutorialId;
|
||||
var selectedVerticalTutorialId = this.state.selectedVerticalTutorialId;
|
||||
var steps = this.props.steps;
|
||||
var activeStep = this.props.activeStep;
|
||||
return (
|
||||
isWidthUp('sm', this.props.width) ?
|
||||
<div style={{marginRight: '10px'}}>
|
||||
<Button
|
||||
style={{minWidth: '30px', margin: 'auto', minHeight: '25px', padding: '0', writingMode: 'vertical-rl'}}
|
||||
disabled={selectedVerticalTutorialId === 0}
|
||||
onClick={() => {this.verticalStepper(-1)}}
|
||||
>
|
||||
{'<'}
|
||||
</Button>
|
||||
<div style={{display: 'flex', height: 'max-content', width: 'max-content'}}>
|
||||
<div style={{position: 'relative'}}>
|
||||
<div
|
||||
className={clsx(this.props.classes.progress, this.props.classes.progressForeground)}
|
||||
style={{ zIndex: 1, borderRadius: `${selectedVerticalTutorialId/(tutorials.length-1) === 1 ? '2px' : '2px 2px 0 0'}`, height: `${((selectedVerticalTutorialId+1)/tutorials.length)*100}%`}}>
|
||||
</div>
|
||||
<div className={clsx(this.props.classes.progress, this.props.classes.progressBackground)}>
|
||||
</div>
|
||||
</div>
|
||||
<Stepper
|
||||
activeStep={tutorialId+1}
|
||||
orientation="vertical"
|
||||
connector={<div style={{height: '10px'}}></div>}
|
||||
classes={{root: this.props.classes.verticalStepper}}
|
||||
>
|
||||
{this.state.tutorialArray.map((tutorial, i) => {
|
||||
var index = this.state.tutorialArray.indexOf(tutorials[selectedVerticalTutorialId]);
|
||||
var verticalTutorialId = i === index ? selectedVerticalTutorialId+1 : selectedVerticalTutorialId+1 - index + i;
|
||||
var tutorialStatus = this.props.status[verticalTutorialId-1].status === 'success' ? 'Success' :
|
||||
this.props.status[verticalTutorialId-1].status === 'error' ? 'Error' : 'Other';
|
||||
return (
|
||||
<Step key={i}>
|
||||
<Tooltip title={Object.keys(tutorial).length > 0 ? tutorial.title : ''} placement='right' arrow >
|
||||
<Link to={`/tutorial/${verticalTutorialId}`}>
|
||||
<StepLabel
|
||||
StepIconComponent={'div'}
|
||||
classes={{
|
||||
root: tutorial === tutorials[selectedVerticalTutorialId] ?
|
||||
tutorial === tutorials[tutorialId] ?
|
||||
clsx(this.props.classes.stepIcon, this.props.classes.stepIconLarge, this.props.classes['stepIcon'+tutorialStatus], this.props.classes['stepIconActive'+tutorialStatus])
|
||||
: clsx(this.props.classes.stepIcon, this.props.classes.stepIconLarge, this.props.classes['stepIcon'+tutorialStatus])
|
||||
: tutorial === tutorials[selectedVerticalTutorialId-1] || tutorial === tutorials[selectedVerticalTutorialId+1] ||
|
||||
tutorial === tutorials[verticalTutorialId-2] ?
|
||||
tutorial === tutorials[tutorialId] ?
|
||||
clsx(this.props.classes.stepIcon, this.props.classes.stepIconMedium, this.props.classes['stepIcon'+tutorialStatus], this.props.classes['stepIconActive'+tutorialStatus])
|
||||
: clsx(this.props.classes.stepIcon, this.props.classes.stepIconMedium, this.props.classes['stepIcon'+tutorialStatus])
|
||||
: tutorial === tutorials[tutorialId] ?
|
||||
clsx(this.props.classes.stepIcon, this.props.classes['stepIcon'+tutorialStatus], this.props.classes['stepIconActive'+tutorialStatus])
|
||||
: clsx(this.props.classes.stepIcon, this.props.classes['stepIcon'+tutorialStatus])
|
||||
}}
|
||||
>
|
||||
</StepLabel>
|
||||
</Link>
|
||||
</Tooltip>
|
||||
</Step>
|
||||
)})}
|
||||
</Stepper>
|
||||
</div>
|
||||
<Button
|
||||
style={{minWidth: '30px', minHeight: '25px', padding: '0', writingMode: 'vertical-rl'}}
|
||||
disabled={selectedVerticalTutorialId === tutorials.length-1}
|
||||
onClick={() => {this.verticalStepper(1)}}
|
||||
>
|
||||
{'>'}
|
||||
</Button>
|
||||
</div>
|
||||
: null
|
||||
<div style={{marginRight: '10px'}}>
|
||||
<Stepper
|
||||
activeStep={activeStep}
|
||||
orientation="vertical"
|
||||
connector={<div className={this.props.classes.connector}></div>}
|
||||
classes={{root: this.props.classes.verticalStepper}}
|
||||
>
|
||||
{steps.map((step, i) => {
|
||||
// var tutorialStatus = this.props.status[verticalTutorialId-1].status === 'success' ? 'Success' :
|
||||
// this.props.status[verticalTutorialId-1].status === 'error' ? 'Error' : 'Other';
|
||||
return (
|
||||
<Step key={i}>
|
||||
<Tooltip title={step.headline} placement='right' arrow >
|
||||
<Link onClick={() => {this.props.tutorialStep(i)}}>
|
||||
<StepLabel
|
||||
StepIconComponent={'div'}
|
||||
classes={{
|
||||
root: step.type === 'task' ?
|
||||
i === activeStep ?
|
||||
clsx(this.props.classes.stepIcon, this.props.classes.stepIconLarge, this.props.classes.stepIconActive)
|
||||
: clsx(this.props.classes.stepIcon, this.props.classes.stepIconLarge)
|
||||
: i === activeStep ?
|
||||
clsx(this.props.classes.stepIcon, this.props.classes.stepIconActive)
|
||||
: clsx(this.props.classes.stepIcon)
|
||||
}}
|
||||
>
|
||||
</StepLabel>
|
||||
</Link>
|
||||
</Tooltip>
|
||||
</Step>
|
||||
)})}
|
||||
</Stepper>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
}
|
||||
@ -204,13 +98,16 @@ class StepperVertical extends Component {
|
||||
StepperVertical.propTypes = {
|
||||
status: PropTypes.array.isRequired,
|
||||
change: PropTypes.number.isRequired,
|
||||
currentTutorialId: PropTypes.number.isRequired
|
||||
currentTutorialId: PropTypes.number.isRequired,
|
||||
activeStep: PropTypes.number.isRequired,
|
||||
tutorialStep: PropTypes.func.isRequired
|
||||
};
|
||||
|
||||
const mapStateToProps = state => ({
|
||||
change: state.tutorial.change,
|
||||
status: state.tutorial.status,
|
||||
currentTutorialId: state.tutorial.currentId
|
||||
currentTutorialId: state.tutorial.currentId,
|
||||
activeStep: state.tutorial.activeStep
|
||||
});
|
||||
|
||||
export default connect(mapStateToProps, null)(withRouter(withStyles(styles, {withTheme: true})(withWidth()(StepperVertical))));
|
||||
export default connect(mapStateToProps, { tutorialStep })(withRouter(withStyles(styles, {withTheme: true})(StepperVertical)));
|
||||
|
@ -1,35 +1,29 @@
|
||||
import React, { Component } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { connect } from 'react-redux';
|
||||
import { tutorialId, setTutorialLevel } from '../../actions/tutorialActions';
|
||||
import { tutorialId, tutorialStep } from '../../actions/tutorialActions';
|
||||
|
||||
import Breadcrumbs from '../Breadcrumbs';
|
||||
import StepperHorizontal from './StepperHorizontal';
|
||||
import StepperVertical from './StepperVertical';
|
||||
import Instruction from './Instruction';
|
||||
import BlocklyWindow from '../Blockly/BlocklyWindow';
|
||||
import SolutionCheck from './SolutionCheck';
|
||||
import CodeViewer from '../CodeViewer';
|
||||
import Assessment from './Assessment';
|
||||
import NotFound from '../NotFound';
|
||||
|
||||
import { tutorials } from './tutorials';
|
||||
import tutorials from './tutorials.json';
|
||||
|
||||
import withWidth, { isWidthUp } from '@material-ui/core/withWidth';
|
||||
import Tabs from '@material-ui/core/Tabs';
|
||||
import Tab from '@material-ui/core/Tab';
|
||||
import Grid from '@material-ui/core/Grid';
|
||||
import Card from '@material-ui/core/Card';
|
||||
import Button from '@material-ui/core/Button';
|
||||
|
||||
class Tutorial extends Component {
|
||||
|
||||
componentDidMount(){
|
||||
this.props.tutorialId(Number(this.props.match.params.tutorialId)-1);
|
||||
this.props.tutorialId(Number(this.props.match.params.tutorialId));
|
||||
}
|
||||
|
||||
componentDidUpdate(props, state){
|
||||
if(props.currentTutorialId+1 !== Number(this.props.match.params.tutorialId)){
|
||||
this.props.tutorialId(Number(this.props.match.params.tutorialId)-1);
|
||||
this.props.setTutorialLevel('instruction');
|
||||
if(props.currentTutorialId !== Number(this.props.match.params.tutorialId)){
|
||||
this.props.tutorialId(Number(this.props.match.params.tutorialId));
|
||||
}
|
||||
}
|
||||
|
||||
@ -37,78 +31,55 @@ class Tutorial extends Component {
|
||||
this.props.tutorialId(null);
|
||||
}
|
||||
|
||||
onChange = (e, value) => {
|
||||
this.props.setTutorialLevel(value);
|
||||
}
|
||||
|
||||
render() {
|
||||
var currentTutorialId = this.props.currentTutorialId;
|
||||
var tutorial = tutorials.filter(tutorial => tutorial.id === currentTutorialId)[0];
|
||||
var steps = tutorial ? tutorial.steps : null;
|
||||
var step = steps ? steps[this.props.activeStep] : null;
|
||||
return (
|
||||
!Number.isInteger(currentTutorialId) || currentTutorialId+1 < 1 || currentTutorialId+1 > tutorials.length ?
|
||||
!Number.isInteger(currentTutorialId) || currentTutorialId < 1 || currentTutorialId > tutorials.length ?
|
||||
<NotFound button={{title: 'Zurück zur Tutorials-Übersicht', link: '/tutorial'}}/>
|
||||
:
|
||||
<div>
|
||||
<Breadcrumbs content={[{link: '/', title: 'Home'},{link: '/tutorial', title: 'Tutorial'}, {link: `/tutorial/${currentTutorialId+1}`, title: tutorials[currentTutorialId].title}]}/>
|
||||
<div>
|
||||
<Breadcrumbs content={[{link: '/', title: 'Home'},{link: '/tutorial', title: 'Tutorial'}, {link: `/tutorial/${currentTutorialId}`, title: tutorial.title}]}/>
|
||||
|
||||
<StepperHorizontal />
|
||||
<StepperHorizontal />
|
||||
|
||||
<div style={{display: 'flex'}}>
|
||||
<StepperVertical />
|
||||
<div style={{display: 'flex'}}>
|
||||
<StepperVertical steps={steps}/>
|
||||
|
||||
{/* width of vertical stepper is 30px*/}
|
||||
<Card style={{width: isWidthUp('sm', this.props.width) ? 'calc(100% - 30px)' : '100%', padding: '10px'}}>
|
||||
<Tabs
|
||||
value={this.props.level}
|
||||
indicatorColor="primary"
|
||||
textColor="inherit"
|
||||
variant='fullWidth'
|
||||
onChange={this.onChange}
|
||||
>
|
||||
<Tab label="Anleitung" value='instruction' disableRipple/>
|
||||
<Tab label="Aufgabe" value='assessment' disableRipple/>
|
||||
</Tabs>
|
||||
<Card style={{padding: '10px'}}>
|
||||
{step ?
|
||||
step.type === 'instruction' ?
|
||||
<Instruction step={step}/>
|
||||
: <Assessment step={step}/> // if step.type === 'assessment'
|
||||
: null}
|
||||
|
||||
<div style={{marginTop: '20px'}}>
|
||||
{this.props.level === 'instruction' ?
|
||||
<Instruction /> : null }
|
||||
{this.props.level === 'assessment' ?
|
||||
<Grid container spacing={2}>
|
||||
<Grid item xs={12} md={6} lg={8} style={{ position: 'relative' }}>
|
||||
<SolutionCheck />
|
||||
<BlocklyWindow initialXml={this.props.status[currentTutorialId].xml ? this.props.status[currentTutorialId].xml : null}/>
|
||||
</Grid>
|
||||
<Grid item xs={12} md={6} lg={4}>
|
||||
<Card style={{height: 'calc(50% - 30px)', padding: '10px', marginBottom: '10px'}}>
|
||||
Hier könnte die Problemstellung stehen.
|
||||
</Card>
|
||||
<div style={{height: '50%'}}>
|
||||
<CodeViewer />
|
||||
</div>
|
||||
</Grid>
|
||||
</Grid>
|
||||
: null }
|
||||
</div>
|
||||
</Card>
|
||||
</div>
|
||||
<div style={{marginTop: '20px'}}>
|
||||
<Button style={{marginRight: '10px'}} variant='contained' disabled={this.props.activeStep === 0} onClick={() => this.props.tutorialStep(this.props.activeStep-1)}>Zurück</Button>
|
||||
<Button variant='contained' color='primary' disabled={this.props.activeStep === tutorial.steps.length-1} onClick={() => this.props.tutorialStep(this.props.activeStep+1)}>Weiter</Button>
|
||||
</div>
|
||||
</Card>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
}
|
||||
|
||||
Tutorial.propTypes = {
|
||||
tutorialId: PropTypes.func.isRequired,
|
||||
setTutorialLevel: PropTypes.func.isRequired,
|
||||
tutorialStep: PropTypes.func.isRequired,
|
||||
currentTutorialId: PropTypes.number,
|
||||
status: PropTypes.array.isRequired,
|
||||
change: PropTypes.number.isRequired,
|
||||
level: PropTypes.string.isRequired
|
||||
activeStep: PropTypes.number.isRequired
|
||||
};
|
||||
|
||||
const mapStateToProps = state => ({
|
||||
change: state.tutorial.change,
|
||||
status: state.tutorial.status,
|
||||
currentTutorialId: state.tutorial.currentId,
|
||||
level: state.tutorial.level
|
||||
activeStep: state.tutorial.activeStep
|
||||
});
|
||||
|
||||
export default connect(mapStateToProps, { tutorialId, setTutorialLevel })(withWidth()(Tutorial));
|
||||
export default connect(mapStateToProps, { tutorialId, tutorialStep })(Tutorial);
|
||||
|
128
src/components/Tutorial/TutorialBody.js
Normal file
128
src/components/Tutorial/TutorialBody.js
Normal file
@ -0,0 +1,128 @@
|
||||
import React, { Component } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { connect } from 'react-redux';
|
||||
import { tutorialId, tutorialStep } from '../../actions/tutorialActions';
|
||||
|
||||
import Breadcrumbs from '../Breadcrumbs';
|
||||
import StepperHorizontal from './StepperHorizontal';
|
||||
import StepperVertical from './StepperVertical';
|
||||
import Instruction from './Instruction';
|
||||
import Assessment from './Assessment';
|
||||
import NotFound from '../NotFound';
|
||||
|
||||
import tutorials from './tutorials.json';
|
||||
|
||||
import withWidth, { isWidthUp } from '@material-ui/core/withWidth';
|
||||
import Card from '@material-ui/core/Card';
|
||||
import Button from '@material-ui/core/Button';
|
||||
|
||||
class Tutorial extends Component {
|
||||
|
||||
componentDidMount(){
|
||||
this.props.tutorialId(Number(this.props.match.params.tutorialId));
|
||||
}
|
||||
|
||||
componentDidUpdate(props, state){
|
||||
if(props.currentTutorialId !== Number(this.props.match.params.tutorialId)){
|
||||
this.props.tutorialId(Number(this.props.match.params.tutorialId));
|
||||
}
|
||||
}
|
||||
|
||||
componentWillUnmount(){
|
||||
this.props.tutorialId(null);
|
||||
}
|
||||
|
||||
render() {
|
||||
var currentTutorialId = this.props.currentTutorialId;
|
||||
var tutorial = tutorials.filter(tutorial => tutorial.id === currentTutorialId)[0];
|
||||
var step = tutorial.steps[this.props.activeStep];
|
||||
|
||||
const Tutorial2 = () => (
|
||||
<div>
|
||||
<Breadcrumbs content={[{link: '/', title: 'Home'},{link: '/tutorial', title: 'Tutorial'}, {link: `/tutorial/${currentTutorialId}`, title: tutorial.title}]}/>
|
||||
|
||||
<StepperHorizontal />
|
||||
|
||||
<div style={{display: 'flex'}}>
|
||||
<StepperVertical />
|
||||
|
||||
<div>
|
||||
{step.type === 'instruction' ?
|
||||
<Instruction step={step}/>
|
||||
: <Assessment step={step}/>}
|
||||
|
||||
<div style={{marginTop: '20px'}}>
|
||||
<Button style={{marginRight: '10px'}} variant='contained' disabled={this.props.activeStep === 0} onClick={() => this.props.tutorialStep(this.props.activeStep-1)}>Zurück</Button>
|
||||
<Button variant='contained' color='primary' disabled={this.props.activeStep === tutorial.steps.length-1} onClick={() => this.props.tutorialStep(this.props.activeStep+1)}>Weiter</Button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
return (
|
||||
!Number.isInteger(currentTutorialId) || currentTutorialId < 1 || currentTutorialId > tutorials.length ?
|
||||
<NotFound button={{title: 'Zurück zur Tutorials-Übersicht', link: '/tutorial'}}/>
|
||||
:
|
||||
<TutorialBody />
|
||||
);
|
||||
};
|
||||
}
|
||||
|
||||
Tutorial.propTypes = {
|
||||
tutorialId: PropTypes.func.isRequired,
|
||||
currentTutorialId: PropTypes.number,
|
||||
status: PropTypes.array.isRequired,
|
||||
change: PropTypes.number.isRequired,
|
||||
activeStep: PropTypes.number.isRequired
|
||||
};
|
||||
|
||||
const mapStateToProps = state => ({
|
||||
change: state.tutorial.change,
|
||||
status: state.tutorial.status,
|
||||
currentTutorialId: state.tutorial.currentId,
|
||||
activeStep: state.tutorial.activeStep
|
||||
});
|
||||
|
||||
export default connect(mapStateToProps, { tutorialId, tutorialStep })(withWidth()(Tutorial));
|
||||
|
||||
|
||||
|
||||
// <StepperHorizontal />
|
||||
//
|
||||
|
||||
//
|
||||
// {/* width of vertical stepper is 30px*/}
|
||||
// <Card style={{width: isWidthUp('sm', this.props.width) ? 'calc(100% - 30px)' : '100%', padding: '10px'}}>
|
||||
// <Tabs
|
||||
// value={this.props.level}
|
||||
// indicatorColor="primary"
|
||||
// textColor="inherit"
|
||||
// variant='fullWidth'
|
||||
// onChange={this.onChange}
|
||||
// >
|
||||
// <Tab label="Anleitung" value='instruction' disableRipple/>
|
||||
// <Tab label="Aufgabe" value='assessment' disableRipple/>
|
||||
// </Tabs>
|
||||
//
|
||||
// <div style={{marginTop: '20px'}}>
|
||||
// {this.props.level === 'instruction' ?
|
||||
// <Instruction /> : null }
|
||||
// {this.props.level === 'assessment' ?
|
||||
// <Grid container spacing={2}>
|
||||
// <Grid item xs={12} md={6} lg={8} style={{ position: 'relative' }}>
|
||||
// <SolutionCheck />
|
||||
// <BlocklyWindow initialXml={this.props.status[currentTutorialId].xml ? this.props.status[currentTutorialId].xml : null}/>
|
||||
// </Grid>
|
||||
// <Grid item xs={12} md={6} lg={4}>
|
||||
// <Card style={{height: 'calc(50% - 30px)', padding: '10px', marginBottom: '10px'}}>
|
||||
// Hier könnte die Problemstellung stehen.
|
||||
// </Card>
|
||||
// <div style={{height: '50%'}}>
|
||||
// <CodeViewer />
|
||||
// </div>
|
||||
// </Grid>
|
||||
// </Grid>
|
||||
// : null }
|
||||
// </div>
|
||||
// </Card>
|
||||
// </div>
|
@ -6,7 +6,7 @@ import clsx from 'clsx';
|
||||
|
||||
import Breadcrumbs from '../Breadcrumbs';
|
||||
|
||||
import { tutorials } from './tutorials';
|
||||
import tutorials from './tutorials.json';
|
||||
|
||||
import { Link } from 'react-router-dom';
|
||||
|
||||
@ -59,9 +59,9 @@ class TutorialHome extends Component {
|
||||
this.props.status[i].status === 'error' ? 'Error' : 'Other';
|
||||
return (
|
||||
<Grid item xs={12} sm={6} md={4} xl={3} key={i} style={{}}>
|
||||
<Link to={`/tutorial/${i+1}`} style={{textDecoration: 'none', color: 'inherit'}}>
|
||||
<Link to={`/tutorial/${tutorial.id}`} style={{textDecoration: 'none', color: 'inherit'}}>
|
||||
<Paper style={{height: '150px', padding: '10px', position:'relative', overflow: 'hidden'}}>
|
||||
{tutorials[i].title}
|
||||
{tutorial.title}
|
||||
{tutorialStatus !== 'Other' ?
|
||||
<div className={clsx(this.props.classes.outerDiv, tutorialStatus === 'Error' ? this.props.classes.outerDivError : null)}>
|
||||
<div className={this.props.classes.innerDiv}>
|
||||
@ -72,7 +72,6 @@ class TutorialHome extends Component {
|
||||
}
|
||||
</Paper>
|
||||
</Link>
|
||||
|
||||
</Grid>
|
||||
)})}
|
||||
</Grid>
|
||||
|
@ -4,38 +4,33 @@
|
||||
"title": "Erste Schritte",
|
||||
"steps": [
|
||||
{
|
||||
"id": 1,
|
||||
"type": "instruction",
|
||||
"headline": "Erste Schritte",
|
||||
"text1": "In diesem Tutorial lernst du die ersten Schritte mit der senseBox kennen. Du erstellst ein erstes Programm, baust einen ersten Schaltkreis auf und lernst, wie du das Programm auf die senseBox MCU überträgst",
|
||||
"text1": "In diesem Tutorial lernst du die ersten Schritte mit der senseBox kennen. Du erstellst ein erstes Programm, baust einen ersten Schaltkreis auf und lernst, wie du das Programm auf die senseBox MCU überträgst.",
|
||||
"hardware": ["senseboxmcu", "led", "breadboard", "jst-adapter", "resistor"],
|
||||
"requirements": []
|
||||
},
|
||||
{
|
||||
"id": 2,
|
||||
"type": "instruction",
|
||||
"headline": "Aufbau der Schaltung",
|
||||
"text1": "Stecke die LED auf das Breadboard und verbinde diese mithile des Widerstandes und dem JST Kabel mit dem Port Digital/Analog 1"
|
||||
"text1": "Stecke die LED auf das Breadboard und verbinde diese mithile des Widerstandes und dem JST Kabel mit dem Port Digital/Analog 1."
|
||||
},
|
||||
{
|
||||
"id": 3,
|
||||
"type": "instruction",
|
||||
"headline": "Programmierung",
|
||||
"text1": "Jedes Programm für die senseBox besteht aus zwei Funktionen. Die Setup () Funktion wird zu Begin einmalig ausgeführt und der Programmcode Schrittweise ausgeführt. Nachdem die Setup () Funktion durchlaufen worden ist wird der Programmcode aus der zweiten Funktion, der Endlosschleife, fortlaufend wiederholt.",
|
||||
"xml": "<xml xmlns='https://developers.google.com/blockly/xml'><block type='arduino_functions' id='QWW|$jB8+*EL;}|#uA' deletable='false' x='27' y='16'></block></xml>"
|
||||
},
|
||||
{
|
||||
"id": 4,
|
||||
"type": "instruction",
|
||||
"headline": "Leuchten der LED",
|
||||
"text1": "Um nun die LED zum leuchten zu bringen wird folgender Block in die Endlosschleife eingefügt. Der Block bietet dir auszuwählen an welchen Pin die LED angeschlossen wurd und ob diese ein oder ausgeschaltet werden soll.",
|
||||
"xml": "<xml xmlns='https://developers.google.com/blockly/xml'><block type='arduino_functions' id='QWW|$jB8+*EL;}|#uA' deletable='false' x='27' y='16'></block></xml>"
|
||||
},
|
||||
{
|
||||
"id": 5,
|
||||
"type": "task",
|
||||
"headline": "Aufgabe 1",
|
||||
"text1": "Verwenden den Block zum leuchten der LED und übertrage dein erstes Programm auf die senseBox MCU",
|
||||
"text1": "Verwenden den Block zum leuchten der LED und übertrage dein erstes Programm auf die senseBox MCU.",
|
||||
"xml": "<xml xmlns='https://developers.google.com/blockly/xml'><block type='arduino_functions' id='QWW|$jB8+*EL;}|#uA' deletable='false' x='27' y='16'></block></xml>"
|
||||
}
|
||||
]
|
||||
|
@ -42,7 +42,7 @@ class WorkspaceStats extends Component {
|
||||
style={{ marginRight: '1rem' }}
|
||||
color="primary"
|
||||
avatar={<Avatar><FontAwesomeIcon icon={faPlus} /></Avatar>}
|
||||
label={this.props.create > 0 ? this.props.create : 0}> // initialXML is created automatically, Block is not part of the statistics
|
||||
label={this.props.create > 0 ? this.props.create : 0}> {/* initialXML is created automatically, Block is not part of the statistics */}
|
||||
</Chip>
|
||||
</Tooltip>
|
||||
<Tooltip title="Anzahl veränderter Blöcke" >
|
||||
@ -58,7 +58,7 @@ class WorkspaceStats extends Component {
|
||||
style={{ marginRight: '1rem' }}
|
||||
color="primary"
|
||||
avatar={<Avatar><FontAwesomeIcon icon={faArrowsAlt} /></Avatar>}
|
||||
label={this.props.move > 0 ? this.props.move : 0}> // initialXML is moved automatically, Block is not part of the statistics
|
||||
label={this.props.move > 0 ? this.props.move : 0}> {/* initialXML is moved automatically, Block is not part of the statistics */}
|
||||
</Chip>
|
||||
</Tooltip>
|
||||
<Tooltip title="Anzahl gelöschter Blöcke" >
|
||||
|
@ -1,4 +1,4 @@
|
||||
import { TUTORIAL_SUCCESS, TUTORIAL_ERROR, TUTORIAL_CHANGE, TUTORIAL_XML, TUTORIAL_ID, TUTORIAL_LEVEL } from '../actions/types';
|
||||
import { TUTORIAL_SUCCESS, TUTORIAL_ERROR, TUTORIAL_CHANGE, TUTORIAL_XML, TUTORIAL_ID, TUTORIAL_STEP } from '../actions/types';
|
||||
|
||||
import { tutorials } from '../components/Tutorial/tutorials';
|
||||
|
||||
@ -7,7 +7,8 @@ const initialState = {
|
||||
JSON.parse(window.localStorage.getItem('tutorial'))
|
||||
: new Array(tutorials.length).fill({}),
|
||||
level: 'instruction',
|
||||
currentId: null,
|
||||
currentId: 0,
|
||||
activeStep: 0,
|
||||
change: 0
|
||||
};
|
||||
|
||||
@ -32,10 +33,10 @@ export default function(state = initialState, action){
|
||||
...state,
|
||||
currentId: action.payload
|
||||
}
|
||||
case TUTORIAL_LEVEL:
|
||||
case TUTORIAL_STEP:
|
||||
return {
|
||||
...state,
|
||||
level: action.payload
|
||||
activeStep: action.payload
|
||||
}
|
||||
default:
|
||||
return state;
|
||||
|
Loading…
x
Reference in New Issue
Block a user