Quiz Prototype


by Jeremy Caudle
code

I've been thinking about building an online vocabulary quiz for the students that my wife and I teach English to every once in a while. So I built my first prototype. This was an interesting exercise and I feel like I will be able build out a viable version with a couple of more hours of work.

Vocabulary Quiz 単語のクイズ

Cat photo from placekitten

View the code:

HTML and JS
<section class="code-block">
            <div class="wrapper">
                <h1>Vocabulary Quiz <span lang="ja">単語のクイズ</span></h1>
                <aside id="questionTracker" hidden><p>#<span id="currentQuestion">1</span>/<span id="questionsTotal">10</span></p></aside>
                <img id="wordPhoto" class="hideOnStart" src="https://www.jeremycaudle.com/floorshotJC.jpeg" width='360' height="240" alt="Cat photo from placekitten" />
                <h2 id="vocabWord" hidden>Word</h2>
                <div class="answers" hidden>
                    <button id="answer1" lang="ja">Answer 1</button><button id="answer2" lang="ja">Answer 2</button><button id="answer3" lang="ja">Answer 3</button><button id="answer4" lang="ja">Answer 4</button>
                </div>
                <button id="startBtn" class="startButton">Start Quiz</button>
                <button id="nextBtn" class="nextButton hideOnStart">Next Word</button>
            </div>
        </section>
        <script>
            // Store buttons in variables
            const startBtn = document.querySelector('#startBtn');
            const nextBtn = document.querySelector('#nextBtn');
            let vocabWord = document.querySelector('#vocabWord');
            let answer1 = document.querySelector('#answer1');
            let answer2 = document.querySelector('#answer2');
            let answer3 = document.querySelector('#answer3');
            let answer4 = document.querySelector('#answer4');
            const elementList = document.querySelectorAll('[hidden], .hideOnStart');
            let currentQuestion = document.querySelector('#currentQuestion');

            // Functions

            function unhideAll() {
                for (let i = 0; i < elementList.length; i++) {
                        if(elementList[i].className === "hideOnStart") {
                            console.log(i);
                            elementList[i].removeAttribute('class');
                        } else {
                            elementList[i].toggleAttribute('hidden');
                        }
                    };
                vocabWord.textContent = 'cat';
                answer1.textContent = 'ねこ';
                answer2.textContent = 'いぬ';
                answer3.textContent = 'りす';
                answer4.textContent = 'ねずみ';
                startBtn.className = "hideOnStart";
                }

            function updateQA(questionNum, word, answer1, answer2, answer3, answer4) {
                currentQuestion.textContent = questionNum;
                vocabWord.textContent = word;
                answer1.textContent = answer1;
                answer2.textContent = answer2;
                answer3.textContent = answer3;
                answer4.textContent = answer4;
            }

            // Listen for events
            startBtn.addEventListener('click', () => {
                unhideAll();
            });

            answer1.addEventListener('click', () => {
                answer1.toggleAttribute('disabled');
                answer1.setAttribute('class','correctAnswer');
                nextBtn.setAttribute('class','nextButton');
            });

            answer2.addEventListener('click', () => {
                answer2.toggleAttribute('disabled');
                answer2.setAttribute('class','wrongAnswer');
            });

            answer3.addEventListener('click', () => {
                answer3.toggleAttribute('disabled');
                answer3.setAttribute('class','wrongAnswer');
            });

            answer4.addEventListener('click', () => {
                answer4.toggleAttribute('disabled');
                answer4.setAttribute('class','wrongAnswer');
            });

            nextBtn.addEventListener('click', () => {
                updateQA(2, 'dog', 'いぬ', 'ねこ', 'りす', 'ねずみ');
                answer1.removeAttribute('class');
                answer1.toggleAttribute('disabled');
                answer2.removeAttribute('class');
                answer2.toggleAttribute('disabled');
                answer3.removeAttribute('class');
                answer3.toggleAttribute('disabled');
                answer4.removeAttribute('class');
                answer4.toggleAttribute('disabled');
                nextBtn.setAttribute('class', 'hideOnStart');
            });

        </script>
CSS
/* Variables */
            :root {
                --bg-color: #111;
                --bg-secondary: white;
                --text-color: #232323;
                --radius-main: 1rem;
            }

            /* Animations */


            /* Class for CMS */
            .code-block { 
                font-family: Verdana, Geneva, Tahoma, sans-serif;
                background: var(--bg-color, slateblue);
                z-index: 1;
                padding: 1rem;
                max-width: 60em;
                margin: 0 auto;
                transition: all .25s ease-out;
            }
            
            /* Elements */
            
             .code-block h1 { color:white; position: relative; display: block; font-size: 2rem; margin-bottom: 3rem; }
             .code-block h1 span[lang="ja"] {display: block; color: gray; position: absolute; top: 2.25rem; font-size: .66em; right: 0;}
             .code-block h2 {text-align: center; color: white;}
             img {
                display: block;
                width: 100%;
                max-width: 100%;
                height: auto;
                border-radius: var(--radius-main, 1rem);
            }
            button { 
                border-radius: var(--radius-main, 1rem);
                border: 0;
                padding: .75rem 1.5rem;
                margin: .75rem;
                width: calc(50% - 1.5rem);
                display: inline-block;
                transition: transform .125s ease-out;
                font-size: 1.5rem;
                font-weight: bold;
								background-color: gray;
            }
            button:hover {
                background: yellow;
                color: blue;
            }
            button:active {
                transform: scale(.99);
            }

            /* Custom Classes */
            
            .wrapper {
                position: relative;
            }

            .startButton {
                display: block;
                margin: 1rem auto;
                width: auto;
                max-width: 20em;
                background-color: green;
                font-size: 1.125rem;
            }
            .nextButton {
                display: block;
                margin: 1rem auto;
                width: auto;
                max-width: 20em;
                font-size: 1.125rem;
            }

            .hideOnStart {
                display: none;
            }

            .wrongAnswer {
                background: rgb(209, 72, 72);
                color: white;
                transform: rotate(-3deg) scale(.75);
            }

            .correctAnswer {
                color: rgb(110, 31, 0);
                background-color: gold;
                transform: scale(1.05);
                box-shadow: 0 0 10px 10px rgba(255, 217, 0, 0.5);
            }

            /* IDs */
            #questionTracker {
                color: white;
            }


            /* Support Queries */
            /* @supports (display: flex) {
                #buttons {
                    display: flex;
                    flex-flow: column;
                    justify-content: space-evenly;
                } 
            } */

            /* @supports (display: grid) {
            .code-block {
                display: grid;
                min-height: 100vh;
                place-items: center;
            }

            .wrapper {
                display: grid;
                max-width: 60em;
                grid-template-columns: repeat(5, 1fr);
                grid-template-rows: 5em repeat(2, 1fr);
                grid-gap: 1rem;
                background: rgba(0,0,0,0.2);
                place-items: center;
            }

            h1 {
                grid-column: 1 / 6;
            }
            } */