Getting the value of "on" for radio buttons - javascript

var allQuestions = [{
question1: "What is 1 + 1?",
choices: ["1", "2", "3", 4],
correctAnswer: ["2"]
}, {
question2: "What is 2 + 2?",
choices: ["6", "2", "3", 4, ],
correctAnswer: ["4"]
}, {
question3: "What is 3 + 3?",
choices: ["3", "6", "9", 12],
correctAnswer: ["6"]
}];
var newArray = shuffleArray(allQuestions);
function shuffleArray(array) {
for (var i = array.length - 1; i > 0; i--) {
var j = Math.floor(Math.random() * (i + 1));
var temp = array[i];
array[i] = array[j];
array[j] = temp;
}
return array;
}
function appendQuestions(number) {
if (newArray == "undefined" || newArray == "null" || newArray.length == 0) {
document.getElementById("questionForm").innerHTML = "Complete!";
} else {
for (i = 0; i < 4; i++) {
$("#questionForm").append("<input name='question' type='radio'>" +
JSON.stringify(newArray[0].choices[i]) + "</input>")
}
}
}
$(function() {
$("#questionList").empty();
appendQuestions();
newArray.shift();
})
function isCorrectAnswer() {
checkedVal = $("input[type=radio][name=question]:checked").val();
if (checkedVal == newArray[0].correctAnswer) {
alert("Correct!");
} else {
alert("Wrong!");
}
alert(checkedVal);
}
$("#submitButton").click(function() {
isCorrectAnswer();
$("#questionForm").empty();
appendQuestions();
newArray.shift();
})
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class='container'>
<section id='questions'>
<form id="questionForm">
</form>
<div style='clear:both'></div>
<input id='submitButton' type='button' value='Submit'>
</section>
</div>
First off, sorry for the amount of code pasted. I have no idea if I'm missing some small bug or if I'm just writing the wrong code, so I figured it would be best to post all of it.
I am trying to get the value of a radio button. In the isCorrectAnswer function the first 2 lines are to determine the value of the radio button that is currently checked. The problem is when I alert the value of the radio button, it just says "on". I have searched for the last hour trying to figure out what this means or how to fix it and could not find a thing.
I apologize if this is a stupid question or if it has already been answered.

You have to change this line :
$("#questionForm").append("<input name='question' type='radio'>" +
JSON.stringify(newArray[0].choices[i]) + "</input>");
To :
$("#questionForm").append("<input name='question' type='radio' value='" +
JSON.stringify(newArray[0].correctAnswer[i]) + "' />"+JSON.stringify(newArray[0].choices[i]));
Hope this helps.

Related

Arrays keys with a radio button

