patternphpMinor
Recording user response times for a quiz
Viewed 0 times
userresponsequizforrecordingtimes
Problem
I am working on a simple quiz-type game in which the user basically is asked a series of questions and needs to provide an answer.
I'm trying to find a solid/robust way of recording how long it takes for the user to answer each question. This is a web-based game so I am using JavaScript and PHP. I am very inexperienced, so I suspect this is not the best way to do it; at least I hope it's not because it seems very weak. I would appreciate any suggestions as to how to go about making a more full-proof solution. It's not critical that the time be accurate to the millisecond I'm just looking to build something that will be consistent and accurate to within a second or two.
The reason I'm doing it like this rather than just recording the time in the browser is because, as I understand it, the data could theoretically be altered by the user. This is also why I don't send that correct and answers to the browser until the user provides an answer.
Here is my current approach:
```
diff($endDTO);
$timeTaken = $timeDiff->format('%s');
return $timeTaken;
}
date_default_timezone_set("UTC");
if($_SERVER['REQUEST_METHOD'] === 'POST')
{
if(
isset($_POST['user_answer']) &&
isset($_SESSION['app_index'])
)
{
$index = $_SESSION['app_index'];///current question in the game
$len = count($_SESSION['words']);///number of questions in the game
$userAns = $_POST['user_answer'];
$rightAns = $_SESSION['right_answers'];
if(isset($_SESSION['app_start']))////if this is the first question
{
$responseTime = getTimeTaken($_SESSION['app_start']);
unset($_SESSION['app_start']);
$_SESSION['question_start'] = new DateTime('NOW');
}
else if(isset($_SESSION['question_start']))///not the first question
{
$responseTime = getTimeTaken($_SESSION['question_start']);
$_SESSION['question_start'] = new DateTime('NOW');
}
I'm trying to find a solid/robust way of recording how long it takes for the user to answer each question. This is a web-based game so I am using JavaScript and PHP. I am very inexperienced, so I suspect this is not the best way to do it; at least I hope it's not because it seems very weak. I would appreciate any suggestions as to how to go about making a more full-proof solution. It's not critical that the time be accurate to the millisecond I'm just looking to build something that will be consistent and accurate to within a second or two.
The reason I'm doing it like this rather than just recording the time in the browser is because, as I understand it, the data could theoretically be altered by the user. This is also why I don't send that correct and answers to the browser until the user provides an answer.
Here is my current approach:
```
diff($endDTO);
$timeTaken = $timeDiff->format('%s');
return $timeTaken;
}
date_default_timezone_set("UTC");
if($_SERVER['REQUEST_METHOD'] === 'POST')
{
if(
isset($_POST['user_answer']) &&
isset($_SESSION['app_index'])
)
{
$index = $_SESSION['app_index'];///current question in the game
$len = count($_SESSION['words']);///number of questions in the game
$userAns = $_POST['user_answer'];
$rightAns = $_SESSION['right_answers'];
if(isset($_SESSION['app_start']))////if this is the first question
{
$responseTime = getTimeTaken($_SESSION['app_start']);
unset($_SESSION['app_start']);
$_SESSION['question_start'] = new DateTime('NOW');
}
else if(isset($_SESSION['question_start']))///not the first question
{
$responseTime = getTimeTaken($_SESSION['question_start']);
$_SESSION['question_start'] = new DateTime('NOW');
}
Solution
Just some simple stuff,
a common.php file for common code used by both files. DRY don't repeat yourself.
Writing a script like you have is fine, the points i have noted will help you if you come back to maintain it in a year or so, and have forgotten how it works.
The bulk of programming jobs are about maintaining a code base, not creating new stuff, so if you can learn how to make maintenance easier, it will be beneficial for you in the long run. (I wish i had learnt this stuff much earlier on)
I have added inline comments explaining the changes i made
a common.php file for common code used by both files. DRY don't repeat yourself.
Writing a script like you have is fine, the points i have noted will help you if you come back to maintain it in a year or so, and have forgotten how it works.
The bulk of programming jobs are about maintaining a code base, not creating new stuff, so if you can learn how to make maintenance easier, it will be beneficial for you in the long run. (I wish i had learnt this stuff much earlier on)
I have added inline comments explaining the changes i made
diff($endDTO);
$timeTaken = $timeDiff->format('%s');
return $timeTaken;
}
function is_first_question() {
return isset($_SESSION['app_start']);
}
function is_question_started() {
return isset($_SESSION['question_start'];
}
//
function mark_user_answer($user_answer, $correct_answer) {
return ($user_answer == $correct_answer) ? 1 : 0;
}
function move_to_next_question() {
$_SESSION['app_index']++;
}
function start_question_timer() {
$_SESSION['question_start'] = new DateTime('NOW');}
}
?>Code Snippets
<?php
/* common.php */
require 'classes/Database.php';
session_start();
date_default_timezone_set("UTC");
?>
<?php
/* get_game_data.php
*
* user clicks button to start game
* and triggers ajax request sent to this file
*/
require 'common.php';
// moved into common.php
// session_start();
if($_SERVER['REQUEST_METHOD'] === 'GET')
{
if(isset($_GET['gamesettings'])){///check certian user defined game options are set
// moved into common.php
// require 'classes/Database.php';
// moved into common.php
// date_default_timezone_set("UTC");
$_SESSION['app_start'] = new DateTime('NOW');////store time at which game/first question starts
$_SESSION['app_index'] = 0;
// warning if $_GET['app'] not set this will get a warning notice, we can never trust GET/POST data
// if($_GET['app'] === 'aural') {
if(isset($_GET['app']) && $_GET['app'] === 'aural') {
$db = new Database();
$gameData = getGameData($db);///just an example
//etc...
//query database for game data, i.e. the questions,
// i prefer to do my internal logic before i output data. this way if something fails i can handle it prior to responding to the user
$_SESSION['right_answers'] = $gameData['answers'];///store the right answers to varify against user answers later
echo json_encode($gameData['questions']);//then send back to browser
}
}
}
?>
<?php
/* post_game_data.php
*
* user answers question in a textbox etc.
* then clicks a submit button which posts the answer to
* this file via ajax again
*/
require 'common.php';
// moved into common.php
//session_start();
// moved into common.php
// date_default_timezone_set("UTC");
if($_SERVER['REQUEST_METHOD'] === 'POST')
{
// what you have done is not bad, i just prefer to have all user supplied data handled in one place, POST/GET
// so i know that everything beyond here has been sanitized
// if(
// isset($_POST['user_answer']) &&
// isset($_SESSION['app_index'])
// )
$userAns = isset($_POST['user_answer']) ? $_POST['user_answer'] : null;
// good variable names can also help reduce the need for comments
// which of these two following variable names are easier to understand
// $index = $_SESSION['app_index'];///current question in the game
$current_question_index = isset($_SESSION['app_index']) ? $_SESSION['app_index'] : null;
if($userAns != null && $current_question_index != null)
{
// same here with variable naming
// if you are going to maintain these scripts over time, you need to make it easier to remember what is going on
// $len = count($_SESSION['words']);///number of questions in the game
$num_questions = count($_SESSION['words']);
// handled above, no need to repeat
// $userAns = $_POST['user_answer'];
$rightAns = $_SESSION[Context
StackExchange Code Review Q#39593, answer score: 2
Revisions (0)
No revisions yet.