296 lines
9.9 KiB
C#
296 lines
9.9 KiB
C#
|
|
using System.Collections.Generic;
|
|
using System.Linq;
|
|
using System.Text.RegularExpressions;
|
|
using UnityEngine;
|
|
using UnityEngine.UI;
|
|
|
|
public class QuizController : MonoBehaviour {
|
|
|
|
public GameObject[] answers;
|
|
|
|
public Text counterText;
|
|
|
|
public Text scoreText;
|
|
|
|
public Text questionText;
|
|
|
|
public Button btnNextQuestion;
|
|
|
|
public GameObject haloPrefab;
|
|
|
|
private int scoreValue = 0;
|
|
|
|
private int questionIdx = 0;
|
|
|
|
private const int numberOfAnswers = 4;
|
|
|
|
private const int scoreCorrectAnswer = 10;
|
|
|
|
private const int scoreIncorrectAnswer = -15;
|
|
|
|
private const int scoreTimedOut = 0;
|
|
|
|
private const int counterInitialValue = 10;
|
|
|
|
private const int counterDisplayAnswersInitialValue = 3;
|
|
|
|
private float counterValue;
|
|
|
|
private float counterDisplayAnswersValue;
|
|
|
|
private bool counterDisplayAnswersStarted = false;
|
|
|
|
// List of selected answers
|
|
private List<int> selectedAnswers;
|
|
|
|
// References to answers halo prefabs
|
|
private List<GameObject> answersHaloPrefabs;
|
|
|
|
// List of questions and correct answers
|
|
List<Question> questions = new List<Question>() {
|
|
new Question("1. Neki od ovih prozora imaju 2-3 puta manje toplotnih gubitaka za razliku od drugih, koji su to?", new int[] {1, 4}),
|
|
new Question("2. Na jedan od načina možete uštedjeti i do 10 litara vode po osobi dnevno, uz koji predmet?", new int[] {3, 4}),
|
|
new Question("3. Korištenjem jednog od sljedećih predmeta, u svjetlost se pretvara svega 5% uložene energije, dok se ostatak pretvara u toplotu, koji je to?", new int[] {1}),
|
|
new Question("4. Neki od navedenih predmeta uključeni u utičnicu, iako nisu u u funkciji, i dalje se znatno griju i troše električnu energiju.", new int[] {3}),
|
|
new Question("5. Šta možemo ugraditi na radijatore da nam pomogne smanjiti troškove grijanja za 7-15%?", new int[] {1, 3}),
|
|
new Question("6. Ako je vani temperatura 33oC, koja je optimalna temperatura u kući? ", new int[] {4}),
|
|
new Question("7. Kakvim načinom pranja posuđa, i uz koji uređaj od navedenih, trošimo 60% manje električne energije i do 85% manje vode?", new int[] {2, 3}),
|
|
new Question("8. Koji uređaj u «stand by» načinu rada troši i do 24% energije u odnosu na potrošnju energije kada je upaljen?", new int[] {4}),
|
|
new Question("9. Jednom godišnje stručna osoba treba provjeriti prohodnost čega? Loša prohodnost doprinosi većoj potrošnji energije za grijanje.", new int[] {1}),
|
|
new Question("10. Uvijek odaberite program s najnižom temperaturom vode koji još uvijek obezbjeđuje dobar kvalitet pranja, za šta od navedenog? ", new int[] {1, 4}),
|
|
};
|
|
|
|
/// <summary>
|
|
/// Use this for initialization
|
|
/// </summary>
|
|
void Start () {
|
|
selectedAnswers = new List<int>();
|
|
answersHaloPrefabs = new List<GameObject>();
|
|
counterValue = counterInitialValue;
|
|
UpdateScene();
|
|
UpdateCounter();
|
|
UpdateScore();
|
|
btnNextQuestion.GetComponent<Button>().onClick.AddListener(LoadNextQuestion);
|
|
InstantiateHaloPrefabs();
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
/// // Update is called once per frame
|
|
/// </summary>
|
|
void Update()
|
|
{
|
|
if (counterValue > 0)
|
|
{
|
|
if (!counterDisplayAnswersStarted)
|
|
{
|
|
counterValue -= Time.deltaTime;
|
|
UpdateCounter();
|
|
}
|
|
}
|
|
else
|
|
LoadNextQuestion();
|
|
if (counterDisplayAnswersValue > 0 && counterDisplayAnswersStarted)
|
|
counterDisplayAnswersValue -= Time.deltaTime;
|
|
else
|
|
{
|
|
UpdateScene();
|
|
counterDisplayAnswersStarted = false;
|
|
}
|
|
|
|
// Select answers event handler
|
|
if (Input.GetMouseButtonDown(0))
|
|
{
|
|
Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
|
|
RaycastHit hit;
|
|
|
|
if (Physics.Raycast(ray, out hit, 100))
|
|
{
|
|
if (counterDisplayAnswersStarted)
|
|
return;
|
|
Debug.Log(hit.transform.gameObject.name);
|
|
// answerArrayIdx: [1, 40]
|
|
int answerArrayIdx = GetAnswerIdx(hit.transform.gameObject.name);
|
|
// answerIdx: [1, 4]
|
|
int answerIdx = answerArrayIdx - numberOfAnswers * questionIdx;
|
|
// Answer not selected - select it
|
|
if (!selectedAnswers.Contains(answerIdx))
|
|
{
|
|
SetGlowEffect(answerArrayIdx, true);
|
|
selectedAnswers.Add(answerIdx);
|
|
}
|
|
// Answer selected - unselect it
|
|
else
|
|
{
|
|
SetGlowEffect(answerArrayIdx, false);
|
|
selectedAnswers.Remove(answerIdx);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Next question btn click event handler
|
|
/// </summary>
|
|
void LoadNextQuestion()
|
|
{
|
|
if (counterDisplayAnswersStarted)
|
|
return;
|
|
scoreValue += GetScore();
|
|
UpdateScore();
|
|
selectedAnswers.Clear();
|
|
ClearCurrentSceneGlowEffect();
|
|
counterDisplayAnswersValue = counterDisplayAnswersInitialValue;
|
|
counterDisplayAnswersStarted = true;
|
|
counterValue = counterInitialValue;
|
|
ShowAnswers();
|
|
questionIdx = (questionIdx + 1) % questions.Count;
|
|
}
|
|
|
|
/// <summary>
|
|
/// Updates score value - called from Update() method
|
|
/// </summary>
|
|
private void UpdateScore()
|
|
{
|
|
scoreText.text = scoreValue.ToString();
|
|
}
|
|
|
|
/// <summary>
|
|
/// Updates counter value - called from Update() method
|
|
/// </summary>
|
|
private void UpdateCounter()
|
|
{
|
|
counterText.text = counterValue.ToString("f0");
|
|
}
|
|
|
|
/// <summary>
|
|
/// Shows correct answers
|
|
/// </summary>
|
|
private void ShowAnswers()
|
|
{
|
|
for(int i = numberOfAnswers * questionIdx; i < numberOfAnswers * (questionIdx + 1); i++)
|
|
{
|
|
MarkAnswer(questions[questionIdx].getCorrectAnswers().Contains(i - questionIdx * numberOfAnswers + 1), i);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Updates scene with new question and related answers
|
|
/// </summary>
|
|
private void UpdateScene()
|
|
{
|
|
RemoveMarks();
|
|
// Set new question
|
|
questionText.text = questions[questionIdx].getQuestionText();
|
|
// Set answers for selected question
|
|
for(int i = 0; i < answers.Length; i++)
|
|
{
|
|
if (i >= numberOfAnswers * questionIdx && i < numberOfAnswers * (questionIdx + 1))
|
|
{
|
|
answers[i].SetActive(true);
|
|
}
|
|
else
|
|
answers[i].SetActive(false);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Hides correct/incorrect images for currently shown answers
|
|
/// </summary>
|
|
private void RemoveMarks()
|
|
{
|
|
for(int i = 0; i < numberOfAnswers; i++) {
|
|
int answerIdx = questionIdx * numberOfAnswers + i;
|
|
answers[answerIdx].GetComponent<ObjectController>().imageCorrect.enabled = false;
|
|
answers[answerIdx].GetComponent<ObjectController>().imageIncorrect.enabled = false;
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Sets visibility of correct/incorrect overlay images
|
|
/// </summary>
|
|
/// <param name="isCorrect"></param>
|
|
/// <param name="idx"></param>
|
|
private void MarkAnswer(bool isCorrect, int idx)
|
|
{
|
|
answers[idx].GetComponent<ObjectController>().imageCorrect.enabled = isCorrect;
|
|
answers[idx].GetComponent<ObjectController>().imageIncorrect.enabled = !isCorrect;
|
|
}
|
|
|
|
/// <summary>
|
|
/// Adds Halo prefabs to all answers
|
|
/// </summary>
|
|
private void InstantiateHaloPrefabs()
|
|
{
|
|
for(int i = 0; i < answers.Count(); i++)
|
|
{
|
|
GameObject answerPrefab = Instantiate(haloPrefab) as GameObject;
|
|
answerPrefab.SetActive(false);
|
|
answerPrefab.transform.SetParent(answers[i].transform, false);
|
|
answersHaloPrefabs.Add(answerPrefab);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Clears glow from all currently shown answers
|
|
/// </summary>
|
|
private void ClearCurrentSceneGlowEffect()
|
|
{
|
|
for (int i = 0; i < numberOfAnswers; i++)
|
|
{
|
|
int prefabIdx = questionIdx * numberOfAnswers + i;
|
|
answersHaloPrefabs[prefabIdx].SetActive(false);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Clears/Adds glow from a specific answer GameObject
|
|
/// </summary>
|
|
/// <param name="prefabIdx"></param>
|
|
private void SetGlowEffect(int prefabIdx, bool showGlowEffect)
|
|
{
|
|
answersHaloPrefabs[prefabIdx - 1].SetActive(showGlowEffect);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Returns answer index (X) from answer's name (AnswerX)
|
|
/// </summary>
|
|
/// <param name="gameObjName">GameObject's name</param>
|
|
/// <returns></returns>
|
|
private int GetAnswerIdx(string gameObjName)
|
|
{
|
|
string resultString = Regex.Match(gameObjName, @"\d+").Value;
|
|
return System.Int32.Parse(resultString);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Returns score for a particular question
|
|
/// </summary>
|
|
/// <returns></returns>
|
|
private int GetScore() {
|
|
// Didn't try
|
|
if (selectedAnswers.Count == 0)
|
|
return scoreTimedOut;
|
|
// Correct answer
|
|
if(IsAnswerCorrect(selectedAnswers, questions[questionIdx].getCorrectAnswers()))
|
|
return scoreCorrectAnswer;
|
|
else
|
|
return scoreIncorrectAnswer;
|
|
|
|
}
|
|
|
|
/// <summary>
|
|
/// Compares selected answers with correct answers
|
|
/// </summary>
|
|
/// <param name="selectedAnswers">List of selected answers</param>
|
|
/// <param name="correctAnswers">Array of correct answers</param>
|
|
/// <returns></returns>
|
|
private bool IsAnswerCorrect(List<int> selectedAnswers, int[] correctAnswers)
|
|
{
|
|
HashSet<int> correctAnswersSet = new HashSet<int>(new List<int>(correctAnswers));
|
|
return correctAnswersSet.SetEquals(selectedAnswers);
|
|
}
|
|
|
|
}
|