I'm trying to access my random array keys with a radio button on each of them
I want to place the radio button only on the array
of the allQuestions[index].anwsers keys and it has 3 indexes keys.
I'm couldn't make it and this my work so far.
const allQuestions = [{
question: "Which of them is from compton",
anwsers: ["Nas", "Tupac", "Omarion", "Kendick"],
correctAnswer: "Kendrick"
},
{
question: "founder of HipHop",
anwsers: ["Tupac", "Eazy E", "Kendick", "Bambata"],
correctAnswer: "Bambata"
},
{
question: "Who won BET Hip Hop Album 2018",
anwsers: ["Kendrick", "Bruno", "Jay Z", "Drake"],
correctAnswer: "Kendrick",
},
{
question: "Best Female HipHop Art 2018",
anwsers: ["Azelia", "Nicki", "Cardi_b", "Mama Rap"],
correctAnswer: "Nicki"
}
]
function render() {
var index, unique;
var print = '<ul>';
for (i = 0; i < allQuestions.length; i++) {
index = Math.floor(Math.random() * allQuestions.length);
}
var showQuiz = document.getElementById('showQuiz');
var showAnswers = document.getElementById('showAnswers');
showQuiz.style.color = 'red';
showQuiz.innerHTML = allQuestions[index].question;
showAnswers.innerHTML = allQuestions[index].anwsers;
// I'm tryin to ue sthe unshift method here but it' not workin
showAnswers.unshift('<input type="radio" value="allQuestions.anwsers[]');
}
<div id="question" style="text-align: center"> Quiz</div>
<button type="button" onclick="render()">Next Quiz</button>
<div id="showQuiz"></div>
<div id="showAnswers"></div>
Appears we are trying to use the Array function unshift() on a DOM element. What i believe you are trying to do is create a list of radio buttons for each answer in your allQuestions.answers[], this can be done with a for loop, or a map like so:
Edit to add answersAsHtml and join(" ") this improves readability and joins each array element with a space instead of the default comma.
const allQuestions = [{
question: "Which of them is from compton",
anwsers: ["Nas", "Tupac", "Omarion", "Kendick"],
correctAnswer: "Kendrick"
},
{
question: "founder of HipHop",
anwsers: ["Tupac", "Eazy E", "Kendick", "Bambata"],
correctAnswer: "Bambata"
},
{
question: "Who won BET Hip Hop Album 2018",
anwsers: ["Kendrick", "Bruno", "Jay Z", "Drake"],
correctAnswer: "Kendrick",
},
{
question: "Best Female HipHop Art 2018",
anwsers: ["Azelia", "Nicki", "Cardi_b", "Mama Rap"],
correctAnswer: "Nicki"
}
]
function render() {
var index, unique;
var print = '<ul>';
for (i = 0; i < allQuestions.length; i++) {
index = Math.floor(Math.random() * allQuestions.length);
}
var showQuiz = document.getElementById('showQuiz');
var showAnswers = document.getElementById('showAnswers');
var answersAsHtml = allQuestions[index].anwsers.map(ans => `<input type="radio" value="${ans}">${ans}</input>`).join(" ");
showQuiz.style.color = 'red';
showQuiz.innerHTML = allQuestions[index].question;
showAnswers.innerHTML = answersAsHtml;
}
<div id="question" style="text-align: center"> Quiz</div>
<button type="button" onclick="render()">Next Quiz</button>
<div id="showQuiz"></div>
<div id="showAnswers"></div>
You are trying to write into an html element, that's not an array. You are probably looking for something more like this.
showAnswers.innerHTML = allQuestions[index].anwsers.map(function (answer){
return '<input type="radio" name="answers" value="' + answer + '"/>' + answer
})

next and previous JSON data with javascript

