Skip to content

Instantly share code, notes, and snippets.

@EE2dev
Last active November 9, 2015 23:18
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save EE2dev/c764b19dadd3ba1c5598 to your computer and use it in GitHub Desktop.
Save EE2dev/c764b19dadd3ba1c5598 to your computer and use it in GitHub Desktop.
Math exercise for kids - division
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<style>
circle {
stroke: #000;
fill: #ddd;
fill-opacity: .8;
}
text {
font-size: 32px;
}
div.top {
position: relative;
}
div#answer {
position: absolute;
left: 0px;
}
div.info {
margin-left: 650px;
}
</style>
<script src="http://d3js.org/d3.v3.js"></script>
</head>
<body>
<div class="top">
<div id="answer"></div>
<div class="info">
<select id ="sp" name="Sprache" onchange="setLanguage(this.value, true);">
<option value="german" selected>Deutsch</option>
<option value="english">English</option>
</select>
<select id ="ro" name="Rechnenoperationen" onchange="newQuestion(this.value); displayAnswers();">
<option value="+" selected>Addition</option>
<option value="-">Subtraktion</option>
<option value="*">Multiplikation</option>
<option value=":">Division</option>
</select>
<label><input type="checkbox" id="cbox1" value="first_checkbox" onchange="checkTime()">Zeitmessung (10 Fragen)</label>
<div id="feedback"><h1></h1></div>
<div id="result"></div>
<div class="count"></div>
</div>
</div>
<script>
var width = 700;
var fontSize = 32;
var radius = 25, cx = 30, cy = 150;
var totalCorrect = 0;
var totalQuestions = 0;
var colorIterations = 0;
var data;
var value1, value2, result;
var positiveComment, negativeComment, infoComment, resultComment;
var counter = 0;
var myTimer;
var answerSVG = d3.select("#answer")
.append("svg")
.attr("width", width)
.attr("height", 750);
reset();
function reset() {
newQuestion(d3.select("select#ro").node().value);
displayAnswers();
setLanguage(d3.select("select#sp").node().value);
checkTime();
}
function countNow() {
counter += 0.01;
d3.select("div.count").html(counter.toFixed(2));
}
function checkTime() {
if (document.getElementById("cbox1").checked===false) {
clearInterval(myTimer)
} else {
counter = 0;
myTimer = setInterval(countNow, 10);
}
}
function displayAnswers() {
var answerG = answerSVG.selectAll("g.circle")
.data(data);
answerG.enter()
.append("g")
.attr("class", "circle")
.attr("transform", translateOriginalCircles);
answerG.exit().remove();
d3.selectAll("g")
.on("mouseover", reactUponMouseOver)
.on("mouseout", reactUponMouseOut)
.on("click", evaluate);
answerG.append("circle")
.attr("cx", cx)
.attr("cy", cy)
.attr("r", radius);
answerG.append("text")
.attr("class", "number")
.attr("x", function(d) { if (d > 9) { return cx - fontSize/2; } else {return cx - fontSize*0.25;}})
.attr("y", cy - fontSize*0.7/2)
.attr("dy", ".71em")
.text(function(d) {return d;});
}
function translateOriginalCircles(d) {
var digits = d.toString();
if (digits.length == 1) { digits = "0" + digits;}
console.log("d: " +d + " d[1]: " + digits[1] + " d[0]: " + digits[0]);
var x = digits[1]*(2*radius+5);
var y = digits[0] * (2*radius+5)
return "translate(" + x + ", " + y + ")";
}
function newQuestion(questionType) {
if (!questionType) { questionType = d3.select("#ro").node().value;}
switch (questionType) {
case "+":
data = d3.range(0, 100, 1);
result = getRandomInteger(data[0],data[data.length-1]);
value2 = getRandomInteger(data[0], result);
value1 = result - value2;
break;
case "-":
data = d3.range(0, 100, 1);
value1 = getRandomInteger(data[0],data[data.length-1]);
value2 = getRandomInteger(data[0], value1);
result = value1 - value2;
break;
case "*":
data = d3.range(0, 11, 1);
value1 = getRandomInteger(data[0],data[data.length-1]);
value2 = getRandomInteger(data[0],data[data.length-1]);
result = value1 * value2;
data = d3.range(0, 100, 1);
break;
case ":":
data = d3.range(0, 11, 1);
result = getRandomInteger(data[0],data[data.length-1]);
value2 = getRandomInteger(data[1],data[data.length-1]);
value1 = value2 * result;
break;
}
colorIterations = 0;
// d3.select("#feedback").select("h1").html("Bitte klicke auf die richtige Antwort!");
d3.selectAll("circle").style("fill", "lightgrey");
d3.select("#answer svg").select(".questionbox").remove();
var question = d3.select("#answer").select("svg")
.append("g")
.attr("class", "questionbox");
question.append("rect")
.attr("class", "highlight")
.attr("x", 120)
.attr("y", 15)
.attr("width", 320)
.attr("height", 50)
.style("fill", "lightgreen")
.style("opacity", 0);
question.append("text")
.attr("class", "question")
.attr("x", width/2)
.attr("y", 30)
.attr("dy", ".71em")
.text(value1 + " " + questionType + " " + value2 + " = ")
.style("text-anchor", "end");
}
function setLanguage(language, updateResult) {
// to do: update values for rechenops, name for zeitmessung
switch (language) {
case "german":
positiveComment = ["Bravo!", "Sehr gut!", "Prima!", "Na also, es geht doch!", "Ausgezeichnet!"];
negativeComment = ["Nicht so schnell ... Versuch es noch einmal!",
"Du Schlafmütze ... Mach das bitte nochmal!",
"Leider falsch ...noch ein Versuch!",
"Bist Du sicher? Schau nochmal genau hin!",
"War ein Versuch wert... aber leider falsch ... bitte jetzt aber richtig!"];
infoComment = "Bitte klicke auf die richtige Antwort!";
resultComment = "Ergebnis";
break;
case "english":
positiveComment = ["Great!", "Very good!", "Excellent!", "I told you, you can do it!", "Terrific!"];
negativeComment = ["Not so fast ... Try it again!",
"Hey, wake up ... Try it again, please!",
"Unfortunately wrong ... one more try!",
"Are you sure? think twice!",
"It was worth a try... but wrong ... please do it right next time!"];
infoComment = "Please click on the correct answer!";
resultComment = "Result";
break;
}
d3.select("#feedback").select("h1").html(infoComment);
if (updateResult){
var newResultComment = d3.select("div#result").html().split(":");
d3.select("div#result").html(resultComment + ":" + newResultComment[1]);
}
}
function reactUponMouseOver(d, i) {
var sel = d3.selectAll("text.number").filter( function (da) { return da === d;});
var translationXY = d3.transform(d3.select(this).attr("transform"));
sel.transition()
.duration(750)
.attr("x", width/2 + 5 - translationXY.translate[0])
.attr("y", 30 - translationXY.translate[1])
.style("text-anchor", "start");
}
function reactUponMouseOut(d, i) {
var sel = d3.selectAll("text.number").filter( function (da) { return da === d;});
sel.transition()
.duration(750)
.ease("bounce")
.attr("x", function(d) { if (d > 9) { return cx - fontSize/2; } else {return cx - fontSize*0.25;}})
.attr("y", cy - fontSize*0.7/2);
}
function evaluate(d, i) {
var guess;
totalQuestions++;
if (totalQuestions === 10) {
clearInterval(myTimer);
}
var sel = d3.selectAll("text.number").filter( function (da) { return da === d;});
sel.each(function (d) {guess = d;});
var feedback = d3.select("#feedback")
feedback.select("h1").remove();
if (guess === result) {
totalCorrect++;
d3.select("rect.highlight")
.style("opacity", 0.5);
feedback.append("h1")
.attr("class", "feedback")
.html(function() { return positiveComment[getRandomInteger(0, positiveComment.length-1)]})
.transition()
.duration(2000)
.each("end", newQuestion);
d3.select("div#result").html(resultComment + ": " + totalCorrect + "/" + totalQuestions);
}
else {
var feedback = d3.select("#feedback")
feedback.append("h1")
.html(function() { return negativeComment[getRandomInteger(0, negativeComment.length-1)]});
d3.selectAll("circle")
.filter( function (da) { return da === d;})
.style("fill", "red");
reactUponMouseOut(d, i);
d3.select("div#result").html(resultComment + ": " + totalCorrect + "/" + totalQuestions);
}
}
function getRandomInteger(lower, upper) {
if (arguments.length === 1) {
upper = lower;
lower = 0;
}
return Math.floor(Math.random() * (upper - lower)) + lower;
}
</script>
</body>
</html>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment