1
- // define properties for Quiz constructor
2
- function Quiz ( questions ) {
3
- this . score = 0 ;
4
- this . questions = questions ;
5
- this . currentQuestionIndex = 0 ;
6
- this . color = "" ;
7
- }
1
+ /**
2
+ * Quiz class
3
+ *
4
+ * @constructor
5
+ * @param {Object } questions - questions of a quiz
6
+ */
7
+
8
+ class Quiz {
9
+ constructor ( questions ) {
10
+ this . score = 0 ;
11
+ this . questions = questions ;
12
+ this . currentQuestionIndex = 0 ;
13
+ this . color = "" ;
14
+ }
8
15
9
- // add getCurrentQuestion() function to Quiz's prototype
10
- Quiz . prototype . getCurrentQuestion = function ( ) {
11
- return this . questions [ this . currentQuestionIndex ] ;
12
- }
16
+ getCurrentQuestion ( ) {
17
+ return this . questions [ this . currentQuestionIndex ] ;
18
+ }
13
19
14
- // add guess() function to Quiz's prototype
15
- // if user guesses correctly increase their score
16
- Quiz . prototype . guess = function ( answer ) {
17
- if ( this . getCurrentQuestion ( ) . isCorrectAnswer ( answer ) ) {
18
- this . score ++ ;
19
- this . color = "green " ;
20
- } else {
21
- this . color = "red" ;
20
+ guess ( answer ) {
21
+ if ( this . getCurrentQuestion ( ) . isCorrectAnswer ( answer ) ) {
22
+ this . score ++ ;
23
+ this . color = "green" ;
24
+ } else {
25
+ this . color = "red " ;
26
+ }
27
+ this . currentQuestionIndex ++ ;
22
28
}
23
- this . currentQuestionIndex ++ ; // go to next question
24
- }
25
29
26
- // add hasEnded() function to Quiz's prototype
27
- // ends quiz after last question
28
- Quiz . prototype . hasEnded = function ( ) {
29
- return this . currentQuestionIndex === this . questions . length ;
30
+ hasEnded ( ) {
31
+ return this . currentQuestionIndex === this . questions . length ;
32
+ }
30
33
}
31
34
32
- // define properties for Question constructor
33
- function Question ( text , choices , answer ) {
34
- this . text = text ;
35
- this . choices = choices ;
36
- this . answer = answer ;
37
- }
35
+ /**
36
+ * Question class
37
+ *
38
+ * @constructor
39
+ * @param {String } text - question
40
+ * @param {Array } choices - choices of a question
41
+ * @param {String } answer - answer of a question
42
+ */
43
+
44
+ class Question {
45
+ constructor ( text , choices , answer ) {
46
+ this . text = text ;
47
+ this . choices = choices ;
48
+ this . answer = answer ;
49
+ }
38
50
39
- // add isCorrectAnswer() function to Question's prototype
40
- Question . prototype . isCorrectAnswer = function ( choice ) {
41
- return this . answer === choice ;
51
+ isCorrectAnswer ( choice ) {
52
+ return this . answer === choice ;
53
+ }
42
54
}
43
55
56
+
57
+ /**
58
+ * Progress Bar class
59
+ *
60
+ * @constructor
61
+ * @param {Object } element - DOM element of progress bar
62
+ * @param {Number } initialValue - value of progress bar
63
+ */
64
+
65
+ class ProgressBar {
66
+ constructor ( element , initialValue = 0 ) {
67
+ this . fillElement = element . querySelector ( "#progressBarFill" ) ;
68
+ this . setValue ( initialValue ) ;
69
+ }
70
+
71
+ setValue ( newValue ) {
72
+ if ( newValue < 0 ) {
73
+ newValue = 0 ;
74
+ }
75
+ if ( newValue > 100 ) {
76
+ newValue = 100 ;
77
+ }
78
+ this . value = newValue ;
79
+ this . update ( ) ;
80
+ }
81
+
82
+ update ( ) {
83
+ const percentage = this . value + '%' ;
84
+ this . fillElement . style . width = percentage ;
85
+ }
86
+ }
87
+
88
+
44
89
// populate the quiz on the page
45
90
function populate ( ) {
46
91
if ( quiz . hasEnded ( ) ) {
92
+ // show user's score
47
93
showScore ( ) ;
48
94
} else {
49
95
// show the question
50
96
document . getElementById ( "question" ) . innerHTML = quiz . getCurrentQuestion ( ) . text ;
51
97
52
98
// show the choices
53
- var choices = quiz . getCurrentQuestion ( ) . choices ;
54
- for ( var index = 0 ; index < choices . length ; index ++ ) {
99
+ const choices = quiz . getCurrentQuestion ( ) . choices ;
100
+ for ( let index = 0 ; index < choices . length ; index ++ ) {
55
101
document . getElementById ( "choice" + index ) . innerHTML = choices [ index ] ;
56
102
guessHandler ( "btn" + index , choices [ index ] ) ;
57
103
}
58
104
59
- // show question number
105
+ // show progress
60
106
showProgress ( ) ;
107
+ const progressBar = new ProgressBar ( document . querySelector ( "#progressBar" ) ) ;
108
+ progressBar . setValue ( ( ( quiz . currentQuestionIndex + 1 ) / quiz . questions . length ) * 100 ) ;
61
109
}
62
110
} ;
63
111
64
112
65
-
66
- // once user clicks their guess, excute the guess() function
113
+ // handle user's guesses on click
67
114
function guessHandler ( id , guess ) {
68
- var button = document . getElementById ( id ) ;
115
+ const button = document . getElementById ( id ) ;
69
116
70
117
button . onclick = function ( ) {
71
118
quiz . guess ( guess ) ;
72
119
73
120
// button color changes to green if correct, red if incorrect
74
- // setTimeout delays loading of next question
121
+ // delay loading of next question
75
122
button . style . backgroundColor = quiz . color ;
76
123
setTimeout ( function ( ) {
77
124
button . style . backgroundColor = null ;
@@ -81,15 +128,14 @@ function guessHandler(id, guess) {
81
128
} ;
82
129
83
130
84
- // shows question number user is on
85
131
function showProgress ( ) {
86
- var currentQuestionNum = quiz . currentQuestionIndex + 1 ;
132
+ const currentQuestionNum = quiz . currentQuestionIndex + 1 ;
87
133
document . getElementById ( "progress" ) . innerHTML = "Question " + currentQuestionNum + " of " + quiz . questions . length ;
88
134
} ;
89
135
90
- // shows the user's score at end of quiz
136
+
91
137
function showScore ( ) {
92
- var quizOverHTML = "<h1 class='main-header'>Results</h1>" ;
138
+ let quizOverHTML = "<h1 class='main-header'>Results</h1>" ;
93
139
quizOverHTML += "<h2 id='score'> Your score: " + quiz . score + "/" + quiz . questions . length + "</h2>" ;
94
140
quizOverHTML += "<div class='try-again'><a class='try-again-btn' href='index.html'>Try Again</a></div>"
95
141
document . getElementById ( "quiz" ) . innerHTML = quizOverHTML ;
@@ -111,24 +157,33 @@ function shuffle(array) {
111
157
} ;
112
158
113
159
160
+
114
161
// fetch the quiz data from JSON API
115
- var quiz ;
116
- fetch ( "https://opentdb.com/api.php?amount=10&category=18&difficulty=easy&type=multiple" )
117
- . then ( response => response . json ( ) )
118
- . then ( data => {
119
- var results = data . results ;
120
- var questions = [ ] ;
121
- results . forEach ( function ( result ) {
122
- var answers = result . incorrect_answers . concat ( result . correct_answer ) ;
123
- shuffle ( answers ) ;
124
- var temp = new Question ( result . question , answers , result . correct_answer ) ;
125
- questions . push ( temp ) ;
126
- } )
127
-
128
- // create the quiz
129
- quiz = new Quiz ( questions ) ;
130
-
131
- // display the quiz
132
- populate ( ) ;
133
- } )
134
- . catch ( error => console . log ( error ) ) // catch any errors
162
+ async function fetchData ( ) {
163
+ let response = await fetch ( "https://opentdb.com/api.php?amount=10&category=18&difficulty=easy&type=multiple" ) ;
164
+ if ( ! response . ok ) {
165
+ throw new Error ( `HTTP error status: ${ response . status } ` ) ;
166
+ } else {
167
+ return await response . json ( ) ;
168
+ }
169
+ }
170
+
171
+ let quiz ;
172
+ fetchData ( ) . then ( ( data ) => {
173
+ const results = data . results ;
174
+ const questions = [ ] ;
175
+ results . forEach ( function ( result ) {
176
+ const answers = result . incorrect_answers . concat ( result . correct_answer ) ;
177
+ shuffle ( answers ) ;
178
+ const question = new Question ( result . question , answers , result . correct_answer ) ;
179
+ questions . push ( question ) ;
180
+ } ) ;
181
+
182
+ // create the quiz
183
+ quiz = new Quiz ( questions ) ;
184
+
185
+ // display the quiz
186
+ populate ( ) ;
187
+
188
+ } ) . catch ( err => console . log ( err ) ) ;
189
+
0 commit comments