...

View Full Version : Need Help: Multiplication Test in Javascript



leafeater
11-10-2010, 02:47 AM
Hello,

I am trying to write a javascript page that shuffles an array of questions ( 1x1 , 1x2, 1x3 - 1x12), prints them, then has the user type in the answer, then checks them to make sure the user answer is correct.
I have looked up a lot of source code for javascript "quiz" but they all are multiple choice answers and the questions are not shuffled. This is as far as I have gotten, but now I am not sure how to take the user input text and compare them to the answer / question array to make sure to check.



<html>
<head>
<title> Slick Math </title>
<script type="text/javascript">

var quest = new Array;
var ans = new Array;
var questprint = new Array;

quest[0] = "1 x 1 ";
quest[1] = "1 x 2 ";
quest[2] = "1 x 3 ";
quest[3] = "1 x 4 ";
quest[4] = "1 x 5 ";
quest[5] = "1 x 6 ";
quest[6] = "1 x 7 ";
quest[7] = "1 x 8 ";
quest[8] = "1 x 9 ";
quest[9] = "1 x 10 ";
quest[10] = "1 x 11 ";
quest[11] = "1 x 12 ";

questprint[0] = quest[0]+"<input type='text' name='q0'></input><br/>";
questprint[1] = quest[1]+"<input type='text' name='q1'></input><br/>";
questprint[2] = quest[2]+"<input type='text' name='q2'></input><br/>";
questprint[3] = quest[3]+"<input type='text' name='q3'></input><br/>";
questprint[4] = quest[4]+"<input type='text' name='q4'></input><br/>";
questprint[5] = quest[5]+"<input type='text' name='q5'></input><br/>";
questprint[6] = quest[6]+"<input type='text' name='q6'></input><br/>";
questprint[7] = quest[7]+"<input type='text' name='q7'></input><br/>";
questprint[8] = quest[8]+"<input type='text' name='q8'></input><br/>";
questprint[9] = quest[9]+"<input type='text' name='q9'></input><br/>";
questprint[10] = quest[10]+"<input type='text' name='q10'></input><br/>";
questprint[11] = quest[11]+"<input type='text' name='q11'></input><br/>";


var score = 0;
ans[0] = 1;
ans[1] = 2;
ans[2] = 3;
ans[3] = 4;
ans[4] = 5;
ans[5] = 6;
ans[6] = 7;
ans[7] = 8;
ans[8] = 9;
ans[9] = 10;
ans[10] = 11;
ans[11] = 12;

function shuffle() {
return (Math.round(Math.random())-.5);
}

questprint.sort(shuffle);

</script>
</head>
<body>
<h1>Slick Math</h1>
<form name="form">
<script type="text/javascript">
document.write(questprint[0]);
document.write(questprint[1]);
document.write(questprint[2]);
document.write(questprint[3]);
document.write(questprint[4]);
document.write(questprint[5]);
document.write(questprint[6]);
document.write(questprint[7]);
document.write(questprint[8]);
document.write(questprint[9]);
document.write(questprint[10]);
document.write(questprint[11]);

</script>
</form>
</body>
</html>


Thanks =]

Old Pedant
11-10-2010, 02:58 AM
Ummm...if you only shuffle the questions, then how will you match them up with the *UN*shuffled answers???

There actually is an easy way to do this, but I think it might be beyond where you are at in your classroom and using it would likely make the prof suspicious.

I think maybe the easy way for you, at your likely level, to do this would be to create the array elements as:


var questions = [
'1 x 1? <input name="a1" />',
'7 x 3? <input name="a21" />',
...
];

So you shuffle the questions and the answers are simply the names of the <input> fields, after you lop off the "a".

leafeater
11-10-2010, 03:35 AM
What are your thoughts on the "easy" way to accomplish this with arrays? This is nothing that is being graded by any professor, its more of a little project for my friend who is an elementary teacher.

