今日筆者將接續昨天的內容,為這個小遊戲增加更多的功能,使得它更加的完整。
此次所新增的內容包含:
那麼就讓我們直接開始今日的內容吧!
首先先於主程式中建立一個變數 question_id,用於紀錄現在所進行到的題目編號,並於顯示結果時一併列出一個「下一題」按鈕,當按下時,題號便會增加,表示已經進行到了下一個題目:
<script setup>
const question_id = ref(1);
function nextQuestion() {
question_id.value++;
showResult.value = false;
}
</script>
<template>
<h1>Calculator Game</h1>
<p>Question {{ question_id }}: </p>
<Question @answer="(ans) => correct_ans = ans"/>
<!-- 為了畫面簡潔而暫時省略掉此部份的程式碼 -->
<div id="result" v-if="showResult">
<p v-if="isCorrect">Your answer is correct!</p>
<p v-else>You've answered wrong, the correct result is {{ correct_ans }}</p>
<button @click="nextQuestion">Next</button>
</div>
<p v-else>Click on the button to check your answer</p>
</template>
不過現在的程式有一個問題,那便是現在僅僅只有題號會變動,但題目仍然不會改變,為了解決這個問題,我們可以在 Question 子元件中先利用 props 將題號傳進去,並於其中使用 watcher 來根據變數的數值改變來呼叫更新題目用的函式:
<script setup>
import { ref, watch } from 'vue'
var props = defineProps({ id: Number })
const num1 = ref(Math.floor(Math.random() * 100))
const num2 = ref(Math.floor(Math.random() * 100))
var op_id = Math.floor(Math.random() * 10 % 4)
const op = ['+', '-', '*', '/']
function generate() {
num1.value = Math.floor(Math.random() * 100);
num2.value = Math.floor(Math.random() * 100);
op_id = Math.floor(Math.random() * 10 % 4);
emit('answer', calculate());
}
function calculate() {
switch (op_id) {
case 0:
return num1.value + num2.value
case 1:
return num1.value - num2.value
case 2:
return num1.value * num2.value
default:
return Math.floor(num1.value / num2.value)
}
}
const emit = defineEmits(['answer']);
emit('answer', calculate());
watch(() => props.id, () => { generate() })
</script>
不過,有以下兩點需要特別注意:
watch()
來觀察 id 的值時,需要以 () => props.id
的方式表示,否則會出現錯誤 (網頁參考)emit()
之外,我們也要在新題目生成時再次使用 emit()
將新答案傳給父函式,否則父函式所擁有的答案數值不會有所改變