Merge branch '1.11.x' of github.com:chamilo/chamilo-lms into 1.11.x

pull/3235/head
Angel Fernando Quiroz Campos 6 years ago
commit 9c3bb71ddd
  1. 13
      main/auth/courses.php
  2. 6
      main/auth/inscription.php
  3. 82
      main/exercise/exercise.class.php
  4. 8
      main/exercise/exercise_result.php
  5. 12
      main/exercise/exercise_submit.php
  6. 1
      main/exercise/result.php
  7. 32
      main/inc/ajax/exercise.ajax.php
  8. 3
      main/inc/lib/CoursesAndSessionsCatalog.class.php
  9. 17
      main/inc/lib/course.lib.php
  10. 2392
      main/inc/lib/extra_field.lib.php
  11. 17
      main/inc/lib/formvalidator/FormValidator.class.php
  12. 5
      main/inc/lib/legal.lib.php
  13. 2
      main/inc/lib/pear/HTML/QuickForm/text.php
  14. 17
      main/inc/lib/tracking.lib.php
  15. 6
      main/inc/lib/usermanager.lib.php
  16. 14
      main/inc/lib/userportal.lib.php
  17. 3
      main/install/configuration.dist.php
  18. 1
      main/lang/english/trad4all.inc.php
  19. 1
      main/lang/french/trad4all.inc.php
  20. 1
      main/lang/spanish/trad4all.inc.php
  21. 2
      main/lp/learnpath.class.php
  22. 8
      main/lp/lp_ajax_save_item.php
  23. 5
      main/lp/lp_content.php
  24. 3
      main/lp/lp_controller.php
  25. 6
      main/lp/lp_report.php
  26. 3
      main/lp/lp_stats.php
  27. 75
      main/lp/lp_view.php
  28. 5
      main/mySpace/lp_tracking.php
  29. 2
      main/survey/surveyUtil.class.php
  30. 5
      main/survey/survey_list.php
  31. 5
      main/template/default/user_portal/classic_courses_without_category.tpl
  32. 3
      main/template/default/user_portal/classic_session.tpl
  33. 10
      main/tracking/lp_report.php
  34. 25
      user_portal.php