Old Pedant
11-10-2010, 03:53 AM
Ahhh...okay, so how far will the questions go? You can ENORMOUSLY simplify things if one of the multipliers is always the same in each question (as in your example), but if you want to (say) generate random questions from 1x1 to 12x12, then I'd do it *completely* differently.

leafeater
11-10-2010, 03:58 AM
Like in the example one of the numbers will always be the same. I intend to have a final product of 12 pages. One for multiples of one, two, three, ect, 12.

Afro_Programmer
11-10-2010, 04:27 AM
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Untitled Document</title>


</head>

<body>

<script type="text/javascript">

toPrint = new Array();
var str = "<input type = \"textbar\" name =" + "\"";
var str2 = "\"</input><br />";

for(i = 1; i <= 12; i++)
{
toPrint[i] = "1x" + i + str + i + str2;
}

document.write("<form name = \"frm\" id = \"frm\" action = \"untitled1.php\" method = \"post\" />");
document.write("<input name=\"sub\" type=\"submit\" value=\"Submit Results\" /> <br />");

for (x = 1; x <= 12; x++)
{
document.write(toPrint[x]);
}

document.write("</form>");

window.onload = function()
{
frm = document.getElementById("frm");
}


window.onsubmit = function()
{

for (y = 1; y <= 12; y++)
{
val = frm.elements.item(y).value;
name = frm.elements.item(y).name;
alert(name + " " + val);

if (val == name)
{
alert("question: " + "1x" + y + " is correct!");
}
else
{
alert("question: " + "1x" + y + " is wrong!");
}
}
}

</script>
</body>
</html>

im sleepy...cant finish. ;o

Old Pedant
11-10-2010, 10:16 PM
No need for 12 pages. One page will do it. Back later.

Old Pedant
11-11-2010, 12:25 AM
Here you go...

The line at the top:


var num = 1;

determines the *default* multiplier for the page. But you can override it by just appending a query string to the URL. For example, if you name the page "quiz.html", then hitting the page with the url

quiz.html?3

will make 3 the multiplier for the page. Further, if you use 0 either as the default or after the question mark, you will get random problems between 1x1 and 12x12.



<html>
<head>
<title>Multiplication exercises</title>
<script type="text/javascript">
var num = 1;
if ( location.search.length > 1 )
{
num = parseInt(location.search.substring(1) );
if ( isNaN(num) ) num = 1;
}
if ( num >= 1 && num <= 12 )
{
document.title += " -- multiples of " + num;
} else {
num = 0; // serves as a flag
document.title += " -- random multiples to 12";
}

var m1 = [ 1,2,3,4,5,6,7,8,9,10,11,12 ];
var m2 = [ 1,2,3,4,5,6,7,8,9,10,11,12 ];

function generate( )
{
var form = document.getElementById("TheQuiz");
m1.sort( function() { return(Math.random() - 0.5); } );
m2.sort( function() { return(Math.random() - 0.5); } );

for ( var q = 1; q <= 12; ++q )
{
var mul1 = m1[q-1];
var mul2 = ( num == 0 ) ? m2[q-1] : num;
document.getElementById("q" + q).innerHTML =
mul1 + " x " + mul2;
form["answer"+q].value = mul1 * mul2;
}
}

function checkAnswers( form )
{
// first, make sure there is a numeric answer in each box:
var oops = "";
for ( var q = 1; q <= 12; ++q )
{
var ans = parseFloat( form["question"+q].value );
if ( isNaN(ans) )
{
oops += "\nquestion " + q;
}
}
if ( oops != "" )
{
alert("You have not yet given a NUMBER for:" + oops);
return;
}
// now loop again, this time checking answers and marking right and wrong
var right = 0;
for ( var q = 1; q <= 12; ++q )
{
var fld = form["question"+q];
var ans = parseFloat( fld.value );
var correct = parseInt( form["answer"+q].value );
if ( ans == correct )
{
++right;
fld.style.backgroundColor = "transparent";
} else {
fld.style.backgroundColor = "pink";
}
}
document.getElementById("results").innerHTML =
"You got " + right + " out of 12";
}
</script>

