I'm working on a project that's a quiz like form. You get multiple questions and answers and you can click on any answer to create a personal result. I've already asked a question about this project because I didn't really know how to loop correctly and I fixed that problem, tho it's still not going great. Right now I'm creating a previous button and it kinda works, but not great.
My code:
<div >
<div id="question"></div>
<div id="answer"></div>
<button onclick="NextQuestion()" id="nextbtn">Next</button>
<button onclick="PrevQuestion()" id="prevbtn">Previous</button>
<div id="finalLink"></div>
</div>
JS
class QuizPart{
constructor(questionDescription, chosenAnswer, prefix){
this.questionDescription = questionDescription;
this.chosenAnswer = chosenAnswer;
this.prefix = prefix;
}
}
class ChosenAnswer{
constructor(id, name){
this.id = id;
this.name = name;
}
}
let Quiz = [
new QuizPart('Whats your size?', [
new ChosenAnswer('6595', '41'),
new ChosenAnswer('6598', '42'),
new ChosenAnswer('6601', '43'),
], 'bd_shoe_size_ids='),
new QuizPart('What color would you like?', [
new ChosenAnswer('6053', 'Red'),
new ChosenAnswer('6044', 'Blue'),
new ChosenAnswer('6056', 'Yellow'),
new ChosenAnswer('6048', 'Green'),
], 'color_ids='),
new QuizPart('What brand would you like?', [
new ChosenAnswer('5805', 'Adidas'),
new ChosenAnswer('5866', 'Nike'),
new ChosenAnswer('5875', 'Puma'),
], 'manufacturer_ids='),
]
// console.log(Quiz);
let url = [];
let questionNumber = 0;
let button = document.getElementById('answer');
let questionName = document.getElementById('question');
let nextbtn = document.getElementById('nextbtn');
let prevbtn = document.getElementById('prevbtn')
let resultbtn = document.getElementById('FLink');
function NextQuestion() {
let oldAnswerButton = document.querySelectorAll('.filter_anwser');
// Deletes old question when the next question is clicked
for (let answerButton of oldAnswerButton) {
answerButton.style.display = 'none';
}
let question = Quiz[questionNumber];
// Displays answers of the questions
for (let y = 0; y < question.chosenAnswer.length; y ) {
let item = question.chosenAnswer[y];
// Display answer buttons
let btn = document.createElement('button');
btn.value = item.id;
btn.className = "filter_anwser";
btn.textContent = item.name;
button.appendChild(btn);
}
// Check if your at the last question so the next button will stop being displayed.
if (Quiz.length - 1 === questionNumber) {
nextbtn.style.display = 'none';
resultbtn.style.display = 'grid';
}
// Displays Question
questionName.textContent = question.questionDescription;
questionName.id = "questionID";
// adds 1 to question to see a different question
questionNumber ;
}
function PrevQuestion(){
questionNumber--;
let oldAnswerButton = document.querySelectorAll('.filter_anwser');
// Deletes old question when the next question is clicked
for (let answerButton of oldAnswerButton) {
answerButton.style.display = 'none';
}
let question = Quiz[questionNumber];
// Displays answers of the questions
for (let y = 0; y < question.chosenAnswer.length; y ) {
let item = question.chosenAnswer[y];
// Display answer buttons
let btn = document.createElement('button');
btn.value = item.id;
btn.className = "filter_anwser";
btn.textContent = item.name;
button.appendChild(btn);
}
//Check if your at the last question so the next button will stop being displayed.
if (Quiz.length === questionNumber) {
prevbtn.style.display = 'none';
resultbtn.style.display = 'grid';
}
// Displays Question
questionName.textContent = question.questionDescription;
questionName.id = "questionID";
}
Now as you can see I create a new element when I press the previous button (also seen in the next image):
I'm trying not to create an entire new set of elements, but going back to the previous set. I tried doing it with a simple if statement like:
let i = 0;
if (i < question.chosenAnswer[y]){
y--;
}
This is just something I tried but didn 't work. Can anybody help me do this?
Save the information:
function getLink(url) {
let tmp = [];
for (let i = 0; i < url.length; i ) {
// Check if question is from the same quiz part and adds a , between chosen answers and add the right prefix at the beginning
if (url[i].length > 0){
tmp.push("" Quiz[i].prefix url[i].join(","))
}
}
/// If answers are from different quiz parts add a & between answers.
console.log(url, questionNumber);
return "" tmp.join("&");
};
button.addEventListener("click", function (e) {
const tgt = e.target;
// clear the url array if there's nothing clicked
if (url.length < questionNumber) {
url.push([]);
}
let quizUrl = url[questionNumber - 1];
// Check if a button is clicked. Changes color and adds value to the url array.
if (quizUrl.indexOf(tgt.value) === -1) {
quizUrl.push(tgt.value);
e.target.style.backgroundColor = "orange";
// Check if a button is clicked again. If clicked again changes color back and deletes value in the url array.
} else {
quizUrl.splice(quizUrl.indexOf(tgt.value), 1);
e.target.style.backgroundColor = "white";
}
console.log(getLink(url));
})
CodePudding user response:
You need to use element.remove() instead of element.style.display ="none"
Why? element.remove() - will remove the DOM element altogether. element.style.display ="none" - Will only hide it for the end user. But it will still be there on the DOM tree.
Js Fiddle for solution below:
Fixed a few thing in you code as well. Added comment lines in the places where I fixed things
- Next button now disappears on the last question
- Previous button now disappears on the first question
class QuizPart{
constructor(questionDescription, chosenAnswer, prefix){
this.questionDescription = questionDescription;
this.chosenAnswer = chosenAnswer;
this.prefix = prefix;
}
}
class ChosenAnswer{
constructor(id, name){
this.id = id;
this.name = name;
}
}
let Quiz = [
new QuizPart('Whats your size?', [
new ChosenAnswer('6595', '41'),
new ChosenAnswer('6598', '42'),
new ChosenAnswer('6601', '43'),
], 'bd_shoe_size_ids='),
new QuizPart('What color would you like?', [
new ChosenAnswer('6053', 'Red'),
new ChosenAnswer('6044', 'Blue'),
new ChosenAnswer('6056', 'Yellow'),
new ChosenAnswer('6048', 'Green'),
], 'color_ids='),
new QuizPart('What brand would you like?', [
new ChosenAnswer('5805', 'Adidas'),
new ChosenAnswer('5866', 'Nike'),
new ChosenAnswer('5875', 'Puma'),
], 'manufacturer_ids='),
]
console.log(Quiz);
let url = [];
let questionNumber = 0;
let button = document.getElementById('answer');
let questionName = document.getElementById('question');
let nextbtn = document.getElementById('nextbtn');
let prevbtn = document.getElementById('prevbtn')
let resultbtn = document.getElementById('finalLink');
function NextQuestion() {
let oldAnswerButton = document.querySelectorAll('.filter_anwser');
// Deletes old question when the next question is clicked
for (let answerButton of oldAnswerButton) {
**//CORRECTION DONE HERE**
answerButton.remove();
}
let question = Quiz[questionNumber];
// Displays answers of the questions
for (let y = 0; y < question.chosenAnswer.length; y ) {
let item = question.chosenAnswer[y];
// Display answer buttons
let btn = document.createElement('button');
btn.value = item.id;
btn.className = "filter_anwser";
btn.textContent = item.name;
button.appendChild(btn);
}
//FIX ADDED HERE FOR NEXT BUTTON AND PREVIOUS BUTTON CHANGES
// Check if your at the last question so the next button will stop being displayed.
if (questionNumber > 0 ) {
prevbtn.style.display = 'grid'
}
if (Quiz.length - 1 <= questionNumber) {
nextbtn.style.display = 'none';
resultbtn.style.display = 'grid';
}else{
nextbtn.style.display = 'grid';
}
// Displays Question
questionName.textContent = question.questionDescription;
questionName.id = "questionID";
// adds 1 to question to see a different question
questionNumber ;
}
function PrevQuestion(){
questionNumber--;
let oldAnswerButton = document.querySelectorAll('.filter_anwser');
// Deletes old question when the next question is clicked
for (let answerButton of oldAnswerButton) {
**//CORRECTION DONE HERE**
answerButton.remove();
}
let question = Quiz[questionNumber];
// Displays answers of the questions
for (let y = 0; y < question.chosenAnswer.length; y ) {
let item = question.chosenAnswer[y];
// Display answer buttons
let btn = document.createElement('button');
btn.value = item.id;
btn.className = "filter_anwser";
btn.textContent = item.name;
button.appendChild(btn);
}
//FIX ADDED HERE FOR NEXT BUTTON AND PREVIOUS BUTTON CHANGES
//Check if your at the last question so the prev button will stop being displayed.
if (questionNumber < Quiz.length - 1) {
nextbtn.style.display = 'grid';
}
if (questionNumber <= 0) {
prevbtn.style.display = 'none';
}else{
prevbtn.style.display = 'grid';
}
// Displays Question
questionName.textContent = question.questionDescription;
questionName.id = "questionID";
}
<div >
<div id="question"></div>
<div id="answer"></div>
<button onclick="NextQuestion()" id="nextbtn">Next</button>
<button onclick="PrevQuestion()" id="prevbtn">Previous</button>
<div id="finalLink"></div>
</div>
CodePudding user response:
You have to retrieve the previously created buttons to show(*) them.
For instance you can retrieve them using their id
which is put in their value
attribute:
for (let y = 0; y < question.chosenAnswer.length; y ) {
let item = question.chosenAnswer[y];
// retrieve the button by it's value="id" attribute
let btn = document.querySelector('button[value="' item.id '"]');
btn.style.display = 'grid';
}
(*) Note that when you say "Deletes questions" you actually are just hiding them, not deleting (i.e. removing from document).