@ -37,9 +37,7 @@ if (api_is_platform_admin() || api_is_course_admin() || api_is_allowed_to_create
$defaultAction = CoursesAndSessionsCatalog::is(CATALOG_SESSIONS) ? 'display_sessions' : 'display_courses';
$action = isset($_REQUEST['action']) ? Security::remove_XSS($_REQUEST['action']) : $defaultAction;
$categoryCode = isset($_REQUEST['category_code']) && !empty($_REQUEST['category_code']) ? Security::remove_XSS(
$_REQUEST['category_code']
) : 'ALL';
$categoryCode = isset($_REQUEST['category_code']) ? Security::remove_XSS($_REQUEST['category_code']) : '';
$searchTerm = isset($_REQUEST['search_term']) ? Security::remove_XSS($_REQUEST['search_term']) : '';
$nameTools = CourseCategory::getCourseCatalogNameTools($action);
@ -206,11 +204,16 @@ switch ($action) {
$settings = CoursesAndSessionsCatalog::getCatalogSearchSettings();
$form = new FormValidator('search', 'get', '', null, null, FormValidator::LAYOUT_GRID);
$form->addHidden('action', 'search_course');
if (true === $settings['courses']['by_title']) {
if (isset($settings['courses']) && true === $settings['courses']['by_title']) {
$form->addText('search_term', get_lang('Title'));
}
$select = $form->addSelect('category_code', get_lang('CourseCategories'));
$select = $form->addSelect(
'category_code',
get_lang('CourseCategories'),
[],
['placeholder' => get_lang('SelectAnOption')]
);
$defaults = [];
$listCategories = CoursesAndSessionsCatalog::getCourseCategoriesTree();

@ -1,12 +1,11 @@
<?php
/* For licensing terms, see /license.txt */
use ChamiloSession as Session;
/**
* This script displays a form for registering new users.
*
* @package chamilo.auth
*/
//quick hack to adapt the registration form result to the selected registration language
@ -445,7 +444,6 @@ $content = null;
$tool_name = get_lang('Registration');
if (!CustomPages::enabled()) {
// Load terms & conditions from the current lang
if (api_get_setting('allow_terms_conditions') === 'true') {
$get = array_keys($_GET);
@ -481,7 +479,7 @@ if (!CustomPages::enabled()) {
if (api_get_setting('allow_terms_conditions') === 'true' && $user_already_registered_show_terms) {
$tool_name = get_lang('TermsAndConditions');
}
}
$home = api_get_path(SYS_APP_PATH).'home/';
if (api_is_multiple_url_enabled()) {

@ -9754,6 +9754,88 @@ class Exercise
];
}
public static function saveExerciseInLp($safe_item_id, $safe_exe_id)
{
$lp = Session::read('oLP');
$safe_exe_id = (int) $safe_exe_id;
$safe_item_id = (int) $safe_item_id;
if (empty($lp) || empty($safe_exe_id) || empty($safe_item_id)) {
return false;
}
$viewId = $lp->get_view_id();
$course_id = api_get_course_int_id();
$userId = (int) api_get_user_id();
$viewId = (int) $viewId;
$TBL_TRACK_EXERCICES = Database::get_main_table(TABLE_STATISTIC_TRACK_E_EXERCISES);
$TBL_LP_ITEM_VIEW = Database::get_course_table(TABLE_LP_ITEM_VIEW);
$TBL_LP_ITEM = Database::get_course_table(TABLE_LP_ITEM);
$sql = "SELECT start_date, exe_date, exe_result, exe_weighting, exe_exo_id, exe_duration
FROM $TBL_TRACK_EXERCICES
WHERE exe_id = $safe_exe_id AND exe_user_id = $userId";
$res = Database::query($sql);
$row_dates = Database::fetch_array($res);
if (empty($row_dates)) {
return false;
}
$duration = (int) $row_dates['exe_duration'];
$score = (float) $row_dates['exe_result'];
$max_score = (float) $row_dates['exe_weighting'];
$sql = "UPDATE $TBL_LP_ITEM SET
max_score = '$max_score'
WHERE iid = $safe_item_id";
Database::query($sql);
$sql = "SELECT id FROM $TBL_LP_ITEM_VIEW
WHERE
c_id = $course_id AND
lp_item_id = $safe_item_id AND
lp_view_id = $viewId
ORDER BY id DESC
LIMIT 1";
$res_last_attempt = Database::query($sql);
if (Database::num_rows($res_last_attempt) && !api_is_invitee()) {
$row_last_attempt = Database::fetch_row($res_last_attempt);
$lp_item_view_id = $row_last_attempt[0];
$exercise = new Exercise($course_id);
$exercise->read($row_dates['exe_exo_id']);
$status = 'completed';
if (!empty($exercise->pass_percentage)) {
$status = 'failed';
$success = ExerciseLib::isSuccessExerciseResult(
$score,
$max_score,
$exercise->pass_percentage
);
if ($success) {
$status = 'passed';
}
}
$sql = "UPDATE $TBL_LP_ITEM_VIEW SET
status = '$status',
score = $score,
total_time = $duration
WHERE iid = $lp_item_view_id";
Database::query($sql);
$sql = "UPDATE $TBL_TRACK_EXERCICES SET
orig_lp_item_view_id = $lp_item_view_id
WHERE exe_id = ".$safe_exe_id;
Database::query($sql);
}
}
/**
* Get number of questions in exercise by user attempt.
*

@ -10,8 +10,6 @@ use ChamiloSession as Session;
* that exercise.
* Then it shows the results on the screen.
*
* @package chamilo.exercise
*
* @author Olivier Brouckaert, main author
* @author Roan Embrechts, some refactoring
* @author Julio Montoya switchable fill in blank option added
@ -190,6 +188,12 @@ ExerciseLib::displayQuestionListByAttempt(
$remainingMessage
);
// Save here LP status
if (!empty($learnpath_id) && $saveResults) {
// Save attempt in lp
Exercise::saveExerciseInLp($learnpath_item_id, $exe_id);
}
//Unset session for clock time
ExerciseLib::exercise_time_control_delete(
$objExercise->id,

@ -1,4 +1,5 @@
<?php
/* For licensing terms, see /license.txt */
use ChamiloSession as Session;
@ -19,8 +20,6 @@ use ChamiloSession as Session;
* Notice : This script is also used to show a question before modifying it by
* the administrator
*
* @package chamilo.exercise
*
* @author Olivier Brouckaert
* @author Julio Montoya <gugli100@gmail.com>
* Fill in blank option added (2008)
@ -101,7 +100,6 @@ $currentAnswer = isset($_REQUEST['num_answer']) ? (int) $_REQUEST['num_answer']
$logInfo = [
'tool' => TOOL_QUIZ,
'tool_id' => $exerciseId,
'tool_id_detail' => 0,
'action' => $learnpath_id,
'action_details' => $learnpath_id,
];
@ -467,10 +465,6 @@ if (!isset($questionListInSession)) {
$questionList = explode(',', $exercise_stat_info['data_tracking']);
}
Session::write('questionList', $questionList);
if ($debug > 0) {
error_log('$_SESSION[questionList] was set');
}
} else {
if (isset($objExercise) && isset($exerciseInSession)) {
$questionList = Session::read('questionList');
@ -607,7 +601,7 @@ if ($debug) {
error_log('8. Question list loaded '.print_r($questionList, 1));
}
//Real question count
// Real question count.
$question_count = 0;
if (!empty($questionList)) {
$question_count = count($questionList);
@ -626,7 +620,6 @@ if ($formSent && isset($_POST)) {
error_log('9. $formSent was set');
}
// Initializing
if (!is_array($exerciseResult)) {
$exerciseResult = [];
$exerciseResultCoordinates = [];
@ -686,7 +679,6 @@ if ($formSent && isset($_POST)) {
[]
);
}
//END of saving and qualifying
}
}
}

@ -1,4 +1,5 @@
<?php
/* For licensing terms, see /license.txt */
use ChamiloSession as Session;

@ -460,6 +460,18 @@ switch ($action) {
$attemptList = Event::getAllExerciseEventByExeId($exeId);
}
// No exe id? Can't save answer.
if (empty($exeId)) {
// Fires an error.
echo 'error';
if ($debug) {
error_log('exe_id is empty');
}
exit;
}
Session::write('exe_id', $exeId);
// Updating Reminder algorithm.
if ($objExercise->type == ONE_PER_PAGE) {
$bd_reminder_list = explode(',', $exercise_stat_info['questions_to_check']);
@ -482,21 +494,9 @@ switch ($action) {
}
}
// No exe id? Can't save answer.
if (empty($exeId)) {
// Fires an error.
echo 'error';
if ($debug) {
error_log('exe_id is empty');
}
exit;
}
Session::write('exe_id', $exeId);
// Getting the total weight if the request is simple
$total_weight = 0;
if ($type == 'simple') {
if ($type === 'simple') {
foreach ($question_list as $my_question_id) {
$objQuestionTmp = Question::read($my_question_id, $objExercise->course);
$total_weight += $objQuestionTmp->selectWeighting();
@ -510,7 +510,7 @@ switch ($action) {
error_log("Saving question_id = $my_question_id ");
}
if ($type == 'simple' && $question_id != $my_question_id) {
if ($type === 'simple' && $question_id != $my_question_id) {
continue;
}
@ -537,7 +537,7 @@ switch ($action) {
: null;
}
if ($type == 'all') {
if ($type === 'all') {
$total_weight += $objQuestionTmp->selectWeighting();
}
@ -637,7 +637,7 @@ switch ($action) {
$duration = 0;
$now = time();
if ($type == 'all') {
if ($type === 'all') {
$exercise_stat_info = $objExercise->get_stat_track_exercise_info_by_exe_id($exeId);
}

@ -441,7 +441,7 @@ class CoursesAndSessionsCatalog
}
$categoryFilter = '';
if ($categoryCode === 'ALL') {
if ($categoryCode === 'ALL' || empty($categoryCode)) {
// Nothing to do
} elseif ($categoryCode === 'NONE') {
$categoryFilter = ' AND category_code = "" ';
@ -498,6 +498,7 @@ class CoursesAndSessionsCatalog
";
}
}
//var_dump($sql);
$result = Database::query($sql);
$courses = [];
while ($row = Database::fetch_array($result)) {

@ -2027,7 +2027,7 @@ class CourseManager
$students = [];
$limitCondition = '';
if (!empty($start) && !empty($limit)) {
if (isset($start) && isset($limit) && !empty($limit)) {
$start = (int) $start;
$limit = (int) $limit;
$limitCondition = " LIMIT $start, $limit";
@ -2038,7 +2038,7 @@ class CourseManager
$select = 'count(u.id) as count';
}
if ($sessionId == 0) {
if (empty($sessionId)) {
if (empty($groupId)) {
// students directly subscribed to the course
$sql = "SELECT $select
@ -3933,7 +3933,7 @@ class CourseManager
'not_category' => [],
];
$collapsable = api_get_configuration_value('allow_user_course_category_collapsable');
$stok = Security::get_token();
$stok = Security::get_existing_token();
while ($row = Database::fetch_array($result)) {
// We simply display the title of the category.
$courseInCategory = self::returnCoursesCategories(
@ -4183,6 +4183,17 @@ class CourseManager
$params['extrafields'] = CourseManager::getExtraFieldsToBePresented($course_info['real_id']);
$params['real_id'] = $course_info['real_id'];
if (api_get_configuration_value('enable_unsubscribe_button_on_my_course_page')
&& '1' === $course_info['unsubscribe']
) {
$params['unregister_button'] = CoursesAndSessionsCatalog::return_unregister_button(
$course_info,
Security::get_existing_token(),
'',
''
);
}
if ($course_info['visibility'] != COURSE_VISIBILITY_CLOSED) {
$params['notifications'] = $showNotification;
}

File diff suppressed because it is too large Load Diff

@ -136,7 +136,11 @@ EOT;
.form_list {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));;
grid-gap: 50px;
grid-gap: 10px 30px;
gap: 10px 30px;
}
.form_list .input-group {
display:block;
}
</style>
<form{attributes}>
@ -147,17 +151,6 @@ EOT;
</form>';
}
/**
* <div class="col-md-12">
<div class="row">
<fieldset>
{content}
</fieldset>
</div>
</div>
*/
/**
* @todo this function should be added in the element class
*

@ -1,10 +1,9 @@
<?php
/* For licensing terms, see /license.txt */
/**
* Class LegalManager.
*
* @package chamilo.legal
*/
class LegalManager
{
@ -322,7 +321,7 @@ class LegalManager
// max 2000 chars
$languages[] = $legal[1];
if (strlen($legal[2]) > 2000) {
$legal[2] = substr($legal[2], 0, 2000).' ... ';
$legal[2] = substr(strip_tags($legal[2]), 0, 2000).' ... ';
}
if ($legal[4] == 0) {
$legal[4] = get_lang('HTMLText');

@ -110,6 +110,7 @@ class HTML_QuickForm_text extends HTML_QuickForm_input
</div>';
switch ($layout) {
case FormValidator::LAYOUT_GRID:
case FormValidator::LAYOUT_INLINE:
$template = '
<div class="form-group {error_class}">
@ -146,7 +147,6 @@ class HTML_QuickForm_text extends HTML_QuickForm_input
</div>
</div>';
break;
case FormValidator::LAYOUT_GRID:
case FormValidator::LAYOUT_BOX_NO_LABEL:
if (isset($attributes['custom']) && $attributes['custom'] == true) {
$template = '

@ -1,4 +1,5 @@
<?php
/* For licensing terms, see /license.txt */
use Chamilo\CoreBundle\Entity\Course;
@ -566,7 +567,6 @@ class Tracking
// Remove "NaN" if any (@todo: locate the source of these NaN)
$time = str_replace('NaN', '00'.$h.'00\'00"', $time);
if ($row['item_type'] !== 'dir') {
if (!$is_allowed_to_edit && $result_disabled_ext_all) {
$view_score = Display::return_icon(
@ -600,7 +600,7 @@ class Tracking
}
$action = null;
if ($type == 'classic') {
if ($type === 'classic') {
$action = '<td></td>';
}
$timeRow = '<td class="lp_time" colspan="2">'.$time.'</td>';
@ -891,7 +891,7 @@ class Tracking
}
$action = null;
if ($type == 'classic') {
if ($type === 'classic') {
$action = '<td></td>';
}
@ -980,7 +980,7 @@ class Tracking
}
$scoreItem = null;
if ($row['item_type'] == 'quiz') {
if ($row['item_type'] === 'quiz') {
if (!$is_allowed_to_edit && $result_disabled_ext_all) {
$scoreItem .= Display::return_icon(
'invisible.gif',
@ -1039,12 +1039,10 @@ class Tracking
if ($extend_this_attempt || $extend_all) {
$list1 = learnpath::get_iv_interactions_array($row['iv_id'], $course_id);
foreach ($list1 as $id => $interaction) {
$oddclass = 'row_even';
if (($counter % 2) == 0) {
$oddclass = 'row_odd';
} else {
$oddclass = 'row_even';
}
$timeRow = '<td class="lp_time">'.$interaction['time'].'</td>';
if ($hideTime) {
$timeRow = '';
@ -1065,13 +1063,12 @@ class Tracking
</tr>';
$counter++;
}
$list2 = learnpath::get_iv_objectives_array($row['iv_id'], $course_id);
$list2 = learnpath::get_iv_objectives_array($row['iv_id'], $course_id);
foreach ($list2 as $id => $interaction) {
$oddclass = 'row_even';
if (($counter % 2) == 0) {
$oddclass = 'row_odd';
} else {
$oddclass = 'row_even';
}
$output .= '<tr class="'.$oddclass.'">
<td></td>

@ -3826,7 +3826,8 @@ class UserManager
c.visibility,
c.id as real_id,
c.code as course_code,
sc.position
sc.position,
c.unsubscribe
FROM $tbl_session_course_user as scu
INNER JOIN $tbl_session_course sc
ON (scu.session_id = sc.session_id AND scu.c_id = sc.c_id)
@ -3862,7 +3863,8 @@ class UserManager
c.visibility,
c.id as real_id,
c.code as course_code,
sc.position
sc.position,
c.unsubscribe
FROM $tbl_session_course_user as scu
INNER JOIN $tbl_session as s
ON (scu.session_id = s.id)

@ -1920,6 +1920,20 @@ class IndexManager
$course_session['extrafields'] = CourseManager::getExtraFieldsToBePresented($course['real_id']);
if (api_get_configuration_value(
'enable_unsubscribe_button_on_my_course_page'
)
&& '1' === $course['unsubscribe']
) {
$course_session['unregister_button'] =
CoursesAndSessionsCatalog::return_unregister_button(
['code' => $course['course_code']],
Security::get_existing_token(),
'',
''
);
}
$html_courses_session[] = $course_session;
}
}

@ -1508,6 +1508,9 @@ $_configuration['auth_password_links'] = [
];
*/
// Show unsubscribe buttons on page "My courses"
//$_configuration['enable_unsubscribe_button_on_my_course_page'] = false;
// KEEP THIS AT THE END
// -------- Custom DB changes
// Add user activation by confirmation email

@ -8516,4 +8516,5 @@ $SurveyXNotMultiplicated = "Survey %s not multiplicated";
$ExportSurveyResults = "Export survey results";
$PointAverage = "Average score";
$TotalScore = "Score Sum";
$ExportResults = "Export results";
?>

@ -8448,4 +8448,5 @@ $SurveyXNotMultiplicated = "Enquête %s non démultipliée";
$ExportSurveyResults = "Exporter les résultats des enquêtes";
$PointAverage = "Moyenne des scores";
$TotalScore = "Somme des scores";
$ExportResults = "Exporter les résultats";
?>

@ -8544,4 +8544,5 @@ $SurveyXNotMultiplicated = "Encuesta %s no demultiplicada";
$ExportSurveyResults = "Exportar resultados de encuestas";
$PointAverage = "Puntajes promedio";
$TotalScore = "Suma de puntajes";
$ExportResults = "Exportar resultados";
?>

@ -3665,7 +3665,7 @@ class learnpath
$type_quiz = false;
foreach ($list as $toc) {
if ($toc['id'] == $lp_item_id && $toc['type'] == 'quiz') {
if ($toc['id'] == $lp_item_id && $toc['type'] === 'quiz') {
$type_quiz = true;
}
}

@ -183,7 +183,7 @@ function save_item(
$my_type = $myLPI->get_type();
// Set status to completed for hotpotatoes if score > 80%.
if ($my_type == 'hotpotatoes') {
if ($my_type === 'hotpotatoes') {
if ((empty($status) || $status == 'undefined' || $status == 'not attempted') && $max > 0) {
if (($score / $max) > 0.8) {
$myStatus = 'completed';
@ -207,7 +207,7 @@ function save_item(
error_log('Done calling set_status for hotpotatoes - now '.$myLPI->get_status(false));
}
}
} elseif ($my_type == 'sco') {
} elseif ($my_type === 'sco') {
/*
* This is a specific implementation for SCORM 1.2, matching page 26 of SCORM 1.2's RTE
* "Normally the SCO determines its own status and passes it to the LMS.
@ -254,7 +254,7 @@ function save_item(
* the status to either passed or failed depending on the
* student's score compared to the mastery score.
*/
if ($credit == 'credit' &&
if ($credit === 'credit' &&
$masteryScore &&
(isset($score) && $score != -1) &&
!$statusIsSet && !$statusSignalReceived
@ -471,7 +471,7 @@ function save_item(
error_log("progress: $myComplete / $myTotal");
}
if ($myLPI->get_type() != 'sco') {
if ($myLPI->get_type() !== 'sco') {
// If this object's JS status has not been updated by the SCORM API, update now.
$return .= "olms.lesson_status='".$myStatus."';";
}

@ -1,4 +1,5 @@
<?php
/* For licensing terms, see /license.txt */
use ChamiloSession as Session;
@ -6,8 +7,6 @@ use ChamiloSession as Session;
/**
* Script that displays an error message when no content could be loaded.
*
* @package chamilo.learnpath
*
* @author Yannick Warnier <ywarnier@beeznest.org>
*/
require_once __DIR__.'/../inc/global.inc.php';
@ -44,7 +43,7 @@ $list = $learnPath->get_toc();
$dir = false;
foreach ($list as $toc) {
if ($toc['id'] == $lpItemId && $toc['type'] == 'dir') {
if ($toc['id'] == $lpItemId && $toc['type'] === 'dir') {
$dir = true;
}
}

@ -1,4 +1,5 @@
<?php
/* For licensing terms, see /license.txt */
use ChamiloSession as Session;
@ -9,8 +10,6 @@ use ChamiloSession as Session;
*
* @todo remove repeated if $lp_found redirect
*
* @package chamilo.learnpath
*
* @author Yannick Warnier <ywarnier@beeznest.org>
*/

@ -1,4 +1,5 @@
<?php
/* For licensing terms, see /license.txt */
/**
@ -14,7 +15,7 @@ if (!$isAllowedToEdit) {
$lpTable = Database::get_course_table(TABLE_LP_MAIN);
$lpId = isset($_GET['lp_id']) ? intval($_GET['lp_id']) : false;
$lpId = isset($_GET['lp_id']) ? (int) $_GET['lp_id'] : false;
$export = isset($_GET['export']) ? true : false;
if (empty($lpId)) {
@ -145,7 +146,6 @@ $template->assign('course_code', api_get_course_id());
$template->assign('lp_id', $lpId);
$template->assign('show_email', $showEmail === 'true');
$template->assign('export', (int) $export);
$layout = $template->get_template('learnpath/report.tpl');
$template->assign('header', $lpInfo['name']);
@ -160,8 +160,6 @@ $template->assign('content', $result);
if ($export) {
$pdfParams = [
'filename' => get_lang('StudentScore').'_'.api_get_local_time(),
//'pdf_title' => $title,
//'course_code' => $course_code
];
$pdf = new PDF('A4', 'P', $pdfParams);
$pdf->html_to_pdf_with_template(

@ -1,12 +1,11 @@
<?php
/* For licensing terms, see /license.txt */
/**
* This script displays statistics on the current learning path (scorm)
* This script must be included by lp_controller.php to get basic initialisation.
*
* @package chamilo.learnpath
*
* @author Yannick Warnier <ywarnier@beeznest.org>
*/
require_once __DIR__.'/../inc/global.inc.php';

@ -1,4 +1,5 @@
<?php
/* For licensing terms, see /license.txt */
use Chamilo\CourseBundle\Entity\CLpCategory;
@ -9,8 +10,6 @@ use ChamiloSession as Session;
* the direct file view is not needed anymore, if the user uploads a scorm zip file, a directory
* will be automatically created for it, and the files will be uncompressed there for example ;.
*
* @package chamilo.learnpath
*
* @author Yannick Warnier <ywarnier@beeznest.org> - redesign
* @author Denes Nagy, principal author
* @author Isthvan Mandak, several new features
@ -293,12 +292,12 @@ if ($debug) {
error_log('$type_quiz: '.$type_quiz);
error_log('$_REQUEST[exeId]: '.intval($_REQUEST['exeId']));
error_log('$lp_id: '.$lp_id);
error_log('$_GET[lp_item_id]: '.intval($_GET['lp_item_id']));
error_log('$_REQUEST[lp_item_id]: '.intval($_REQUEST['lp_item_id']));
}
if (!empty($_REQUEST['exeId']) &&
isset($lp_id) &&
isset($_GET['lp_item_id'])
isset($_REQUEST['lp_item_id'])
) {
global $src;
$lp->items[$lp->current]->write_to_db();
@ -306,73 +305,15 @@ if (!empty($_REQUEST['exeId']) &&
$TBL_TRACK_EXERCICES = Database::get_main_table(TABLE_STATISTIC_TRACK_E_EXERCISES);
$TBL_LP_ITEM_VIEW = Database::get_course_table(TABLE_LP_ITEM_VIEW);
$TBL_LP_ITEM = Database::get_course_table(TABLE_LP_ITEM);
$safe_item_id = (int) $_GET['lp_item_id'];
$safe_item_id = (int) $_REQUEST['lp_item_id'];
$safe_id = $lp_id;
$safe_exe_id = (int) $_REQUEST['exeId'];
if (!empty($safe_id) && !empty($safe_item_id)) {
$sql = 'SELECT start_date, exe_date, exe_result, exe_weighting, exe_exo_id, exe_duration
FROM '.$TBL_TRACK_EXERCICES.'
WHERE exe_id = '.$safe_exe_id;
$res = Database::query($sql);
$row_dates = Database::fetch_array($res);
$duration = (int) $row_dates['exe_duration'];
$score = (float) $row_dates['exe_result'];
$max_score = (float) $row_dates['exe_weighting'];
$sql = "UPDATE $TBL_LP_ITEM SET
max_score = '$max_score'
WHERE iid = $safe_item_id";
Database::query($sql);
$sql = "SELECT id FROM $TBL_LP_ITEM_VIEW
WHERE
c_id = $course_id AND
lp_item_id = $safe_item_id AND
lp_view_id = ".$lp->get_view_id()."
ORDER BY id DESC
LIMIT 1";
$res_last_attempt = Database::query($sql);
if (Database::num_rows($res_last_attempt) && !api_is_invitee()) {
$row_last_attempt = Database::fetch_row($res_last_attempt);
$lp_item_view_id = $row_last_attempt[0];
$exercise = new Exercise(api_get_course_int_id());
$exercise->read($row_dates['exe_exo_id']);
$status = 'completed';
if (!empty($exercise->pass_percentage)) {
$status = 'failed';
$success = ExerciseLib::isSuccessExerciseResult(
$score,
$max_score,
$exercise->pass_percentage
);
if ($success) {
$status = 'passed';
}
}
$sql = "UPDATE $TBL_LP_ITEM_VIEW SET
status = '$status',
score = $score,
total_time = $duration
WHERE iid = $lp_item_view_id";
if ($debug) {
error_log($sql);
}
Database::query($sql);
$sql = "UPDATE $TBL_TRACK_EXERCICES SET
orig_lp_item_view_id = $lp_item_view_id
WHERE exe_id = ".$safe_exe_id;
Database::query($sql);
}
Exercise::saveExerciseInLp($safe_item_id, $safe_exe_id);
}
if (intval($_GET['fb_type']) != EXERCISE_FEEDBACK_TYPE_END) {
$src = 'blank.php?msg=exerciseFinished';
$src = 'blank.php?msg=exerciseFinished&'.api_get_cidreq(true, true, 'learnpath');
} else {
$src = api_get_path(WEB_CODE_PATH).'exercise/result.php?id='.$safe_exe_id.'&'.api_get_cidreq(true, true, 'learnpath');
if ($debug) {
@ -391,7 +332,7 @@ $_setting['show_navigation_menu'] = 'false';
$scorm_css_header = true;
$lp_theme_css = $lp->get_theme();
// Sets the css theme of the LP this call is also use at the frames (toc, nav, message).
if ($lp->mode == 'fullscreen') {
if ($lp->mode === 'fullscreen') {
$htmlHeadXtra[] = "<script>
window.open('$src','content_id','toolbar=0,location=0,status=0,scrollbars=1,resizable=1');
</script>";
@ -580,7 +521,7 @@ if (Tracking::minimumTimeAvailable(api_get_session_id(), api_get_course_int_id()
}
// Minimum time for each learning path
$time_min = intval($pl * $tc * $perc / 100);
$time_min = (int) ($pl * $tc * $perc / 100);
if ($_SESSION['oLP']->getAccumulateWorkTime() > 0) {
$lpMinTime = '('.$time_min.' min)';

@ -1,4 +1,5 @@
<?php
/* For licensing terms, see /license.txt */
use Chamilo\CoreBundle\Component\Utils\ChamiloApi;
@ -14,7 +15,7 @@ require_once __DIR__.'/../inc/global.inc.php';
$cidReset = true;
$from_myspace = false;
$from_link = '';
if (isset($_GET['from']) && $_GET['from'] == 'myspace') {
if (isset($_GET['from']) && $_GET['from'] === 'myspace') {
$from_link = '&from=myspace';
$this_section = SECTION_TRACKING;
} else {
@ -22,7 +23,7 @@ if (isset($_GET['from']) && $_GET['from'] == 'myspace') {
}
$session_id = isset($_REQUEST['id_session']) ? (int) $_REQUEST['id_session'] : api_get_session_id();
$export_csv = isset($_GET['export']) && $_GET['export'] == 'csv';
$export_csv = isset($_GET['export']) && $_GET['export'] === 'csv';
$user_id = isset($_GET['student_id']) ? (int) $_GET['student_id'] : api_get_user_id();
$courseCode = isset($_GET['course']) ? Security::remove_XSS($_GET['course']) : api_get_course_id();
$origin = api_get_origin();

@ -2934,7 +2934,7 @@ class SurveyUtil
$table->set_column_filter(8, 'anonymous_filter');
$actions = [
'export_all' => get_lang('Export'),
'export_all' => get_lang('ExportResults'),
'send_to_tutors' => get_lang('SendToGroupTutors'),
'multiplicate' => get_lang('MultiplicateQuestions'),
'delete' => get_lang('DeleteSurvey'),

@ -87,17 +87,16 @@ if (isset($_POST['action']) && $_POST['action'] && isset($_POST['id']) && is_arr
}
$exportList = [];
foreach ($_POST['id'] as $value) {
$surveyData = SurveyManager::get_survey($value);
if (empty($surveyData)) {
continue;
}
$surveyData['title'] = strip_tags($surveyData['title']);
$surveyData['title'] = trim(strip_tags($surveyData['title']));
switch ($action) {
case 'export_all':
$filename = 'survey_results_'.$value.'.xlsx';
$filename = $surveyData['code'].'.xlsx';
$exportList[] = @SurveyUtil::export_complete_report_xls($surveyData, $filename, 0, true);
break;
case 'send_to_tutors':

@ -26,8 +26,9 @@
{% endif %}
</div>
<div class="col-md-10">
{% if item.edit_actions != '' %}
<div class="pull-right">
{{ item.unregister_button }}
{% if item.edit_actions != '' %}
{% if item.document == '' %}
<a class="btn btn-default btn-sm" href="{{ item.edit_actions }}">
<i class="fa fa-pencil" aria-hidden="true"></i>
@ -40,8 +41,8 @@
{{ item.document }}
</div>
{% endif %}
</div>
{% endif %}
</div>
<h4 class="course-items-title">
{% if item.visibility == constant('COURSE_VISIBILITY_CLOSED') and not item.current_user_is_teacher %}
{{ item.title }} {{ item.code_course }}

@ -97,6 +97,9 @@
</a>
</div>
<div class="col-md-10">
<div class="pull-right">
{{ item.unregister_button }}
</div>
{% if item.requirements %}
<h4>{{ item.name }}</h4>
{% else %}

@ -20,13 +20,6 @@ if (!$is_allowedToTrack) {
}
$action = isset($_GET['action']) ? $_GET['action'] : null;
$htmlHeadXtra[] = '<script>
$(function ()
});
</script>';
$lps = learnpath::getLpList($courseId);
Session::write('lps', $lps);
@ -432,7 +425,10 @@ $actionsRight = Display::url(
);
// Create a sortable table with user-data
$parameters = [];
$parameters['sec_token'] = Security::get_token();
$parameters['cidReq'] = api_get_course_id();
$parameters['id_session'] = api_get_session_id();
$table = new SortableTable(
'lps',

@ -45,16 +45,15 @@ Event::registerLog($logInfo);
$userId = api_get_user_id();
$collapsable = api_get_configuration_value('allow_user_session_collapsable');
if ($collapsable) {
$action = isset($_REQUEST['action']) ? $_REQUEST['action'] : '';
$sessionId = isset($_REQUEST['session_id']) ? $_REQUEST['session_id'] : '';
$value = isset($_REQUEST['value']) ? (int) $_REQUEST['value'] : '';
switch ($action) {
if (array_key_exists('action', $_REQUEST)) {
switch ($_REQUEST['action']) {
case 'collapse_session':
if (!empty($sessionId)) {
$userRelSession = SessionManager::getUserSession($userId, $sessionId);
if (api_get_configuration_value('allow_user_session_collapsable')
&& array_key_exists('session_id', $_REQUEST)
) {
$userRelSession = SessionManager::getUserSession($userId, $_REQUEST['session_id']);
if ($userRelSession) {
$value = isset($_REQUEST['value']) ? (int) $_REQUEST['value'] : '';
$table = Database::get_main_table(TABLE_MAIN_SESSION_USER);
$sql = "UPDATE $table SET collapsed = $value WHERE id = ".$userRelSession['id'];
Database::query($sql);
@ -64,6 +63,16 @@ if ($collapsable) {
exit;
}
break;
case 'unsubscribe':
if (\Security::check_token('get')) {
$auth = new Auth();
if ($auth->remove_user_from_course($_GET['course_code'])) {
Display::addFlash(Display::return_message(get_lang('YouAreNowUnsubscribed')));
}
header('Location: user_portal.php');
exit;
}
break;
}
}

Loading…
Cancel
Save