Version19.199

This commit is contained in:
acanas 2020-04-26 11:56:52 +02:00
parent 963919bc82
commit eb48ee477c
5 changed files with 351 additions and 3 deletions

View File

@ -544,10 +544,11 @@ enscript -2 --landscape --color --file-align=2 --highlight --line-numbers -o - *
En OpenSWAD:
ps2pdf source.ps destination.pdf
*/
#define Log_PLATFORM_VERSION "SWAD 19.198 (2020-04-26)"
#define Log_PLATFORM_VERSION "SWAD 19.199 (2020-04-26)"
#define CSS_FILE "swad19.193.1.css"
#define JS_FILE "swad19.193.1.js"
/*
Version 19.199: Apr 26, 2020 Move set of questions up and down. (299344 lines)
Version 19.198: Apr 26, 2020 Remove set of questions. (299054 lines)
3 changes necessary in database:
ALTER TABLE exa_questions DROP INDEX ExaCod;

View File

@ -172,8 +172,15 @@ static void ExaSet_PutParamSetCod (long SetCod);
static void Exa_RemAnswersOfAQuestion (long ExaCod,unsigned QstInd);
static unsigned ExaSet_GetSetIndFromSetCod (long ExaCod,long SetCod);
static long ExaSet_GetSetCodFromSetInd (long ExaCod,unsigned SetInd);
static unsigned ExaSet_GetMaxSetIndexInExam (long ExaCod);
static unsigned Exa_GetMaxQuestionIndexInExam (long ExaCod);
static unsigned ExaSet_GetPrevSetIndexInExam (long ExaCod,unsigned SetInd);
static unsigned ExaSet_GetNextSetIndexInExam (long ExaCod,unsigned SetInd);
static void ExaSet_ListExamSets (struct Exa_Exams *Exams,
struct Exa_Exam *Exam,
struct ExaSet_Set *Set);
@ -201,6 +208,8 @@ static void Exa_AllocateListSelectedQuestions (struct Exa_Exams *Exams);
static void Exa_FreeListsSelectedQuestions (struct Exa_Exams *Exams);
static unsigned Exa_CountNumQuestionsInList (const struct Exa_Exams *Exams);
static void ExaSet_ExchangeSets (long ExaCod,
unsigned SetIndTop,unsigned SetIndBottom);
static void Exa_ExchangeQuestions (long ExaCod,
unsigned QstIndTop,unsigned QstIndBottom);
@ -2235,6 +2244,62 @@ static void Exa_RemAnswersOfAQuestion (long ExaCod,unsigned QstInd)
ExaCod,QstInd);
}
/*****************************************************************************/
/****************** Get set index given exam and set code ********************/
/*****************************************************************************/
static unsigned ExaSet_GetSetIndFromSetCod (long ExaCod,long SetCod)
{
MYSQL_RES *mysql_res;
MYSQL_ROW row;
long SetInd;
/***** Get set index from set code *****/
if (!DB_QuerySELECT (&mysql_res,"can not get set index",
"SELECT SetInd FROM exa_sets"
" WHERE SetCod=%u"
" AND ExaCod=%ld", // Extra check
SetCod,ExaCod))
Lay_ShowErrorAndExit ("Error: wrong set code.");
/***** Get set code (row[0]) *****/
row = mysql_fetch_row (mysql_res);
SetInd = Str_ConvertStrToUnsigned (row[0]);
/***** Free structure that stores the query result *****/
DB_FreeMySQLResult (&mysql_res);
return SetInd;
}
/*****************************************************************************/
/****************** Get set code given exam and set index ********************/
/*****************************************************************************/
static long ExaSet_GetSetCodFromSetInd (long ExaCod,unsigned SetInd)
{
MYSQL_RES *mysql_res;
MYSQL_ROW row;
long SetCod;
/***** Get set code from set index *****/
if (!DB_QuerySELECT (&mysql_res,"can not get set code",
"SELECT SetCod FROM exa_sets"
" WHERE ExaCod=%ld AND SetInd=%u",
ExaCod,SetInd))
Lay_ShowErrorAndExit ("Error: wrong set index.");
/***** Get set code (row[0]) *****/
row = mysql_fetch_row (mysql_res);
if ((SetCod = Str_ConvertStrCodToLongCod (row[0])) <= 0)
Lay_ShowErrorAndExit ("Error: wrong set code.");
/***** Free structure that stores the query result *****/
DB_FreeMySQLResult (&mysql_res);
return SetCod;
}
/*****************************************************************************/
/************ Get question code given exam and index of question *************/
/*****************************************************************************/
@ -2245,7 +2310,7 @@ long Exa_GetQstCodFromQstInd (long ExaCod,unsigned QstInd)
MYSQL_ROW row;
long QstCod;
/***** Get question code of thw question to be moved up *****/
/***** Get question code of the question to be moved up *****/
if (!DB_QuerySELECT (&mysql_res,"can not get question code",
"SELECT QstCod FROM exa_questions"
" WHERE ExaCod=%ld AND QstInd=%u",
@ -2321,6 +2386,74 @@ static unsigned Exa_GetMaxQuestionIndexInExam (long ExaCod)
return QstInd;
}
/*****************************************************************************/
/*********** Get previous set index to a given set index in an exam **********/
/*****************************************************************************/
// Input set index can be 1, 2, 3... n-1
// Return set index will be 1, 2, 3... n if previous set exists, or 0 if no previous set
static unsigned ExaSet_GetPrevSetIndexInExam (long ExaCod,unsigned SetInd)
{
MYSQL_RES *mysql_res;
MYSQL_ROW row;
unsigned PrevSetInd = 0;
/***** Get previous set index in an exam from database *****/
// Although indexes are always continuous...
// ...this implementation works even with non continuous indexes
if (!DB_QuerySELECT (&mysql_res,"can not get previous set index",
"SELECT MAX(SetInd) FROM exa_sets"
" WHERE ExaCod=%ld AND SetInd<%u",
ExaCod,SetInd))
Lay_ShowErrorAndExit ("Error: previous set index not found.");
/***** Get previous set index (row[0]) *****/
row = mysql_fetch_row (mysql_res);
if (row)
if (row[0])
if (sscanf (row[0],"%u",&PrevSetInd) != 1)
Lay_ShowErrorAndExit ("Error when getting previous set index.");
/***** Free structure that stores the query result *****/
DB_FreeMySQLResult (&mysql_res);
return PrevSetInd;
}
/*****************************************************************************/
/*************** Get next set index to a given index in an exam **************/
/*****************************************************************************/
// Input set index can be 0, 1, 2, 3... n-1
// Return set index will be 1, 2, 3... n if next set exists, or 0 if no next set
static unsigned ExaSet_GetNextSetIndexInExam (long ExaCod,unsigned SetInd)
{
MYSQL_RES *mysql_res;
MYSQL_ROW row;
unsigned NextSetInd = ExaEvt_AFTER_LAST_QUESTION; // End of sets has been reached
/***** Get next set index in an exam from database *****/
// Although indexes are always continuous...
// ...this implementation works even with non continuous indexes
if (!DB_QuerySELECT (&mysql_res,"can not get next set index",
"SELECT MIN(SetInd) FROM exa_sets"
" WHERE ExaCod=%ld AND SetInd>%u",
ExaCod,SetInd))
Lay_ShowErrorAndExit ("Error: next set index not found.");
/***** Get next set index (row[0]) *****/
row = mysql_fetch_row (mysql_res);
if (row)
if (row[0])
if (sscanf (row[0],"%u",&NextSetInd) != 1)
Lay_ShowErrorAndExit ("Error when getting next set index.");
/***** Free structure that stores the query result *****/
DB_FreeMySQLResult (&mysql_res);
return NextSetInd;
}
/*****************************************************************************/
/*********** Get previous question index to a given index in an exam **********/
/*****************************************************************************/
@ -3154,6 +3287,61 @@ void ExaSet_RemoveSet (void)
void ExaSet_MoveUpSet (void)
{
extern const char *Txt_The_set_of_questions_has_been_moved_up;
extern const char *Txt_Movement_not_allowed;
struct Exa_Exams Exams;
struct Exa_Exam Exam;
struct ExaSet_Set Set;
unsigned SetIndTop;
unsigned SetIndBottom;
/***** Reset exams context *****/
Exa_ResetExams (&Exams);
/***** Reset exam and set *****/
Exa_ResetExam (&Exam);
ExaSet_ResetSet (&Set);
/***** Get parameters *****/
Exa_GetParams (&Exams);
if (Exams.ExaCod <= 0)
Lay_WrongExamExit ();
Set.ExaCod = Exam.ExaCod = Exams.ExaCod;
Set.SetCod = ExaSet_GetParamSetCod ();
if (Set.SetCod <= 0)
Lay_WrongSetExit ();
/***** Get exam data from database *****/
Exa_GetDataOfExamByCod (&Exam);
if (!Exa_CheckIfEditable (&Exam))
Lay_NoPermissionExit ();
/***** Get set data from database *****/
ExaSet_GetDataOfSetByCod (&Set);
/***** Get set index *****/
SetIndBottom = ExaSet_GetSetIndFromSetCod (Exam.ExaCod,Set.SetCod);
/***** Move up set *****/
if (SetIndBottom > 1)
{
/* Indexes of sets to be exchanged */
SetIndTop = ExaSet_GetPrevSetIndexInExam (Exam.ExaCod,SetIndBottom);
if (!SetIndTop)
Lay_ShowErrorAndExit ("Wrong index of set.");
/* Exchange sets */
ExaSet_ExchangeSets (Exam.ExaCod,SetIndTop,SetIndBottom);
/* Success alert */
Ale_ShowAlert (Ale_SUCCESS,Txt_The_set_of_questions_has_been_moved_up);
}
else
Ale_ShowAlert (Ale_WARNING,Txt_Movement_not_allowed);
/***** Show current exam and its sets *****/
Exa_PutFormsOneExam (&Exams,&Exam,&Set,
false); // It's not a new exam
}
/*****************************************************************************/
@ -3162,6 +3350,71 @@ void ExaSet_MoveUpSet (void)
void ExaSet_MoveDownSet (void)
{
extern const char *Txt_The_set_of_questions_has_been_moved_down;
extern const char *Txt_Movement_not_allowed;
extern const char *Txt_This_exam_has_no_sets_of_questions;
struct Exa_Exams Exams;
struct Exa_Exam Exam;
struct ExaSet_Set Set;
unsigned SetIndTop;
unsigned SetIndBottom;
unsigned MaxSetInd; // 0 if no sets
/***** Reset exams context *****/
Exa_ResetExams (&Exams);
/***** Reset exam and set *****/
Exa_ResetExam (&Exam);
ExaSet_ResetSet (&Set);
/***** Get parameters *****/
Exa_GetParams (&Exams);
if (Exams.ExaCod <= 0)
Lay_WrongExamExit ();
Set.ExaCod = Exam.ExaCod = Exams.ExaCod;
Set.SetCod = ExaSet_GetParamSetCod ();
if (Set.SetCod <= 0)
Lay_WrongSetExit ();
/***** Get exam data from database *****/
Exa_GetDataOfExamByCod (&Exam);
if (!Exa_CheckIfEditable (&Exam))
Lay_NoPermissionExit ();
/***** Get set data from database *****/
ExaSet_GetDataOfSetByCod (&Set);
/***** Get set index *****/
SetIndTop = ExaSet_GetSetIndFromSetCod (Exam.ExaCod,Set.SetCod);
/***** Get maximum set index *****/
MaxSetInd = ExaSet_GetMaxSetIndexInExam (Exam.ExaCod);
/***** Move down set *****/
if (MaxSetInd)
{
if (SetIndTop < MaxSetInd)
{
/* Indexes of sets to be exchanged */
SetIndBottom = ExaSet_GetNextSetIndexInExam (Exam.ExaCod,SetIndTop);
if (!SetIndBottom)
Lay_ShowErrorAndExit ("Wrong index of set.");
/* Exchange sets */
ExaSet_ExchangeSets (Exam.ExaCod,SetIndTop,SetIndBottom);
/* Success alert */
Ale_ShowAlert (Ale_SUCCESS,Txt_The_set_of_questions_has_been_moved_down);
}
else
Ale_ShowAlert (Ale_WARNING,Txt_Movement_not_allowed);
}
else
Ale_ShowAlert (Ale_WARNING,Txt_This_exam_has_no_sets_of_questions);
/***** Show current exam and its sets *****/
Exa_PutFormsOneExam (&Exams,&Exam,&Set,
false); // It's not a new exam
}
/*****************************************************************************/
@ -3414,6 +3667,57 @@ void Exa_MoveDownQst (void)
false); // Do not put form to start new event
}
/*****************************************************************************/
/*********** Exchange the order of two consecutive sets in an exam ***********/
/*****************************************************************************/
static void ExaSet_ExchangeSets (long ExaCod,
unsigned SetIndTop,unsigned SetIndBottom)
{
long SetCodTop;
long SetCodBottom;
/***** Lock table to make the move atomic *****/
DB_Query ("can not lock tables to exchange sets of questions",
"LOCK TABLES exa_sets WRITE");
Gbl.DB.LockedTables = true;
/***** Get set codes of the sets to be moved *****/
SetCodTop = ExaSet_GetSetCodFromSetInd (ExaCod,SetIndTop);
SetCodBottom = ExaSet_GetSetCodFromSetInd (ExaCod,SetIndBottom);
/***** Exchange indexes of sets *****/
/*
Example:
SetIndTop = 1; SetCodTop = 218
SetIndBottom = 2; SetCodBottom = 220
+--------+--------+ +--------+--------+ +--------+--------+
| SetInd | SetCod | | SetInd | SetCod | | SetInd | SetCod |
+--------+--------+ +--------+--------+ +--------+--------+
| 1 | 218 | -----> | 2 | 218 | = | 1 | 220 |
| 2 | 220 | | 1 | 220 | | 2 | 218 |
| 3 | 232 | | 3 | 232 | | 3 | 232 |
+--------+--------+ +--------+--------+ +--------+--------+
*/
DB_QueryUPDATE ("can not exchange indexes of sets",
"UPDATE exa_sets SET SetInd=%u"
" WHERE ExaCod=%ld AND SetCod=%ld",
SetIndBottom,
ExaCod,SetCodTop);
DB_QueryUPDATE ("can not exchange indexes of sets",
"UPDATE exa_sets SET SetInd=%u"
" WHERE ExaCod=%ld AND SetCod=%ld",
SetIndTop,
ExaCod,SetCodBottom);
/***** Unlock table *****/
Gbl.DB.LockedTables = false; // Set to false before the following unlock...
// ...to not retry the unlock if error in unlocking
DB_Query ("can not unlock tables after exchanging sets of questions",
"UNLOCK TABLES");
}
/*****************************************************************************/
/********* Exchange the order of two consecutive questions in an exam *********/
/*****************************************************************************/

