2022-06-30 23:13:43 +02:00
/***************************************************************************
* Copyright ( C ) 2003 - 2007 by Oliver Saal *
* osaal @ gmx . de *
* http : //www.oliver-saal.de/software/afutrainer/ *
* *
* This program is free software ; you can redistribute it and / or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation ; either version 2 of the License , or *
* ( at your option ) any later version . *
* *
* This program is distributed in the hope that it will be useful , *
* but WITHOUT ANY WARRANTY ; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the *
* GNU General Public License for more details . *
* *
* You should have received a copy of the GNU General Public License *
* along with this program ; if not , write to the *
* Free Software Foundation , Inc . , *
* 59 Temple Place - Suite 330 , Boston , MA 02111 - 1307 , USA . *
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
# include "dlgexam.h"
# include "question.h"
# include "error.h"
# include "catalog.h"
# include <qmessagebox.h>
CDlgExam : : CDlgExam ( CCatalog * pCatalog , QWidget * pParent ) : QDialog ( pParent , Qt : : WindowMaximizeButtonHint )
{
m_pCatalog = pCatalog ;
m_iCurrentQuestion = - 1 ;
m_bIsFinished = false ;
m_bTimeout = false ;
setupUi ( this ) ;
connect ( & m_timer , SIGNAL ( timeout ( ) ) , this , SLOT ( onTimer ( ) ) ) ;
}
CDlgExam : : ~ CDlgExam ( )
{
}
bool CDlgExam : : setup ( const CExam & exam )
{
m_exam = exam ;
labHeader - > setText ( exam . name ( ) ) ;
try
{
m_listQuestion = exam . createQuestionPool ( m_pCatalog - > questionPool ( ) ) ;
}
catch ( CError e )
{
QMessageBox : : critical ( this , tr ( " Fehler " ) , e . toHtml ( ) ) ;
return false ;
}
m_listAnswerMask . clear ( ) ;
while ( m_listAnswerMask . size ( ) < m_listQuestion . size ( ) )
m_listAnswerMask . append ( 0 ) ;
// Antworten bei Bedarf durchmischen
if ( m_pCatalog - > useMixedAnswers ( ) )
{
for ( int i = 0 ; i < m_listQuestion . size ( ) ; i + + )
m_listQuestion . at ( i ) - > mixAnswers ( ) ;
}
init ( ) ;
return true ;
}
void CDlgExam : : init ( )
{
// Zeitbalken & Zeitüberwachung
m_timer . setInterval ( 1000 ) ;
m_timer . start ( ) ;
m_dtStart = QDateTime : : currentDateTime ( ) ;
pgTime - > setMaximum ( m_exam . duration ( ) * 60 ) ;
// Sonstiges
pgQuestions - > setMaximum ( m_listQuestion . size ( ) ) ;
m_bIsFinished = false ;
m_bTimeout = false ;
labMaxWrong - > setText ( QString ( " %1 " ) . arg ( m_exam . maxErrorPoints ( ) ) ) ;
// Navigation
spinBox - > setRange ( 1 , m_listQuestion . size ( ) ) ;
spinBox - > setValue ( 1 ) ;
m_iCurrentQuestion = 1 ;
// Alles updaten
updateNavi ( ) ;
showQuestion ( ) ;
updateProgressTimer ( ) ;
updateProgressQuestion ( ) ;
}
void CDlgExam : : onTimer ( )
{
updateProgressTimer ( ) ;
}
void CDlgExam : : updateNavi ( )
{
pbFirst - > setEnabled ( spinBox - > value ( ) > spinBox - > minimum ( ) ) ;
pbPrev - > setEnabled ( spinBox - > value ( ) > spinBox - > minimum ( ) ) ;
pbNext - > setEnabled ( spinBox - > value ( ) < spinBox - > maximum ( ) ) ;
pbLast - > setEnabled ( spinBox - > value ( ) < spinBox - > maximum ( ) ) ;
}
unsigned CDlgExam : : answeredQuestionCount ( )
{
unsigned u = 0 ;
for ( int i = 0 ; i < m_listAnswerMask . size ( ) ; i + + )
{
if ( m_listAnswerMask . at ( i ) ! = 0 ) u + + ;
}
return u ;
}
void CDlgExam : : updateProgressQuestion ( )
{
unsigned uAnswered = answeredQuestionCount ( ) ;
labProgressQuestions - > setText ( tr ( " %1 von %2 " ) . arg ( uAnswered ) . arg ( m_listAnswerMask . size ( ) ) ) ;
pgQuestions - > setValue ( uAnswered ) ;
}
void CDlgExam : : updateProgressTimer ( )
{
QDateTime dt = QDateTime : : currentDateTime ( ) ;
unsigned uSecs = m_dtStart . secsTo ( dt ) ;
labProgessTime - > setText ( tr ( " Abgelaufene Zeit: %1:%2 min von %3:00 min " )
. arg ( uSecs / 60 )
. arg ( uSecs % 60 , 2 , 10 , QChar ( ' 0 ' ) )
. arg ( m_exam . duration ( ) ) ) ;
pgTime - > setValue ( uSecs ) ;
if ( uSecs > m_exam . duration ( ) * 60 )
{
m_bTimeout = true ;
m_timer . stop ( ) ;
QMessageBox : : information ( this , tr ( " Information " ) , tr ( " Die Zeit ist abgelaufen. \n Die Prüfung wird deswegen beendet. " ) ) ;
on_pbFinish_clicked ( ) ;
}
}
void CDlgExam : : on_pbFirst_clicked ( )
{
spinBox - > setValue ( 1 ) ;
}
void CDlgExam : : on_pbPrev_clicked ( )
{
int iNew = spinBox - > value ( ) - 1 ;
if ( iNew < 1 ) iNew = 1 ;
spinBox - > setValue ( iNew ) ;
}
void CDlgExam : : on_pbNext_clicked ( )
{
int iNew = spinBox - > value ( ) + 1 ;
if ( iNew > m_listQuestion . size ( ) ) iNew = m_listQuestion . size ( ) ;
spinBox - > setValue ( iNew ) ;
}
void CDlgExam : : on_pbLast_clicked ( )
{
spinBox - > setValue ( m_listQuestion . size ( ) ) ;
}
void CDlgExam : : on_spinBox_valueChanged ( int i )
{
Q_UNUSED ( i ) ;
onQuestionChanged ( ) ;
}
void CDlgExam : : saveCurrentAnswer ( )
{
unsigned uAnswerMask = 0 ;
if ( m_iCurrentQuestion > = 0 )
{ // Antwort zur aktuellen Frage abspeichern
if ( rbA - > isChecked ( ) ) uAnswerMask | = 1 ;
if ( rbB - > isChecked ( ) ) uAnswerMask | = 2 ;
if ( rbC - > isChecked ( ) ) uAnswerMask | = 4 ;
if ( rbD - > isChecked ( ) ) uAnswerMask | = 8 ;
m_listAnswerMask [ m_iCurrentQuestion ] = uAnswerMask ;
}
}
void CDlgExam : : onQuestionChanged ( )
{
saveCurrentAnswer ( ) ;
updateNavi ( ) ;
updateProgressQuestion ( ) ;
showQuestion ( ) ; // neue Frage anzeigen
}
void CDlgExam : : showQuestion ( )
{
CQuestion * q = 0 ;
unsigned uAnswerMask ;
QString str ;
m_iCurrentQuestion = spinBox - > value ( ) - 1 ;
q = m_listQuestion . at ( m_iCurrentQuestion ) ;
uAnswerMask = m_listAnswerMask . at ( m_iCurrentQuestion ) ;
str = q - > learnText ( m_pCatalog , m_bIsFinished , false ) ;
if ( m_bIsFinished )
{
str + = " <hr><p><b> " ;
if ( ! q - > isCorrectAnswer ( uAnswerMask ) )
str + = " <font color='red'> " ;
else
str + = " <font color='green'> " ;
str + = q - > correctionText ( uAnswerMask ) + " </font></p> " ;
}
textBrowser - > setHtml ( str ) ;
rbA - > setChecked ( uAnswerMask & 1 ) ;
rbB - > setChecked ( uAnswerMask & 2 ) ;
rbC - > setChecked ( uAnswerMask & 4 ) ;
rbD - > setChecked ( uAnswerMask & 8 ) ;
rbNoIdea - > setChecked ( uAnswerMask = = 0 ) ;
}
void CDlgExam : : on_pbFinish_clicked ( )
{
unsigned uCorrect = 0 , uWrong = 0 , uAnsweredCount = answeredQuestionCount ( ) , uErrorPoints = 0 ;
bool bSaveStat = true , bPassed = false ;
QDateTime dt = QDateTime : : currentDateTime ( ) ;
unsigned uSecs = m_dtStart . secsTo ( dt ) ;
saveCurrentAnswer ( ) ;
if ( uAnsweredCount < ( unsigned ) m_listQuestion . size ( ) & & ! m_bTimeout )
{
if ( QMessageBox : : question ( this ,
tr ( " Sicherheitsabfrage " ) ,
tr ( " Sie haben noch nicht alle Fragen beantwortet. \n Wirklich abgeben? " ) ,
QMessageBox : : Yes | QMessageBox : : No , QMessageBox : : No ) = = QMessageBox : : No ) return ;
}
m_timer . stop ( ) ;
pbFinish - > setEnabled ( false ) ;
rbA - > setEnabled ( false ) ;
rbB - > setEnabled ( false ) ;
rbC - > setEnabled ( false ) ;
rbD - > setEnabled ( false ) ;
rbNoIdea - > setEnabled ( false ) ;
pbCancel - > setText ( tr ( " Beenden " ) ) ;
m_bIsFinished = true ;
showQuestion ( ) ;
for ( int i = 0 ; i < m_listQuestion . size ( ) ; i + + )
{
CQuestion * q = m_listQuestion . at ( i ) ;
unsigned uAnswerMask = m_listAnswerMask . at ( i ) ;
if ( q - > isCorrectAnswer ( uAnswerMask ) )
uCorrect + + ;
else
{
uWrong + + ;
uErrorPoints + = q - > errorPoints ( ) ;
}
}
labCorrect - > setText ( QString ( " %1 " ) . arg ( uCorrect ) ) ;
labWrong - > setText ( QString ( " %1 " ) . arg ( uWrong ) ) ;
if ( uAnsweredCount < ( unsigned ) m_listQuestion . size ( ) / 2 )
{
bPassed = false ;
bSaveStat = false ;
labResult - > setText ( tr ( " Ohne Wertung \n (Nicht bestanden) " ) ) ;
QMessageBox : : information ( this , tr ( " Information " ) , tr ( " Sie haben weniger als die Hälfte aller Fragen beantwortet. \n Diese Prüfung wird deswegen nicht gewertet. " ) ) ;
}
else if ( uErrorPoints > m_exam . maxErrorPoints ( ) )
{
bPassed = false ;
labResult - > setText ( tr ( " <font color='red'>Nicht bestanden</font> " ) ) ;
QMessageBox : : information ( this , tr ( " Ergebnis " ) , tr ( " Sie haben die Prüfung leider nicht bestanden. " ) ) ;
}
else
{
bPassed = true ;
labResult - > setText ( tr ( " <font color='green'>Bestanden</font> " ) ) ;
QMessageBox : : information ( this , tr ( " Ergebnis " ) , tr ( " <b>Herzlichen Glückwunsch!</b><p>Sie haben die Prüfung bestanden! " ) ) ;
}
if ( bSaveStat )
{ // Prüfungsstatistik speichern
CExamStat es ( m_exam ) ;
es . setSecs ( uSecs ) ;
es . setQuestions ( m_listQuestion , m_listAnswerMask ) ;
es . setResult ( uCorrect , uWrong , uErrorPoints , bPassed ) ;
m_pCatalog - > appendExamStat ( es ) ;
m_pCatalog - > saveStatistic ( this ) ;
}
}