145 lines
3.1 KiB
PHP
145 lines
3.1 KiB
PHP
<?php
|
|
namespace TestProject;
|
|
|
|
/*
|
|
* Question class
|
|
*/
|
|
class Question extends Item {
|
|
private const tb_str = 'question';
|
|
private const resultTb_str = 'question_result';
|
|
|
|
private $text_str;
|
|
private $answers_arr;
|
|
|
|
/**
|
|
* Load question
|
|
*
|
|
* @param int $id_int ID of question to load
|
|
*/
|
|
public function __construct( int $id_int ){
|
|
$db = DB::getDB();
|
|
|
|
$rows_arr = $db->select( self::tb_str, array(), array( 'id' => $id_int ) );
|
|
|
|
if ( empty( $rows_arr ) ){
|
|
throw new \RuntimeException( 'Invalid question ID' );
|
|
}
|
|
|
|
$this->id_int = $rows_arr[0]['id'];
|
|
$this->text_str = $rows_arr[0]['text'];
|
|
|
|
$answerID_arr = Answer::getList( $this->id_int );
|
|
$this->answers_arr = array();
|
|
|
|
foreach( $answerID_arr as $answerID_int ){
|
|
$this->answers_arr[] = new Answer( $answerID_int );
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Get a list of question IDs for a quiz
|
|
*
|
|
* @param int $quizID_int ID of quiz to load questions for
|
|
*
|
|
* @return int[] Array of question IDs
|
|
*/
|
|
public static function getList( int $quizID_int ){
|
|
$db = DB::getDB();
|
|
|
|
$rows_arr = $db->select( self::tb_str, array( 'id' ), array( 'quiz' => $quizID_int ) );
|
|
|
|
$id_arr = array();
|
|
foreach( $rows_arr as $row_arr ){
|
|
$id_arr[] = $row_arr['id'];
|
|
}
|
|
|
|
return $id_arr;
|
|
}
|
|
|
|
/**
|
|
* Get question text
|
|
*
|
|
* @return string Question text
|
|
*/
|
|
public function getText(){
|
|
return $this->text_str;
|
|
}
|
|
|
|
/**
|
|
* Get Answers for question
|
|
*
|
|
* @return TestProject\Answer[] Array of answer objects
|
|
*/
|
|
public function getAnswers(){
|
|
return $this->answers_arr;
|
|
}
|
|
|
|
/**
|
|
* Calculate user's score and save to DB
|
|
*
|
|
* @param int $userID_int ID of user
|
|
* @param int[] $ans_arr Array of answer IDs
|
|
*/
|
|
public function saveAnswer( int $userID_int, $ans_arr ){
|
|
$maxScore_int = 0;
|
|
$score_int = 0;
|
|
|
|
foreach( $this->answers_arr as $answer ){
|
|
if ( $answer->isCorrect() ){
|
|
$maxScore_int++;
|
|
|
|
// User selected correct answer
|
|
if ( in_array( $answer->getID(), $ans_arr ) ){
|
|
$score_int++;
|
|
}
|
|
}
|
|
}
|
|
|
|
// Apply penalty if more answers selected than correct options
|
|
$diff_int = count( $ans_arr ) - $maxScore_int;
|
|
if ( $diff_int > 0 ){
|
|
$score_int -= $diff_int;
|
|
}
|
|
// Do not allow a negative score
|
|
if ( $score_int < 0 ){
|
|
$score_int = 0;
|
|
}
|
|
|
|
$db = DB::getDB();
|
|
|
|
// Check for existing answer
|
|
$row_arr = $db->select( self::resultTb_str, array( 'id' ), array( 'user' => $userID_int, 'question' => $this->id_int ) );
|
|
if ( empty( $row_arr ) ){
|
|
$db->insert(
|
|
self::resultTb_str,
|
|
array(
|
|
'user' => $userID_int,
|
|
'question' => $this->id_int,
|
|
'score' => $score_int
|
|
)
|
|
);
|
|
} else {
|
|
$db->update( self::resultTb_str, array( 'score' => $score_int ), array( 'id' => $row_arr[0]['id'] ) );
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Get a user's score for the question
|
|
*
|
|
* @param int $userID_int ID of user
|
|
*
|
|
* @return int Score
|
|
*/
|
|
public function getScore( int $userID_int ){
|
|
$db = DB::getDB();
|
|
|
|
$row_arr = $db->select( self::resultTb_str, array( 'score' ), array( 'user' => $userID_int, 'question' => $this->id_int ) );
|
|
if ( empty( $row_arr ) ){
|
|
// Question not answered
|
|
return 0;
|
|
}
|
|
|
|
return $row_arr[0]['score'];
|
|
}
|
|
}
|