</head>
<body onload="generate()">
<form id="TheQuiz">
<table cellpadding="12">
<tr>
<td>1. What is <span id="q1"></span>? </td>
<td> <input type="hidden" name="answer1" />
<input type="text" name="question1" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>2. What is <span id="q2"></span>? </td>
<td> <input type="hidden" name="answer2" />
<input type="text" name="question2" /> </td>
</tr><tr>
<td>3. What is <span id="q3"></span>? </td>
<td> <input type="hidden" name="answer3" />
<input type="text" name="question3" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>4. What is <span id="q4"></span>? </td>
<td> <input type="hidden" name="answer4" />
<input type="text" name="question4" /> </td>
</tr><tr>
<td>5. What is <span id="q5"></span>? </td>
<td> <input type="hidden" name="answer5" />
<input type="text" name="question5" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>6. What is <span id="q6"></span>? </td>
<td> <input type="hidden" name="answer6" />
<input type="text" name="question6" /> </td>
</tr><tr>
<td>7. What is <span id="q7"></span>? </td>
<td> <input type="hidden" name="answer7" />
<input type="text" name="question7" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>8. What is <span id="q8"></span>? </td>
<td> <input type="hidden" name="answer8" />
<input type="text" name="question8" /> </td>
</tr><tr>
<td>9. What is <span id="q9"></span>? </td>
<td> <input type="hidden" name="answer9" />
<input type="text" name="question9" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>10. What is <span id="q10"></span>? </td>
<td> <input type="hidden" name="answer10" />
<input type="text" name="question10" /> </td>
</tr><tr>
<td>11. What is <span id="q11"></span>? </td>
<td> <input type="hidden" name="answer11" />
<input type="text" name="question11" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>12. What is <span id="q12"></span>? </td>
<td> <input type="hidden" name="answer12" />
<input type="text" name="question12" /> </td>
</table>
<input type="button" name="check" value="Check my answers!" onclick="checkAnswers(this.form);"/>
<span id="results"></span>
</form>
</body>
</html>

Old Pedant
11-11-2010, 12:26 AM
I could have used JS to create the <table>, et al., but I think it's easier to understand this way. And not a single document.write( ) in the bunch!

james720
11-11-2010, 12:46 PM
What are your thoughts on the "easy" way to accomplish this with arrays? This is nothing that is being graded by any professor, its more of a little project for my friend who is an elementary teacher.

Old Pedant
11-11-2010, 08:07 PM
Um...excuse me, but did you miss this part:


var m1 = [ 1,2,3,4,5,6,7,8,9,10,11,12 ];
var m2 = [ 1,2,3,4,5,6,7,8,9,10,11,12 ];

...
m1.sort( function() { return(Math.random() - 0.5); } );
m2.sort( function() { return(Math.random() - 0.5); } );

If that's not "with arrays" what is it?

But I assume you mean "with arrays that generate the HTML"?

<shrug>Avoid document.write when possible. Good general rule. There are those who go further and say *NEVER* use it, that it's a terrible evil.

So if you used arrays to generate the HTML "properly", you would end up with a pretty ugly and complex mess. Tons and tons of document.createElement() and appendChild() and hard to read code and and and...

Is it doable? Sure. Done all the time (witness Google Maps). But is there a reason to do it when the problem is as constrained as this one is? (To wit, 12 questions in a fixed format, where only the content of the questions changes.) I don't think so. I wouldn't have coded this the way I did if I thought otherwise.

K.I.S.S. -- Keep It Simple, Stupid. Or, as I prefer to think of it, Keep It Successfully Simple. Don't look for overblown solutions when they aren't needed.

leafeater
11-11-2010, 09:20 PM
Thanks a ton for the help here Old Pedant, I throughly enjoyed taking this apart, and I envy your skill.

