diff --git a/src/components/question/question.css b/src/components/question/question.css
new file mode 100644
index 000000000..7c6e672a9
--- /dev/null
+++ b/src/components/question/question.css
@@ -0,0 +1,57 @@
+@import "../../css/units.css";
+@import "../../css/colors.css";
+
+.question-wrapper {
+ position: absolute;
+ bottom: 0;
+ left: 0;
+ width: 100%;
+}
+
+.question-container {
+ margin: $space;
+ border: 1px solid $form-border;
+ border-radius: $space;
+ border-width: 2px;
+ padding: 1rem;
+ background: white;
+}
+
+.question-label {
+ font-size: 0.75rem;
+ font-weight: bold;
+ font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
+ color: $text-primary;
+ padding-bottom: $space;
+}
+
+.question-input {
+ display: flex; /* Keeps the input from going outside this container */
+ position: relative;
+}
+
+.question-submit-button {
+ position: absolute;
+ top: calc($space / 2);
+ right: calc($space / 2);
+
+ width: calc(2rem - $space);
+ height: calc(2rem - $space);
+
+ border: none;
+ border-radius: 100%;
+
+ color: white;
+ background: $motion-primary;
+}
+
+/* Input overrides: width, font-weight, focus outline and padding */
+.question-input > input {
+ width: 100%;
+ padding: 0 2rem 0 0.75rem; /* To make room for the submit button */
+ font-weight: normal;
+}
+
+.question-input > input:focus {
+ box-shadow: 0px 0px 0px 3px $motion-transparent;
+}
diff --git a/src/components/question/question.jsx b/src/components/question/question.jsx
new file mode 100644
index 000000000..11927bf96
--- /dev/null
+++ b/src/components/question/question.jsx
@@ -0,0 +1,47 @@
+import PropTypes from 'prop-types';
+import React from 'react';
+import styles from './question.css';
+import Input from '../forms/input.jsx';
+
+const QuestionComponent = props => {
+ const {
+ answer,
+ question,
+ onChange,
+ onClick,
+ onKeyPress
+ } = props;
+ return (
+
+
+ {question ? (
+
{question}
+ ) : null}
+
+
+
+
+
+
+ );
+};
+
+QuestionComponent.propTypes = {
+ answer: PropTypes.string,
+ onChange: PropTypes.func.isRequired,
+ onClick: PropTypes.func.isRequired,
+ onKeyPress: PropTypes.func.isRequired,
+ question: PropTypes.string
+};
+
+export default QuestionComponent;
diff --git a/src/components/stage/stage.jsx b/src/components/stage/stage.jsx
index 7a23c099d..ae5ff92a6 100644
--- a/src/components/stage/stage.jsx
+++ b/src/components/stage/stage.jsx
@@ -5,6 +5,7 @@ import classNames from 'classnames';
import Box from '../box/box.jsx';
import Loupe from '../loupe/loupe.jsx';
import MonitorList from '../../containers/monitor-list.jsx';
+import Question from '../../containers/question.jsx';
import styles from './stage.css';
const StageComponent = props => {
@@ -15,6 +16,8 @@ const StageComponent = props => {
colorInfo,
onDeactivateColorPicker,
isColorPicking,
+ question,
+ onQuestionAnswered,
...boxProps
} = props;
return (
@@ -40,6 +43,12 @@ const StageComponent = props => {
) : null}
+ {question === null ? null : (
+
+ )}
{isColorPicking ? (
+ );
+ }
+}
+
+Question.propTypes = {
+ onQuestionAnswered: PropTypes.func.isRequired,
+ question: PropTypes.string
+};
+
+export default Question;
diff --git a/src/containers/stage.jsx b/src/containers/stage.jsx
index 1de93d23d..fcff811bf 100644
--- a/src/containers/stage.jsx
+++ b/src/containers/stage.jsx
@@ -24,12 +24,14 @@ class Stage extends React.Component {
'cancelMouseDownTimeout',
'detachMouseEvents',
'handleDoubleClick',
+ 'handleQuestionAnswered',
'onMouseUp',
'onMouseMove',
'onMouseDown',
'onStartDrag',
'onStopDrag',
'updateRect',
+ 'questionListener',
'setCanvas'
]);
this.state = {
@@ -38,7 +40,8 @@ class Stage extends React.Component {
isDragging: false,
dragOffset: null,
dragId: null,
- colorInfo: null
+ colorInfo: null,
+ question: null
};
}
componentDidMount () {
@@ -47,12 +50,14 @@ class Stage extends React.Component {
this.updateRect();
this.renderer = new Renderer(this.canvas);
this.props.vm.attachRenderer(this.renderer);
+ this.props.vm.runtime.addListener('QUESTION', this.questionListener);
}
shouldComponentUpdate (nextProps, nextState) {
return this.props.width !== nextProps.width ||
this.props.height !== nextProps.height ||
this.props.isColorPicking !== nextProps.isColorPicking ||
- this.state.colorInfo !== nextState.colorInfo;
+ this.state.colorInfo !== nextState.colorInfo ||
+ this.state.question !== nextState.question;
}
componentDidUpdate (prevProps) {
if (this.props.isColorPicking && !prevProps.isColorPicking) {
@@ -66,6 +71,14 @@ class Stage extends React.Component {
this.detachRectEvents();
this.stopColorPickingLoop();
}
+ questionListener (question) {
+ this.setState({question: question});
+ }
+ handleQuestionAnswered (answer) {
+ this.setState({question: null}, () => {
+ this.props.vm.runtime.emit('ANSWER', answer);
+ });
+ }
startColorPickingLoop () {
this.intervalId = setInterval(() => {
this.setState({colorInfo: this.getColorInfo(this.pickX, this.pickY)});
@@ -251,7 +264,9 @@ class Stage extends React.Component {
);
diff --git a/src/lib/make-toolbox-xml.js b/src/lib/make-toolbox-xml.js
index 1c3843a09..315e1388c 100644
--- a/src/lib/make-toolbox-xml.js
+++ b/src/lib/make-toolbox-xml.js
@@ -336,12 +336,12 @@ const control = `
-
+
${blockSeparator}
-
-
+
+
${blockSeparator}
${blockSeparator}
@@ -382,7 +382,7 @@ const sensing = `
${blockSeparator}
-
+
What's your name?