Move selectors around
This commit is contained in:
@ -1,13 +1,26 @@
|
|||||||
import React, { PropTypes } from 'react';
|
import React, { PropTypes } from 'react';
|
||||||
|
import { connect } from 'react-redux';
|
||||||
import PureComponent from 'react-pure-render/component';
|
|
||||||
import { Col } from 'react-bootstrap';
|
import { Col } from 'react-bootstrap';
|
||||||
|
import { createSelector } from 'reselect';
|
||||||
|
import PureComponent from 'react-pure-render/component';
|
||||||
|
|
||||||
import Editor from './Editor.jsx';
|
import Editor from './Editor.jsx';
|
||||||
import SidePanel from './Side-Panel.jsx';
|
import SidePanel from './Side-Panel.jsx';
|
||||||
import Preview from './Preview.jsx';
|
import Preview from './Preview.jsx';
|
||||||
|
import { challengeSelector } from '../redux/selectors';
|
||||||
|
|
||||||
export default class extends PureComponent {
|
const mapStateToProps = createSelector(
|
||||||
|
challengeSelector,
|
||||||
|
state => state.challengesApp.content,
|
||||||
|
({ challenge, showPreview, mode }, content) => ({
|
||||||
|
content,
|
||||||
|
challenge,
|
||||||
|
showPreview,
|
||||||
|
mode
|
||||||
|
})
|
||||||
|
);
|
||||||
|
|
||||||
|
export class Challenge extends PureComponent {
|
||||||
static displayName = 'Challenge';
|
static displayName = 'Challenge';
|
||||||
|
|
||||||
static propTypes = {
|
static propTypes = {
|
||||||
@ -54,3 +67,5 @@ export default class extends PureComponent {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export default connect(mapStateToProps)(Challenge);
|
||||||
|
@ -8,35 +8,16 @@ import PureComponent from 'react-pure-render/component';
|
|||||||
import Challenge from './Challenge.jsx';
|
import Challenge from './Challenge.jsx';
|
||||||
import Step from './step/Step.jsx';
|
import Step from './step/Step.jsx';
|
||||||
import { fetchChallenge } from '../../../redux/actions';
|
import { fetchChallenge } from '../../../redux/actions';
|
||||||
import { STEP, HTML } from '../../../utils/challengeTypes';
|
import { challengeSelector } from '../redux/selectors';
|
||||||
|
|
||||||
const bindableActions = {
|
const bindableActions = {
|
||||||
fetchChallenge
|
fetchChallenge
|
||||||
};
|
};
|
||||||
|
|
||||||
const challengeSelector = createSelector(
|
|
||||||
state => state.challengesApp.challenge,
|
|
||||||
state => state.entities.challenge,
|
|
||||||
(challengeName, challengeMap) => {
|
|
||||||
const challenge = challengeMap[challengeName];
|
|
||||||
return {
|
|
||||||
challenge: challenge,
|
|
||||||
showPreview: !!challenge && challenge.challengeType === HTML,
|
|
||||||
isStep: !!challenge && challenge.challengeType === STEP,
|
|
||||||
mode: !!challenge && challenge.challengeType === HTML ?
|
|
||||||
'text/html' :
|
|
||||||
'javascript'
|
|
||||||
};
|
|
||||||
}
|
|
||||||
);
|
|
||||||
|
|
||||||
const mapStateToProps = createSelector(
|
const mapStateToProps = createSelector(
|
||||||
challengeSelector,
|
challengeSelector,
|
||||||
state => state.challengesApp.content,
|
state => state.challengesApp.challenge,
|
||||||
(challengeProps, content) => ({
|
({ isStep }, challenge) => ({ challenge, isStep })
|
||||||
...challengeProps,
|
|
||||||
content
|
|
||||||
})
|
|
||||||
);
|
);
|
||||||
|
|
||||||
const fetchOptions = {
|
const fetchOptions = {
|
||||||
@ -45,24 +26,19 @@ const fetchOptions = {
|
|||||||
return [ dashedName ];
|
return [ dashedName ];
|
||||||
},
|
},
|
||||||
isPrimed({ challenge }) {
|
isPrimed({ challenge }) {
|
||||||
return challenge;
|
return !!challenge;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
export class Challenges extends PureComponent {
|
export class Challenges extends PureComponent {
|
||||||
static displayName = 'Challenges';
|
static displayName = 'Challenges';
|
||||||
static propTypes = {
|
static propTypes = { isStep: PropTypes.bool };
|
||||||
challenge: PropTypes.object,
|
|
||||||
showPreview: PropTypes.bool,
|
|
||||||
mode: PropTypes.string,
|
|
||||||
isStep: PropTypes.bool
|
|
||||||
};
|
|
||||||
|
|
||||||
render() {
|
render() {
|
||||||
if (this.props.isStep) {
|
if (this.props.isStep) {
|
||||||
return <Step { ...this.props }/>;
|
return <Step />;
|
||||||
}
|
}
|
||||||
return <Challenge { ...this.props }/>;
|
return <Challenge />;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2,17 +2,20 @@ import React, { PropTypes } from 'react';
|
|||||||
import classnames from 'classnames';
|
import classnames from 'classnames';
|
||||||
import { connect } from 'react-redux';
|
import { connect } from 'react-redux';
|
||||||
import { createSelector } from 'reselect';
|
import { createSelector } from 'reselect';
|
||||||
import { goToStep } from '../../redux/actions';
|
|
||||||
import PureComponent from 'react-pure-render/component';
|
import PureComponent from 'react-pure-render/component';
|
||||||
import ReactTransitionReplace from 'react-css-transition-replace';
|
import ReactTransitionReplace from 'react-css-transition-replace';
|
||||||
|
|
||||||
|
import { goToStep } from '../../redux/actions';
|
||||||
|
import { challengeSelector } from '../../redux/selectors';
|
||||||
import { Button, Col, Image, Row } from 'react-bootstrap';
|
import { Button, Col, Image, Row } from 'react-bootstrap';
|
||||||
|
|
||||||
const transitionTimeout = 1000;
|
const transitionTimeout = 1000;
|
||||||
const mapStateToProps = createSelector(
|
const mapStateToProps = createSelector(
|
||||||
|
challengeSelector,
|
||||||
state => state.challengesApp.currentStep,
|
state => state.challengesApp.currentStep,
|
||||||
state => state.challengesApp.previousStep,
|
state => state.challengesApp.previousStep,
|
||||||
(currentStep, previousStep) => ({
|
({ challenge }, currentStep, previousStep) => ({
|
||||||
|
challenge,
|
||||||
currentStep,
|
currentStep,
|
||||||
previousStep,
|
previousStep,
|
||||||
isGoingForward: currentStep > previousStep
|
isGoingForward: currentStep > previousStep
|
||||||
|
21
common/app/routes/challenges/redux/selectors.js
Normal file
21
common/app/routes/challenges/redux/selectors.js
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
import { STEP, HTML } from '../../../utils/challengeTypes';
|
||||||
|
import { createSelector } from 'reselect';
|
||||||
|
|
||||||
|
export const challengeSelector = createSelector(
|
||||||
|
state => state.challengesApp.challenge,
|
||||||
|
state => state.entities.challenge,
|
||||||
|
(challengeName, challengeMap) => {
|
||||||
|
if (!challengeName || !challengeMap) {
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
const challenge = challengeMap[challengeName];
|
||||||
|
return {
|
||||||
|
challenge: challenge,
|
||||||
|
showPreview: !!challenge && challenge.challengeType === HTML,
|
||||||
|
isStep: !!challenge && challenge.challengeType === STEP,
|
||||||
|
mode: !!challenge && challenge.challengeType === HTML ?
|
||||||
|
'text/html' :
|
||||||
|
'javascript'
|
||||||
|
};
|
||||||
|
}
|
||||||
|
);
|
Reference in New Issue
Block a user