Skip to content
This repository has been archived by the owner on Jan 19, 2024. It is now read-only.

Commit

Permalink
Merge branch 'recover-user-attempts'
Browse files Browse the repository at this point in the history
  • Loading branch information
huangins committed Feb 17, 2017
2 parents a14b6aa + ac85c60 commit 8226997
Show file tree
Hide file tree
Showing 13 changed files with 344 additions and 10 deletions.
179 changes: 173 additions & 6 deletions build/perseus-1.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
/*! Perseus | http://github.com/Khan/perseus */
// commit ffd9f90a81ec1f7ac6a5cca8dd38e88931a8c4dc
// branch fixbug_math_input_is_hidden_by_answer_area
// commit b364c00630574736c71927535c25d15db1f15d38
// branch master
(function(f){if(typeof exports==="object"&&typeof module!=="undefined"){module.exports=f()}else if(typeof define==="function"&&define.amd){define([],f)}else{var g;if(typeof window!=="undefined"){g=window}else if(typeof global!=="undefined"){g=global}else if(typeof self!=="undefined"){g=self}else{g=this}g.Perseus = f()}})(function(){var define,module,exports;return (function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o<r.length;o++)s(r[o]);return s})({1:[function(require,module,exports){
/*
Software License Agreement (BSD License)
Expand Down Expand Up @@ -4113,6 +4113,32 @@ var AnswerAreaRenderer = React.createClass({displayName: 'AnswerAreaRenderer',
this.refs.widget.focus();
},

showGuess: function(answerData) {
if( !answerData )
return;
if (answerData instanceof Array) {
// Answer area contains no widgets.
} else if (this.refs.widget.setAnswerFromJSON === undefined) {
// Target widget cannot show answer.
console.log("Target widget cannot show in answerarea",answerData);
return 'no setAnswerFromJSON implemented for widgets in answer area.';
} else {
console.log("Target widget show in answerarea")
// Just show the given answer.
this.refs.widget.setAnswerFromJSON(answerData);
}
},

canShowAllHistoryWidgets: function(answerData) {
if(!answerData)
return true;
if (this.refs.widget.setAnswerFromJSON === undefined) {
console.log('no setAnswerFromJSON implemented for widgets in answer area.');
return false;
}
return true;
},

guessAndScore: function() {
// TODO(alpert): These should probably have the same signature...
if (this.props.type === "multiple") {
Expand Down Expand Up @@ -10907,8 +10933,13 @@ var ItemRenderer = React.createClass({displayName: 'ItemRenderer',
document.querySelector(this.props.hintsAreaSelector));
},

showHint: function() {
if (this.state.hintsVisible < this.getNumHints()) {
showHint: function(hintNum) {
if( hintNum ){
this.setState({
hintsVisible: ( hintNum + 1 )
});
}
else if (this.state.hintsVisible < this.getNumHints()) {
this.setState({
hintsVisible: this.state.hintsVisible + 1
});
Expand All @@ -10919,6 +10950,22 @@ var ItemRenderer = React.createClass({displayName: 'ItemRenderer',
return this.props.item.hints.length;
},

showGuess: function(answerData) {
this.questionRenderer.showGuess(answerData)
if (answerData !== undefined && this.questionRenderer.widgetIds.length > 0) {
// Left answers for answer widgets only.
answerData = answerData[1];
}
this.answerAreaRenderer.showGuess(answerData);
return ;
},
canShowAllHistoryWidgets: function() {
var canShowAllHistoryWidgetsInAnswer = this.answerAreaRenderer.canShowAllHistoryWidgets();
var canShowAllHistoryWidgetsInQuestion = this.questionRenderer.canShowAllHistoryWidgets();
if (canShowAllHistoryWidgetsInAnswer && canShowAllHistoryWidgetsInQuestion)
return true;
return false;
},
scoreInput: function() {
var qGuessAndScore = this.questionRenderer.guessAndScore();
var aGuessAndScore = this.answerAreaRenderer.guessAndScore();
Expand Down Expand Up @@ -11706,6 +11753,38 @@ var Renderer = React.createClass({displayName: 'Renderer',
}, function() {return focus;});
},

showGuess: function(answerData) {
if( !answerData )
return {};
return _.map(this.widgetIds, function(id, index) {
if (this.refs[id].setAnswerFromJSON === undefined) {
// Target widget cannot show answer.
return {showSuccess:false,err:'no setAnswerFromJSON implemented for ' + id + ' widget'};
} else {
// Just show the given answer.
if(answerData[0].length<=index) {
console.log("showGuess err");
return {};
}
widgetAnswerData = answerData[0][index];
this.refs[id].setAnswerFromJSON(widgetAnswerData);
return {showSuccess:true};
}
}, this);
},

canShowAllHistoryWidgets: function(answerData) {
var r = true;
_.map(this.widgetIds, function(id, index) {
if (this.refs[id].setAnswerFromJSON === undefined) {
if ( id !== 'image 1') {
r = false;
}
}
}, this);
return r;
},

guessAndScore: function() {
var widgetProps = this.props.widgets;
var onInputError = this.props.apiOptions.onInputError ||
Expand Down Expand Up @@ -12799,7 +12878,9 @@ var Categorizer = React.createClass({displayName: 'Categorizer',
values: []
};
},

setAnswerFromJSON: function(answerData) {
this.props.onChange(answerData);
},
getInitialState: function() {
return {
uniqueId: _.uniqueId("perseus_radio_")
Expand Down Expand Up @@ -12983,7 +13064,9 @@ var Dropdown = React.createClass({displayName: 'Dropdown',
apiOptions: ApiOptions.defaults
};
},

setAnswerFromJSON: function(answerData) {
this.props.onChange({selected:answerData.value});
},
render: function() {
var choices = this.props.choices.slice();

Expand Down Expand Up @@ -13811,6 +13894,13 @@ var Expression = React.createClass({displayName: 'Expression',
return Expression.validate(this.toJSON(), rubric, onInputError);
},

setAnswerFromJSON: function(answerData) {
if (answerData === undefined) {
answerData = {value: ""};
}
this.props.onChange(answerData);
},

toJSON: function(skipValidation) {
return {value: this.props.value};
},
Expand Down Expand Up @@ -14846,6 +14936,13 @@ var InputNumber = React.createClass({displayName: 'InputNumber',
return true;
},

setAnswerFromJSON: function(answerData) {
if (answerData === undefined) {
answerData = {currentValue: ""};
}
this.props.onChange(answerData);
},

toJSON: function(skipValidation) {
return {
currentValue: this.props.currentValue
Expand Down Expand Up @@ -17775,6 +17872,17 @@ var InteractiveNumberLine = React.createClass({displayName: 'InteractiveNumberLi
}
},

setAnswerFromJSON: function(answerData) {
if (answerData === undefined) {
answerData = this.getDefaultProps();
}
if (answerData.rel === "eq") {
answerData.rel = "ge";
answerData.isInequality = false;
}
this.props.onChange(answerData);
},

toJSON: function() {
return {
pointX: this.props.pointX,
Expand Down Expand Up @@ -19489,6 +19597,17 @@ var NumberLine = React.createClass({displayName: 'NumberLine',
graphie.line([center, 0], [left, 0], {arrows: "->"});
},

setAnswerFromJSON: function(answerData) {
if (answerData === undefined) {
answerData = this.getDefaultProps();
}
if (answerData.rel === "eq") {
answerData.rel = "ge";
answerData.isInequality = false;
}
this.props.onChange(answerData);
},

toJSON: function() {
return {
numLinePosition: this.props.numLinePosition,
Expand Down Expand Up @@ -19938,6 +20057,13 @@ var NumericInput = React.createClass({displayName: 'NumericInput',
return {currentValue: this.props.currentValue};
},

setAnswerFromJSON: function(answerData) {
if (answerData === undefined) {
answerData = {currentValue: ""};
}
this.props.onChange(answerData);
},

simpleValidate: function(rubric) {
return NumericInput.validate(this.toJSON(), rubric);
},
Expand Down Expand Up @@ -22182,6 +22308,18 @@ var Radio = React.createClass({displayName: 'Radio',
});
},

setAnswerFromJSON: function(answerData) {
if (answerData === undefined) {
renderedAnswerData = {values: undefined};
} else {
var renderedAnswerData = {'values': []};
for (var i = 0; i < this.props.choices.length; i++) {
renderedAnswerData['values'].push(answerData['values'][this.props.choices[i].originalIndex]);
}
}
this.props.onChange(renderedAnswerData);
},

toJSON: function(skipValidation) {
// Return checked inputs in the form {values: [bool]}. (Dear future
// timeline implementers: this used to be {value: i} before multiple
Expand Down Expand Up @@ -22573,6 +22711,35 @@ var Sorter = React.createClass({displayName: 'Sorter',
);
},

setAnswerFromJSON: function(answerData) {
sortable = this.refs.sortable;
if (answerData === undefined) {
sortable.setState({
items: sortable.clearItemMeasurements(sortable.state.items)
});
} else {
items = sortable.state.items;
result = [];

answerData.options.forEach(function(key) {
var found = false;
items = items.filter(function(item) {
if(!found && item['option'] == key) {
result.push(item);
found = true;
return false;
} else
return true;
})
});
sortable.setState({items: result});
}
// HACK: We need to know *that* the widget changed, but currently it's
// not set up in a nice way to tell us *how* it changed, since the
// permutation of the items is stored in state.
this.props.onChange({});
},

toJSON: function(skipValidation) {
return {options: this.refs.sortable.getOptions()};
},
Expand Down
26 changes: 26 additions & 0 deletions src/answer-area-renderer.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -329,6 +329,32 @@ var AnswerAreaRenderer = React.createClass({
this.refs.widget.focus();
},

showGuess: function(answerData) {
if( !answerData )
return;
if (answerData instanceof Array) {
// Answer area contains no widgets.
} else if (this.refs.widget.setAnswerFromJSON === undefined) {
// Target widget cannot show answer.
console.log("Target widget cannot show in answerarea",answerData);
return 'no setAnswerFromJSON implemented for widgets in answer area.';
} else {
console.log("Target widget show in answerarea")
// Just show the given answer.
this.refs.widget.setAnswerFromJSON(answerData);
}
},

canShowAllHistoryWidgets: function(answerData) {
if(!answerData)
return true;
if (this.refs.widget.setAnswerFromJSON === undefined) {
console.log('no setAnswerFromJSON implemented for widgets in answer area.');
return false;
}
return true;
},

guessAndScore: function() {
// TODO(alpert): These should probably have the same signature...
if (this.props.type === "multiple") {
Expand Down
25 changes: 23 additions & 2 deletions src/item-renderer.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -257,8 +257,13 @@ var ItemRenderer = React.createClass({
document.querySelector(this.props.hintsAreaSelector));
},

showHint: function() {
if (this.state.hintsVisible < this.getNumHints()) {
showHint: function(hintNum) {
if( hintNum ){
this.setState({
hintsVisible: ( hintNum + 1 )
});
}
else if (this.state.hintsVisible < this.getNumHints()) {
this.setState({
hintsVisible: this.state.hintsVisible + 1
});
Expand All @@ -269,6 +274,22 @@ var ItemRenderer = React.createClass({
return this.props.item.hints.length;
},

showGuess: function(answerData) {
this.questionRenderer.showGuess(answerData)
if (answerData !== undefined && this.questionRenderer.widgetIds.length > 0) {
// Left answers for answer widgets only.
answerData = answerData[1];
}
this.answerAreaRenderer.showGuess(answerData);
return ;
},
canShowAllHistoryWidgets: function() {
var canShowAllHistoryWidgetsInAnswer = this.answerAreaRenderer.canShowAllHistoryWidgets();
var canShowAllHistoryWidgetsInQuestion = this.questionRenderer.canShowAllHistoryWidgets();
if (canShowAllHistoryWidgetsInAnswer && canShowAllHistoryWidgetsInQuestion)
return true;
return false;
},
scoreInput: function() {
var qGuessAndScore = this.questionRenderer.guessAndScore();
var aGuessAndScore = this.answerAreaRenderer.guessAndScore();
Expand Down
32 changes: 32 additions & 0 deletions src/renderer.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -514,6 +514,38 @@ var Renderer = React.createClass({
}, () => focus);
},

showGuess: function(answerData) {
if( !answerData )
return {};
return _.map(this.widgetIds, function(id, index) {
if (this.refs[id].setAnswerFromJSON === undefined) {
// Target widget cannot show answer.
return {showSuccess:false,err:'no setAnswerFromJSON implemented for ' + id + ' widget'};
} else {
// Just show the given answer.
if(answerData[0].length<=index) {
console.log("showGuess err");
return {};
}
widgetAnswerData = answerData[0][index];
this.refs[id].setAnswerFromJSON(widgetAnswerData);
return {showSuccess:true};
}
}, this);
},

canShowAllHistoryWidgets: function(answerData) {
var r = true;
_.map(this.widgetIds, function(id, index) {
if (this.refs[id].setAnswerFromJSON === undefined) {
if ( id !== 'image 1') {
r = false;
}
}
}, this);
return r;
},

guessAndScore: function() {
var widgetProps = this.props.widgets;
var onInputError = this.props.apiOptions.onInputError ||
Expand Down
4 changes: 3 additions & 1 deletion src/widgets/categorizer.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,9 @@ var Categorizer = React.createClass({
values: []
};
},

setAnswerFromJSON: function(answerData) {
this.props.onChange(answerData);
},
getInitialState: function() {
return {
uniqueId: _.uniqueId("perseus_radio_")
Expand Down
Loading

0 comments on commit 8226997

Please sign in to comment.