Would it be too much to ask tho if you could include a timer in this program that starts at 0 and is visible onload and stops when checkAnwsers button is pressed, or if the timer reaches one minute then it stops and automatically calls checkAnwsers?

Thanks.

Old Pedant
11-11-2010, 09:48 PM
Not quite what you asked for, but I think more effective. As you'll see if you let the timer just go.


<html>
<head>
<title>Multiplication exercises</title>
<script type="text/javascript">
var num = 1;
if ( location.search.length > 1 )
{
num = parseInt(location.search.substring(1) );
if ( isNaN(num) ) num = 1;
}
if ( num >= 1 && num <= 12 )
{
document.title += " -- multiples of " + num;
} else {
num = 0; // serves as a flag
document.title += " -- random multiples to 12";
}

var m1 = [ 1,2,3,4,5,6,7,8,9,10,11,12 ];
var m2 = [ 1,2,3,4,5,6,7,8,9,10,11,12 ];
var ticker = null;
var seconds = 60;

function generate( )
{
var form = document.getElementById("TheQuiz");
m1.sort( function() { return(Math.random() - 0.5); } );
m2.sort( function() { return(Math.random() - 0.5); } );

for ( var q = 1; q <= 12; ++q )
{
var mul1 = m1[q-1];
var mul2 = ( num == 0 ) ? m2[q-1] : num;
document.getElementById("q" + q).innerHTML =
mul1 + " x " + mul2;
form["answer"+q].value = mul1 * mul2;
}
ticker = setInterval( clock, 1000 );
}

function clock( )
{
--seconds;
document.getElementById("tick").innerHTML = seconds;
if ( seconds <= 0 )
{
clearInterval(ticker);
checkAnswers( document.getElementById("TheQuiz") );
} else if ( seconds <= 10 ) {
document.getElementById("TIMED").style.color = "red";
}
}

function checkAnswers( form )
{
var oops = "";

// if time is not expired, make sure there is a numeric answer in each box:
if ( seconds > 0 )
{
for ( var q = 1; q <= 12; ++q )
{
var ans = parseFloat( form["question"+q].value );
if ( isNaN(ans) )
{
oops += "\nquestion " + q;
}
}
}
if ( oops != "" )
{
alert("You have not yet given a NUMBER for:" + oops);
return;
}
clearInterval(ticker); // stop the timer & check answers

// now loop again, this time checking answers and marking right and wrong
var right = 0;
for ( var q = 1; q <= 12; ++q )
{
var fld = form["question"+q];
var ans = parseFloat( fld.value );
var correct = parseInt( form["answer"+q].value );
if ( ans == correct )
{
++right;
fld.style.backgroundColor = "transparent";
} else {
fld.style.backgroundColor = "pink";
}
}
document.getElementById("results").innerHTML =
"You got " + right + " out of 12";
}
</script>
<style type="text/css">
div#TIMED {
font-size: large;
font-weight: bold;
}
</style>
</head>
<body onload="generate()">
<div id="TIMED">Time remaining: <span id="tick">60</span> seconds.</div>
<br/><br/>
<form id="TheQuiz">
<table cellpadding="12">
<tr>
<td>1. What is <span id="q1"></span>? </td>
<td> <input type="hidden" name="answer1" />
<input type="text" name="question1" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>2. What is <span id="q2"></span>? </td>
<td> <input type="hidden" name="answer2" />
<input type="text" name="question2" /> </td>
</tr><tr>
<td>3. What is <span id="q3"></span>? </td>
<td> <input type="hidden" name="answer3" />
<input type="text" name="question3" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>4. What is <span id="q4"></span>? </td>
<td> <input type="hidden" name="answer4" />
<input type="text" name="question4" /> </td>
</tr><tr>
<td>5. What is <span id="q5"></span>? </td>
<td> <input type="hidden" name="answer5" />
<input type="text" name="question5" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>6. What is <span id="q6"></span>? </td>
<td> <input type="hidden" name="answer6" />
<input type="text" name="question6" /> </td>
</tr><tr>
<td>7. What is <span id="q7"></span>? </td>
<td> <input type="hidden" name="answer7" />
<input type="text" name="question7" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>8. What is <span id="q8"></span>? </td>
<td> <input type="hidden" name="answer8" />
<input type="text" name="question8" /> </td>
</tr><tr>
<td>9. What is <span id="q9"></span>? </td>
<td> <input type="hidden" name="answer9" />
<input type="text" name="question9" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>10. What is <span id="q10"></span>? </td>
<td> <input type="hidden" name="answer10" />
<input type="text" name="question10" /> </td>
</tr><tr>
<td>11. What is <span id="q11"></span>? </td>
<td> <input type="hidden" name="answer11" />
<input type="text" name="question11" /> </td>
<td>&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td>12. What is <span id="q12"></span>? </td>
<td> <input type="hidden" name="answer12" />
<input type="text" name="question12" /> </td>
</table>
<input type="button" name="check" value="Check my answers!" onclick="checkAnswers(this.form);"/>
<span id="results"></span>
</form>
</body>
</html>

