From 314482040524b2faa9311fa5c73c9344ee861ed6 Mon Sep 17 00:00:00 2001 From: Mikhail Pontus Date: Sat, 16 Dec 2017 14:53:07 +0300 Subject: [PATCH] fix(challenges): Implement Help Dialog This commit applies changes from 78e86f514f90dc3fd392a52fa52feb180a91f3af. It introduces Help dialog which guides the user to review Read-Search-Ask methodology, ask the question on the forums or in gitter chatroom. This dialog replaces existing Help button which was leading to Gitter Chatroom. --- client/less/lib/bootstrap/modals.less | 4 - client/less/main.less | 4 +- common/app/routes/Challenges/Help-Modal.jsx | 94 +++++++++++ common/app/routes/Challenges/Side-Panel.jsx | 18 +-- common/app/routes/Challenges/Tool-Panel.jsx | 14 +- common/app/routes/Challenges/challenges.less | 8 + .../app/routes/Challenges/redux/bug-epic.js | 82 ---------- common/app/routes/Challenges/redux/index.js | 23 ++- .../app/routes/Challenges/redux/modal-epic.js | 146 ++++++++++++++++++ 9 files changed, 284 insertions(+), 109 deletions(-) create mode 100644 common/app/routes/Challenges/Help-Modal.jsx delete mode 100644 common/app/routes/Challenges/redux/bug-epic.js create mode 100644 common/app/routes/Challenges/redux/modal-epic.js diff --git a/client/less/lib/bootstrap/modals.less b/client/less/lib/bootstrap/modals.less index 3671ff0715..e2a0c6309a 100755 --- a/client/less/lib/bootstrap/modals.less +++ b/client/less/lib/bootstrap/modals.less @@ -81,10 +81,6 @@ border-bottom: 1px solid @modal-header-border-color; min-height: (@modal-title-padding + @modal-title-line-height); } -// Close icon -.modal-header .close { - margin-top: -2px; -} // Title text within header .modal-title { diff --git a/client/less/main.less b/client/less/main.less index 8c4c3c3bd6..d02dd193ce 100644 --- a/client/less/main.less +++ b/client/less/main.less @@ -500,7 +500,7 @@ form.update-email .btn{ } } -.challenge-list-header { +.challenges-list-header { background-color: @brand-primary; color: @gray-lighter; font-size: 36px; @@ -825,7 +825,7 @@ code { color: @night-text-color; .btn-group, .text-success, - .challenge-list-header, + .challenges-list-header, .fcc-footer { background-color: @night-body-bg; } diff --git a/common/app/routes/Challenges/Help-Modal.jsx b/common/app/routes/Challenges/Help-Modal.jsx new file mode 100644 index 0000000000..ebac1a5509 --- /dev/null +++ b/common/app/routes/Challenges/Help-Modal.jsx @@ -0,0 +1,94 @@ +import React, { PureComponent } from 'react'; +import PropTypes from 'prop-types'; +import { connect } from 'react-redux'; +import { Button, Modal } from 'react-bootstrap'; + +import ns from './ns.json'; +import { + createQuestion, + openHelpChatRoom, + closeHelpModal, + helpModalSelector +} from './redux'; + +const mapStateToProps = state => ({ isOpen: helpModalSelector(state) }); +const mapDispatchToProps = { createQuestion, openHelpChatRoom, closeHelpModal }; +const methodologyUrl = 'https://forum.freecodecamp.org/t/the-read-search-ask-methodology-for-getting-unstuck/137307'; // eslint-disable-line max-len + +const propTypes = { + closeHelpModal: PropTypes.func, + createQuestion: PropTypes.func, + isOpen: PropTypes.bool, + openHelpChatRoom: PropTypes.func +}; + +export class HelpModal extends PureComponent { + render() { + const { + isOpen, + closeHelpModal, + openHelpChatRoom, + createQuestion + } = this.props; + return ( + + + Ask for help? + + × + + + +

+ If you've already tried the Read-Search-Ask method, + then you can ask for help on the freeCodeCamp forum. +

+ + + + +
+
+ ); + } +} + +HelpModal.displayName = 'HelpModal'; +HelpModal.propTypes = propTypes; + +export default connect(mapStateToProps, mapDispatchToProps)(HelpModal); diff --git a/common/app/routes/Challenges/Side-Panel.jsx b/common/app/routes/Challenges/Side-Panel.jsx index 0faa9bd992..bc6d87d408 100644 --- a/common/app/routes/Challenges/Side-Panel.jsx +++ b/common/app/routes/Challenges/Side-Panel.jsx @@ -7,6 +7,7 @@ import { connect } from 'react-redux'; import ns from './ns.json'; import BugModal from './Bug-Modal.jsx'; +import HelpModal from './Help-Modal.jsx'; import ToolPanel from './Tool-Panel.jsx'; import ChallengeTitle from './Challenge-Title.jsx'; import ChallengeDescription from './Challenge-Description.jsx'; @@ -14,6 +15,7 @@ import TestSuite from './Test-Suite.jsx'; import Output from './Output.jsx'; import { openBugModal, + openHelpModal, updateHint, executeChallenge, unlockUntrustedCode, @@ -22,8 +24,7 @@ import { testsSelector, outputSelector, hintIndexSelector, - codeLockedSelector, - chatRoomSelector + codeLockedSelector } from './redux'; import { descriptionRegex } from './utils'; @@ -35,6 +36,7 @@ const mapDispatchToProps = { executeChallenge, updateHint, openBugModal, + openHelpModal, unlockUntrustedCode }; const mapStateToProps = createSelector( @@ -44,7 +46,6 @@ const mapStateToProps = createSelector( outputSelector, hintIndexSelector, codeLockedSelector, - chatRoomSelector, ( { description }, { title }, @@ -52,24 +53,22 @@ const mapStateToProps = createSelector( output, hintIndex, isCodeLocked, - helpChatRoom ) => ({ title, description, tests, output, - isCodeLocked, - helpChatRoom + isCodeLocked }) ); const propTypes = { description: PropTypes.arrayOf(PropTypes.string), executeChallenge: PropTypes.func, - helpChatRoom: PropTypes.string, hint: PropTypes.string, isCodeLocked: PropTypes.bool, makeToast: PropTypes.func, openBugModal: PropTypes.func, + openHelpModal: PropTypes.func, output: PropTypes.string, tests: PropTypes.arrayOf(PropTypes.object), title: PropTypes.string, @@ -125,8 +124,8 @@ export class SidePanel extends PureComponent { executeChallenge, updateHint, makeToast, - helpChatRoom, openBugModal, + openHelpModal, isCodeLocked, unlockUntrustedCode } = this.props; @@ -147,15 +146,16 @@ export class SidePanel extends PureComponent { +

@@ -12,11 +14,11 @@ const unlockWarning = ( const propTypes = { executeChallenge: PropTypes.func.isRequired, - helpChatRoom: PropTypes.string, hint: PropTypes.string, isCodeLocked: PropTypes.bool, makeToast: PropTypes.func.isRequired, openBugModal: PropTypes.func.isRequired, + openHelpModal: PropTypes.func.isRequired, unlockUntrustedCode: PropTypes.func.isRequired, updateHint: PropTypes.func.isRequired }; @@ -93,10 +95,10 @@ export default class ToolPanel extends PureComponent { render() { const { executeChallenge, - helpChatRoom, hint, isCodeLocked, openBugModal, + openHelpModal, unlockUntrustedCode } = this.props; return ( @@ -111,13 +113,12 @@ export default class ToolPanel extends PureComponent { }