I' would like to create Next/Previous buttons for json array, but I can't get it to work.
This is the last one I have tried
<div id="text"></div>
<button name="prev">go to previous div</button>
<button name="next">go to next div</button>
<script>
myFunction([
{
"text": "text0"
},
{
"text": "text1"
},
{
"text": "text2"
},
{
"text": "text3"
}
]);
function myFunction(arr) {
var out = "";
var i ;
out = '<p>' + arr[i].text + '</p> <br>';
document.getElementById("text").innerHTML = out;
}
</script>
You can convert json data to string or better say html with $.each like below. as you tagged jQuery, here is jQuery approach:
myFunction([{
"text": "text0"
},
{
"text": "text1"
},
{
"text": "text2"
},
{
"text": "text3"
}
]);
function myFunction(arr) {
$.each(arr, function(i, v) {
$('#text').append('<div>' + v.text + '</div>');
});
}
var divs = $('.mydivs>div');
var now = 0;
divs.hide().first().show();
$("button[name=next]").click(function(e) {
divs.eq(now).hide();
now = (now + 1 < divs.length) ? now + 1 : 0;
divs.eq(now).show();
});
$("button[name=prev]").click(function(e) {
divs.eq(now).hide();
now = (now > 0) ? now - 1 : divs.length - 1;
divs.eq(now).show();
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="text" class="mydivs"></div>
<button name="prev">go to previous div</button>
<button name="next">go to next div</button>
<div id="text">
</div>
<script>
var i = 0;
let arr = [
{
"text": "text0"
},
{
"text": "text1"
},
{
"text": "text2"
},
{
"text": "text3"
}
];
setInterval(function myFunction() {
var out = "";
out = '<p>' + arr[i].text + '</p> <br>';
document.getElementById("text").innerHTML = out;
console.log(out);
if (i < arr.length - 1) {
i += 1;
} else {
i = 0;
}
}, 1000)
</script>

Calculation does not return the correct value

can anyone tell me what is the error on this javascript code?
Program: http://utilizaweb.com.br/aposentadorianovo/
function calcula(){
var fieldsContainer=document.getElementsByClassName("trabalho")[0].
getElementsByClassName("row"),
i,
jobFields=[],
len,
newAge=0,
selfGender=document.aposentadoria.sexo.value,
workedDays=0,
workedMonthies=0,
workedYears=0;
len=fieldsContainer.length;
for(i=0;len>i;i++){
jobFields[i]={
admissionDate:new Date(fieldsContainer[i].getElementsByClassName("admissao-area")[0].children[1].value),//data de admissão,
ageRule:fieldsContainer[i].getElementsByClassName("regra-area")[0].children[0].value,//regra
demissionDate:new Date(fieldsContainer[i].getElementsByClassName("demissao-area")[0].children[1].value),//data de demissão
jobBusiness:fieldsContainer[i].getElementsByClassName("empresa-area")[0].children[1].value//empresa do trabalho
};
if (jobFields[i].demissionDate > jobFields[i].admissionDate) {
jobFields[i].workedYears=jobFields[i].demissionDate.getFullYear() - jobFields[i].admissionDate.getFullYear();
jobFields[i].workedMonthies=jobFields[i].demissionDate.getMonth() - jobFields[i].admissionDate.getMonth();
jobFields[i].workedDays=jobFields[i].demissionDate.getDate() - jobFields[i].admissionDate.getDate();
alert(jobFields[i].workedYears)
} else {
alert("A data de admissão deve ser anterior à data de demissão.");
throw new Error("Conversor :: Admission date must be older than demission date.")
}
}
var fieldsRule=[];
len=jobFields.length;
for(i=0;len>i;i++){
fieldsRule[i]=jobFields[i].ageRule
}
var calculateFields=[],
higherRule=Math.max.apply(fieldsRule)
len=jobFields.length;
for(i=0;len>i;i++){
if(fieldsRule[i]===higherRule){
calculateFields[i]=i
}
}
var ageMultiplyBy,
missingYears,
jobYearsEnd;
len=calculateFields.length;
if (selfGender === "M") {
for(i=0;len>i;i++){
ageMultiplyBy=
jobFields[calculateFields[i]].ageRule==="25"?1.40:
jobFields[calculateFields[i]].ageRule==="20"?1.75:
jobFields[calculateFields[i]].ageRule==="15"?2.33:
1.75;
newAge=jobFields[calculateFields[i]].workedYears*ageMultiplyBy;
missingYears=newAge - 35
}
} else {
for(i=0;len>i;i++){
ageMultiplyBy=
jobFields[calculateFields[i]].ageRule==="25"?1.20:
jobFields[calculateFields[i]].ageRule==="20"?1.50:
jobFields[calculateFields[i]].ageRule==="15"?2:
1.20;
newAge=jobFields[calculateFields[i]].workedYears*ageMultiplyBy;
missingYears=newAge - 30
}
}
alert(missingYears)
if (missingYears < 0) {
jobYearsEnd=missingYears * -1;
}
document.getElementById("anosTrabalhados").innerHTML = workedYears+ " anos";
document.getElementById("result").innerHTML = "<img src='./img/aviso.png'>" +"Você trabalhou " +workedYears+ " anos, " +workedMonthies+ " meses e " +workedDays+ " dias"+ "<br />" +"Faltam " +jobYearsEnd+ " anos para se aposentar"
}
[IF WASN'T WELL EXPLAINED, PLEASE TELL ME. I DONT SPEAK ENGLISH SO WELL]
I need get the value of the admissionDate and of the demissionDate and subtract of each line, including those added by the user. Then, I need get the biggest values of rules are equal, and add up the time worked in each one. Then, the program takes the time worked added up and multiply by the value of each rule and subtract of 35 in case of male and of 30 in case of female. And then displays the value calculated last (minus 30 or 35).
Where the code is wrong?
Look the code by View Source
I did what I could with this one as there are several challenges and a couple of points where I am not 100 percent sure your intent. I believe you can work from here. Date stuff is hard when you work with multiple related dates. What if the boundary crosses daylight savings time etc. To assist with that I used a date library, feel free to get another or use it, I pasted it into the fiddle code; use it or get another that does that stuff rather than re-invent one. I did not use it extensively.
Here is a saved fiddle to test/try it out: (see the bottom for the good parts) https://jsfiddle.net/MarkSchultheiss/1ttmecoe/
Link the the date library: http://slingfive.com/pages/code/jsDate/jsDate.html
Explanation:
First off, your undisclosed code replicates an ID and those MUST be unique, and when you use that it is in error. I fixed that by using jQuery .clone() I also put a method to add/remove rows (all but last one) from your list) which was lacking on your page.
Code snip:
document.getElementById("anosTrabalhados").innerHTML
I will show you how to fix that (see the markup and .clone())
You have some rather complex selectors which can be simplified by the use of classes.
Code snip:
jobFields[i]={
admissionDate:new Date(fieldsContainer[i].getElementsByClassName("admissao-area")[0].children[1].value),//data de admissão,
revised:
var thisRow = fieldsContainer[i];
jobFields[i] = {
admissionDate: new Date(thisRow.getElementsByClassName("dataAdmissao")[0].value),
Checking/validation of dates right in the middle of a loop, perhaps you might check those before you loop? I left that for now as it was.
Code snip:
if (jobFields[i].demissionDate > jobFields[i].admissionDate) {
This appears to be a syntax issue here:
higherRule=Math.max.apply(fieldsRule) //old
higherRule=Math.max.apply(null, fieldsRule); //repaired
ref: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Math/max
Remove constants from code and put them in an object:
Code snip:
var calcVals = {
rules: {
male: {
sex: "M",
defaultRate: 1.75,
ageVar: 35,
ageRules: [{
age: "25",
val: 1.40
}, {
age: "20",
val: 1.75
}, {
age: "15",
val: 2.33
}]
},
female: {
sex: "M",
defaultRate: 1.50,
ageVar: 30,
ageRules: [{
age: "25",
val: 1.20
}, {
age: "20",
val: 1.50
}, {
age: "15",
val: 2.00
}]
}
}
};
then use it later: (this gets rid of the duplicate hard coded conditional making it simpler and more maintainable)
calcT = (selfGender === "M") ? calcT = calcVals.rules.male : calcT = calcVals.rules.female;
ageMultiplyBy = calcT.defaultRate;
for (i = 0; len > i; i++) {
for (var j = 0; j < calcT.ageRules.length; j++) {
if (jobFields[calculateFields[i]].ageRule === calcT.ageRules[j].age) {
ageMultiplyBy = calcT.ageRules[j].val;
break;
}
}
...more code
Assignment of a string to an array
Code snip:
fieldsRule[i]=jobFields[i].ageRule
This changes this comparison: (see the next code segment as well)
if(fieldsRule[i]===higherRule){
The fieldsRule[i] is a string and higherRule is a numeric (see the Math.max.apply above)
You set the iteration variable len based on jobFields but access the fieldsRule[i] which MIGHT be undefined. Did you mean to push to the array rather than assign to it? I ask because later on you use len=calculateFields.length; as an iterate value. Note that all the fieldsRule[i] might not be evaluated if the lengths differ on the arrays OR it might have an undefined value. (note that this is where your desired functionality becomes less clear)
len=jobFields.length;
for(i=0;len>i;i++){
if(fieldsRule[i]===higherRule){
calculateFields[i]=i
}
}
See this later down: newAge=jobFields[calculateFields[i]].workedYears*ageMultiplyBy; where calculateFields[i] might be undefined.
Revised markup:
<form class="form-calculadora" name="aposentadoria">
<fieldset class="sexo">
<legend>Sexo</legend>
<select id="sexo" class="text-area">
<option value="M">Masculino</option>
<option value="F">Feminino</option>
</select>
</fieldset>
<fieldset class="trabalho">
<div class="row p_scents">
<div class="empresa-area">
<p class="title">Empresa</p>
<input type="text" class="text-area empresa" placeholder="Empresa: ">
</div>
<div class="regra-area">
<p class="title">Regra</p>
<select class="text-area regra">
<option value="25">25 anos</option>
<option value="20">20 anos</option>
<option value="15">15 anos</option>
</select>
</div>
<div class="admissao-area">
<p class="title">Admissão</p>
<input type="date" class="text-area dataAdmissao" placeholder="Admissão: " />
</div>
<div class="demissao-area">
<p class="title">Demissão</p>
<input type="date" class="text-area dataDemissao" placeholder="Demissão: " />
</div>
<div class="anos-area">
<p class="anosTrabalhados">0 anos</p>
</div>
<button class="removerow">
Remove Row
</button>
</div>
</fieldset>
<p class="add-empresa"><i class="fa fa-user-plus"></i> Adicionar Empresa</p>
<p id="result">Você trabalhou 0 anos, 0 meses e 0 dias
<br/>Faltam undefined anos para se aposentar</p>
<input type="button" value="Calcular" class="btn" id="calcular" />
</form>
Revised code:
var calcVals = {
rules: {
male: {
sex: "M",
defaultRate: 1.75,
ageVar: 35,
ageRules: [{
age: "25",
val: 1.40
}, {
age: "20",
val: 1.75
}, {
age: "15",
val: 2.33
}]
},
female: {
sex: "M",
defaultRate: 1.50,
ageVar: 30,
ageRules: [{
age: "25",
val: 1.20
}, {
age: "20",
val: 1.50
}, {
age: "15",
val: 2.00
}]
}
}
};
function calcula() {
var rows = $('.row');
var fieldsContainer = document.getElementsByClassName("trabalho")[0].
getElementsByClassName("row"),
i,
jobFields = [],
len,
newAge = 0,
selfGender = document.aposentadoria.sexo.value,
workedDays = 0,
workedMonthies = 0,
workedYears = 0;
var fieldsRule = [];
var calculateFields = [],
len = fieldsContainer.length;
for (i = 0; i < len; i++) {
var thisRow = fieldsContainer[i];
jobFields[i] = {
admissionDate: new Date(thisRow.getElementsByClassName("dataAdmissao")[0].value),
demissionDate: new Date(thisRow.getElementsByClassName("dataDemissao")[0].value),
ageRule: thisRow.getElementsByClassName("regra")[0].value,
jobBusiness: thisRow.getElementsByClassName("empresa")[0].value
};
// console.dir(jobFields);
if (jobFields[i].demissionDate > jobFields[i].admissionDate) {
jobFields[i].workedYears = Date.DateDiff('yyyy', jobFields[i].admissionDate, jobFields[i].demissionDate);
// get months after remove years
jobFields[i].workedMonthies = Date.DateDiff('m', jobFields[i].admissionDate, jobFields[i].demissionDate) - (jobFields[i].workedYears * 12);
// console.log('days:' + Date.DateDiff('d', jobFields[i].admissionDate, jobFields[i].demissionDate) );
// get days worked after remove years/months
var adate = new Date(jobFields[i].demissionDate);
adate = new Date(adate.setFullYear(jobFields[i].demissionDate.getFullYear() - jobFields[i].workedYears));
adate = new Date(adate.setMonth((adate.getMonth()) - jobFields[i].workedMonthies));
jobFields[i].workedDays = Date.DateDiff('d', jobFields[i].admissionDate, adate); //- (new Date(jobFields[i].admissionDate) - new Date(jobFields[i].demissionDate));
// console.log('worked' + i + ":" + jobFields[i].workedYears);
} else {
alert("A data de admissão deve ser anterior à data de demissão. not less");
// throw new Error("Conversor :: Admission date must be older than demission date.")
}
}
len = jobFields.length;
for (i = 0; len > i; i++) {
fieldsRule[i] = +jobFields[i].ageRule;
}
var higherRule = Math.max.apply(null, fieldsRule);
console.log("higherRule:" + higherRule + " fLen:" + fieldsRule.length);
len = jobFields.length;
console.dir({
"jobf": jobFields
});
//console.dir(fieldsRule);
for (i = 0; i < len; i++) {
if (fieldsRule[i] === higherRule) {
calculateFields[i] = i;
}
}
console.dir({
"calcf": calculateFields
});
var ageMultiplyBy,
missingYears,
jobYearsEnd;
console.dir(fieldsRule);
len = calculateFields.length;
var calcT = {};
calcT = (selfGender === "M") ? calcT = calcVals.rules.male : calcT = calcVals.rules.female;
ageMultiplyBy = calcT.defaultRate;
for (i = 0; len > i; i++) {
for (var j = 0; j < calcT.ageRules.length; j++) {
if (jobFields[calculateFields[i]].ageRule === calcT.ageRules[j].age) {
ageMultiplyBy = calcT.ageRules[j].val;
break;
}
}
newAge = jobFields[calculateFields[i]].workedYears * ageMultiplyBy;
missingYears = newAge - calcT.ageVar;
}
console.log('mys:' + missingYears);
if (missingYears < 0) {
jobYearsEnd = (+missingYears) * -1;
}
len = jobFields.length;
for (i = 0; i < len; i++) {
workedYears = workedYears + jobFields[i].workedYears;
workedMonthies = workedMonthies + jobFields[i].workedMonthies;
workedDays = workedDays + jobFields[i].workedDays;;
}
//invalid id cannot be dupe document.getElementById("anosTrabalhados").innerHTML = workedYears + " anos";
for (var m = 0; m < rows.length; m++) {
console.log('wy:' + workedYears);
$('.row').eq(m).find('.anosTrabalhados').text(workedYears + " anos");
}
// document.getElementById("anosTrabalhados").innerHTML = workedYears + " anos";
document.getElementById("result").innerHTML = "<img src='./img/aviso.png'>" + "Você trabalhou " + workedYears + " anos, " + workedMonthies + " meses e " + workedDays + " dias" + "<br />" + "Faltam " + jobYearsEnd + " anos para se aposentar"
}
$(function() {
// set defaults for testing
makedefaults(0);
$('#calcular').on('click', function() {
calcula();
});
// add a row
$('#addScnt').on('click', function(e) {
var rowContainer = $('.trabalho');
var rows = rowContainer.find('.row');
var newRow = rows.eq(0).clone(true);
rowContainer.append(newRow);
e.preventDefault();
return false;
});
// remove any row but last one
$('.trabalho').on('click', '.removerow', function(e) {
var rowsCount = $('.trabalho').find('.row').length;
if (rowsCount > 1) {
$(this).parents('.row').remove();
}
e.preventDefault();
return false;
});
});

Repopulating objects with a click

I'm attempting to repopulate my radio buttons with the next question that is stored in my array. I'm unsure of how to remove the current question and repopulate the radio buttons with the next question.
var questionsArray = [];
//Create counters for both correct answers and current question
var correctAnswers = 0;
var currentQuestion = 0;
//Contructor Function to create questions
function Question (question, choices, answer){
this.question = question;
this.choices = choices;
this.answer = answer;
}
//Question Creations
questionsArray.push(new Question(...
To append the questions to my radio buttons I've used this code:
$('.q_question').append(questionsArray[0]['question']);
//In order to be able to check what radio is click you have to change to value of the radio buttons to the correct answer.
$('.btn1').after(questionsArray[0]['choices'][0]);
$('.btn1').val(questionsArray[0]['choices'][0]);
$('.btn2').after(questionsArray[0]['choices'][1]);
$('.btn2').val(questionsArray[0]['choices'][1]);
$('.btn3').after(questionsArray[0]['choices'][2]);
$('.btn3').val(questionsArray[0]['choices'][2]);
$('.btn4').after(questionsArray[0]['choices'][3]);
$('.btn4').val(questionsArray[0]['choices'][3]);
To check the answers I've got with:
$('#submit').on('click', function(){
currentQuestion ++;
var answer = $('input[name="1"]:checked').val(); //By creating the answer variable we are able to store which radio button value is submitted.
if(answer == questionsArray[0]['answer']){
correctAnswers ++;
$('.jumbotron').append(answer + "?<br><br> That's correct! You have " + correctAnswers + " out of 10 correct!");
} else {
$('.jumbotron').append(answer+ "? <br><br> Oh dear, that's so so wrong! You have " + correctAnswers + " out of 10 correct");
}
return false;
});
I'm totally stuck now.
Here's an example of something you could do: Fiddle
Create a function to populate the question and options. Add <span> or <label> elements and change the html in them instead of just using .after().
function populateQuestion(index) {
$('.q_question').html(questionsArray[index]['question']);
for (var i = 0; i < 4; i++) {
$('.jumbotron').html('');
$('.btn' + (i + 1)).val(questionsArray[index]['choices'][i]).prop('checked', false);
$('.label' + (i + 1)).html(questionsArray[index]['choices'][i]);
}
}
Add an event listener for the "Continue" button that runs the function with the correct (updated) index:
$('.continue').on('click', function() {
populateQuestion(++currentQuestion);
});
Just be sure to remove currentQuestion++ from your submit handler.
I had the urge to restructure the questionnaire, so here is my proposal:
var questions = [];
questions.push({
question: "What does HTML stand for?",
choices: [
"Hyper Text Markup Language",
"High Text Main Language",
"Hyper Translated Modern Language"
],
answer: 0
});
questions.push({
question: "What does CSS stand for?",
choices: [
"C-Style-Source",
"Cascading Style Source",
"Cascading Style Sheets"
],
answer: 2
});
questions.push({
question: "What does JS stand for?",
choices: [
"JavaSource",
"JavaScript",
"JavaStuff"
],
answer: 1
});
// create question elements
for (var i = 0; i < questions.length; i++) {
var question = $('<div>').addClass('question');
question.append(
$('<div>').addClass('caption').text(questions[i].question)
);
var choices = $('<ul>').addClass('choices');
for (var n = 0; n < questions[i].choices.length; n++) {
var choice = $('<li>').addClass('choice');
choice.append(
$('<input>').attr('type', 'radio').attr('name', 'question' + i).val(n).attr('id', 'label_question' + i + '_' + n)
);
choice.append(
$('<label>').attr('for', 'label_question' + i + '_' + n).text(questions[i].choices[n])
);
choices.append(choice);
}
question.append(choices);
$('.questions').append(question);
}
// attach evaluation of answers
$('#submit').click(function() {
var result = $('#result');
var correctAnswers = 0;
for (var i = 0; i < questions.length; i++) {
if ( $('input[name="question' + i + '"]:checked').val() == questions[i].answer ) {
correctAnswers += 1;
}
}
result.text('You answered ' + correctAnswers + ' of ' + questions.length + ' questions correctly.').show();
})
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div class="questions">
</div>
<button id="submit" type="button">
check answers
</button>
<div id="result" style="display: none;">
</div>

Making a quiz app, stuck on a function

I'm making a simple quiz app. But I'm stuck on ordering the functions.
Here is the code
// questions set
var qtnsSet = [
// format: [question, [comma, separated, options], index of correct ans. eg. 1]
["What is the full form of IP?", ["Internet Provider", "Internet Port", "Internet Protocol"], 2],
["Who is the founder of Microsoft?", ["Bill Gates", "Steve Jobs", "Steve Wozniak"], 0],
["Full name of IBM?", ["Internet Business Machine", "International Business Machine", "Indian Business Machine"], 1]
]
// init vars
var qtnNo = 0,
score = 0;
// define elements
var qtnContainer = $("qtn-container"),
optnsContainer = $("optns-container"),
submitBtn = $("submit-btn");
function $(id) { // Shortcut for document.getElementById
return document.getElementById(id);
}
function askQtn() { // ask question
var optns = qtnsSet[qtnNo][1], // options array
optnsHtml = "";
for (var optnNo = 0; optnNo < optns.length; optnNo++) {
optnsHtml += createOptnHtml(optnNo, optns[optnNo]);
}
qtnContainer.textContent = qtnsSet[qtnNo][0]; // question
optnsContainer.innerHTML = optnsHtml; // options
}
function createOptnHtml(optnNo, optn) { // create html elements for options
// eg. <li><input type='radio' name='optn' value='Option' id='optn-0'>
// <label for='optn-0'>Option</label></li>
return "<li><h3><input type='radio' name='optn' value='" + optn + "' id='optn-" + optnNo + "'>" +
" <label for='optn-" + optnNo + "'>" + optn + "</label></h3></li>";
}
function getGivenAns() { // get the answer given by user
var optns = document.getElementsByName("optn");
for (var optnNo = 0; optnNo < optns.length; optnNo++) {
if (optns[optnNo].checked) {
return optnNo; // index of the chosen answer
}
}
}
function checkAns() { // check if user's right or not
if (getGivenAns() == qtnsSet[qtnNo][2]) {
score += 6; // 6 points for right answer
}
}
function submitAns() {
if (qtnNo <= qtnsSet.length) {
if (getGivenAns()) {
checkAns();
qtnNo++;
askQtn();
} else {
alert("Please choose an answer.");
};
} else {
alert("Score: " + score);
};
}
window.addEventListener("load", askQtn, false);
submitBtn.addEventListener("click", submitAns, false);
I'm unable to configure the submitAns() function so that every thing works correctly.
How can I order the functions inside submitAns()?
getGivenAns()
Returns the index of the options, which can be 0 if the first option is selected which would evaluate to false here:
if (getGivenAns()) {
so just return true if an option is checked.
Also
if (qtnNo <= qtnsSet.length) {
Will be true after the last question it should just be
if (qtnNo < qtnsSet.length) {

Categories

Resources