View File

@ -165,6 +165,7 @@ void Exa_ListQuestionsToSelect (void);
void Exa_PutParamQstInd (unsigned QstInd);
unsigned Exa_GetParamQstInd (void);
long Exa_GetQstCodFromQstInd (long ExaCod,unsigned QstInd);
unsigned Exa_GetPrevQuestionIndexInExam (long ExaCod,unsigned QstInd);
unsigned Exa_GetNextQuestionIndexInExam (long ExaCod,unsigned QstInd);

View File

@ -1780,7 +1780,7 @@ long Gam_GetQstCodFromQstInd (long GamCod,unsigned QstInd)
MYSQL_ROW row;
long QstCod;
/***** Get question code of thw question to be moved up *****/
/***** Get question code of the question to be moved up *****/
if (!DB_QuerySELECT (&mysql_res,"can not get question code",
"SELECT QstCod FROM gam_questions"
" WHERE GamCod=%ld AND QstInd=%u",

View File

@ -49741,6 +49741,48 @@ const char *Txt_The_set_of_questions_has_been_modified =
"O conjunto de perguntas foi modificado.";
#endif
const char *Txt_The_set_of_questions_has_been_moved_down =
#if L==1 // ca
"El conjunt de preguntes ha estat mogut cap avall.";
#elif L==2 // de
"Der Satz von Fragen wurde nach unten bewegt.";
#elif L==3 // en
"The set of questions has been moved down.";
#elif L==4 // es
"El conjunto de preguntas se ha movido hacia abajo.";
#elif L==5 // fr
"L'ensemble de questions a &eacute;t&eacute; d&eacute;plac&eacute; vers le bas.";
#elif L==6 // gn
"El conjunto de preguntas se ha movido hacia abajo."; // Okoteve traducción
#elif L==7 // it
"Il set di domande &egrave; stato abbattuto.";
#elif L==8 // pl
"Zestaw pyta&nacute; zosta&lstrok;o przeniesione.";
#elif L==9 // pt
"O conjunto de perguntas foi movido para baixo.";
#endif
const char *Txt_The_set_of_questions_has_been_moved_up =
#if L==1 // ca
"El conjunt de preguntes ha estat mogut cap amunt.";
#elif L==2 // de
"Der Satz von Fragen wurde nach oben verschoben.";
#elif L==3 // en
"The set of questions has been moved up.";
#elif L==4 // es
"El conjunto de preguntas se ha movido hacia arriba.";
#elif L==5 // fr
"L'ensemble de questions a &eacute;t&eacute; d&eacute;plac&eacute; vers le haut.";
#elif L==6 // gn
"El conjunto de preguntas se ha movido hacia arriba."; // Okoteve traducción
#elif L==7 // it
"Il set di domande &egrave; stato spostato.";
#elif L==8 // pl
"Zestaw pyta&nacute; zosta&lstrok;o poruszone.";
#elif L==9 // pt
"O conjunto de perguntas foi movido para cima.";
#endif
const char *Txt_The_size_of_the_file_exceeds_the_maximum_allowed_X = // Warning: it is very important to include %s in the following sentences
#if L==1 // ca
"La mida del fitxer"