Philip M
11-11-2010, 09:50 PM
Here you are:-


<div>You have <span id="timer">61</span> seconds.</div>
<input type = "button" value = "Check Answers" onclick = "stop()">

<script type = "text/javascript">

window.onload = answersTimer;

var tim;
function answersTimer(){
var timerDiv = document.getElementById("timer");
var time = Number(timerDiv.innerHTML);
timerDiv.innerHTML = time--;
if (time < 6) {
timerDiv.style.color = "red"; // last 5 seconds are shown in red
}
if (time > 0){
tim = setTimeout(answersTimer, 1000);
}
else{
checkAnswers("TheQuiz"); // when time expires
}
}

function stop() {
clearTimeout(tim); // stop the clock
checkAnswers("TheQuiz");
}

</script>

You should give your form a name as well as an id.

Old Pedant
11-11-2010, 11:10 PM
You should give your form a name as well as an id.

??? I thought form names were now deprecated??

leafeater
11-11-2010, 11:23 PM
Not gonna lie, im a little confused on were to implement all that Philip ><

Old Pedant
11-11-2010, 11:36 PM
You can't quite use Philip's answer "as-is" with my code. For one thing, his timer will keep on running after the user answers all the questions. He expects you to call his stop() function at the appropriate point. In addition, if time does expire, my code will still tell the user that he didn't give answers in various posts. Presumably, you'd want to bypass that.

If you take the code I posted, the timer part is a near clone of Philip's code, and I *did* integrate it to handle the points noted above.

leafeater
11-12-2010, 01:04 AM
I ended up changing a few things up and implementing your code. This is what I ended up doing to your masterpiece if you care to know.


<html>
<head>
<title>Slick Math</title>
<script type="text/javascript">
var num = 1;
if ( location.search.length > 1 )
{
num = parseInt(location.search.substring(1) );
if ( isNaN(num) ) num = 1;
}
if ( num >= 1 && num <= 12 )
{
document.title += " -- multiples of " + num;
} else {
num = 0; // serves as a flag
document.title += " -- random multiples to 12";
}

var m1 = [ 1,2,3,4,5,6,7,8,9,10,11,12 ];
var m2 = [ 1,2,3,4,5,6,7,8,9,10,11,12 ];
var ticker = null;
var seconds = 60;

function generate( )
{
var form = document.getElementById("TheQuiz");
m1.sort( function() { return(Math.random() - 0.5); } );
m2.sort( function() { return(Math.random() - 0.5); } );

for ( var q = 1; q <= 12; ++q )
{
var mul1 = m1[q-1];
var mul2 = ( num == 0 ) ? m2[q-1] : num;
document.getElementById("q" + q).innerHTML =
mul1 + " x " + mul2;
form["answer"+q].value = mul1 * mul2;
}
ticker = setInterval( clock, 1000 );
}

function clock( )
{
--seconds;
document.getElementById("tick").innerHTML = seconds;
if ( seconds <= 0 )
{
clearInterval(ticker);
checkAnswers( document.getElementById("TheQuiz") );
} else if ( seconds <= 10 ) {
document.getElementById("TIMED").style.color = "red";
}
}

function checkAnswers( form )
{
// first, make sure there is a numeric answer in each box:
/*var oops = "";
for ( var q = 1; q <= 12; ++q )
{
var ans = parseFloat( form["question"+q].value );
if ( isNaN(ans) )
{
oops += "\nquestion " + q;
}
}
if ( oops != "" )
{
alert("You have not yet given a NUMBER for:" + oops);
return;
}*/
// now loop again, this time checking answers and marking right and wrong
clearInterval(ticker); // stop the timer & check answers
var right = 0;
var wrong = 0;
var percent;
for ( var q = 1; q <= 12; ++q )
{
var fld = form["question"+q];
var ans = parseFloat( fld.value );
var correct = parseInt( form["answer"+q].value );
if ( ans == correct )
{
++right;
fld.style.backgroundColor = "transparent";
} else {
++wrong;
fld.style.backgroundColor = "pink";
}
}
percent = Math.round((right / 12) * 100);
timetofinish = 60 - seconds;
document.getElementById("results").innerHTML =
"<br /> Correct: " + right + "<br /> Incorect: " + wrong + "<br /> Percent: " + percent + "% <br /> Time to Complete: " + timetofinish + " seconds";

}
</script>
<style type="text/css">
div#TIMED {
font-size: large;
font-weight: bold;
}
</style>
</head>
<body onLoad="generate()">
<div id="TIMED">Time remaining: <span id="tick">60</span> seconds.</div>
<br/><br/>
<form id="TheQuiz">
<table width="438" cellpadding="12">
<tr>
<td> <span id="q1"></span> </td>
<td><input type="hidden" name="answer1" />
<input type="text" name="question1" /></td>
</tr>
<tr>
<td> <span id="q2"></span> </td>
<td><input type="hidden" name="answer2" />
<input type="text" name="question2" /></td>
</tr>
<tr>
<td> <span id="q3"></span> </td>
<td><input type="hidden" name="answer3" />
<input type="text" name="question3" /></td>
</tr>
<tr>
<td> <span id="q4"></span> </td>
<td><input type="hidden" name="answer4" />
<input type="text" name="question4" /></td>
</tr>
<tr>
<td> <span id="q5"></span> </td>
<td><input type="hidden" name="answer5" />
<input type="text" name="question5" /></td>
</tr>
<tr>
<td> <span id="q6"></span> </td>
<td><input type="hidden" name="answer6" />
<input type="text" name="question6" /></td>
<tr>
<td> <span id="q7"></span> </td>
<td><input type="hidden" name="answer7" />
<input type="text" name="question7" /></td>
</tr>
<tr>
<td> <span id="q8"></span> </td>
<td><input type="hidden" name="answer8" />
<input type="text" name="question8" /></td>
</tr>
<tr>
<td> <span id="q9"></span> </td>
<td><input type="hidden" name="answer9" />
<input type="text" name="question9" /></td>
</tr>
<tr>
<td> <span id="q10"></span> </td>
<td><input type="hidden" name="answer10" />
<input type="text" name="question10" /></td>
</tr>
<tr>
<td> <span id="q11"></span> </td>
<td><input type="hidden" name="answer11" />
<input type="text" name="question11" /></td>
</tr>
<tr>
<td> <span id="q12"></span> </td>
<td><input type="hidden" name="answer12" />
<input type="text" name="question12" /></td>
</table>
<input type="button" name="check" value="Check my Answers!" onClick="checkAnswers(this.form)"/>
<span id="results"></span>
</form>
</body>
</html>


Thank you ^ 5.



EZ Archive Ads Plugin for vBulletin Copyright 2006 Computer Help Forum