From e5ee0c55749c82fda331fe33397a4f5047ed35e3 Mon Sep 17 00:00:00 2001 From: Neill Magill Date: Thu, 29 Aug 2013 14:09:16 +0100 Subject: [PATCH 01/75] Security fix to stop students being able to see the attendance records of other students. --- view.php | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/view.php b/view.php index 5117605..6fd1794 100644 --- a/view.php +++ b/view.php @@ -63,7 +63,9 @@ $PAGE->navbar->add(get_string('attendancereport', 'attendance')); $output = $PAGE->get_renderer('mod_attendance'); -$userid = isset($pageparams->studentid) ? $pageparams->studentid : $USER->id; +// Only users with proper permissions should be able to see any users individual report. +$userid = (isset($pageparams->studentid) && + ($att->perm->can_manage() || $att->perm->can_take() || $att->perm->can_change())) ? $pageparams->studentid : $USER->id; $userdata = new attendance_user_data($att, $userid); echo $output->header(); From 9aaf4d69d6fbd6f1d9696f9ee51f63cfd209a839 Mon Sep 17 00:00:00 2001 From: NeillM Date: Fri, 30 Aug 2013 09:31:04 +0100 Subject: [PATCH 02/75] Security fix changed to use mod/attendance:viewreports capability. Refactored the code. --- view.php | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/view.php b/view.php index 6fd1794..5bd155c 100644 --- a/view.php +++ b/view.php @@ -63,9 +63,14 @@ $PAGE->navbar->add(get_string('attendancereport', 'attendance')); $output = $PAGE->get_renderer('mod_attendance'); -// Only users with proper permissions should be able to see any users individual report. -$userid = (isset($pageparams->studentid) && - ($att->perm->can_manage() || $att->perm->can_take() || $att->perm->can_change())) ? $pageparams->studentid : $USER->id; +if (isset($pageparams->studentid) && has_capability('mod/attendance:viewreports', $PAGE->context)) { + // Only users with proper permissions should be able to see any user's individual report. + $userid = $pageparams->studentid; +} else { + // A valid request to see another users report has not been sent, show the user's own. + $userid = $USER->id; +} + $userdata = new attendance_user_data($att, $userid); echo $output->header(); From 3c04dc5fd59740337882238116ea40249a4a79b5 Mon Sep 17 00:00:00 2001 From: NeillM Date: Fri, 30 Aug 2013 10:00:14 +0100 Subject: [PATCH 03/75] changed to use require --- view.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/view.php b/view.php index 5bd155c..51e7eb4 100644 --- a/view.php +++ b/view.php @@ -63,8 +63,9 @@ $PAGE->navbar->add(get_string('attendancereport', 'attendance')); $output = $PAGE->get_renderer('mod_attendance'); -if (isset($pageparams->studentid) && has_capability('mod/attendance:viewreports', $PAGE->context)) { +if (isset($pageparams->studentid) && $USER->id != $pageparams->studentid) { // Only users with proper permissions should be able to see any user's individual report. + require_capability('mod/attendance:viewreports', $PAGE->context); $userid = $pageparams->studentid; } else { // A valid request to see another users report has not been sent, show the user's own. From c4a479e0962001ec5a584dbd3c600cee958ca581 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Mon, 2 Sep 2013 09:38:10 +1200 Subject: [PATCH 04/75] version bump for security release --- version.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/version.php b/version.php index e7ab8e3..2a10679 100644 --- a/version.php +++ b/version.php @@ -22,9 +22,9 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -$module->version = 2013082900; +$module->version = 2013082901; $module->requires = 2013040500; -$module->release = '2.5.1'; +$module->release = '2.5.2'; $module->maturity = MATURITY_STABLE; $module->cron = 0; $module->component = 'mod_attendance'; From 759c848b86c1e4cc307f78b683a8411c2bf7ac39 Mon Sep 17 00:00:00 2001 From: Tim Lock Date: Thu, 12 Sep 2013 13:33:54 +0930 Subject: [PATCH 05/75] Added paging to reporting and taking attendance configable via module setting. --- export.php | 1 + lang/en/attendance.php | 1 + locallib.php | 31 +++++++++++++++++++-- manage.php | 1 + renderables.php | 6 ++-- renderer.php | 62 ++++++++++++++++++++++++++++++++++++++++-- report.php | 2 ++ settings.php | 44 ++++++++++++++++++++++++++++++ take.php | 2 ++ 9 files changed, 143 insertions(+), 7 deletions(-) create mode 100644 settings.php diff --git a/export.php b/export.php index 57d7ebc..5d2d32f 100644 --- a/export.php +++ b/export.php @@ -55,6 +55,7 @@ if ($mform->is_submitted()) { $pageparams = new att_page_with_filter_controls(); $pageparams->init($cm); + $pageparams->page = 0; $pageparams->group = $formdata->group; $pageparams->set_current_sesstype($formdata->group ? $formdata->group : att_page_with_filter_controls::SESSTYPE_ALL); if (isset($formdata->includeallsessions)) { diff --git a/lang/en/attendance.php b/lang/en/attendance.php index 5dd803c..9d4387a 100755 --- a/lang/en/attendance.php +++ b/lang/en/attendance.php @@ -130,6 +130,7 @@ The teacher can create multiple sessions and can mark the attendance status as " Reports are available for the entire class or individual students.'; $string['modulenameplural'] = 'Attendances'; $string['months'] = 'Months'; +$string['moreattendance'] = 'Attendance has been successfully taken for this page'; $string['myvariables'] = 'My Variables'; $string['newdate'] = 'New date'; $string['newduration'] = 'New duration'; diff --git a/locallib.php b/locallib.php index 1975b0b..a772da0 100644 --- a/locallib.php +++ b/locallib.php @@ -887,13 +887,33 @@ class attendance { $url = $this->url_take($params); add_to_log($this->course->id, 'attendance', 'taken', $url, '', $this->cm->id); + $group = 0; + if ($this->pageparams->grouptype != attendance::SESSION_COMMON) { + $group = $this->pageparams->grouptype; + } else { + if ($this->pageparams->group) { + $group = $this->pageparams->group; + } + } + + $totalusers = count_enrolled_users(get_context_instance(CONTEXT_MODULE, $this->cm->id), 'mod/attendance:canbelisted', $group); + $usersperpage = $this->pageparams->perpage; + + if (!empty($this->pageparams->page) && $this->pageparams->page && $totalusers && $usersperpage) { + $numberofpages = ceil($totalusers / $usersperpage); + if ($this->pageparams->page < $numberofpages) { + $params['page'] = $this->pageparams->page + 1; + redirect($this->url_take($params), get_string('moreattendance', 'attendance')); + } + } + redirect($this->url_manage(), get_string('attendancesuccess', 'attendance')); } /** * MDL-27591 made this method obsolete. */ - public function get_users($groupid = 0) { + public function get_users($groupid = 0, $page = 1) { global $DB; // Fields we need from the user table. @@ -905,7 +925,14 @@ class attendance { $orderby = "u.lastname ASC, u.firstname ASC"; } - $users = get_enrolled_users($this->context, 'mod/attendance:canbelisted', $groupid, $userfields, $orderby); + if ($page) { + $totalusers = count_enrolled_users($this->context, 'mod/attendance:canbelisted', $groupid); + $usersperpage = $this->pageparams->perpage; + $startusers = ($page - 1) * $usersperpage; + $users = get_enrolled_users($this->context, 'mod/attendance:canbelisted', $groupid, $userfields, $orderby, $startusers, $usersperpage); + } else { + $users = get_enrolled_users($this->context, 'mod/attendance:canbelisted', $groupid, $userfields, $orderby); + } // Add a flag to each user indicating whether their enrolment is active. if (!empty($users)) { diff --git a/manage.php b/manage.php index 03a394c..0099d5e 100644 --- a/manage.php +++ b/manage.php @@ -31,6 +31,7 @@ $id = required_param('id', PARAM_INT); $from = optional_param('from', null, PARAM_ALPHANUMEXT); $pageparams->view = optional_param('view', null, PARAM_INT); $pageparams->curdate = optional_param('curdate', null, PARAM_INT); +$pageparams->perpage = get_config('attendance', 'resultsperpage'); $cm = get_coursemodule_from_id('attendance', $id, 0, false, MUST_EXIST); $course = $DB->get_record('course', array('id' => $cm->course), '*', MUST_EXIST); diff --git a/renderables.php b/renderables.php index 4234bcd..af38c0f 100644 --- a/renderables.php +++ b/renderables.php @@ -265,9 +265,9 @@ class attendance_take_data implements renderable { public function __construct(attendance $att) { if ($att->pageparams->grouptype) { - $this->users = $att->get_users($att->pageparams->grouptype); + $this->users = $att->get_users($att->pageparams->grouptype, $att->pageparams->page); } else { - $this->users = $att->get_users($att->pageparams->group); + $this->users = $att->get_users($att->pageparams->group, $att->pageparams->page); } $this->pageparams = $att->pageparams; @@ -458,7 +458,7 @@ class attendance_report_data implements renderable { $this->perm = $att->perm; $this->pageparams = $att->pageparams; - $this->users = $att->get_users($att->pageparams->group); + $this->users = $att->get_users($att->pageparams->group, $att->pageparams->page); $this->groups = groups_get_all_groups($att->course->id); diff --git a/renderer.php b/renderer.php index 2b7dae2..5192f2a 100644 --- a/renderer.php +++ b/renderer.php @@ -57,12 +57,14 @@ class mod_attendance_renderer extends plugin_renderer_base { $filtertable = new html_table(); $filtertable->attributes['class'] = ' '; $filtertable->width = '100%'; - $filtertable->align = array('left', 'center', 'right'); + $filtertable->align = array('left', 'center', 'right', 'right'); $filtertable->data[0][] = $this->render_sess_group_selector($fcontrols); $filtertable->data[0][] = $this->render_curdate_controls($fcontrols); + $filtertable->data[0][] = $this->render_paging_controls($fcontrols); + $filtertable->data[0][] = $this->render_view_controls($fcontrols); $o = html_writer::table($filtertable); @@ -91,6 +93,37 @@ class mod_attendance_renderer extends plugin_renderer_base { return ''; } + protected function render_paging_controls(attendance_filter_controls $fcontrols) { + global $CFG; + + $paging_controls = ''; + + $group = 0; + if (!empty($fcontrols->pageparams->group)) { + $group = $fcontrols->pageparams->group; + } + + $totalusers = count_enrolled_users(get_context_instance(CONTEXT_MODULE, $fcontrols->cm->id), 'mod/attendance:canbelisted', $group); + $usersperpage = $fcontrols->pageparams->perpage; + if (empty($fcontrols->pageparams->page) || !$fcontrols->pageparams->page || !$totalusers || !$usersperpage) { + return $paging_controls; + } + + $numberofpages = ceil($totalusers / $usersperpage); + + if ($fcontrols->pageparams->page > 1) { + $paging_controls .= html_writer::link($fcontrols->url(array('curdate' => $fcontrols->nextcur, 'page' => $fcontrols->pageparams->page - 1)), + $this->output->larrow()); + } + $paging_controls .= html_writer::tag('span', "Page {$fcontrols->pageparams->page} of $numberofpages", array('class' => 'attbtn')); + if ($fcontrols->pageparams->page < $numberofpages) { + $paging_controls .= html_writer::link($fcontrols->url(array('curdate' => $fcontrols->nextcur, 'page' => $fcontrols->pageparams->page + 1)), + $this->output->rarrow()); + } + + return $paging_controls ; + } + protected function render_curdate_controls(attendance_filter_controls $fcontrols) { global $CFG; @@ -280,7 +313,7 @@ class mod_attendance_renderer extends plugin_renderer_base { } else { $table = $this->render_attendance_take_grid($takedata); } - $table .= html_writer::input_hidden_params($takedata->url(array('sesskey' => sesskey()))); + $table .= html_writer::input_hidden_params($takedata->url(array('sesskey' => sesskey(), 'page' => $takedata->pageparams->page))); $params = array( 'type' => 'submit', 'value' => get_string('save', 'attendance')); @@ -316,6 +349,31 @@ class mod_attendance_renderer extends plugin_renderer_base { private function construct_take_controls(attendance_take_data $takedata) { $controls = ''; + + $group = 0; + if ($takedata->pageparams->grouptype != attendance::SESSION_COMMON) { + $group = $takedata->pageparams->grouptype; + } else { + if ($takedata->pageparams->group) { + $group = $takedata->pageparams->group; + } + } + + $totalusers = count_enrolled_users(get_context_instance(CONTEXT_MODULE, $takedata->cm->id), 'mod/attendance:canbelisted', $group); + $usersperpage = $takedata->pageparams->perpage; + if (!empty($takedata->pageparams->page) && $takedata->pageparams->page && $totalusers && $usersperpage) { + $controls .= html_writer::empty_tag('br'); + $numberofpages = ceil($totalusers / $usersperpage); + + if ($takedata->pageparams->page > 1) { + $controls .= html_writer::link($takedata->url(array('page' => $takedata->pageparams->page - 1)), $this->output->larrow()); + } + $controls .= html_writer::tag('span', "Page {$takedata->pageparams->page} of $numberofpages", array('class' => 'attbtn')); + if ($takedata->pageparams->page < $numberofpages) { + $controls .= html_writer::link($takedata->url(array('page' => $takedata->pageparams->page + 1)), $this->output->rarrow()); + } + } + if ($takedata->pageparams->grouptype == attendance::SESSION_COMMON and ($takedata->groupmode == VISIBLEGROUPS or ($takedata->groupmode and $takedata->perm->can_access_all_groups()))) { diff --git a/report.php b/report.php index 032c4fd..8a4d4cf 100644 --- a/report.php +++ b/report.php @@ -33,6 +33,8 @@ $pageparams->view = optional_param('view', null, PARAM_INT); $pageparams->curdate = optional_param('curdate', null, PARAM_INT); $pageparams->group = optional_param('group', null, PARAM_INT); $pageparams->sort = optional_param('sort', null, PARAM_INT); +$pageparams->page = optional_param('page', 1, PARAM_INT); +$pageparams->perpage = get_config('attendance', 'resultsperpage'); $cm = get_coursemodule_from_id('attendance', $id, 0, false, MUST_EXIST); $course = $DB->get_record('course', array('id' => $cm->course), '*', MUST_EXIST); diff --git a/settings.php b/settings.php new file mode 100644 index 0000000..66c5805 --- /dev/null +++ b/settings.php @@ -0,0 +1,44 @@ +. + +/** + * Attendance plugin settings + * + * @package mod_attendance + * @copyright 2013 Netspot, Tim Lock. + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + +defined('MOODLE_INTERNAL') || die; + +if ($ADMIN->fulltree) { + require_once(dirname(__FILE__).'/lib.php'); + + // Paging options. + $options = array( + 0 => get_string('donotusepaging', 'attendance'), + 25 => 25, + 50 => 50, + 75 => 75, + 100 => 100, + 250 => 250, + 500 => 500, + 1000 => 1000, + ); + + $settings->add(new admin_setting_configselect('attendance/resultsperpage', + get_string('resultsperpage', 'attendance'), get_string('resultsperpage_desc', 'attendance'), 25, $options)); +} diff --git a/take.php b/take.php index d7c7ac0..4452927 100644 --- a/take.php +++ b/take.php @@ -34,6 +34,8 @@ $pageparams->sort = optional_param('sort', null, PARAM_INT); $pageparams->copyfrom = optional_param('copyfrom', null, PARAM_INT); $pageparams->viewmode = optional_param('viewmode', null, PARAM_INT); $pageparams->gridcols = optional_param('gridcols', null, PARAM_INT); +$pageparams->page = optional_param('page', 1, PARAM_INT); +$pageparams->perpage = get_config('attendance', 'resultsperpage'); $cm = get_coursemodule_from_id('attendance', $id, 0, false, MUST_EXIST); $course = $DB->get_record('course', array('id' => $cm->course), '*', MUST_EXIST); From a10d92e882a41b211dd30b556b9f93c51aa281f5 Mon Sep 17 00:00:00 2001 From: Tim Lock Date: Thu, 12 Sep 2013 13:38:27 +0930 Subject: [PATCH 06/75] Add validation rule for session days if they are empty when creating multiple sessions --- add_form.php | 6 ++++++ lang/en/attendance.php | 1 + 2 files changed, 7 insertions(+) diff --git a/add_form.php b/add_form.php index dabaeb1..51bffba 100644 --- a/add_form.php +++ b/add_form.php @@ -161,6 +161,12 @@ class mod_attendance_add_form extends moodleform { if ($data['sessiontype'] == attendance::SESSION_GROUP and empty($data['groups'])) { $errors['groups'] = get_string('errorgroupsnotselected', 'attendance'); } + + $addmulti = isset($data['addmultiply'])? (int)$data['addmultiply'] : 0; + if (($addmulti != 0) && (!array_key_exists('sdays',$data) || empty($data['sdays']))) { + $data['sdays']= array(); + $errors['sdays'] = get_string('required', 'attendance'); + } return $errors; } diff --git a/lang/en/attendance.php b/lang/en/attendance.php index 9d4387a..f79b88a 100755 --- a/lang/en/attendance.php +++ b/lang/en/attendance.php @@ -153,6 +153,7 @@ $string['pluginname'] = 'Attendance'; $string['pluginadministration'] = 'Attendance administration'; $string['remarks'] = 'Remarks'; $string['report'] = 'Report'; +$string['required'] = 'Required*'; $string['resetdescription'] = 'Remember that deleting attendance data will erase information from database. You can just hide older sessions having changed start date of course!'; $string['resetstatuses'] = 'Reset statuses to default'; $string['restoredefaults'] = 'Restore defaults'; From fb8f7ced16e1b61ef8829e0b2c489d1e3a48dbc6 Mon Sep 17 00:00:00 2001 From: Tim Lock Date: Thu, 12 Sep 2013 13:39:13 +0930 Subject: [PATCH 07/75] Add validation rule so session end date must be after session start date --- add_form.php | 4 ++++ lang/en/attendance.php | 1 + 2 files changed, 5 insertions(+) diff --git a/add_form.php b/add_form.php index 51bffba..6cec532 100644 --- a/add_form.php +++ b/add_form.php @@ -158,6 +158,10 @@ class mod_attendance_add_form extends moodleform { public function validation($data, $files) { $errors = parent::validation($data, $files); + if ($data['sessiondate'] != 0 && $data['sessionenddate'] != 0 && $data['sessionenddate'] < $data['sessiondate']) { + $errors['sessionenddate'] = get_string('invalidsessionenddate', 'attendance'); + } + if ($data['sessiontype'] == attendance::SESSION_GROUP and empty($data['groups'])) { $errors['groups'] = get_string('errorgroupsnotselected', 'attendance'); } diff --git a/lang/en/attendance.php b/lang/en/attendance.php index f79b88a..3ade055 100755 --- a/lang/en/attendance.php +++ b/lang/en/attendance.php @@ -121,6 +121,7 @@ $string['identifyby'] = 'Identify student by'; $string['includeall'] = 'Select all sessions'; $string['includenottaken'] = 'Include not taken sessions'; $string['indetail'] = 'In detail...'; +$string['invalidsessionenddate'] = 'The session end date can not be earlier than the session start date'; $string['jumpto'] = 'Jump to'; $string['modulename'] = 'Attendance'; $string['modulename_help'] = 'The attendance activity module enables a teacher to take attendance during class and students to view their own attendance record. From 7ef4a5218835fb7584677d67ccfe8cda4fcaf816 Mon Sep 17 00:00:00 2001 From: NeillM Date: Mon, 16 Sep 2013 09:25:50 +0100 Subject: [PATCH 08/75] Revert "Fix for sessions with taken attendance show twice in student report." This reverts commit 5bddb944c0b912ef3f0bc74ff3d99dfae3be1300. --- locallib.php | 48 ++++++++++++++++++++++++++---------------------- 1 file changed, 26 insertions(+), 22 deletions(-) diff --git a/locallib.php b/locallib.php index a772da0..5d50ff6 100644 --- a/locallib.php +++ b/locallib.php @@ -1128,47 +1128,51 @@ class attendance { // All taked sessions (including previous groups). - $groups = array_keys(groups_get_all_groups($this->course->id, $userid)); - $groups[] = 0; - list($gsql, $gparams) = $DB->get_in_or_equal($groups, SQL_PARAMS_NAMED, 'gid0'); - if ($this->pageparams->startdate && $this->pageparams->enddate) { $where = "ats.attendanceid = :aid AND ats.sessdate >= :csdate AND ats.sessdate >= :sdate AND ats.sessdate < :edate"; - $where2 = "ats.attendanceid = :aid2 AND ats.sessdate >= :csdate2 AND - ats.sessdate >= :sdate2 AND ats.sessdate < :edate2 AND ats.groupid $gsql"; } else { $where = "ats.attendanceid = :aid AND ats.sessdate >= :csdate"; - $where2 = "ats.attendanceid = :aid2 AND ats.sessdate >= :csdate2 AND ats.groupid $gsql"; } $sql = "SELECT ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks FROM {attendance_sessions} ats - RIGHT JOIN {attendance_log} al + RIGHT JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid WHERE $where - UNION - SELECT ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks - FROM {attendance_sessions} ats - LEFT JOIN {attendance_log} al - ON ats.id = al.sessionid AND al.studentid = :uid2 - WHERE $where2 - ORDER BY sessdate ASC"; + ORDER BY ats.sessdate ASC"; $params = array( 'uid' => $userid, 'aid' => $this->id, 'csdate' => $this->course->startdate, 'sdate' => $this->pageparams->startdate, - 'edate' => $this->pageparams->enddate, - 'uid2' => $userid, - 'aid2' => $this->id, - 'csdate2' => $this->course->startdate, - 'sdate2' => $this->pageparams->startdate, - 'edate2' => $this->pageparams->enddate); - $params = array_merge($params, $gparams); + 'edate' => $this->pageparams->enddate); $sessions = $DB->get_records_sql($sql, $params); + // All sessions for current groups. + + $groups = array_keys(groups_get_all_groups($this->course->id, $userid)); + $groups[] = 0; + list($gsql, $gparams) = $DB->get_in_or_equal($groups, SQL_PARAMS_NAMED, 'gid0'); + + if ($this->pageparams->startdate && $this->pageparams->enddate) { + $where = "ats.attendanceid = :aid AND ats.sessdate >= :csdate AND + ats.sessdate >= :sdate AND ats.sessdate < :edate AND ats.groupid $gsql"; + } else { + $where = "ats.attendanceid = :aid AND ats.sessdate >= :csdate AND ats.groupid $gsql"; + } + + $sql = "SELECT ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks + FROM {attendance_sessions} ats + LEFT JOIN {attendance_log} al + ON ats.id = al.sessionid AND al.studentid = :uid + WHERE $where + ORDER BY ats.sessdate ASC"; + + $params = array_merge($params, $gparams); + $sessions = array_merge($sessions, $DB->get_records_sql($sql, $params)); + foreach ($sessions as $sess) { if (empty($sess->description)) { $sess->description = get_string('nodescription', 'attendance'); From 47d04704c6470e3883bc6ffa835c343c78b0f6b8 Mon Sep 17 00:00:00 2001 From: NeillM Date: Mon, 16 Sep 2013 09:51:34 +0100 Subject: [PATCH 09/75] Duplicate fix that will work on MSSQL --- locallib.php | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/locallib.php b/locallib.php index 5d50ff6..011c56c 100644 --- a/locallib.php +++ b/locallib.php @@ -1135,7 +1135,12 @@ class attendance { $where = "ats.attendanceid = :aid AND ats.sessdate >= :csdate"; } - $sql = "SELECT ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks + // We need to add this concatination so that moodle will use it as the array index that is a string. + // If the array's index is a number it will not merge entries. + // It would be better as a UNION query butunfortunatly MS SQL does not seem to support doing a DISTINCT on a the description field. + $id = $DB->sql_concat(':value', 'ats.id'); + + $sql = "SELECT $id, ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks FROM {attendance_sessions} ats RIGHT JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid @@ -1147,7 +1152,8 @@ class attendance { 'aid' => $this->id, 'csdate' => $this->course->startdate, 'sdate' => $this->pageparams->startdate, - 'edate' => $this->pageparams->enddate); + 'edate' => $this->pageparams->enddate, + 'value' => 'c'); $sessions = $DB->get_records_sql($sql, $params); // All sessions for current groups. @@ -1163,7 +1169,7 @@ class attendance { $where = "ats.attendanceid = :aid AND ats.sessdate >= :csdate AND ats.groupid $gsql"; } - $sql = "SELECT ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks + $sql = "SELECT $id, ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks FROM {attendance_sessions} ats LEFT JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid From cfc9f351cfd4b4eb6e942c37bd32c666366b20d4 Mon Sep 17 00:00:00 2001 From: Tim Lock Date: Thu, 19 Sep 2013 07:39:13 +0930 Subject: [PATCH 10/75] Fixed validation rule for multiple sessions that end date must be after start date --- add_form.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/add_form.php b/add_form.php index 6cec532..4026324 100644 --- a/add_form.php +++ b/add_form.php @@ -158,7 +158,7 @@ class mod_attendance_add_form extends moodleform { public function validation($data, $files) { $errors = parent::validation($data, $files); - if ($data['sessiondate'] != 0 && $data['sessionenddate'] != 0 && $data['sessionenddate'] < $data['sessiondate']) { + if (!empty($data['addmultiply']) && $data['sessiondate'] != 0 && $data['sessionenddate'] != 0 && $data['sessionenddate'] < $data['sessiondate']) { $errors['sessionenddate'] = get_string('invalidsessionenddate', 'attendance'); } From 5cd532f951fd56007ea46b4562f70dbe6df5b47e Mon Sep 17 00:00:00 2001 From: Tim Lock Date: Wed, 2 Oct 2013 12:30:48 +0930 Subject: [PATCH 11/75] On upgrade, update grade items to 'attendance' --- locallib.php | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/locallib.php b/locallib.php index 011c56c..28a081e 100644 --- a/locallib.php +++ b/locallib.php @@ -1432,6 +1432,12 @@ function attforblock_upgrade() { $module->name = 'attendance'; $DB->update_record('modules', $module); + // Now convert grade items to 'attendance' + $sql = "UPDATE {grade_items} + SET itemmodule = ? + WHERE itemmodule = ?"; + $DB->execute($sql, array('attendance', 'attforblock')); + // Clear cache for courses with attendances. $attendances = $DB->get_recordset('attendance', array(), '', 'course'); foreach ($attendances as $attendance) { From 5b1c00e09eaaf871cc5917af195fef50adfeb426 Mon Sep 17 00:00:00 2001 From: Tim Lock Date: Mon, 28 Oct 2013 09:39:59 +1030 Subject: [PATCH 12/75] Fix capability upgrade issues for Attendance --- locallib.php | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/locallib.php b/locallib.php index 28a081e..f377c18 100644 --- a/locallib.php +++ b/locallib.php @@ -1438,6 +1438,13 @@ function attforblock_upgrade() { WHERE itemmodule = ?"; $DB->execute($sql, array('attendance', 'attforblock')); + // Now convert role capabilities to 'attendance' + $sql = "UPDATE {role_capabilities} + SET capability = REPLACE(capability, ?, ?) + WHERE " . $DB->sql_like('capability', '?'); + $params = array("mod/attforblock:", "mod/attendance:", "mod/attforblock:%"); + $DB->execute($sql, $params); + // Clear cache for courses with attendances. $attendances = $DB->get_recordset('attendance', array(), '', 'course'); foreach ($attendances as $attendance) { From 3e0f9f046483c0da69e36077e190c511f5e3802a Mon Sep 17 00:00:00 2001 From: Tim Lock Date: Fri, 1 Nov 2013 15:24:03 +1030 Subject: [PATCH 13/75] Show Common groups always --- locallib.php | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/locallib.php b/locallib.php index f377c18..e836788 100644 --- a/locallib.php +++ b/locallib.php @@ -329,9 +329,8 @@ class att_page_with_filter_controls { if ($groupmode == VISIBLEGROUPS or has_capability('moodle/site:accessallgroups', $PAGE->context)) { $this->sessgroupslist[self::SESSTYPE_ALL] = get_string('all', 'attendance'); } - if ($groupmode == VISIBLEGROUPS) { - $this->sessgroupslist[self::SESSTYPE_COMMON] = get_string('commonsessions', 'attendance'); - } + // Show Common groups always + $this->sessgroupslist[self::SESSTYPE_COMMON] = get_string('commonsessions', 'attendance'); foreach ($allowedgroups as $group) { $this->sessgroupslist[$group->id] = format_string($group->name); } From c9de75091a8c272a719fbbd5462e4bfcc7921b2a Mon Sep 17 00:00:00 2001 From: Gregory Faller Date: Thu, 7 Nov 2013 10:47:00 +1030 Subject: [PATCH 14/75] Fix missing language strings and enable groupings Fix missing language strings and enable groupings and enablegroupmembersonly. Most places already support groupings. --- add_form.php | 4 ++-- lang/en/attendance.php | 3 +++ lib.php | 8 ++------ locallib.php | 34 +++++++++++++++++++++++++++++----- renderer.php | 17 ++++++++++++++++- 5 files changed, 52 insertions(+), 14 deletions(-) diff --git a/add_form.php b/add_form.php index 4026324..9fc813a 100644 --- a/add_form.php +++ b/add_form.php @@ -78,9 +78,9 @@ class mod_attendance_add_form extends moodleform { } if ($groupmode == SEPARATEGROUPS or $groupmode == VISIBLEGROUPS) { if ($groupmode == SEPARATEGROUPS and !has_capability('moodle/site:accessallgroups', $modcontext)) { - $groups = groups_get_all_groups ($course->id, $USER->id); + $groups = groups_get_all_groups ($course->id, $USER->id, $cm->groupingid); } else { - $groups = groups_get_all_groups($course->id); + $groups = groups_get_all_groups($course->id, 0, $cm->groupingid); } if ($groups) { $selectgroups = array(); diff --git a/lang/en/attendance.php b/lang/en/attendance.php index 3ade055..e8697a9 100755 --- a/lang/en/attendance.php +++ b/lang/en/attendance.php @@ -96,6 +96,7 @@ $string['displaymode'] = 'Display mode'; $string['downloadexcel'] = 'Download in Excel format'; $string['downloadooo'] = 'Download in OpenOffice format'; $string['downloadtext'] = 'Download in text format'; +$string['donotusepaging'] = 'Do not use paging'; $string['duration'] = 'Duration'; $string['editsession'] = 'Edit Session'; $string['endtime'] = 'Session end time'; @@ -158,6 +159,8 @@ $string['required'] = 'Required*'; $string['resetdescription'] = 'Remember that deleting attendance data will erase information from database. You can just hide older sessions having changed start date of course!'; $string['resetstatuses'] = 'Reset statuses to default'; $string['restoredefaults'] = 'Restore defaults'; +$string['resultsperpage'] = 'Results per page'; +$string['resultsperpage_desc'] = 'Number of students displayed on a page'; $string['save'] = 'Save attendance'; $string['session'] = 'Session'; $string['session_help'] = 'Session'; diff --git a/lib.php b/lib.php index 32d65e5..a13f2fe 100644 --- a/lib.php +++ b/lib.php @@ -35,14 +35,10 @@ function attendance_supports($feature) { return true; case FEATURE_GROUPS: return true; - // Artem Andreev: AFAIK it's not tested - // we need implement filtration of groups list by grouping. case FEATURE_GROUPINGS: - return false; - // Artem Andreev: AFAIK it's not tested - // harder "All courses" report. + return true; case FEATURE_GROUPMEMBERSONLY: - return false; + return true; case FEATURE_MOD_INTRO: return false; case FEATURE_BACKUP_MOODLE2: diff --git a/locallib.php b/locallib.php index e836788..4828047 100644 --- a/locallib.php +++ b/locallib.php @@ -913,7 +913,7 @@ class attendance { * MDL-27591 made this method obsolete. */ public function get_users($groupid = 0, $page = 1) { - global $DB; + global $DB, $CFG; // Fields we need from the user table. $userfields = user_picture::fields('u').',u.username'; @@ -925,12 +925,36 @@ class attendance { } if ($page) { - $totalusers = count_enrolled_users($this->context, 'mod/attendance:canbelisted', $groupid); $usersperpage = $this->pageparams->perpage; - $startusers = ($page - 1) * $usersperpage; - $users = get_enrolled_users($this->context, 'mod/attendance:canbelisted', $groupid, $userfields, $orderby, $startusers, $usersperpage); + if (!empty($CFG->enablegroupmembersonly) and $this->cm->groupmembersonly) { + $startusers = ($page - 1) * $usersperpage; + if ($groupid == 0) { + $groups = array_keys(groups_get_all_groups($this->cm->course, 0, $this->cm->groupingid, 'g.id')); + } else { + $groups = $groupid; + } + $users = get_users_by_capability($this->context, 'mod/attendance:canbelisted', + $userfields.',u.id, u.firstname, u.lastname, u.email', + $orderby, $startusers, $usersperpage, $groups, + '', false, true); + } else { + $startusers = ($page - 1) * $usersperpage; + $users = get_enrolled_users($this->context, 'mod/attendance:canbelisted', $groupid, $userfields, $orderby, $startusers, $usersperpage); + } } else { - $users = get_enrolled_users($this->context, 'mod/attendance:canbelisted', $groupid, $userfields, $orderby); + if (!empty($CFG->enablegroupmembersonly) and $this->cm->groupmembersonly) { + if ($groupid == 0) { + $groups = array_keys(groups_get_all_groups($this->cm->course, 0, $this->cm->groupingid, 'g.id')); + } else { + $groups = $groupid; + } + $users = get_users_by_capability($this->context, 'mod/attendance:canbelisted', + $userfields.',u.id, u.firstname, u.lastname, u.email', + $orderby, '', '', $groups, + '', false, true); + } else { + $users = get_enrolled_users($this->context, 'mod/attendance:canbelisted', $groupid, $userfields, $orderby); + } } // Add a flag to each user indicating whether their enrolment is active. diff --git a/renderer.php b/renderer.php index 5192f2a..c335682 100644 --- a/renderer.php +++ b/renderer.php @@ -348,6 +348,8 @@ class mod_attendance_renderer extends plugin_renderer_base { } private function construct_take_controls(attendance_take_data $takedata) { + GLOBAL $CFG; + $controls = ''; $group = 0; @@ -359,7 +361,20 @@ class mod_attendance_renderer extends plugin_renderer_base { } } - $totalusers = count_enrolled_users(get_context_instance(CONTEXT_MODULE, $takedata->cm->id), 'mod/attendance:canbelisted', $group); + if (!empty($CFG->enablegroupmembersonly) and $takedata->cm->groupmembersonly) { + if ($group == 0) { + $groups = array_keys(groups_get_all_groups($takedata->cm->course, 0, $takedata->cm->groupingid, 'g.id')); + } else { + $groups = $group; + } + $users = get_users_by_capability(get_context_instance(CONTEXT_MODULE, $takedata->cm->id), 'mod/attendance:canbelisted', + 'u.id, u.firstname, u.lastname, u.email', + '', '', '', $groups, + '', false, true); + $totalusers = count($users); + } else { + $totalusers = count_enrolled_users(get_context_instance(CONTEXT_MODULE, $takedata->cm->id), 'mod/attendance:canbelisted', $group); + } $usersperpage = $takedata->pageparams->perpage; if (!empty($takedata->pageparams->page) && $takedata->pageparams->page && $totalusers && $usersperpage) { $controls .= html_writer::empty_tag('br'); From 4605ea942dbd90a629750b9f7b6d0cc3e972e20e Mon Sep 17 00:00:00 2001 From: Pavel Pisklakov Date: Mon, 11 Nov 2013 21:15:34 +0600 Subject: [PATCH 15/75] Added Russian Translation Added translation of module into Russian language --- lang/ru/attendance.php | 217 +++++++++++++++++++++++++++++++++++++++++ 1 file changed, 217 insertions(+) create mode 100755 lang/ru/attendance.php diff --git a/lang/ru/attendance.php b/lang/ru/attendance.php new file mode 100755 index 0000000..c091290 --- /dev/null +++ b/lang/ru/attendance.php @@ -0,0 +1,217 @@ +. + +/** + * Strings for component 'attendance', language 'ru' + * + * @package mod_attendance + * @copyright 2011 Artem Andreev + * @copyright 2013 Pavel Pisklakov (improving Russian translation) + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + +$string['attendance:addinstance'] = 'Добавить новый элемент «Посещаемость»'; +$string['Aacronym'] = 'Н'; +$string['Afull'] = 'Не был'; +$string['Eacronym'] = 'У'; +$string['Efull'] = 'Уважительная причина'; +$string['Lacronym'] = 'О'; +$string['Lfull'] = 'Опоздал'; +$string['Pacronym'] = 'П'; +$string['Pfull'] = 'Присутствовал'; +$string['acronym'] = 'Сокращ.'; +$string['add'] = 'Добавить'; +$string['addmultiplesessions'] = 'Добавить несколько занятий'; +$string['addsession'] = 'Добавить занятие'; +$string['allcourses'] = 'Все курсы'; +$string['all'] = 'Все'; +$string['allpast'] = 'Все прошедшие'; +$string['attendancedata'] = 'Информация о посещаемости'; +$string['attendanceforthecourse'] = 'Посещаемость для курса'; +$string['attendancegrade'] = 'Оценка за посещаемость'; +$string['attendancenotstarted'] = 'Пока нет отметок о посещаемости в данном курсе'; +$string['attendancepercent'] = 'Процент посещаемости'; +$string['attendancereport'] = 'Отчет о посещаемости'; +$string['attendancesuccess'] = 'Информация о присутствии успешно запомнена'; +$string['attendanceupdated'] = 'Информация о присутствии успешно обновлена'; +$string['attendance:canbelisted'] = 'Отображается в реестре'; +$string['attendance:changepreferences'] = 'Изменение настроек'; +$string['attendance:changeattendances'] = 'Редактирование посещаемости'; +$string['attendance:export'] = 'Экспорт отчетов'; +$string['attendance:manageattendances'] = 'Управление посещаемостью'; +$string['attendance:takeattendances'] = 'Отметка посещаемости'; +$string['attendance:view'] = 'Просмотр посещаемости'; +$string['attendance:viewreports'] = 'Просмотр отчетов'; +$string['attforblockdirstillexists'] = 'старый каталог mod/attforblock еще существует - вы должны удалить его на сервере перед запуском этого обновления.'; +$string['attrecords'] = 'Отметок о посещаемости'; +$string['calclose'] = 'Закрыть'; +$string['calmonths'] = 'Январь,Февраль,Март,Апрель,Май,Июнь,Июль,Август,Сентябрь,Октябрь,Ноябрь,Декабрь'; +$string['calshow'] = 'Выбрать дату'; +$string['caltoday'] = 'Сегодня'; +$string['calweekdays'] = 'Вс,Пн,Вт,Ср,Чт,Пт,Сб'; +$string['cannottakeforgroup'] = 'Вы не можете отмечать посещаемость для группы «{$a}»'; +$string['changeattendance'] = 'Изменить посещаемость'; +$string['changeduration'] = 'Изменить продолжительность'; +$string['changesession'] = 'Изменить занятие'; +$string['column'] = 'колонка'; +$string['columns'] = 'колонок'; +$string['commonsession'] = 'Общее'; +$string['commonsessions'] = 'Общие'; +$string['countofselected'] = 'Выбрано занятий'; +$string['copyfrom'] = 'Копировать данные посещаемости из занятия'; +$string['createmultiplesessions'] = 'Создать несколько занятий'; +$string['createmultiplesessions_help'] = 'Эта функция позволяет создать несколько занятий за один шаг. + + * Дата начала занятий: Выберите дату начала вашего курса (первый день занятий) + * Дата завершения занятий: Выберите последний день занятий (последний день отметки вами посещаемости занятий). + * Дни занятий: Выберите дни недели, когда будут проходить занятия (например, Понедельник/Среда/Пятница). + * Периодичность: Позволяет задать частоту занятий. Если ваши занятия будут проходить каждую неделю, выберите 1; если раз в две недели — выберите 2; раз втри недели — выберите 3 и т.д. +'; +$string['createonesession'] = 'Создать одно занятие для курса'; +$string['days'] = 'День'; +$string['defaults'] = 'По умолчанию'; +$string['defaultdisplaymode'] = 'Режим отображения по умолчанию'; +$string['delete'] = 'Удалить'; +$string['deletelogs'] = 'Удалить информацию о посещаемости'; +$string['deleteselected'] = 'Удалить выбранные'; +$string['deletesession'] = 'Удалить занятие'; +$string['deletesessions'] = 'Удалить все занятия'; +$string['deletingsession'] = 'Удаление занятия из курса'; +$string['deletingstatus'] = 'Удаление статуса из курса'; +$string['description'] = 'Описание'; +$string['display'] = 'Отображать'; +$string['displaymode'] = 'Режим отображения'; +$string['downloadexcel'] = 'Скачать в формате Excel'; +$string['downloadooo'] = 'Скачать в формате OpenOffice'; +$string['downloadtext'] = 'Скачать в текстовом формате'; +$string['donotusepaging'] = 'Не использовать разбивку на страницы'; +$string['duration'] = 'Продолжительность'; +$string['editsession'] = 'Редактировать занятие'; +$string['endtime'] = 'Время завершения занятия'; +$string['endofperiod'] = 'Конец периода'; +$string['enrolmentend'] = 'Подписка на курс заканчивается {$a}'; +$string['enrolmentstart'] = 'Подписка на курс начинается с {$a}'; +$string['enrolmentsuspended'] = 'Подписка на курс приостановлена'; +$string['errorgroupsnotselected'] = 'Выберите одну или более групп'; +$string['errorinaddingsession'] = 'Ошибка при добавлении занятия'; +$string['erroringeneratingsessions'] = 'Ошибка при создании занятий '; +$string['gradebookexplanation'] = 'Оценка в журнале оценок'; +$string['gradebookexplanation_help'] = 'Ваша оценка в модуле «Посещаемость» рассчитывается как отношение количества баллов, полученных за посещаемость до текущей даты, к максимальному количеству баллов, которые вы могли получить за посещаемость до текущей даты; будущие занятия в этой оценке не учитываются. В журнале оценок ваша оценка основывается на доле баллов, полученных за посещаемость, и максимальном количестве баллов, которые вы можете получить за посещаемость за весь курс, включая будущие занятия. Таким образом, оценки посещаемости в баллах, отображаемые в модуле «Посещаемость» и в журнале оценок могут различаться, однако доля (процент) будет совпадать. + +Например, если вы на текущий момент заработали 8 баллов из 10 (80% посещаемости) и максимальный балл за посещаемость всего курса в журнале оценок – 50, то в модуле «Посещаемость» отобразится оценка «8/10», а в журнале оценок — «40/50». Вы еще не заработали 40 баллов, но на данный момент ваш процент посещаемости (80%) соответствует этим баллам. Ваши баллы в модуле «Посещаемость» никогда не могут уменьшаться, т.к. они зависят только от посещаемости на текущую дату; однако, оценка в журнале оценок может увеличиваться и уменьшаться, в зависимости от вашей будущей успеваемости, т.к. эта оценка зависит от посещаемости на протяжении всего курса.'; +$string['gridcolumns'] = 'Колонки сетки'; +$string['groupsession'] = 'Групповое'; +$string['hiddensessions'] = 'Скрытых занятий'; +$string['hiddensessions_help'] = ' +Занятия скрываются, если их дата раньше даты начала курса. Чтобы отобразить эти занятия, измените дату начала курса. + +Эту возможность можно использовать для скрытия старых занятий, вместо их удаления. Имейте в виду, что для подсчета оценки в журнале оценок используются только видимые занятия.'; +$string['identifyby'] = 'Идентифицировать студента по'; +$string['includeall'] = 'Включить все занятия'; +$string['includenottaken'] = 'Включить не прошедшие занятия'; +$string['indetail'] = 'Подробнее...'; +$string['invalidsessionenddate'] = 'Дата завершения занятий не может быть ранее даты начала занятий'; +$string['jumpto'] = 'Перейти к занятию'; +$string['modulename'] = 'Посещаемость'; +$string['modulename_help'] = 'Модуль «Посещаемость» позволяет преподавателю вести учет посещаемости занятий, а студентам видеть информацию о их собственной посещаемости. + +Преподаватель может создать несколько занятий и отмечать посещаемость как статусы «Присутствовал», «Не был», «Опоздал», «Уважительная причина» или изменить эти статусы так, чтобы они соответствовали потребностям преподавателя. + +В модуле доступны отчеты по всем студентам или по каждому студенту отдельно.'; +$string['modulenameplural'] = 'Посещаемость'; +$string['months'] = 'Месяц'; +$string['moreattendance'] = 'Посещаемость успешно была сохранена для этой страницы'; +$string['myvariables'] = 'Мои переменные'; +$string['newdate'] = 'Новая дата'; +$string['newduration'] = 'Новая продолжительность'; +$string['noattforuser'] = 'Нет отметок посещаемости для этого пользователя'; +$string['nodescription'] = 'Обычное занятие'; +$string['noguest'] = 'Гость не может видеть информацию о посещаемости'; +$string['nogroups'] = 'Вы не можете добавлять групповые занятия. В курсе не определено ни одной группы.'; +$string['noofdaysabsent'] = 'Дней пропусков'; +$string['noofdaysexcused'] = 'Дней пропусков по ув. причине'; +$string['noofdayslate'] = 'Дней опозданий'; +$string['noofdayspresent'] = 'Дней присутствия'; +$string['nosessiondayselected'] = 'Не выбран день занятия'; +$string['nosessionexists'] = 'В данном курсе отсутствуют занятия'; +$string['nosessionsselected'] = 'Не выбрано ни одного занятия'; +$string['notfound'] = 'Элемент курса «Посещаемость» не найден в данном курсе!'; +$string['noupgradefromthisversion'] = 'Модуль «Посещаемость» не может быть обновлен с установленной у вас версии attforblock. - Удалите attforblock или обновите его до последней версии перед установкой нового модуля attendance'; +$string['olddate'] = 'Старая дата'; +$string['period'] = 'Периодичность'; +$string['pluginname'] = 'Посещаемость'; +$string['pluginadministration'] = 'Управление модулем «Посещаемость»'; +$string['remarks'] = 'Заметки'; +$string['report'] = 'Отчет'; +$string['required'] = 'Обязательное поле*'; +$string['resetdescription'] = 'Внимание! Чистка данных посещаемости удаляет информацию из БД. Вы можете просто скрыть старые занятия, изменив дату начала курса!'; +$string['resetstatuses'] = 'Восстановить набор статусов по умолчанию'; +$string['restoredefaults'] = 'Востановить значения по умолчанию'; +$string['resultsperpage'] = 'Результатов на страницу'; +$string['resultsperpage_desc'] = 'Количество студентов, отображаемых на странице'; +$string['save'] = 'Сохранить посещаемость'; +$string['session'] = 'Занятие'; +$string['session_help'] = 'Занятие'; +$string['sessionadded'] = 'Занятие успешно добавлено'; +$string['sessionalreadyexists'] = 'В этот день занятие уже существует'; +$string['sessiondate'] = 'Дата занятия'; +$string['sessiondays'] = 'Дни занятий'; +$string['sessiondeleted'] = 'Занятие успешно удалено'; +$string['sessionenddate'] = 'Дата завершения занятий'; +$string['sessionexist'] = 'Занятие не добавлено (уже существует)!'; +$string['sessions'] = 'Занятия'; +$string['sessionscompleted'] = 'Прошло занятий'; +$string['sessionsids'] = 'Идентификаторы занятий: '; +$string['sessionsgenerated'] = 'Занятия успешно созданы'; +$string['sessionsnotfound'] = 'В выбранный диапазон времени не попадает ни одно занятие'; +$string['sessionstartdate'] = 'Дата начала занятий'; +$string['sessiontype'] = 'Тип занятия'; +$string['sessiontype_help'] = 'Существует 2 типа занятий: общие и групповые. Возможность добавлять занятия различных типов зависит от группового режима элемента курса. + +* В групповом режиме «Нет групп» можно добавлять только общие занятия. +* В групповом режиме «Видимые группы» можно добавлять и общие, и групповые занятия. +* В групповом режиме «Изолированные группы» можно добавлять только групповые занятия. +'; +$string['sessiontypeshort'] = 'Тип'; +$string['sessionupdated'] = 'Занятие успешно изменено'; +$string['setallstatusesto'] = 'Установить статус для всех учащихся в «{$a}»'; +$string['settings'] = 'Настройки'; +$string['showdefaults'] = 'Показать значения по умолчанию'; +$string['showduration'] = 'Показать продолжительность'; +$string['sortedgrid'] = 'Таблица'; +$string['sortedlist'] = 'Список'; +$string['startofperiod'] = 'Начало периода'; +$string['status'] = 'Статус'; +$string['statuses'] = 'Статусы'; +$string['statusdeleted'] = 'Статус удален'; +$string['strftimedm'] = '%d.%m'; +$string['strftimedmy'] = '%d.%m.%Y'; +$string['strftimedmyhm'] = '%d.%m.%Y %H.%M'; // Line added to allow multiple sessions in the same day. +$string['strftimedmyw'] = '%d.%m.%y (%a)'; +$string['strftimehm'] = '%H:%M'; // Line added to allow display of time. +$string['strftimeshortdate'] = '%d.%m.%Y'; +$string['studentid'] = 'ID студента'; +$string['takeattendance'] = 'Отметить посещаемость'; +$string['thiscourse'] = 'Текущий курс'; +$string['tablerenamefailed'] = 'Переименование страой таблицы attforblock в attendance не удалось'; +$string['update'] = 'Обновить'; +$string['variable'] = 'переменную'; +$string['variablesupdated'] = 'Переменные успешно обновлены'; +$string['versionforprinting'] = 'версия для печати'; +$string['viewmode'] = 'Режим просмотра'; +$string['week'] = 'неделя(и)'; +$string['weeks'] = 'Неделя'; +$string['youcantdo'] = 'Вы ничего не можете сделать'; From 913246c0867ab88ffaeaad3d147c699ada62f309 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 29 Nov 2013 14:43:47 +1300 Subject: [PATCH 16/75] add missing grade_items_history upgrade step --- locallib.php | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/locallib.php b/locallib.php index 4828047..b2e6552 100644 --- a/locallib.php +++ b/locallib.php @@ -1461,6 +1461,11 @@ function attforblock_upgrade() { WHERE itemmodule = ?"; $DB->execute($sql, array('attendance', 'attforblock')); + $sql = "UPDATE {grade_items_history} + SET itemmodule = 'attendance' + WHERE itemmodule = 'attforblock'"; + $DB->execute($sql); + // Now convert role capabilities to 'attendance' $sql = "UPDATE {role_capabilities} SET capability = REPLACE(capability, ?, ?) From 68c8ff6626f1e4b061582864d2e4231fb8679189 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 29 Nov 2013 14:50:55 +1300 Subject: [PATCH 17/75] use cross-db update of capabilities --- locallib.php | 27 +++++++++++++++++++++------ 1 file changed, 21 insertions(+), 6 deletions(-) diff --git a/locallib.php b/locallib.php index b2e6552..a645366 100644 --- a/locallib.php +++ b/locallib.php @@ -1466,12 +1466,27 @@ function attforblock_upgrade() { WHERE itemmodule = 'attforblock'"; $DB->execute($sql); - // Now convert role capabilities to 'attendance' - $sql = "UPDATE {role_capabilities} - SET capability = REPLACE(capability, ?, ?) - WHERE " . $DB->sql_like('capability', '?'); - $params = array("mod/attforblock:", "mod/attendance:", "mod/attforblock:%"); - $DB->execute($sql, $params); + /* + * The user's custom capabilities need to be preserved due to the module renaming. + * Capabilities with a modifierid = 0 value are installed by default. + * Only update the user's custom capabilities where modifierid is not zero. + */ + $sql = $DB->sql_like('capability', '?').' AND modifierid <> 0'; + $rs = $DB->get_recordset_select('role_capabilities', $sql, array('%mod/attforblock%')); + foreach ($rs as $cap) { + $renamedcapability = str_replace('mod/attforblock', 'mod/attendance', $cap->capability); + $exists = $DB->record_exists('role_capabilities', array('roleid' => $cap->roleid, 'capability' => $renamedcapability)); + if (!$exists) { + $DB->update_record('role_capabilities', array('id' => $cap->id, 'capability' => $renamedcapability)); + } + } + + // Delete old role capabilities. + $sql = $DB->sql_like('capability', '?'); + $DB->delete_records_select('role_capabilities', $sql, array('%mod/attforblock%')); + + // Delete old capabilities. + $DB->delete_records_select('capabilities', 'component = ?', array('mod_attforblock')); // Clear cache for courses with attendances. $attendances = $DB->get_recordset('attendance', array(), '', 'course'); From 6ef315d0943ec63d769105c6b3bc60217f25be29 Mon Sep 17 00:00:00 2001 From: Tim Gus Date: Thu, 28 Nov 2013 16:27:20 -0500 Subject: [PATCH 18/75] CONTRIB-4754 Added upgrade step to account for name change from "attforblock" to "attendance": - updated itemmodule field in the grade tables - updated role_capabilities table to preserve old capabilities - deleted old data from capabilities and role_capabilities tables --- db/upgrade.php | 40 +++++++++++++++++++++++++++++++++++++++- version.php | 2 +- 2 files changed, 40 insertions(+), 2 deletions(-) diff --git a/db/upgrade.php b/db/upgrade.php index 0e9336d..c00926f 100644 --- a/db/upgrade.php +++ b/db/upgrade.php @@ -34,6 +34,44 @@ function xmldb_attendance_upgrade($oldversion=0) { $result = true; - // UPGRADES from attforblock are only supported for sites that are running attforblock version 2012120700. + if ($oldversion < 2013082902) { + // Replace values that reference old module "attforblock" to "attendance". + $sql = "UPDATE {grade_items} + SET itemmodule = 'attendance' + WHERE itemmodule = 'attforblock'"; + + $DB->execute($sql); + + $sql = "UPDATE {grade_items_history} + SET itemmodule = 'attendance' + WHERE itemmodule = 'attforblock'"; + + $DB->execute($sql); + + /* + * The user's custom capabilities need to be preserved due to the module renaming. + * Capabilities with a modifierid = 0 value are installed by default. + * Only update the user's custom capabilities where modifierid is not zero. + */ + $sql = $DB->sql_like('capability', '?').' AND modifierid <> 0'; + $rs = $DB->get_recordset_select('role_capabilities', $sql, array('%mod/attforblock%')); + foreach ($rs as $cap) { + $renamedcapability = str_replace('mod/attforblock', 'mod/attendance', $cap->capability); + $exists = $DB->record_exists('role_capabilities', array('roleid' => $cap->roleid, 'capability' => $renamedcapability)); + if (!$exists) { + $DB->update_record('role_capabilities', array('id' => $cap->id, 'capability' => $renamedcapability)); + } + } + + // Delete old role capabilities. + $sql = $DB->sql_like('capability', '?'); + $DB->delete_records_select('role_capabilities', $sql, array('%mod/attforblock%')); + + // Delete old capabilities. + $DB->delete_records_select('capabilities', 'component = ?', array('mod_attforblock')); + + upgrade_plugin_savepoint($result, 2013082902, 'mod', 'attendance'); + } + return $result; } diff --git a/version.php b/version.php index 2a10679..1cfb89d 100644 --- a/version.php +++ b/version.php @@ -22,7 +22,7 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -$module->version = 2013082901; +$module->version = 2013082902; $module->requires = 2013040500; $module->release = '2.5.2'; $module->maturity = MATURITY_STABLE; From 8758c451606680c9af242728becf4a69f587c7f2 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 29 Nov 2013 14:59:30 +1300 Subject: [PATCH 19/75] bump version to release to plugins db --- version.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.php b/version.php index 1cfb89d..bacd533 100644 --- a/version.php +++ b/version.php @@ -24,7 +24,7 @@ $module->version = 2013082902; $module->requires = 2013040500; -$module->release = '2.5.2'; +$module->release = '2.5.3'; $module->maturity = MATURITY_STABLE; $module->cron = 0; $module->component = 'mod_attendance'; From b451aed01f9767247001a18d687382b87779f600 Mon Sep 17 00:00:00 2001 From: Pavel Pisklakov Date: Sat, 30 Nov 2013 02:32:49 +0600 Subject: [PATCH 20/75] Changed deprecated get_context_instance to context_module::instance --- renderer.php | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) mode change 100644 => 100755 renderer.php diff --git a/renderer.php b/renderer.php old mode 100644 new mode 100755 index c335682..6e0264e --- a/renderer.php +++ b/renderer.php @@ -103,7 +103,7 @@ class mod_attendance_renderer extends plugin_renderer_base { $group = $fcontrols->pageparams->group; } - $totalusers = count_enrolled_users(get_context_instance(CONTEXT_MODULE, $fcontrols->cm->id), 'mod/attendance:canbelisted', $group); + $totalusers = count_enrolled_users(context_module::instance($fcontrols->cm->id), 'mod/attendance:canbelisted', $group); $usersperpage = $fcontrols->pageparams->perpage; if (empty($fcontrols->pageparams->page) || !$fcontrols->pageparams->page || !$totalusers || !$usersperpage) { return $paging_controls; @@ -367,13 +367,13 @@ class mod_attendance_renderer extends plugin_renderer_base { } else { $groups = $group; } - $users = get_users_by_capability(get_context_instance(CONTEXT_MODULE, $takedata->cm->id), 'mod/attendance:canbelisted', + $users = get_users_by_capability(context_module::instance($takedata->cm->id), 'mod/attendance:canbelisted', 'u.id, u.firstname, u.lastname, u.email', '', '', '', $groups, '', false, true); $totalusers = count($users); } else { - $totalusers = count_enrolled_users(get_context_instance(CONTEXT_MODULE, $takedata->cm->id), 'mod/attendance:canbelisted', $group); + $totalusers = count_enrolled_users(context_module::instance($takedata->cm->id), 'mod/attendance:canbelisted', $group); } $usersperpage = $takedata->pageparams->perpage; if (!empty($takedata->pageparams->page) && $takedata->pageparams->page && $totalusers && $usersperpage) { From 0116ecc7d3e5ab21a6bb7e0bd1798ec783211a79 Mon Sep 17 00:00:00 2001 From: Pavel Pisklakov Date: Sat, 30 Nov 2013 10:16:39 +0600 Subject: [PATCH 21/75] Added Russian translation to AMOS --- lang/ru/attendance.php | 217 ----------------------------------------- 1 file changed, 217 deletions(-) delete mode 100755 lang/ru/attendance.php diff --git a/lang/ru/attendance.php b/lang/ru/attendance.php deleted file mode 100755 index c091290..0000000 --- a/lang/ru/attendance.php +++ /dev/null @@ -1,217 +0,0 @@ -. - -/** - * Strings for component 'attendance', language 'ru' - * - * @package mod_attendance - * @copyright 2011 Artem Andreev - * @copyright 2013 Pavel Pisklakov (improving Russian translation) - * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later - */ - -$string['attendance:addinstance'] = 'Добавить новый элемент «Посещаемость»'; -$string['Aacronym'] = 'Н'; -$string['Afull'] = 'Не был'; -$string['Eacronym'] = 'У'; -$string['Efull'] = 'Уважительная причина'; -$string['Lacronym'] = 'О'; -$string['Lfull'] = 'Опоздал'; -$string['Pacronym'] = 'П'; -$string['Pfull'] = 'Присутствовал'; -$string['acronym'] = 'Сокращ.'; -$string['add'] = 'Добавить'; -$string['addmultiplesessions'] = 'Добавить несколько занятий'; -$string['addsession'] = 'Добавить занятие'; -$string['allcourses'] = 'Все курсы'; -$string['all'] = 'Все'; -$string['allpast'] = 'Все прошедшие'; -$string['attendancedata'] = 'Информация о посещаемости'; -$string['attendanceforthecourse'] = 'Посещаемость для курса'; -$string['attendancegrade'] = 'Оценка за посещаемость'; -$string['attendancenotstarted'] = 'Пока нет отметок о посещаемости в данном курсе'; -$string['attendancepercent'] = 'Процент посещаемости'; -$string['attendancereport'] = 'Отчет о посещаемости'; -$string['attendancesuccess'] = 'Информация о присутствии успешно запомнена'; -$string['attendanceupdated'] = 'Информация о присутствии успешно обновлена'; -$string['attendance:canbelisted'] = 'Отображается в реестре'; -$string['attendance:changepreferences'] = 'Изменение настроек'; -$string['attendance:changeattendances'] = 'Редактирование посещаемости'; -$string['attendance:export'] = 'Экспорт отчетов'; -$string['attendance:manageattendances'] = 'Управление посещаемостью'; -$string['attendance:takeattendances'] = 'Отметка посещаемости'; -$string['attendance:view'] = 'Просмотр посещаемости'; -$string['attendance:viewreports'] = 'Просмотр отчетов'; -$string['attforblockdirstillexists'] = 'старый каталог mod/attforblock еще существует - вы должны удалить его на сервере перед запуском этого обновления.'; -$string['attrecords'] = 'Отметок о посещаемости'; -$string['calclose'] = 'Закрыть'; -$string['calmonths'] = 'Январь,Февраль,Март,Апрель,Май,Июнь,Июль,Август,Сентябрь,Октябрь,Ноябрь,Декабрь'; -$string['calshow'] = 'Выбрать дату'; -$string['caltoday'] = 'Сегодня'; -$string['calweekdays'] = 'Вс,Пн,Вт,Ср,Чт,Пт,Сб'; -$string['cannottakeforgroup'] = 'Вы не можете отмечать посещаемость для группы «{$a}»'; -$string['changeattendance'] = 'Изменить посещаемость'; -$string['changeduration'] = 'Изменить продолжительность'; -$string['changesession'] = 'Изменить занятие'; -$string['column'] = 'колонка'; -$string['columns'] = 'колонок'; -$string['commonsession'] = 'Общее'; -$string['commonsessions'] = 'Общие'; -$string['countofselected'] = 'Выбрано занятий'; -$string['copyfrom'] = 'Копировать данные посещаемости из занятия'; -$string['createmultiplesessions'] = 'Создать несколько занятий'; -$string['createmultiplesessions_help'] = 'Эта функция позволяет создать несколько занятий за один шаг. - - * Дата начала занятий: Выберите дату начала вашего курса (первый день занятий) - * Дата завершения занятий: Выберите последний день занятий (последний день отметки вами посещаемости занятий). - * Дни занятий: Выберите дни недели, когда будут проходить занятия (например, Понедельник/Среда/Пятница). - * Периодичность: Позволяет задать частоту занятий. Если ваши занятия будут проходить каждую неделю, выберите 1; если раз в две недели — выберите 2; раз втри недели — выберите 3 и т.д. -'; -$string['createonesession'] = 'Создать одно занятие для курса'; -$string['days'] = 'День'; -$string['defaults'] = 'По умолчанию'; -$string['defaultdisplaymode'] = 'Режим отображения по умолчанию'; -$string['delete'] = 'Удалить'; -$string['deletelogs'] = 'Удалить информацию о посещаемости'; -$string['deleteselected'] = 'Удалить выбранные'; -$string['deletesession'] = 'Удалить занятие'; -$string['deletesessions'] = 'Удалить все занятия'; -$string['deletingsession'] = 'Удаление занятия из курса'; -$string['deletingstatus'] = 'Удаление статуса из курса'; -$string['description'] = 'Описание'; -$string['display'] = 'Отображать'; -$string['displaymode'] = 'Режим отображения'; -$string['downloadexcel'] = 'Скачать в формате Excel'; -$string['downloadooo'] = 'Скачать в формате OpenOffice'; -$string['downloadtext'] = 'Скачать в текстовом формате'; -$string['donotusepaging'] = 'Не использовать разбивку на страницы'; -$string['duration'] = 'Продолжительность'; -$string['editsession'] = 'Редактировать занятие'; -$string['endtime'] = 'Время завершения занятия'; -$string['endofperiod'] = 'Конец периода'; -$string['enrolmentend'] = 'Подписка на курс заканчивается {$a}'; -$string['enrolmentstart'] = 'Подписка на курс начинается с {$a}'; -$string['enrolmentsuspended'] = 'Подписка на курс приостановлена'; -$string['errorgroupsnotselected'] = 'Выберите одну или более групп'; -$string['errorinaddingsession'] = 'Ошибка при добавлении занятия'; -$string['erroringeneratingsessions'] = 'Ошибка при создании занятий '; -$string['gradebookexplanation'] = 'Оценка в журнале оценок'; -$string['gradebookexplanation_help'] = 'Ваша оценка в модуле «Посещаемость» рассчитывается как отношение количества баллов, полученных за посещаемость до текущей даты, к максимальному количеству баллов, которые вы могли получить за посещаемость до текущей даты; будущие занятия в этой оценке не учитываются. В журнале оценок ваша оценка основывается на доле баллов, полученных за посещаемость, и максимальном количестве баллов, которые вы можете получить за посещаемость за весь курс, включая будущие занятия. Таким образом, оценки посещаемости в баллах, отображаемые в модуле «Посещаемость» и в журнале оценок могут различаться, однако доля (процент) будет совпадать. - -Например, если вы на текущий момент заработали 8 баллов из 10 (80% посещаемости) и максимальный балл за посещаемость всего курса в журнале оценок – 50, то в модуле «Посещаемость» отобразится оценка «8/10», а в журнале оценок — «40/50». Вы еще не заработали 40 баллов, но на данный момент ваш процент посещаемости (80%) соответствует этим баллам. Ваши баллы в модуле «Посещаемость» никогда не могут уменьшаться, т.к. они зависят только от посещаемости на текущую дату; однако, оценка в журнале оценок может увеличиваться и уменьшаться, в зависимости от вашей будущей успеваемости, т.к. эта оценка зависит от посещаемости на протяжении всего курса.'; -$string['gridcolumns'] = 'Колонки сетки'; -$string['groupsession'] = 'Групповое'; -$string['hiddensessions'] = 'Скрытых занятий'; -$string['hiddensessions_help'] = ' -Занятия скрываются, если их дата раньше даты начала курса. Чтобы отобразить эти занятия, измените дату начала курса. - -Эту возможность можно использовать для скрытия старых занятий, вместо их удаления. Имейте в виду, что для подсчета оценки в журнале оценок используются только видимые занятия.'; -$string['identifyby'] = 'Идентифицировать студента по'; -$string['includeall'] = 'Включить все занятия'; -$string['includenottaken'] = 'Включить не прошедшие занятия'; -$string['indetail'] = 'Подробнее...'; -$string['invalidsessionenddate'] = 'Дата завершения занятий не может быть ранее даты начала занятий'; -$string['jumpto'] = 'Перейти к занятию'; -$string['modulename'] = 'Посещаемость'; -$string['modulename_help'] = 'Модуль «Посещаемость» позволяет преподавателю вести учет посещаемости занятий, а студентам видеть информацию о их собственной посещаемости. - -Преподаватель может создать несколько занятий и отмечать посещаемость как статусы «Присутствовал», «Не был», «Опоздал», «Уважительная причина» или изменить эти статусы так, чтобы они соответствовали потребностям преподавателя. - -В модуле доступны отчеты по всем студентам или по каждому студенту отдельно.'; -$string['modulenameplural'] = 'Посещаемость'; -$string['months'] = 'Месяц'; -$string['moreattendance'] = 'Посещаемость успешно была сохранена для этой страницы'; -$string['myvariables'] = 'Мои переменные'; -$string['newdate'] = 'Новая дата'; -$string['newduration'] = 'Новая продолжительность'; -$string['noattforuser'] = 'Нет отметок посещаемости для этого пользователя'; -$string['nodescription'] = 'Обычное занятие'; -$string['noguest'] = 'Гость не может видеть информацию о посещаемости'; -$string['nogroups'] = 'Вы не можете добавлять групповые занятия. В курсе не определено ни одной группы.'; -$string['noofdaysabsent'] = 'Дней пропусков'; -$string['noofdaysexcused'] = 'Дней пропусков по ув. причине'; -$string['noofdayslate'] = 'Дней опозданий'; -$string['noofdayspresent'] = 'Дней присутствия'; -$string['nosessiondayselected'] = 'Не выбран день занятия'; -$string['nosessionexists'] = 'В данном курсе отсутствуют занятия'; -$string['nosessionsselected'] = 'Не выбрано ни одного занятия'; -$string['notfound'] = 'Элемент курса «Посещаемость» не найден в данном курсе!'; -$string['noupgradefromthisversion'] = 'Модуль «Посещаемость» не может быть обновлен с установленной у вас версии attforblock. - Удалите attforblock или обновите его до последней версии перед установкой нового модуля attendance'; -$string['olddate'] = 'Старая дата'; -$string['period'] = 'Периодичность'; -$string['pluginname'] = 'Посещаемость'; -$string['pluginadministration'] = 'Управление модулем «Посещаемость»'; -$string['remarks'] = 'Заметки'; -$string['report'] = 'Отчет'; -$string['required'] = 'Обязательное поле*'; -$string['resetdescription'] = 'Внимание! Чистка данных посещаемости удаляет информацию из БД. Вы можете просто скрыть старые занятия, изменив дату начала курса!'; -$string['resetstatuses'] = 'Восстановить набор статусов по умолчанию'; -$string['restoredefaults'] = 'Востановить значения по умолчанию'; -$string['resultsperpage'] = 'Результатов на страницу'; -$string['resultsperpage_desc'] = 'Количество студентов, отображаемых на странице'; -$string['save'] = 'Сохранить посещаемость'; -$string['session'] = 'Занятие'; -$string['session_help'] = 'Занятие'; -$string['sessionadded'] = 'Занятие успешно добавлено'; -$string['sessionalreadyexists'] = 'В этот день занятие уже существует'; -$string['sessiondate'] = 'Дата занятия'; -$string['sessiondays'] = 'Дни занятий'; -$string['sessiondeleted'] = 'Занятие успешно удалено'; -$string['sessionenddate'] = 'Дата завершения занятий'; -$string['sessionexist'] = 'Занятие не добавлено (уже существует)!'; -$string['sessions'] = 'Занятия'; -$string['sessionscompleted'] = 'Прошло занятий'; -$string['sessionsids'] = 'Идентификаторы занятий: '; -$string['sessionsgenerated'] = 'Занятия успешно созданы'; -$string['sessionsnotfound'] = 'В выбранный диапазон времени не попадает ни одно занятие'; -$string['sessionstartdate'] = 'Дата начала занятий'; -$string['sessiontype'] = 'Тип занятия'; -$string['sessiontype_help'] = 'Существует 2 типа занятий: общие и групповые. Возможность добавлять занятия различных типов зависит от группового режима элемента курса. - -* В групповом режиме «Нет групп» можно добавлять только общие занятия. -* В групповом режиме «Видимые группы» можно добавлять и общие, и групповые занятия. -* В групповом режиме «Изолированные группы» можно добавлять только групповые занятия. -'; -$string['sessiontypeshort'] = 'Тип'; -$string['sessionupdated'] = 'Занятие успешно изменено'; -$string['setallstatusesto'] = 'Установить статус для всех учащихся в «{$a}»'; -$string['settings'] = 'Настройки'; -$string['showdefaults'] = 'Показать значения по умолчанию'; -$string['showduration'] = 'Показать продолжительность'; -$string['sortedgrid'] = 'Таблица'; -$string['sortedlist'] = 'Список'; -$string['startofperiod'] = 'Начало периода'; -$string['status'] = 'Статус'; -$string['statuses'] = 'Статусы'; -$string['statusdeleted'] = 'Статус удален'; -$string['strftimedm'] = '%d.%m'; -$string['strftimedmy'] = '%d.%m.%Y'; -$string['strftimedmyhm'] = '%d.%m.%Y %H.%M'; // Line added to allow multiple sessions in the same day. -$string['strftimedmyw'] = '%d.%m.%y (%a)'; -$string['strftimehm'] = '%H:%M'; // Line added to allow display of time. -$string['strftimeshortdate'] = '%d.%m.%Y'; -$string['studentid'] = 'ID студента'; -$string['takeattendance'] = 'Отметить посещаемость'; -$string['thiscourse'] = 'Текущий курс'; -$string['tablerenamefailed'] = 'Переименование страой таблицы attforblock в attendance не удалось'; -$string['update'] = 'Обновить'; -$string['variable'] = 'переменную'; -$string['variablesupdated'] = 'Переменные успешно обновлены'; -$string['versionforprinting'] = 'версия для печати'; -$string['viewmode'] = 'Режим просмотра'; -$string['week'] = 'неделя(и)'; -$string['weeks'] = 'Неделя'; -$string['youcantdo'] = 'Вы ничего не можете сделать'; From 6b89d922d4d12c507187efd470858413308e0d3b Mon Sep 17 00:00:00 2001 From: Nadav Kavalerchik Date: Mon, 2 Dec 2013 00:09:41 +0200 Subject: [PATCH 22/75] Add user's remarks to report --- locallib.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/locallib.php b/locallib.php index d26e464..ce1cc4e 100644 --- a/locallib.php +++ b/locallib.php @@ -1078,7 +1078,7 @@ class attendance { $where = "ats.attendanceid = :aid AND ats.sessdate >= :csdate"; } - $sql = "SELECT ats.id, ats.sessdate, ats.groupid, al.statusid + $sql = "SELECT ats.id, ats.sessdate, ats.groupid, al.statusid, al.remarks FROM {attendance_sessions} ats JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid @@ -1405,4 +1405,4 @@ function attforblock_upgrade() { rebuild_course_cache($attendance->courseid, true); } $attendances->close(); -} \ No newline at end of file +} From 33db1a1b04fc8686b187a2e85c0f60d844197fad Mon Sep 17 00:00:00 2001 From: Nadav Kavalerchik Date: Mon, 2 Dec 2013 00:05:07 +0200 Subject: [PATCH 23/75] Add user's remarks to report --- renderer.php | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/renderer.php b/renderer.php index 6e0264e..e49578b 100755 --- a/renderer.php +++ b/renderer.php @@ -689,8 +689,8 @@ class mod_attendance_renderer extends plugin_renderer_base { get_string('status', 'attendance'), get_string('remarks', 'attendance') ); - $table->align = array('', '', '', 'left', 'left', 'center', 'left'); - $table->size = array('1px', '1px', '1px', '1px', '*', '1px', '1px'); + $table->align = array('', '', '', 'left', 'left', 'center', 'left', 'center'); + $table->size = array('1px', '1px', '1px', '1px', '*', '1px', '1px', '*'); $i = 0; foreach ($userdata->sessionslog as $sess) { @@ -773,7 +773,13 @@ class mod_attendance_renderer extends plugin_renderer_base { $table->align[] = 'center'; $table->size[] = '1px'; } - + + if ($reportdata->sessionslog) { + $table->head[] = get_string('remarks', 'attendance'); + $table->align[] = 'center'; + $table->size[] = '200px'; + } + foreach ($reportdata->users as $user) { $row = new html_table_row(); @@ -795,6 +801,9 @@ class mod_attendance_renderer extends plugin_renderer_base { $row->cells[] = $reportdata->grades[$user->id].' / '.$reportdata->maxgrades[$user->id]; } + if ($reportdata->sessionslog) { + $row->cells[] = $reportdata->sessionslog[$user->id][$sess->id]->remarks; + } $table->data[] = $row; } From 3bfcc5a4765add9febf5d124600ef6c165dd75bf Mon Sep 17 00:00:00 2001 From: Gregory Faller Date: Fri, 6 Dec 2013 13:08:38 +1030 Subject: [PATCH 24/75] Option to export remarks --- export.php | 5 ++++- export_form.php | 1 + lang/en/attendance.php | 1 + renderer.php | 3 ++- renderhelpers.php | 17 ++++++++++++++++- 5 files changed, 24 insertions(+), 3 deletions(-) diff --git a/export.php b/export.php index 5d2d32f..e56d8db 100644 --- a/export.php +++ b/export.php @@ -98,6 +98,9 @@ if ($mform->is_submitted()) { $text .= ' '; $text .= $sess->groupid ? $reportdata->groups[$sess->groupid]->name : get_string('commonsession', 'attendance'); $data->tabhead[] = $text; + if (isset($formdata->includeremarks)) { + $data->tabhead[] = get_string('remark', 'attendance', $text); + } } } else { print_error('sessionsnotfound', 'attendance', $att->url_manage()); @@ -118,7 +121,7 @@ if ($mform->is_submitted()) { $data->table[$i][] = $user->lastname; $data->table[$i][] = $user->firstname; $cellsgenerator = new user_sessions_cells_text_generator($reportdata, $user); - $data->table[$i] = array_merge($data->table[$i], $cellsgenerator->get_cells()); + $data->table[$i] = array_merge($data->table[$i], $cellsgenerator->get_cells($formdata->includeremarks)); if ($reportdata->gradable) { $data->table[$i][] = $reportdata->grades[$user->id].' / '.$reportdata->maxgrades[$user->id]; } diff --git a/export_form.php b/export_form.php index e43e1c6..17a932c 100644 --- a/export_form.php +++ b/export_form.php @@ -72,6 +72,7 @@ class mod_attendance_export_form extends moodleform { $mform->addElement('checkbox', 'includeallsessions', get_string('includeall', 'attendance'), get_string('yes')); $mform->setDefault('includeallsessions', true); $mform->addElement('checkbox', 'includenottaken', get_string('includenottaken', 'attendance'), get_string('yes')); + $mform->addElement('checkbox', 'includeremarks', get_string('includeremarks', 'attendance'), get_string('yes')); $mform->addElement('date_selector', 'sessionstartdate', get_string('startofperiod', 'attendance')); $mform->setDefault('sessionstartdate', $course->startdate); $mform->disabledIf('sessionstartdate', 'includeallsessions', 'checked'); diff --git a/lang/en/attendance.php b/lang/en/attendance.php index e8697a9..8c53022 100755 --- a/lang/en/attendance.php +++ b/lang/en/attendance.php @@ -153,6 +153,7 @@ $string['olddate'] = 'Old date'; $string['period'] = 'Frequency'; $string['pluginname'] = 'Attendance'; $string['pluginadministration'] = 'Attendance administration'; +$string['remark'] = 'Remark for: {a}'; $string['remarks'] = 'Remarks'; $string['report'] = 'Report'; $string['required'] = 'Required*'; diff --git a/renderer.php b/renderer.php index e49578b..0a58dc9 100755 --- a/renderer.php +++ b/renderer.php @@ -600,7 +600,8 @@ class mod_attendance_renderer extends plugin_renderer_base { } $params = array( 'type' => 'text', - 'name' => 'remarks'.$user->id); + 'name' => 'remarks'.$user->id, + 'maxlength' => 255); if (array_key_exists($user->id, $takedata->sessionlog)) { $params['value'] = $takedata->sessionlog[$user->id]->remarks; } diff --git a/renderhelpers.php b/renderhelpers.php index e25bfb0..a501537 100644 --- a/renderhelpers.php +++ b/renderhelpers.php @@ -43,7 +43,7 @@ class user_sessions_cells_generator { $this->user = $user; } - public function get_cells() { + public function get_cells($remarks = false) { $this->init_cells(); foreach ($this->reportdata->sessions as $sess) { if (array_key_exists($sess->id, $this->reportdata->sessionslog[$this->user->id])) { @@ -53,6 +53,9 @@ class user_sessions_cells_generator { } else { $this->construct_hidden_status_cell($this->reportdata->allstatuses[$statusid]->acronym); } + if ($remarks) { + $this->construct_remarks_cell($this->reportdata->sessionslog[$this->user->id][$sess->id]->remarks); + } } else { if ($this->user->enrolmentstart > $sess->sessdate) { $starttext = get_string('enrolmentstart', 'attendance', userdate($this->user->enrolmentstart, '%d.%m.%Y')); @@ -71,6 +74,9 @@ class user_sessions_cells_generator { $this->construct_not_existing_for_user_session_cell(''); } } + if ($remarks) { + $this->construct_remarks_cell(''); + } } } $this->finalize_cells(); @@ -97,6 +103,10 @@ class user_sessions_cells_generator { protected function construct_not_taken_cell($text) { $this->cells[] = $text; } + + protected function construct_remarks_cell($text) { + $this->cells[] = $text; + } protected function construct_not_existing_for_user_session_cell($text) { $this->cells[] = $text; @@ -150,6 +160,11 @@ class user_sessions_cells_html_generator extends user_sessions_cells_generator { $this->close_open_cell_if_needed(); $this->cells[] = $text; } + + protected function construct_remarks_cell($text) { + $this->close_open_cell_if_needed(); + $this->cells[] = $text; + } protected function construct_not_existing_for_user_session_cell($text) { $this->close_open_cell_if_needed(); From d4de7cb94a11b748e5085d55fa8d7b37687327ec Mon Sep 17 00:00:00 2001 From: Gregory Faller Date: Fri, 6 Dec 2013 13:09:54 +1030 Subject: [PATCH 25/75] Fix errors when using Activities block Current module throws an error when using the Activities block as set_url is not set. Fixing this throws a seperate error around array_pop. Put this on a separate line. --- index.php | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/index.php b/index.php index dcb421c..f699052 100644 --- a/index.php +++ b/index.php @@ -29,8 +29,11 @@ $id = required_param('id', PARAM_INT); $course = $DB->get_record('course', array('id' => $id), '*', MUST_EXIST); require_login($course); +$PAGE->set_url('/mod/attendance/index.php', array('id' => $id)); + // TODO: check if this is correct behaviour - other modules list all the instances of the module in the course. -if ($att = array_pop(get_all_instances_in_course('attendance', $course, null, true))) { +if ($att = get_all_instances_in_course('attendance', $course, null, true)) { + $att = array_pop($att); redirect("view.php?id=$att->coursemodule"); } else { print_error('notfound', 'attendance'); From fdc4ef50f62240d131af8b6d501da9f5d3cda4d0 Mon Sep 17 00:00:00 2001 From: cedict Date: Fri, 6 Dec 2013 13:21:16 +1030 Subject: [PATCH 26/75] Export remarks Fixed error when remarks are not being exported --- export.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/export.php b/export.php index e56d8db..215191a 100644 --- a/export.php +++ b/export.php @@ -121,7 +121,7 @@ if ($mform->is_submitted()) { $data->table[$i][] = $user->lastname; $data->table[$i][] = $user->firstname; $cellsgenerator = new user_sessions_cells_text_generator($reportdata, $user); - $data->table[$i] = array_merge($data->table[$i], $cellsgenerator->get_cells($formdata->includeremarks)); + $data->table[$i] = array_merge($data->table[$i], $cellsgenerator->get_cells(isset($formdata->includeremarks))); if ($reportdata->gradable) { $data->table[$i][] = $reportdata->grades[$user->id].' / '.$reportdata->maxgrades[$user->id]; } From f7f04af620219e35eea9fda64c45f2099d1db493 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Mon, 9 Dec 2013 20:23:43 +1300 Subject: [PATCH 27/75] fix context call and debug messages from remarks code --- locallib.php | 2 +- renderer.php | 8 ++++++-- 2 files changed, 7 insertions(+), 3 deletions(-) diff --git a/locallib.php b/locallib.php index 803ea54..f5512ee 100644 --- a/locallib.php +++ b/locallib.php @@ -895,7 +895,7 @@ class attendance { } } - $totalusers = count_enrolled_users(get_context_instance(CONTEXT_MODULE, $this->cm->id), 'mod/attendance:canbelisted', $group); + $totalusers = count_enrolled_users(context_module::instance($this->cm->id), 'mod/attendance:canbelisted', $group); $usersperpage = $this->pageparams->perpage; if (!empty($this->pageparams->page) && $this->pageparams->page && $totalusers && $usersperpage) { diff --git a/renderer.php b/renderer.php index 0a58dc9..ab1983f 100755 --- a/renderer.php +++ b/renderer.php @@ -803,8 +803,12 @@ class mod_attendance_renderer extends plugin_renderer_base { } if ($reportdata->sessionslog) { - $row->cells[] = $reportdata->sessionslog[$user->id][$sess->id]->remarks; - } + if (isset($reportdata->sessionslog[$user->id][$sess->id]->remarks)) { + $row->cells[] = $reportdata->sessionslog[$user->id][$sess->id]->remarks; + } else { + $row->cells[] = ''; + } + } $table->data[] = $row; } From 224111e571181ed90c9fdbdb0821283e8f3dbfc9 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Mon, 9 Dec 2013 21:26:47 +1300 Subject: [PATCH 28/75] add missing string from remarks patch --- lang/en/attendance.php | 1 + 1 file changed, 1 insertion(+) diff --git a/lang/en/attendance.php b/lang/en/attendance.php index 8c53022..4c8df1f 100755 --- a/lang/en/attendance.php +++ b/lang/en/attendance.php @@ -121,6 +121,7 @@ You can use this feature to hide older sessions instead delete. Remember than on $string['identifyby'] = 'Identify student by'; $string['includeall'] = 'Select all sessions'; $string['includenottaken'] = 'Include not taken sessions'; +$string['includeremarks'] = 'Include remarks'; $string['indetail'] = 'In detail...'; $string['invalidsessionenddate'] = 'The session end date can not be earlier than the session start date'; $string['jumpto'] = 'Jump to'; From b44d683b8f9dbd00538d826e17929174b16d7c8a Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Mon, 9 Dec 2013 21:27:04 +1300 Subject: [PATCH 29/75] Check group membership if using groups when displaying/exporting reports. --- locallib.php | 39 +++++++++++++++++++++++++++++++++++---- 1 file changed, 35 insertions(+), 4 deletions(-) diff --git a/locallib.php b/locallib.php index f5512ee..de63376 100644 --- a/locallib.php +++ b/locallib.php @@ -1070,7 +1070,21 @@ class attendance { global $DB; if (!array_key_exists($userid, $this->userstatusesstat)) { - $qry = "SELECT al.statusid, count(al.statusid) AS stcnt + if (!empty($this->cm->groupmode)) { + $qry = "SELECT al.statusid, count(al.statusid) AS stcnt + FROM {attendance_log} al + JOIN {attendance_sessions} ats ON al.sessionid = ats.id + JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid + WHERE ats.attendanceid = :aid AND + ats.sessdate >= :cstartdate AND + al.studentid = :uid + GROUP BY al.statusid"; + $params = array( + 'aid' => $this->id, + 'cstartdate' => $this->course->startdate, + 'uid' => $userid); + } else { + $qry = "SELECT al.statusid, count(al.statusid) AS stcnt FROM {attendance_log} al JOIN {attendance_sessions} ats ON al.sessionid = ats.id @@ -1078,10 +1092,11 @@ class attendance { ats.sessdate >= :cstartdate AND al.studentid = :uid GROUP BY al.statusid"; - $params = array( + $params = array( 'aid' => $this->id, 'cstartdate' => $this->course->startdate, 'uid' => $userid); + } $this->userstatusesstat[$userid] = $DB->get_records_sql($qry, $params); } @@ -1127,20 +1142,36 @@ class attendance { } else { $where = "ats.attendanceid = :aid AND ats.sessdate >= :csdate"; } + if (!empty($this->cm->groupmode)) { + $sql = "SELECT ats.id, ats.sessdate, ats.groupid, al.statusid, al.remarks + FROM {attendance_sessions} ats + JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid + JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid + WHERE $where + ORDER BY ats.sessdate ASC"; + + $params = array( + 'uid' => $userid, + 'aid' => $this->id, + 'csdate' => $this->course->startdate, + 'sdate' => $this->pageparams->startdate, + 'edate' => $this->pageparams->enddate); - $sql = "SELECT ats.id, ats.sessdate, ats.groupid, al.statusid, al.remarks + } else { + $sql = "SELECT ats.id, ats.sessdate, ats.groupid, al.statusid, al.remarks FROM {attendance_sessions} ats JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid WHERE $where ORDER BY ats.sessdate ASC"; - $params = array( + $params = array( 'uid' => $userid, 'aid' => $this->id, 'csdate' => $this->course->startdate, 'sdate' => $this->pageparams->startdate, 'edate' => $this->pageparams->enddate); + } $sessions = $DB->get_records_sql($sql, $params); return $sessions; From b5bde93866e4e162151c17366c5f3b6bed4328c8 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Mon, 9 Dec 2013 21:55:25 +1300 Subject: [PATCH 30/75] add field to export that lists groups that a user is a member of. --- export.php | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/export.php b/export.php index 215191a..19f9619 100644 --- a/export.php +++ b/export.php @@ -90,6 +90,9 @@ if ($mform->is_submitted()) { } $data->tabhead[] = get_string('lastname'); $data->tabhead[] = get_string('firstname'); + if (!empty($cm->groupmode)) { + $data->tabhead[] = get_string('groups'); + } if (count($reportdata->sessions) > 0) { @@ -120,6 +123,15 @@ if ($mform->is_submitted()) { } $data->table[$i][] = $user->lastname; $data->table[$i][] = $user->firstname; + if (!empty($cm->groupmode)) { + $grouptext = ''; + $groupsraw = groups_get_all_groups($course->id, $user->id, 0, 'g.name'); + $groups = array(); + foreach ($groupsraw as $group) { + $groups[] = $group->name;; + } + $data->table[$i][] = implode(', ', $groups); + } $cellsgenerator = new user_sessions_cells_text_generator($reportdata, $user); $data->table[$i] = array_merge($data->table[$i], $cellsgenerator->get_cells(isset($formdata->includeremarks))); if ($reportdata->gradable) { From 350d6f076abc2edad8db68a478d8d05464328f19 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Mon, 16 Dec 2013 12:35:24 +1300 Subject: [PATCH 31/75] Attendance - only show groups in reports that user is a member of. --- lib.php | 7 +++---- locallib.php | 52 ++++++++++++++++++++++++++++++++++++----------- preferences.php | 2 +- renderables.php | 4 ++-- renderhelpers.php | 8 ++++---- sessions.php | 4 ++-- 6 files changed, 52 insertions(+), 25 deletions(-) diff --git a/lib.php b/lib.php index a13f2fe..737d5e7 100644 --- a/lib.php +++ b/lib.php @@ -213,7 +213,6 @@ function attendance_reset_userdata($data) { */ function attendance_user_outline($course, $user, $mod, $attendance) { global $CFG; - require_once(dirname(__FILE__).'/locallib.php'); require_once($CFG->libdir.'/gradelib.php'); @@ -229,9 +228,9 @@ function attendance_user_outline($course, $user, $mod, $attendance) { if (has_capability('mod/attendance:canbelisted', $mod->context, $user->id)) { $statuses = att_get_statuses($attendance->id); $grade = att_get_user_grade(att_get_user_statuses_stat($attendance->id, $course->startdate, - $user->id), $statuses); + $user->id, $mod), $statuses); $maxgrade = att_get_user_max_grade(att_get_user_taken_sessions_count($attendance->id, $course->startdate, - $user->id), $statuses); + $user->id, $mod), $statuses); $result->info = $grade.' / '.$maxgrade; } @@ -250,7 +249,7 @@ function attendance_user_complete($course, $user, $mod, $attendance) { require_once($CFG->libdir.'/gradelib.php'); if (has_capability('mod/attendance:canbelisted', $mod->context, $user->id)) { - echo construct_full_user_stat_html_table($attendance, $course, $user); + echo construct_full_user_stat_html_table($attendance, $course, $user, $mod); } } function attendance_print_recent_activity($course, $isteacher, $timestart) { diff --git a/locallib.php b/locallib.php index de63376..40c7a85 100644 --- a/locallib.php +++ b/locallib.php @@ -1061,7 +1061,7 @@ class attendance { public function get_user_taken_sessions_count($userid) { if (!array_key_exists($userid, $this->usertakensesscount)) { - $this->usertakensesscount[$userid] = att_get_user_taken_sessions_count($this->id, $this->course->startdate, $userid); + $this->usertakensesscount[$userid] = att_get_user_taken_sessions_count($this->id, $this->course->startdate, $userid, $this->cm); } return $this->usertakensesscount[$userid]; } @@ -1179,7 +1179,6 @@ class attendance { public function get_user_filtered_sessions_log_extended($userid) { global $DB; - // All taked sessions (including previous groups). if ($this->pageparams->startdate && $this->pageparams->enddate) { @@ -1193,13 +1192,22 @@ class attendance { // If the array's index is a number it will not merge entries. // It would be better as a UNION query butunfortunatly MS SQL does not seem to support doing a DISTINCT on a the description field. $id = $DB->sql_concat(':value', 'ats.id'); - - $sql = "SELECT $id, ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks + if (!empty($this->cm->groupmode)) { + $sql = "SELECT $id, ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks FROM {attendance_sessions} ats RIGHT JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid + JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid WHERE $where ORDER BY ats.sessdate ASC"; + } else { + $sql = "SELECT $id, ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks + FROM {attendance_sessions} ats + RIGHT JOIN {attendance_log} al + ON ats.id = al.sessionid AND al.studentid = :uid + WHERE $where + ORDER BY ats.sessdate ASC"; + } $params = array( 'uid' => $userid, @@ -1339,16 +1347,25 @@ function att_get_statuses($attid, $onlyvisible=true) { return $statuses; } -function att_get_user_taken_sessions_count($attid, $coursestartdate, $userid) { +function att_get_user_taken_sessions_count($attid, $coursestartdate, $userid, $coursemodule) { global $DB; - - $qry = "SELECT count(*) as cnt + if (!empty($coursemodule->groupmode)) { + $qry = "SELECT count(*) as cnt + FROM {attendance_log} al + JOIN {attendance_sessions} ats ON al.sessionid = ats.id + JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid + WHERE ats.attendanceid = :aid AND + ats.sessdate >= :cstartdate AND + al.studentid = :uid"; + } else { + $qry = "SELECT count(*) as cnt FROM {attendance_log} al JOIN {attendance_sessions} ats ON al.sessionid = ats.id WHERE ats.attendanceid = :aid AND ats.sessdate >= :cstartdate AND al.studentid = :uid"; + } $params = array( 'aid' => $attid, 'cstartdate' => $coursestartdate, @@ -1357,10 +1374,20 @@ function att_get_user_taken_sessions_count($attid, $coursestartdate, $userid) { return $DB->count_records_sql($qry, $params); } -function att_get_user_statuses_stat($attid, $coursestartdate, $userid) { +function att_get_user_statuses_stat($attid, $coursestartdate, $userid, $coursemodule) { global $DB; - $qry = "SELECT al.statusid, count(al.statusid) AS stcnt + if (!empty($coursemodule->groupmode)) { + $qry = "SELECT al.statusid, count(al.statusid) AS stcnt + FROM {attendance_log} al + JOIN {attendance_sessions} ats ON al.sessionid = ats.id + JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid + WHERE ats.attendanceid = :aid AND + ats.sessdate >= :cstartdate AND + al.studentid = :uid + GROUP BY al.statusid"; + } else { + $qry = "SELECT al.statusid, count(al.statusid) AS stcnt FROM {attendance_log} al JOIN {attendance_sessions} ats ON al.sessionid = ats.id @@ -1368,6 +1395,7 @@ function att_get_user_statuses_stat($attid, $coursestartdate, $userid) { ats.sessdate >= :cstartdate AND al.studentid = :uid GROUP BY al.statusid"; + } $params = array( 'aid' => $attid, 'cstartdate' => $coursestartdate, @@ -1424,7 +1452,7 @@ function att_get_gradebook_maxgrade($attid) { return $DB->get_field('attendance', 'grade', array('id' => $attid)); } -function att_update_all_users_grades($attid, $course, $context) { +function att_update_all_users_grades($attid, $course, $context, $coursemodule) { $grades = array(); $userids = array_keys(get_enrolled_users($context, 'mod/attendance:canbelisted', 0, 'u.id')); @@ -1434,8 +1462,8 @@ function att_update_all_users_grades($attid, $course, $context) { foreach ($userids as $userid) { $grade = new stdClass; $grade->userid = $userid; - $userstatusesstat = att_get_user_statuses_stat($attid, $course->startdate, $userid); - $usertakensesscount = att_get_user_taken_sessions_count($attid, $course->startdate, $userid); + $userstatusesstat = att_get_user_statuses_stat($attid, $course->startdate, $userid, $coursemodule); + $usertakensesscount = att_get_user_taken_sessions_count($attid, $course->startdate, $userid, $coursemodule); $usergrade = att_get_user_grade($userstatusesstat, $statuses); $usermaxgrade = att_get_user_max_grade($usertakensesscount, $statuses); $grade->rawgrade = att_calc_user_grade_fraction($usergrade, $usermaxgrade) * $gradebook_maxgrade; diff --git a/preferences.php b/preferences.php index b597958..37b8128 100644 --- a/preferences.php +++ b/preferences.php @@ -93,7 +93,7 @@ switch ($att->pageparams->action) { foreach ($acronym as $id => $v) { $att->update_status($id, $acronym[$id], $description[$id], $grade[$id], null); } - att_update_all_users_grades($att->id, $att->course, $att->context); + att_update_all_users_grades($att->id, $att->course, $att->context, $cm); break; } diff --git a/renderables.php b/renderables.php index af38c0f..373bdc0 100644 --- a/renderables.php +++ b/renderables.php @@ -385,8 +385,8 @@ class attendance_user_data implements renderable { $this->maxgrade = array(); foreach ($this->coursesatts as $ca) { $statuses = att_get_statuses($ca->attid); - $user_taken_sessions_count = att_get_user_taken_sessions_count($ca->attid, $ca->coursestartdate, $userid); - $user_statuses_stat = att_get_user_statuses_stat($ca->attid, $ca->coursestartdate, $userid); + $user_taken_sessions_count = att_get_user_taken_sessions_count($ca->attid, $ca->coursestartdate, $userid, $att->cm); + $user_statuses_stat = att_get_user_statuses_stat($ca->attid, $ca->coursestartdate, $userid, $att->cm); $this->statuses[$ca->attid] = $statuses; diff --git a/renderhelpers.php b/renderhelpers.php index a501537..15ab178 100644 --- a/renderhelpers.php +++ b/renderhelpers.php @@ -254,17 +254,17 @@ function construct_user_data_stat($stat, $statuses, $gradable, $grade, $maxgrade return html_writer::table($stattable); } -function construct_full_user_stat_html_table($attendance, $course, $user) { +function construct_full_user_stat_html_table($attendance, $course, $user, $coursemodule) { global $CFG; $gradeable = $attendance->grade > 0; $statuses = att_get_statuses($attendance->id); - $userstatusesstat = att_get_user_statuses_stat($attendance->id, $course->startdate, $user->id); - $stat['completed'] = att_get_user_taken_sessions_count($attendance->id, $course->startdate, $user->id); + $userstatusesstat = att_get_user_statuses_stat($attendance->id, $course->startdate, $user->id, $coursemodule); + $stat['completed'] = att_get_user_taken_sessions_count($attendance->id, $course->startdate, $user->id, $coursemodule); $stat['statuses'] = $userstatusesstat; if ($gradeable) { $grade = att_get_user_grade($userstatusesstat, $statuses); $maxgrade = att_get_user_max_grade(att_get_user_taken_sessions_count($attendance->id, $course->startdate, - $user->id), $statuses); + $user->id, $coursemodule), $statuses); if (!$decimalpoints = grade_get_setting($course->id, 'decimalpoints')) { $decimalpoints = $CFG->grade_decimalpoints; } diff --git a/sessions.php b/sessions.php index 046a596..b32e087 100644 --- a/sessions.php +++ b/sessions.php @@ -85,7 +85,7 @@ switch ($att->pageparams->action) { if (isset($confirm) && confirm_sesskey()) { $att->delete_sessions(array($sessionid)); - att_update_all_users_grades($att->id, $att->course, $att->context); + att_update_all_users_grades($att->id, $att->course, $att->context, $cm); redirect($att->url_manage(), get_string('sessiondeleted', 'attendance')); } @@ -112,7 +112,7 @@ switch ($att->pageparams->action) { $sessionsids = explode('_', $sessionsids); $att->delete_sessions($sessionsids); - att_update_all_users_grades($att->id, $att->course, $att->context); + att_update_all_users_grades($att->id, $att->course, $att->context, $cm); redirect($att->url_manage(), get_string('sessiondeleted', 'attendance')); } $sessid = required_param('sessid', PARAM_SEQUENCE); From 6eca918d3e3b2aaf9e42400a3e5fe0515c841e81 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Thu, 19 Dec 2013 09:18:08 +1300 Subject: [PATCH 32/75] bump version due to group changes. --- version.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.php b/version.php index bacd533..970719d 100644 --- a/version.php +++ b/version.php @@ -22,7 +22,7 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -$module->version = 2013082902; +$module->version = 2013082903; $module->requires = 2013040500; $module->release = '2.5.3'; $module->maturity = MATURITY_STABLE; From c6e2c05d098197253eb6ef408b26be82b93641fd Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Thu, 19 Dec 2013 09:37:33 +1300 Subject: [PATCH 33/75] make correct check for group mode --- export.php | 5 +++-- export_form.php | 2 +- locallib.php | 17 +++++++++-------- 3 files changed, 13 insertions(+), 11 deletions(-) diff --git a/export.php b/export.php index 19f9619..a0a690a 100644 --- a/export.php +++ b/export.php @@ -90,7 +90,8 @@ if ($mform->is_submitted()) { } $data->tabhead[] = get_string('lastname'); $data->tabhead[] = get_string('firstname'); - if (!empty($cm->groupmode)) { + $groupmode = groups_get_activity_groupmode($cm, $course); + if (!empty($groupmode)) { $data->tabhead[] = get_string('groups'); } @@ -123,7 +124,7 @@ if ($mform->is_submitted()) { } $data->table[$i][] = $user->lastname; $data->table[$i][] = $user->firstname; - if (!empty($cm->groupmode)) { + if (!empty($groupmode)) { $grouptext = ''; $groupsraw = groups_get_all_groups($course->id, $user->id, 0, 'g.name'); $groups = array(); diff --git a/export_form.php b/export_form.php index 17a932c..994c5e1 100644 --- a/export_form.php +++ b/export_form.php @@ -48,7 +48,7 @@ class mod_attendance_export_form extends moodleform { $mform->addElement('header', 'general', get_string('export', 'quiz')); - $groupmode=groups_get_activity_groupmode($cm); + $groupmode=groups_get_activity_groupmode($cm, $course); $groups = groups_get_activity_allowed_groups($cm, $USER->id); if ($groupmode == VISIBLEGROUPS or has_capability('moodle/site:accessallgroups', $modcontext)) { $grouplist[0] = get_string('allparticipants'); diff --git a/locallib.php b/locallib.php index 40c7a85..bba91a9 100644 --- a/locallib.php +++ b/locallib.php @@ -599,7 +599,7 @@ class attendance { public function get_group_mode() { if (is_null($this->groupmode)) { - $this->groupmode = groups_get_activity_groupmode($this->cm); + $this->groupmode = groups_get_activity_groupmode($this->cm, $this->course); } return $this->groupmode; } @@ -1070,7 +1070,7 @@ class attendance { global $DB; if (!array_key_exists($userid, $this->userstatusesstat)) { - if (!empty($this->cm->groupmode)) { + if (!empty($this->groupmode)) { $qry = "SELECT al.statusid, count(al.statusid) AS stcnt FROM {attendance_log} al JOIN {attendance_sessions} ats ON al.sessionid = ats.id @@ -1142,7 +1142,7 @@ class attendance { } else { $where = "ats.attendanceid = :aid AND ats.sessdate >= :csdate"; } - if (!empty($this->cm->groupmode)) { + if (!empty($this->groupmode)) { $sql = "SELECT ats.id, ats.sessdate, ats.groupid, al.statusid, al.remarks FROM {attendance_sessions} ats JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid @@ -1192,7 +1192,7 @@ class attendance { // If the array's index is a number it will not merge entries. // It would be better as a UNION query butunfortunatly MS SQL does not seem to support doing a DISTINCT on a the description field. $id = $DB->sql_concat(':value', 'ats.id'); - if (!empty($this->cm->groupmode)) { + if (!empty($this->groupmode)) { $sql = "SELECT $id, ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks FROM {attendance_sessions} ats RIGHT JOIN {attendance_log} al @@ -1348,8 +1348,9 @@ function att_get_statuses($attid, $onlyvisible=true) { } function att_get_user_taken_sessions_count($attid, $coursestartdate, $userid, $coursemodule) { - global $DB; - if (!empty($coursemodule->groupmode)) { + global $DB, $COURSE; + $groupmode = groups_get_activity_groupmode($coursemodule, $COURSE); + if (!empty($groupmode)) { $qry = "SELECT count(*) as cnt FROM {attendance_log} al JOIN {attendance_sessions} ats ON al.sessionid = ats.id @@ -1375,8 +1376,8 @@ function att_get_user_taken_sessions_count($attid, $coursestartdate, $userid, $c } function att_get_user_statuses_stat($attid, $coursestartdate, $userid, $coursemodule) { - global $DB; - + global $DB, $COURSE; + $groupmode = groups_get_activity_groupmode($coursemodule, $COURSE); if (!empty($coursemodule->groupmode)) { $qry = "SELECT al.statusid, count(al.statusid) AS stcnt FROM {attendance_log} al From a1a1a120fbdadbc01c667ab5558b63adf88dbde6 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 20 Dec 2013 08:55:35 +1300 Subject: [PATCH 34/75] Check groupmode correctly. --- locallib.php | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/locallib.php b/locallib.php index bba91a9..d52ceed 100644 --- a/locallib.php +++ b/locallib.php @@ -1070,7 +1070,7 @@ class attendance { global $DB; if (!array_key_exists($userid, $this->userstatusesstat)) { - if (!empty($this->groupmode)) { + if (!empty($this->get_group_mode())) { $qry = "SELECT al.statusid, count(al.statusid) AS stcnt FROM {attendance_log} al JOIN {attendance_sessions} ats ON al.sessionid = ats.id @@ -1142,7 +1142,7 @@ class attendance { } else { $where = "ats.attendanceid = :aid AND ats.sessdate >= :csdate"; } - if (!empty($this->groupmode)) { + if (!empty($this->get_group_mode())) { $sql = "SELECT ats.id, ats.sessdate, ats.groupid, al.statusid, al.remarks FROM {attendance_sessions} ats JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid @@ -1192,7 +1192,7 @@ class attendance { // If the array's index is a number it will not merge entries. // It would be better as a UNION query butunfortunatly MS SQL does not seem to support doing a DISTINCT on a the description field. $id = $DB->sql_concat(':value', 'ats.id'); - if (!empty($this->groupmode)) { + if (!empty($this->get_group_mode())) { $sql = "SELECT $id, ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks FROM {attendance_sessions} ats RIGHT JOIN {attendance_log} al @@ -1378,7 +1378,7 @@ function att_get_user_taken_sessions_count($attid, $coursestartdate, $userid, $c function att_get_user_statuses_stat($attid, $coursestartdate, $userid, $coursemodule) { global $DB, $COURSE; $groupmode = groups_get_activity_groupmode($coursemodule, $COURSE); - if (!empty($coursemodule->groupmode)) { + if (!empty($groupmode)) { $qry = "SELECT al.statusid, count(al.statusid) AS stcnt FROM {attendance_log} al JOIN {attendance_sessions} ats ON al.sessionid = ats.id From bd11e0e4daffea76b673be75850e187c3a99fe13 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 20 Dec 2013 09:02:38 +1300 Subject: [PATCH 35/75] convert a couple of get_records to recordset - memory usage in attendance is nasty. --- lib.php | 3 ++- locallib.php | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/lib.php b/lib.php index 737d5e7..134288b 100644 --- a/lib.php +++ b/lib.php @@ -54,12 +54,13 @@ function attendance_supports($feature) { function att_add_default_statuses($attid) { global $DB; - $statuses = $DB->get_records('attendance_statuses', array('attendanceid'=> 0), 'id'); + $statuses = $DB->get_recordset('attendance_statuses', array('attendanceid'=> 0), 'id'); foreach ($statuses as $st) { $rec = $st; $rec->attendanceid = $attid; $DB->insert_record('attendance_statuses', $rec); } + $statuses->close(); } function attendance_add_instance($attendance) { diff --git a/locallib.php b/locallib.php index d52ceed..2977b34 100644 --- a/locallib.php +++ b/locallib.php @@ -1267,12 +1267,13 @@ class attendance { global $DB; $now = time(); - $sessions = $DB->get_records_list('attendance_sessions', 'id', $sessionsids); + $sessions = $DB->get_recordset_list('attendance_sessions', 'id', $sessionsids); foreach ($sessions as $sess) { $sess->duration = $duration; $sess->timemodified = $now; $DB->update_record('attendance_sessions', $sess); } + $sessions->close(); add_to_log($this->course->id, 'attendance', 'sessions duration updated', $this->url_manage(), get_string('sessionsids', 'attendance').implode(', ', $sessionsids), $this->cm->id); } From c1596896f149fbcebe28718b87c714f8d592dd3e Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Mon, 6 Jan 2014 08:36:18 +1300 Subject: [PATCH 36/75] correct usage of group check Fixes #26 --- locallib.php | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/locallib.php b/locallib.php index 2977b34..0982f44 100644 --- a/locallib.php +++ b/locallib.php @@ -1070,7 +1070,7 @@ class attendance { global $DB; if (!array_key_exists($userid, $this->userstatusesstat)) { - if (!empty($this->get_group_mode())) { + if ($this->get_group_mode()) { $qry = "SELECT al.statusid, count(al.statusid) AS stcnt FROM {attendance_log} al JOIN {attendance_sessions} ats ON al.sessionid = ats.id @@ -1142,7 +1142,7 @@ class attendance { } else { $where = "ats.attendanceid = :aid AND ats.sessdate >= :csdate"; } - if (!empty($this->get_group_mode())) { + if ($this->get_group_mode()) { $sql = "SELECT ats.id, ats.sessdate, ats.groupid, al.statusid, al.remarks FROM {attendance_sessions} ats JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid @@ -1192,7 +1192,7 @@ class attendance { // If the array's index is a number it will not merge entries. // It would be better as a UNION query butunfortunatly MS SQL does not seem to support doing a DISTINCT on a the description field. $id = $DB->sql_concat(':value', 'ats.id'); - if (!empty($this->get_group_mode())) { + if ($this->get_group_mode()) { $sql = "SELECT $id, ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks FROM {attendance_sessions} ats RIGHT JOIN {attendance_log} al From 101c3fbb07103e8b999935039a6e927571747b9d Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Tue, 7 Jan 2014 09:10:27 +1300 Subject: [PATCH 37/75] CONTRIB-4823 - include common attendances correctly when using groups. --- locallib.php | 23 +++++++++++++---------- 1 file changed, 13 insertions(+), 10 deletions(-) diff --git a/locallib.php b/locallib.php index 0982f44..8d4ff15 100644 --- a/locallib.php +++ b/locallib.php @@ -1074,10 +1074,11 @@ class attendance { $qry = "SELECT al.statusid, count(al.statusid) AS stcnt FROM {attendance_log} al JOIN {attendance_sessions} ats ON al.sessionid = ats.id - JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid + LEFT JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid WHERE ats.attendanceid = :aid AND ats.sessdate >= :cstartdate AND - al.studentid = :uid + al.studentid = :uid AND + (ats.groupid = 0 or gm.id is NOT NULL) GROUP BY al.statusid"; $params = array( 'aid' => $this->id, @@ -1146,8 +1147,8 @@ class attendance { $sql = "SELECT ats.id, ats.sessdate, ats.groupid, al.statusid, al.remarks FROM {attendance_sessions} ats JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid - JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid - WHERE $where + LEFT JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid + WHERE $where AND (ats.groupid = 0 or gm.id is NOT NULL) ORDER BY ats.sessdate ASC"; $params = array( @@ -1197,8 +1198,8 @@ class attendance { FROM {attendance_sessions} ats RIGHT JOIN {attendance_log} al ON ats.id = al.sessionid AND al.studentid = :uid - JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid - WHERE $where + LEFT JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid + WHERE $where AND (ats.groupid = 0 or gm.id is NOT NULL) ORDER BY ats.sessdate ASC"; } else { $sql = "SELECT $id, ats.id, ats.groupid, ats.sessdate, ats.duration, ats.description, al.statusid, al.remarks @@ -1355,10 +1356,11 @@ function att_get_user_taken_sessions_count($attid, $coursestartdate, $userid, $c $qry = "SELECT count(*) as cnt FROM {attendance_log} al JOIN {attendance_sessions} ats ON al.sessionid = ats.id - JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid + LEFT JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid WHERE ats.attendanceid = :aid AND ats.sessdate >= :cstartdate AND - al.studentid = :uid"; + al.studentid = :uid AND + (ats.groupid = 0 or gm.id is NOT NULL)"; } else { $qry = "SELECT count(*) as cnt FROM {attendance_log} al @@ -1383,10 +1385,11 @@ function att_get_user_statuses_stat($attid, $coursestartdate, $userid, $coursemo $qry = "SELECT al.statusid, count(al.statusid) AS stcnt FROM {attendance_log} al JOIN {attendance_sessions} ats ON al.sessionid = ats.id - JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid + LEFT JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid WHERE ats.attendanceid = :aid AND ats.sessdate >= :cstartdate AND - al.studentid = :uid + al.studentid = :uid AND + (ats.groupid = 0 or gm.id is NOT NULL) GROUP BY al.statusid"; } else { $qry = "SELECT al.statusid, count(al.statusid) AS stcnt From e43ce52d54e34c60865d4ec6b5ccc041e540b8d7 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Tue, 7 Jan 2014 09:28:10 +1300 Subject: [PATCH 38/75] bump version --- version.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.php b/version.php index 970719d..26aa4d7 100644 --- a/version.php +++ b/version.php @@ -22,7 +22,7 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -$module->version = 2013082903; +$module->version = 2013082904; $module->requires = 2013040500; $module->release = '2.5.3'; $module->maturity = MATURITY_STABLE; From 598fe89c99297ecb12216a7f86e5ece6d7fd9e5e Mon Sep 17 00:00:00 2001 From: Nadav Kavalerchik Date: Mon, 20 Jan 2014 18:51:36 +0200 Subject: [PATCH 39/75] Calculate the sum of statuses for each user Hi Dan, Please review this little patch that sum up the number of each status occurrence for each user, and display it at the bottom of the attendance table. Nadav :-) --- renderer.php | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/renderer.php b/renderer.php index ab1983f..42bba70 100755 --- a/renderer.php +++ b/renderer.php @@ -320,7 +320,20 @@ class mod_attendance_renderer extends plugin_renderer_base { $table .= html_writer::tag('center', html_writer::empty_tag('input', $params)); $table = html_writer::tag('form', $table, array('method' => 'post', 'action' => $takedata->url_path())); - return $controls.$table; + // Calculate the sum of statuses for each user + $sessionstats[] = array(); + foreach ($takedata->sessionlog as $userlog) { + foreach($takedata->statuses as $status) { + if ($userlog->statusid == $status->id) $sessionstats[$status->id]++; + } + } + + $statsoutput = '
'; + foreach($takedata->statuses as $status) { + $statsoutput .= "$status->description = ".$sessionstats[$status->id]."
"; + } + + return $controls.$table.$statsoutput; } protected function render_attendance_take_controls(attendance_take_data $takedata) { From 3c3f90df083bbb478d7c4636797df9c2929813a2 Mon Sep 17 00:00:00 2001 From: Nadav Kavalerchik Date: Mon, 20 Jan 2014 19:42:49 +0200 Subject: [PATCH 40/75] Calculate the sum of statuses for all users in each session Hi Dan, Here is another patch the calculates the sum of statuses for all users in each session. Please review and see if you can accept. Nadav :-) --- renderer.php | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/renderer.php b/renderer.php index ab1983f..e3af1ad 100755 --- a/renderer.php +++ b/renderer.php @@ -812,6 +812,27 @@ class mod_attendance_renderer extends plugin_renderer_base { $table->data[] = $row; } + // Calculate the sum of statuses for each user + $statrow = new html_table_row(); + $statrow->cells[] = ''; + $statrow->cells[] = get_string('summary'); + foreach ($reportdata->sessions as $sess) { + $sessionstats = array(); + foreach ($reportdata->users as $user) { + foreach($reportdata->statuses as $status) { + if ($reportdata->sessionslog[$user->id][$sess->id]->statusid == $status->id) $sessionstats[$status->id]++; + } + } + + $statsoutput = '
'; + foreach($reportdata->statuses as $status) { + $statsoutput .= "$status->description:".$sessionstats[$status->id]."
"; + } + $statrow->cells[] = $statsoutput; + + } + $table->data[] = $statrow; + return html_writer::table($table); } From d01030946a04a55fc7cffddb7bc838cd5ad79d97 Mon Sep 17 00:00:00 2001 From: Gordon Bateson Date: Sun, 9 Feb 2014 15:05:20 +0900 Subject: [PATCH 41/75] CONTRIB-4868 fix duplicate records found warning in courses with meta enrolments --- locallib.php | 28 +++++++++++++++++----------- 1 file changed, 17 insertions(+), 11 deletions(-) diff --git a/locallib.php b/locallib.php index 8d4ff15..288b979 100644 --- a/locallib.php +++ b/locallib.php @@ -916,7 +916,7 @@ class attendance { global $DB, $CFG; // Fields we need from the user table. - $userfields = user_picture::fields('u').',u.username'; + $userfields = user_picture::fields('u', array('username')); if (isset($this->pageparams->sort) and ($this->pageparams->sort == ATT_SORT_FIRSTNAME)) { $orderby = "u.firstname ASC, u.lastname ASC"; @@ -959,23 +959,29 @@ class attendance { // Add a flag to each user indicating whether their enrolment is active. if (!empty($users)) { - list($usql, $uparams) = $DB->get_in_or_equal(array_keys($users), SQL_PARAMS_NAMED, 'usid0'); + list($sql, $params) = $DB->get_in_or_equal(array_keys($users), SQL_PARAMS_NAMED, 'usid0'); - // CONTRIB-3549. - $sql = "SELECT ue.userid, ue.status, ue.timestart, ue.timeend + // CONTRIB-4868 + $mintime = 'MIN(CASE WHEN (ue.timestart > :mintime) THEN ue.timestart ELSE ue.timecreated END)'; + $maxtime = 'MAX(CASE WHEN (ue.timeend > :maxtime) THEN ue.timeend ELSE ue.timemodified END)'; + + // CONTRIB-3549 + $sql = "SELECT ue.userid, ue.status, + $mintime AS mintime, + $maxtime AS maxtime FROM {user_enrolments} ue JOIN {enrol} e ON e.id = ue.enrolid - WHERE ue.userid $usql + WHERE ue.userid $sql AND e.status = :estatus AND e.courseid = :courseid - GROUP BY ue.userid, ue.status, ue.timestart, ue.timeend"; - $params = array_merge($uparams, array('estatus'=>ENROL_INSTANCE_ENABLED, 'courseid'=>$this->course->id)); - $enrolmentsparams = $DB->get_records_sql($sql, $params); + GROUP BY ue.userid, ue.status"; + $params += array('mintime'=>0, 'maxtime'=>0, 'estatus'=>ENROL_INSTANCE_ENABLED, 'courseid'=>$this->course->id); + $enrolments = $DB->get_records_sql($sql, $params); foreach ($users as $user) { - $users[$user->id]->enrolmentstatus = $enrolmentsparams[$user->id]->status; - $users[$user->id]->enrolmentstart = $enrolmentsparams[$user->id]->timestart; - $users[$user->id]->enrolmentend = $enrolmentsparams[$user->id]->timeend; + $users[$user->id]->enrolmentstatus = $enrolments[$user->id]->status; + $users[$user->id]->enrolmentstart = $enrolments[$user->id]->mintime; + $users[$user->id]->enrolmentend = $enrolments[$user->id]->maxtime; } } From 8681bb2133bf014b99681bc87a2cfe0dcb1c8ba1 Mon Sep 17 00:00:00 2001 From: Gordon Bateson Date: Mon, 10 Feb 2014 08:45:02 +0900 Subject: [PATCH 42/75] CONTRIB-4868 (1) do not set maxtime to timemodified; (2) use mintime and maxtime in get_user() function too --- locallib.php | 30 ++++++++++++++++++------------ 1 file changed, 18 insertions(+), 12 deletions(-) diff --git a/locallib.php b/locallib.php index 288b979..11b73ff 100644 --- a/locallib.php +++ b/locallib.php @@ -936,10 +936,10 @@ class attendance { $users = get_users_by_capability($this->context, 'mod/attendance:canbelisted', $userfields.',u.id, u.firstname, u.lastname, u.email', $orderby, $startusers, $usersperpage, $groups, - '', false, true); + '', false, true); } else { $startusers = ($page - 1) * $usersperpage; - $users = get_enrolled_users($this->context, 'mod/attendance:canbelisted', $groupid, $userfields, $orderby, $startusers, $usersperpage); + $users = get_enrolled_users($this->context, 'mod/attendance:canbelisted', $groupid, $userfields, $orderby, $startusers, $usersperpage); } } else { if (!empty($CFG->enablegroupmembersonly) and $this->cm->groupmembersonly) { @@ -962,8 +962,8 @@ class attendance { list($sql, $params) = $DB->get_in_or_equal(array_keys($users), SQL_PARAMS_NAMED, 'usid0'); // CONTRIB-4868 - $mintime = 'MIN(CASE WHEN (ue.timestart > :mintime) THEN ue.timestart ELSE ue.timecreated END)'; - $maxtime = 'MAX(CASE WHEN (ue.timeend > :maxtime) THEN ue.timeend ELSE ue.timemodified END)'; + $mintime = 'MIN(CASE WHEN (ue.timestart > :zerotime) THEN ue.timestart ELSE ue.timecreated END)'; + $maxtime = 'MAX(ue.timeend)'; // CONTRIB-3549 $sql = "SELECT ue.userid, ue.status, @@ -975,7 +975,7 @@ class attendance { AND e.status = :estatus AND e.courseid = :courseid GROUP BY ue.userid, ue.status"; - $params += array('mintime'=>0, 'maxtime'=>0, 'estatus'=>ENROL_INSTANCE_ENABLED, 'courseid'=>$this->course->id); + $params += array('zerotime'=>0, 'estatus'=>ENROL_INSTANCE_ENABLED, 'courseid'=>$this->course->id); $enrolments = $DB->get_records_sql($sql, $params); foreach ($users as $user) { @@ -993,19 +993,25 @@ class attendance { $user = $DB->get_record('user', array('id' => $userid), '*', MUST_EXIST); - $sql = "SELECT ue.userid, ue.status, ue.timestart, ue.timeend + // CONTRIB-4868 + $mintime = 'MIN(CASE WHEN (ue.timestart > :zerotime) THEN ue.timestart ELSE ue.timecreated END)'; + $maxtime = 'MAX(ue.timeend)'; + + $sql = "SELECT ue.userid, ue.status, + $mintime AS mintime, + $maxtime AS maxtime FROM {user_enrolments} ue JOIN {enrol} e ON e.id = ue.enrolid WHERE ue.userid = :uid AND e.status = :estatus AND e.courseid = :courseid - GROUP BY ue.userid, ue.status, ue.timestart, ue.timeend"; - $params = array('uid' => $userid, 'estatus'=>ENROL_INSTANCE_ENABLED, 'courseid'=>$this->course->id); - $enrolmentsparams = $DB->get_record_sql($sql, $params); + GROUP BY ue.userid, ue.status"; + $params = array('zerotime'=>0, 'uid'=>$userid, 'estatus'=>ENROL_INSTANCE_ENABLED, 'courseid'=>$this->course->id); + $enrolments = $DB->get_record_sql($sql, $params); - $user->enrolmentstatus = $enrolmentsparams->status; - $user->enrolmentstart = $enrolmentsparams->timestart; - $user->enrolmentend = $enrolmentsparams->timeend; + $user->enrolmentstatus = $enrolments->status; + $user->enrolmentstart = $enrolments->mintime; + $user->enrolmentend = $enrolments->maxtime; return $user; } From b5038fa89dc4fafd4ad33d596470e11b5bf46782 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 28 Feb 2014 09:03:17 +1300 Subject: [PATCH 43/75] Update version.php bump version for release in plugins db --- version.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/version.php b/version.php index 26aa4d7..70a3faa 100644 --- a/version.php +++ b/version.php @@ -22,9 +22,9 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -$module->version = 2013082904; +$module->version = 2014022800; $module->requires = 2013040500; -$module->release = '2.5.3'; +$module->release = '2.6.0'; $module->maturity = MATURITY_STABLE; $module->cron = 0; $module->component = 'mod_attendance'; From 6120daed579550654aa0e788e1a3b5b4c6e9d610 Mon Sep 17 00:00:00 2001 From: Michael Aherne Date: Thu, 1 May 2014 15:44:15 +0100 Subject: [PATCH 44/75] Get version from config if necessary --- locallib.php | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/locallib.php b/locallib.php index 11b73ff..2df274b 100644 --- a/locallib.php +++ b/locallib.php @@ -1511,6 +1511,14 @@ function att_log_convert_url(moodle_url $fullurl) { function attforblock_upgrade() { global $DB, $CFG; $module = $DB->get_record('modules', array('name' => 'attforblock')); + + // Deal with Moodle versions above 2013092001.02, where version is in config + $versioninmodtable = true; + if (!isset($module->version)) { + $versioninmodtable = false; + $module->version = get_config('mod_attforblock', 'version'); + } + if ($module->version <= '2011061800') { print_error("noupgradefromthisversion", 'attendance'); } @@ -1529,6 +1537,10 @@ function attforblock_upgrade() { } // Now convert module record. $module->name = 'attendance'; + if (!$versioninmodtable) { + set_config('version', $module->version, 'mod_attendance'); + unset($module->version); + } $DB->update_record('modules', $module); // Now convert grade items to 'attendance' From 7b3a7add92b8e6d1e1f557135edc4804420be27b Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 9 May 2014 11:46:16 +1200 Subject: [PATCH 45/75] CONTRIB-4864 Correct grade calculation when timeframe used in export. --- locallib.php | 45 ++++++++++++++++++++++++++++++--------------- 1 file changed, 30 insertions(+), 15 deletions(-) diff --git a/locallib.php b/locallib.php index 2df274b..230baab 100644 --- a/locallib.php +++ b/locallib.php @@ -1073,13 +1073,28 @@ class attendance { public function get_user_taken_sessions_count($userid) { if (!array_key_exists($userid, $this->usertakensesscount)) { - $this->usertakensesscount[$userid] = att_get_user_taken_sessions_count($this->id, $this->course->startdate, $userid, $this->cm); + if ($this->pageparams->startdate && $this->pageparams->enddate) { + $this->usertakensesscount[$userid] = att_get_user_taken_sessions_count($this->id, $this->course->startdate, $userid, $this->cm, $this->pageparams->startdate, $this->pageparams->enddate); + } else { + $this->usertakensesscount[$userid] = att_get_user_taken_sessions_count($this->id, $this->course->startdate, $userid, $this->cm); + } } return $this->usertakensesscount[$userid]; } public function get_user_statuses_stat($userid) { global $DB; + $params = array( + 'aid' => $this->id, + 'cstartdate' => $this->course->startdate, + 'uid' => $userid); + + $period = ''; + if (!empty($this->pageparams->startdate) && !empty($this->pageparams->enddate)) { + $period = ' AND ats.sessdate >= :sdate AND ats.sessdate < :edate '; + $params['sdate'] = $this->pageparams->startdate; + $params['edate'] = $this->pageparams->enddate; + } if (!array_key_exists($userid, $this->userstatusesstat)) { if ($this->get_group_mode()) { @@ -1090,12 +1105,8 @@ class attendance { WHERE ats.attendanceid = :aid AND ats.sessdate >= :cstartdate AND al.studentid = :uid AND - (ats.groupid = 0 or gm.id is NOT NULL) + (ats.groupid = 0 or gm.id is NOT NULL)".$period." GROUP BY al.statusid"; - $params = array( - 'aid' => $this->id, - 'cstartdate' => $this->course->startdate, - 'uid' => $userid); } else { $qry = "SELECT al.statusid, count(al.statusid) AS stcnt FROM {attendance_log} al @@ -1103,14 +1114,12 @@ class attendance { ON al.sessionid = ats.id WHERE ats.attendanceid = :aid AND ats.sessdate >= :cstartdate AND - al.studentid = :uid + al.studentid = :uid".$period." GROUP BY al.statusid"; - $params = array( - 'aid' => $this->id, - 'cstartdate' => $this->course->startdate, - 'uid' => $userid); + } + $this->userstatusesstat[$userid] = $DB->get_records_sql($qry, $params); } @@ -1361,7 +1370,7 @@ function att_get_statuses($attid, $onlyvisible=true) { return $statuses; } -function att_get_user_taken_sessions_count($attid, $coursestartdate, $userid, $coursemodule) { +function att_get_user_taken_sessions_count($attid, $coursestartdate, $userid, $coursemodule, $startdate = '', $enddate = '') { global $DB, $COURSE; $groupmode = groups_get_activity_groupmode($coursemodule, $COURSE); if (!empty($groupmode)) { @@ -1383,9 +1392,15 @@ function att_get_user_taken_sessions_count($attid, $coursestartdate, $userid, $c al.studentid = :uid"; } $params = array( - 'aid' => $attid, - 'cstartdate' => $coursestartdate, - 'uid' => $userid); + 'aid' => $attid, + 'cstartdate' => $coursestartdate, + 'uid' => $userid); + + if (!empty($startdate) && !empty($enddate)) { + $qry .= ' AND sessdate >= :sdate AND sessdate < :edate '; + $params['sdate'] = $startdate; + $params['edate'] = $enddate; + } return $DB->count_records_sql($qry, $params); } From 499636fcc06dd8ec41eddbd881bb6f09be6fc3b9 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 9 May 2014 12:08:36 +1200 Subject: [PATCH 46/75] CONTRIB-4052 Prevent gradebook entry from being added when using nograde --- preferences.php | 4 +++- sessions.php | 8 ++++++-- 2 files changed, 9 insertions(+), 3 deletions(-) diff --git a/preferences.php b/preferences.php index 37b8128..8597fdd 100644 --- a/preferences.php +++ b/preferences.php @@ -93,7 +93,9 @@ switch ($att->pageparams->action) { foreach ($acronym as $id => $v) { $att->update_status($id, $acronym[$id], $description[$id], $grade[$id], null); } - att_update_all_users_grades($att->id, $att->course, $att->context, $cm); + if ($att->grade > 0) { + att_update_all_users_grades($att->id, $att->course, $att->context, $cm); + } break; } diff --git a/sessions.php b/sessions.php index b32e087..b03b3df 100644 --- a/sessions.php +++ b/sessions.php @@ -85,7 +85,9 @@ switch ($att->pageparams->action) { if (isset($confirm) && confirm_sesskey()) { $att->delete_sessions(array($sessionid)); - att_update_all_users_grades($att->id, $att->course, $att->context, $cm); + if ($att->grade > 0) { + att_update_all_users_grades($att->id, $att->course, $att->context, $cm); + } redirect($att->url_manage(), get_string('sessiondeleted', 'attendance')); } @@ -112,7 +114,9 @@ switch ($att->pageparams->action) { $sessionsids = explode('_', $sessionsids); $att->delete_sessions($sessionsids); - att_update_all_users_grades($att->id, $att->course, $att->context, $cm); + if ($att->grade > 0) { + att_update_all_users_grades($att->id, $att->course, $att->context, $cm); + } redirect($att->url_manage(), get_string('sessiondeleted', 'attendance')); } $sessid = required_param('sessid', PARAM_SEQUENCE); From 116c4d55eee295fe77d1cb96d0b290094255cedb Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 9 May 2014 13:29:41 +1200 Subject: [PATCH 47/75] CONTRIB-4864 prevent PHP warning when checking var --- locallib.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/locallib.php b/locallib.php index 230baab..ace0f42 100644 --- a/locallib.php +++ b/locallib.php @@ -1073,7 +1073,7 @@ class attendance { public function get_user_taken_sessions_count($userid) { if (!array_key_exists($userid, $this->usertakensesscount)) { - if ($this->pageparams->startdate && $this->pageparams->enddate) { + if (!empty($this->pageparams->startdate) && !empty($this->pageparams->enddate)) { $this->usertakensesscount[$userid] = att_get_user_taken_sessions_count($this->id, $this->course->startdate, $userid, $this->cm, $this->pageparams->startdate, $this->pageparams->enddate); } else { $this->usertakensesscount[$userid] = att_get_user_taken_sessions_count($this->id, $this->course->startdate, $userid, $this->cm); From 53c8be2acd21619ca38b22cf184bc795a9c355e1 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 9 May 2014 13:33:07 +1200 Subject: [PATCH 48/75] bump version of stable release to include latest fixes --- version.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/version.php b/version.php index 70a3faa..ed95d2e 100644 --- a/version.php +++ b/version.php @@ -22,9 +22,9 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -$module->version = 2014022800; +$module->version = 2014022801; $module->requires = 2013040500; -$module->release = '2.6.0'; +$module->release = '2.6.1'; $module->maturity = MATURITY_STABLE; $module->cron = 0; $module->component = 'mod_attendance'; From 52d116dbb7301c6b27c6d3f6e2b119cb18487604 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 9 May 2014 13:35:28 +1200 Subject: [PATCH 49/75] convert to using $plugin instead of $module --- version.php | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/version.php b/version.php index ed95d2e..ae31eea 100644 --- a/version.php +++ b/version.php @@ -22,12 +22,12 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -$module->version = 2014022801; -$module->requires = 2013040500; -$module->release = '2.6.1'; -$module->maturity = MATURITY_STABLE; -$module->cron = 0; -$module->component = 'mod_attendance'; +$plugin->version = 2014022801; +$plugin->requires = 2013040500; +$plugin->release = '2.6.1'; +$plugin->maturity = MATURITY_STABLE; +$plugin->cron = 0; +$plugin->component = 'mod_attendance'; // Nasty upgrade code to check if need to upgrade from attforblock. // TODO: remove this asap. From ce9eb2a16f01c333c73d06045cd66f5f6e0cd040 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Fri, 9 May 2014 13:55:09 +1200 Subject: [PATCH 50/75] remove php warning from report page when no sessions exist --- renderer.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/renderer.php b/renderer.php index 6b7cdbf..cbfa0ab 100755 --- a/renderer.php +++ b/renderer.php @@ -816,7 +816,7 @@ class mod_attendance_renderer extends plugin_renderer_base { } if ($reportdata->sessionslog) { - if (isset($reportdata->sessionslog[$user->id][$sess->id]->remarks)) { + if (isset($sess) && isset($reportdata->sessionslog[$user->id][$sess->id]->remarks)) { $row->cells[] = $reportdata->sessionslog[$user->id][$sess->id]->remarks; } else { $row->cells[] = ''; From 6cbe5405495ebc19238d5465206bf5af2e52b28c Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Mon, 12 May 2014 08:52:17 +1200 Subject: [PATCH 51/75] init sessionstat vars correctly --- renderer.php | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/renderer.php b/renderer.php index cbfa0ab..f2dd992 100755 --- a/renderer.php +++ b/renderer.php @@ -320,6 +320,9 @@ class mod_attendance_renderer extends plugin_renderer_base { $table .= html_writer::tag('center', html_writer::empty_tag('input', $params)); $table = html_writer::tag('form', $table, array('method' => 'post', 'action' => $takedata->url_path())); + foreach($takedata->statuses as $status) { + $sessionstats[$status->id] = 0; + } // Calculate the sum of statuses for each user $sessionstats[] = array(); foreach ($takedata->sessionlog as $userlog) { @@ -760,6 +763,7 @@ class mod_attendance_renderer extends plugin_renderer_base { $table->head[] = $this->construct_fullname_head($reportdata); $table->align[] = 'left'; $table->size[] = ''; + $sessionstats = array(); foreach ($reportdata->sessions as $sess) { $sesstext = userdate($sess->sessdate, get_string('strftimedm', 'attendance')); @@ -780,6 +784,7 @@ class mod_attendance_renderer extends plugin_renderer_base { $table->head[] = $status->acronym; $table->align[] = 'center'; $table->size[] = '1px'; + $sessionstats[$status->id] = 0; } if ($reportdata->gradable) { @@ -830,7 +835,6 @@ class mod_attendance_renderer extends plugin_renderer_base { $statrow->cells[] = ''; $statrow->cells[] = get_string('summary'); foreach ($reportdata->sessions as $sess) { - $sessionstats = array(); foreach ($reportdata->users as $user) { foreach($reportdata->statuses as $status) { if ($reportdata->sessionslog[$user->id][$sess->id]->statusid == $status->id) $sessionstats[$status->id]++; From 05ea479905ee3e037556c08dd4fb515bba68acda Mon Sep 17 00:00:00 2001 From: Nadav Kavalerchik Date: Mon, 12 May 2014 00:08:25 +0300 Subject: [PATCH 52/75] Display the number of users in the sessions report (take II) --- renderer.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/renderer.php b/renderer.php index f2dd992..631cd00 100755 --- a/renderer.php +++ b/renderer.php @@ -850,7 +850,7 @@ class mod_attendance_renderer extends plugin_renderer_base { } $table->data[] = $statrow; - return html_writer::table($table); + return html_writer::table($table).html_writer::tag('div',get_string('users').': '.count($reportdata->users));; } protected function render_attendance_preferences_data(attendance_preferences_data $prefdata) { From a7c20c31c9820a27172f162da61b323bde2d39a8 Mon Sep 17 00:00:00 2001 From: Dan Marsden Date: Mon, 12 May 2014 10:04:18 +1200 Subject: [PATCH 53/75] remove double semi-colon --- renderer.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/renderer.php b/renderer.php index 631cd00..f8ce347 100755 --- a/renderer.php +++ b/renderer.php @@ -850,7 +850,7 @@ class mod_attendance_renderer extends plugin_renderer_base { } $table->data[] = $statrow; - return html_writer::table($table).html_writer::tag('div',get_string('users').': '.count($reportdata->users));; + return html_writer::table($table).html_writer::tag('div', get_string('users').': '.count($reportdata->users)); } protected function render_attendance_preferences_data(attendance_preferences_data $prefdata) { From c3ea7631ed6c5ac35d150acba77b5c19d4b3be88 Mon Sep 17 00:00:00 2001 From: Neill Magill Date: Thu, 29 Aug 2013 14:05:07 +0100 Subject: [PATCH 54/75] UoN Changes to allow students to mark their own attendance on sessions that have been set to allow it. Adds a Report that lists only students who do not have full attendance. Adds the Ability to send e-mails to students. --- add_form.php | 4 ++ attendance.php | 84 +++++++++++++++++++++++++++++++++ db/install.xml | 1 + db/upgrade.php | 12 ++++- lang/en/attendance.php | 8 ++++ locallib.php | 95 ++++++++++++++++++++++++++++++++++++-- renderables.php | 38 +++++++++++---- renderer.php | 54 +++++++++++++++++++++- report.php | 2 +- sessions.php | 6 +++ student_attenance_form.php | 63 +++++++++++++++++++++++++ 11 files changed, 352 insertions(+), 15 deletions(-) create mode 100644 attendance.php mode change 100755 => 100644 renderer.php create mode 100644 student_attenance_form.php diff --git a/add_form.php b/add_form.php index 9fc813a..53dc051 100644 --- a/add_form.php +++ b/add_form.php @@ -103,6 +103,10 @@ class mod_attendance_add_form extends moodleform { $mform->addElement('checkbox', 'addmultiply', '', get_string('createmultiplesessions', 'attendance')); $mform->addHelpButton('addmultiply', 'createmultiplesessions', 'attendance'); + // Studetns can mark own attendance. + $mform->addElement('checkbox', 'studentscanmark', '', get_string('studentscanmark','attforblock')); + $mform->addHelpButton('studentscanmark', 'studentscanmark', 'attforblock'); + $mform->addElement('date_time_selector', 'sessiondate', get_string('sessiondate', 'attendance')); for ($i=0; $i<=23; $i++) { diff --git a/attendance.php b/attendance.php new file mode 100644 index 0000000..9f5699b --- /dev/null +++ b/attendance.php @@ -0,0 +1,84 @@ +. + +/** + * Prints attendance info for particular user + * + * @package mod + * @subpackage attforblock + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + +require_once(dirname(__FILE__).'/../../config.php'); +require_once(dirname(__FILE__).'/locallib.php'); +require_once(dirname(__FILE__).'/student_attenance_form.php'); + +$pageparams = new att_sessions_page_params(); + +// Check that the required parameters are present. +$id = required_param('sessid', PARAM_INT); +$attendance_session_id = required_param('sessid', PARAM_INT); + + +$attforsession = $DB->get_record('attendance_sessions', array('id' => $id), '*', MUST_EXIST); +$attforblock = $DB->get_record('attforblock', array('id' => $attforsession->attendanceid), '*', MUST_EXIST); +$cm = get_coursemodule_from_instance('attforblock', $attforblock->id, 0, false, MUST_EXIST); +$course = $DB->get_record('course', array('id' => $cm->course), '*', MUST_EXIST); + +// Require the user is logged in. +require_login($course, true, $cm); + +$pageparams->sessionid = $id; +$att = new attforblock($attforblock, $cm, $course, $PAGE->context, $pageparams); + +// Require that a session key is passed to this page. +require_sesskey(); + +// Create the form. +$mform = new mod_attforblock_student_attendance_form(null, + array('course' => $course, 'cm' => $cm, 'modcontext' => $PAGE->context, 'session' => $attforsession, 'attendance' => $att)); + +if ($mform->is_cancelled()) { + // The user cancelled the form, so redirect them to the view page. + $url = new moodle_url('/mod/attforblock/view.php', array('id' => $cm->id)); + redirect($url); +} else if ($fromform = $mform->get_data()) { + if (!empty($fromform->status)) { + $success = $att->take_from_student($fromform); + + $url = new moodle_url('/mod/attforblock/view.php', array('id' => $cm->id)); + if ($success) { + // Redirect back to the view page for the block. + redirect($url); + } else { + print_error ('attendance_already_submitted', 'mod_attforblock', $url); + } + } + + // The form did not validate correctly so we will set it to display the data they submitted. + $mform->set_data($fromform); +} + +$PAGE->set_url($att->url_sessions()); +$PAGE->set_title($course->shortname. ": ".$att->name); +$PAGE->set_heading($course->fullname); +$PAGE->set_cacheable(true); +$PAGE->navbar->add($att->name); + +$output = $PAGE->get_renderer('mod_attforblock'); +echo $output->header(); +$mform->display(); +echo $output->footer(); diff --git a/db/install.xml b/db/install.xml index 1bc5a05..ca4e6b0 100644 --- a/db/install.xml +++ b/db/install.xml @@ -30,6 +30,7 @@ + diff --git a/db/upgrade.php b/db/upgrade.php index c00926f..b38d71f 100644 --- a/db/upgrade.php +++ b/db/upgrade.php @@ -32,7 +32,17 @@ function xmldb_attendance_upgrade($oldversion=0) { global $CFG, $THEME, $DB; $dbman = $DB->get_manager(); // Loads ddl manager and xmldb classes. - $result = true; + if ($oldversion < 2013082901) { + $table = new xmldb_table('attendance_sessions'); + + $field = new xmldb_field('studentscanmark'); + $field->set_attributes(XMLDB_TYPE_INTEGER, '1', XMLDB_UNSIGNED, XMLDB_NOTNULL, null, '0'); + if (!$dbman->field_exists($table, $field)) { + $dbman->add_field($table, $field); + } + + upgrade_mod_savepoint(true, 2013082901, 'attendance'); + } if ($oldversion < 2013082902) { // Replace values that reference old module "attforblock" to "attendance". diff --git a/lang/en/attendance.php b/lang/en/attendance.php index 4c8df1f..ee35575 100755 --- a/lang/en/attendance.php +++ b/lang/en/attendance.php @@ -216,3 +216,11 @@ $string['viewmode'] = 'View mode'; $string['week'] = 'week(s)'; $string['weeks'] = 'Weeks'; $string['youcantdo'] = 'You can\'t do anything'; +// New strings. +$string['studentscanmark'] = 'Allow students to record own attendance'; +$string['studentscanmark_help'] = 'If checked students will be able to change their own attendance status for the session.'; +$string['set_by_student'] = 'Self-recorded'; +$string['attendance_already_submitted'] = 'You may not self register attendance that has already been set.'; +$string['lowgrade'] = 'Low grade'; +$string['submitattendance'] = 'Submit attendance'; +$string['attendancenotset'] = 'You must set your attendance'; diff --git a/locallib.php b/locallib.php index ace0f42..d5d2d79 100644 --- a/locallib.php +++ b/locallib.php @@ -33,6 +33,7 @@ define('ATT_VIEW_WEEKS', 2); define('ATT_VIEW_MONTHS', 3); define('ATT_VIEW_ALLPAST', 4); define('ATT_VIEW_ALL', 5); +define('ATT_VIEW_NOTPRESENT', 6); define('ATT_SORT_LASTNAME', 1); define('ATT_SORT_FIRSTNAME', 2); @@ -701,6 +702,8 @@ class attendance { if ($this->pageparams->startdate && $this->pageparams->enddate) { $where = "attendanceid = :aid AND sessdate >= :csdate AND sessdate >= :sdate AND sessdate < :edate"; + } else if ($this->pageparams->enddate) { + $where = "attendanceid = :aid AND sessdate >= :csdate AND sessdate < :edate"; } else { $where = "attendanceid = :aid AND sessdate >= :csdate"; } @@ -833,6 +836,57 @@ class attendance { add_to_log($this->course->id, 'attendance', 'session updated', $url, $info, $this->cm->id); } + /** + * Used to record attendance submitted by the student. + * + * @global type $DB + * @global type $USER + * @param type $mformdata + * @return boolean + */ + public function take_from_student($mformdata) { + global $DB, $USER; + + $statuses = implode(',', array_keys( (array)$this->get_statuses() )); + $now = time(); + + $record = new stdClass(); + $record->studentid = $USER->id; + $record->statusid = $mformdata->status; + $record->statusset = $statuses; + $record->remarks = get_string('set_by_student', 'mod_attforblock'); + $record->sessionid = $mformdata->sessid; + $record->timetaken = $now; + $record->takenby = $USER->id; + + $dbsesslog = $this->get_session_log($mformdata->sessid); + if (array_key_exists($record->studentid, $dbsesslog)) { + // Already recorded do not save. + return false; + } + else { + $DB->insert_record('attendance_log', $record, false); + } + + // Update the session to show that a register has been taken, or staff may overwrite records. + $rec = new object(); + $rec->id = $mformdata->sessid; + $rec->lasttaken = $now; + $rec->lasttakenby = $USER->id; + $DB->update_record('attendance_sessions', $rec); + + // Update the users grade. + $this->update_users_grade(array($USER->id)); + + // Log the change. + $params = array( + 'sessionid' => $mformdata->sessid); + $url = $this->url_take($params); + $this->log('attendance taked', $url, $USER->firstname.' '.$USER->lastname); + + return true; + } + public function take_from_form_data($formdata) { global $DB, $USER; // TODO: WARNING - $formdata is unclean - comes from direct $_POST - ideally needs a rewrite but we do some cleaning below. @@ -1082,7 +1136,14 @@ class attendance { return $this->usertakensesscount[$userid]; } - public function get_user_statuses_stat($userid) { + /** + * + * @global type $DB + * @param type $userid + * @param type $filters - An array things to filter by. For now only enddate is valid. + * @return type + */ + public function get_user_statuses_stat($userid, array $filters = null) { global $DB; $params = array( 'aid' => $this->id, @@ -1120,14 +1181,42 @@ class attendance { } + // Make the filter array into a SQL string. + if (!empty($processed_filters)) { + $processed_filters = 'AND '.implode(' AND ', $processed_filters); + } else { + $processed_filters = ''; + } + + $qry = "SELECT al.statusid, count(al.statusid) AS stcnt + FROM {attendance_log} al + JOIN {attendance_sessions} ats + ON al.sessionid = ats.id + WHERE ats.attendanceid = :aid AND + ats.sessdate >= :cstartdate AND + al.studentid = :uid + $processed_filters + GROUP BY al.statusid"; + + if ($filters !== null) { // We do not want to cache, or use a cached version of the results when a filter is set. + return $DB->get_records_sql($qry, $params); + } else if (!array_key_exists($userid, $this->userstatusesstat)) { + // Not filtered so if we do not already have them do the query. $this->userstatusesstat[$userid] = $DB->get_records_sql($qry, $params); } + // Return the cached stats. return $this->userstatusesstat[$userid]; } - public function get_user_grade($userid) { - return att_get_user_grade($this->get_user_statuses_stat($userid), $this->get_statuses()); + /** + * + * @param type $userid + * @param type $filters - An array things to filter by. For now only enddate is valid. + * @return type + */ + public function get_user_grade($userid, array $filters = null) { + return att_get_user_grade($this->get_user_statuses_stat($userid, $filters), $this->get_statuses()); } // For getting sessions count implemented simplest method - taken sessions. diff --git a/renderables.php b/renderables.php index 373bdc0..75c5324 100644 --- a/renderables.php +++ b/renderables.php @@ -109,19 +109,23 @@ class attendance_filter_controls implements renderable { public $prevcur; public $nextcur; public $curdatetxt; + public $reportcontrol; private $urlpath; private $urlparams; private $att; - public function __construct(attendance $att) { + public function __construct(attendance $att, $report = false) { global $PAGE; $this->pageparams = $att->pageparams; $this->cm = $att->cm; + // This is a report control only if $reports is true and the attendance block can be graded. + $this->reportcontrol = $report && ($att->grade > 0); + $this->curdate = $att->pageparams->curdate; $date = usergetdate($att->pageparams->curdate); @@ -456,6 +460,12 @@ class attendance_report_data implements renderable { global $CFG; $this->perm = $att->perm; + + $currenttime = time(); + if ($att->pageparams->view == ATT_VIEW_NOTPRESENT) { + $att->pageparams->enddate = $currenttime; + } + $this->pageparams = $att->pageparams; $this->users = $att->get_users($att->pageparams->group, $att->pageparams->page); @@ -473,16 +483,28 @@ class attendance_report_data implements renderable { $this->decimalpoints = $CFG->grade_decimalpoints; } - foreach ($this->users as $user) { - $this->usersgroups[$user->id] = groups_get_all_groups($att->course->id, $user->id); + $maxgrade = att_get_user_max_grade(count($this->sessions), $this->statuses); - $this->sessionslog[$user->id] = $att->get_user_filtered_sessions_log($user->id); + foreach ($this->users as $key => $user) { + $grade = 0; + if ($this->gradable) { + $grade = $att->get_user_grade($user->id, array('enddate' => $currenttime)); + $totalgrade = $att->get_user_grade($user->id); + } - $this->usersstats[$user->id] = $att->get_user_statuses_stat($user->id); + if ($att->pageparams->view != ATT_VIEW_NOTPRESENT || $grade < $maxgrade) { + $this->usersgroups[$user->id] = groups_get_all_groups($att->course->id, $user->id); - if ($this->gradable) { - $this->grades[$user->id] = $att->get_user_grade($user->id); - $this->maxgrades[$user->id] = $att->get_user_max_grade($user->id); + $this->sessionslog[$user->id] = $att->get_user_filtered_sessions_log($user->id); + + $this->usersstats[$user->id] = $att->get_user_statuses_stat($user->id); + + if ($this->gradable) { + $this->grades[$user->id] = $totalgrade; + $this->maxgrades[$user->id] = $att->get_user_max_grade($user->id);; + } + } else { + unset($this->users[$key]); } } diff --git a/renderer.php b/renderer.php old mode 100755 new mode 100644 index f8ce347..7ec3216 --- a/renderer.php +++ b/renderer.php @@ -173,6 +173,9 @@ class mod_attendance_renderer extends plugin_renderer_base { protected function render_view_controls(attendance_filter_controls $fcontrols) { $views[ATT_VIEW_ALL] = get_string('all', 'attendance'); $views[ATT_VIEW_ALLPAST] = get_string('allpast', 'attendance'); + if ($fcontrols->reportcontrol) { + $views[ATT_VIEW_NOTPRESENT] = get_string('lowgrade', 'attforblock'); + } $views[ATT_VIEW_MONTHS] = get_string('months', 'attendance'); $views[ATT_VIEW_WEEKS] = get_string('weeks', 'attendance'); $views[ATT_VIEW_DAYS] = get_string('days', 'attendance'); @@ -734,8 +737,17 @@ class mod_attendance_renderer extends plugin_renderer_base { $cell->colspan = 2; $row->cells[] = $cell; } else { - $row->cells[] = '?'; - $row->cells[] = ''; + if (!empty($sess->studentscanmark)) { // Student can mark their own attendance. + // URL to the page that lets the student modify their attendance. + $url = new moodle_url('/mod/attforblock/attendance.php', + array('sessid' => $sess->id, 'sesskey' => sesskey())); + $cell = new html_table_cell(html_writer::link($url, get_string('submitattendance', 'attforblock'))); + $cell->colspan = 2; + $row->cells[] = $cell; + } else { // Student cannot mark their own attendace. + $row->cells[] = '?'; + $row->cells[] = ''; + } } $table->data[] = $row; @@ -751,6 +763,14 @@ class mod_attendance_renderer extends plugin_renderer_base { } protected function render_attendance_report_data(attendance_report_data $reportdata) { + global $PAGE; + + // Initilise Javascript used to (un)check all checkboxes. + $this->page->requires->js_init_call('M.mod_attforblock.init_manage'); + + // Check if the user should be able to bulk send messages to other users on the course. + $bulkmessagecapability = has_capability('moodle/course:bulkmessaging', $PAGE->context); + $table = new html_table(); $table->attributes['class'] = 'generaltable attwidth'; @@ -792,6 +812,14 @@ class mod_attendance_renderer extends plugin_renderer_base { $table->align[] = 'center'; $table->size[] = '1px'; } + + if ($bulkmessagecapability) { // Display the table header for bulk messaging. + // The checkbox must have an id of cb_selector so that the JavaScript will pick it up. + $table->head[] = html_writer::checkbox('cb_selector', 0, false, '', array('id' => 'cb_selector')); + $table->align[] = 'center'; + $table->size[] = '1px'; + } + if ($reportdata->sessionslog) { $table->head[] = get_string('remarks', 'attendance'); @@ -820,6 +848,28 @@ class mod_attendance_renderer extends plugin_renderer_base { $row->cells[] = $reportdata->grades[$user->id].' / '.$reportdata->maxgrades[$user->id]; } + if ($bulkmessagecapability) { // Create the checkbox for bulk messaging. + $row->cells[] = html_writer::checkbox('user'.$user->id, 'on', false); + } + + $table->data[] = $row; + } + + if ($bulkmessagecapability) { // Require that the user can bulk message users. + // Display check boxes that will allow the user to send a message to the students that have been checked. + $output = html_writer::empty_tag('input', array('name' => 'sesskey', 'type' => 'hidden', 'value' => sesskey())); + $output .= html_writer::empty_tag('input', array('name' => 'formaction', 'type' => 'hidden', 'value' => 'messageselect.php')); + $output .= html_writer::empty_tag('input', array('name' => 'id', 'type' => 'hidden', 'value' => $GLOBALS['COURSE']->id)); + $output .= html_writer::empty_tag('input', array('name' => 'returnto', 'type' => 'hidden', 'value' => s(me()))); + $output .= html_writer::table($table); + $output .= html_writer::tag('div', + html_writer::empty_tag('input', array('type' => 'submit', 'value' => get_string('messageselectadd'))), + array('class' => 'buttons')); + $url = new moodle_url('/user/action_redir.php'); + return html_writer::tag('form', $output, array('action' => $url->out(), 'method' => 'post')); + } else { + return html_writer::table($table); + } if ($reportdata->sessionslog) { if (isset($sess) && isset($reportdata->sessionslog[$user->id][$sess->id]->remarks)) { $row->cells[] = $reportdata->sessionslog[$user->id][$sess->id]->remarks; diff --git a/report.php b/report.php index 8a4d4cf..a0503f5 100644 --- a/report.php +++ b/report.php @@ -58,7 +58,7 @@ $PAGE->navbar->add(get_string('report', 'attendance')); $output = $PAGE->get_renderer('mod_attendance'); $tabs = new attendance_tabs($att, attendance_tabs::TAB_REPORT); $filtercontrols = new attendance_filter_controls($att); -$reportdata = new attendance_report_data($att); +$reportdata = new attendance_report_data($att, true); add_to_log($course->id, 'attendance', 'report viewed', '/mod/attendance/report.php?id='.$id, '', $cm->id); diff --git a/sessions.php b/sessions.php index b03b3df..fda84fe 100644 --- a/sessions.php +++ b/sessions.php @@ -220,6 +220,9 @@ function construct_sessions_data_for_add($formdata) { $sess->description = $formdata->sdescription['text']; $sess->descriptionformat = $formdata->sdescription['format']; $sess->timemodified = $now; + if (isset($formdata->studentscanmark)) { // Students will be able to mark their own attendance. + $sess->studentscanmark = 1; + } fill_groupid($formdata, $sessions, $sess); } @@ -237,6 +240,9 @@ function construct_sessions_data_for_add($formdata) { $sess->description = $formdata->sdescription['text']; $sess->descriptionformat = $formdata->sdescription['format']; $sess->timemodified = $now; + if (isset($formdata->studentscanmark)) { // Students will be able to mark their own attendance. + $sess->studentscanmark = 1; + } fill_groupid($formdata, $sessions, $sess); } diff --git a/student_attenance_form.php b/student_attenance_form.php new file mode 100644 index 0000000..7089b39 --- /dev/null +++ b/student_attenance_form.php @@ -0,0 +1,63 @@ +. + +require_once($CFG->libdir.'/formslib.php'); + +class mod_attforblock_student_attendance_form extends moodleform { + public function definition() { + global $CFG, $USER; + + $mform =& $this->_form; + + $course = $this->_customdata['course']; + $cm = $this->_customdata['cm']; + $modcontext = $this->_customdata['modcontext']; + $attforsession = $this->_customdata['session']; + $attblock = $this->_customdata['attendance']; + + $statuses = $attblock->get_statuses(); + + $mform->addElement('hidden', 'sessid', null); + $mform->setType('sessid', PARAM_INT); + $mform->setConstant('sessid', $attforsession->id); + + $mform->addElement('hidden', 'sesskey', null); + $mform->setType('sesskey', PARAM_INT); + $mform->setConstant('sesskey', sesskey()); + + // Set a title as the date and time of the session. + $sesstiontitle = userdate($attforsession->sessdate, get_string('strftimedate')).' ' + .userdate($attforsession->sessdate, get_string('strftimehm', 'mod_attforblock')); + + $mform->addElement('header', 'session', $sesstiontitle); + + // If a session description is set display it. + if (!empty($attforsession->description)) { + $mform->addElement('html', $attforsession->description); + } + + // Create radio buttons for setting the attendance status. + $radioarray = array(); + foreach ($statuses as $status) { + $radioarray[] =& $mform->createElement('radio', 'status', '', $status->description, $status->id, array()); + } + // Add the radio buttons as a control with the user's name in front. + $mform->addGroup($radioarray, 'statusarray', $USER->firstname.' '.$USER->lastname.':', array(''), false); + $mform->addRule('statusarray', get_string('attendancenotset', 'attforblock'), 'required', '', 'client', false, false); + + $this->add_action_buttons(); + } +} \ No newline at end of file From 91d19e10eafe0b0eec3f6733e173e17cce9e4a31 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Wed, 21 May 2014 14:51:27 +0100 Subject: [PATCH 55/75] first round of fixes --- add_form.php | 6 +++--- attendance.php | 18 +++++++++--------- .../backup_attendance_activity_task.class.php | 4 ++-- .../restore_attendance_activity_task.class.php | 4 ++-- locallib.php | 6 +++--- renderer.php | 8 ++++---- student_attenance_form.php | 6 +++--- 7 files changed, 26 insertions(+), 26 deletions(-) diff --git a/add_form.php b/add_form.php index 53dc051..a9550a3 100644 --- a/add_form.php +++ b/add_form.php @@ -103,9 +103,9 @@ class mod_attendance_add_form extends moodleform { $mform->addElement('checkbox', 'addmultiply', '', get_string('createmultiplesessions', 'attendance')); $mform->addHelpButton('addmultiply', 'createmultiplesessions', 'attendance'); - // Studetns can mark own attendance. - $mform->addElement('checkbox', 'studentscanmark', '', get_string('studentscanmark','attforblock')); - $mform->addHelpButton('studentscanmark', 'studentscanmark', 'attforblock'); + // Students can mark own attendance. + $mform->addElement('checkbox', 'studentscanmark', '', get_string('studentscanmark','attendance')); + $mform->addHelpButton('studentscanmark', 'studentscanmark', 'attendance'); $mform->addElement('date_time_selector', 'sessiondate', get_string('sessiondate', 'attendance')); diff --git a/attendance.php b/attendance.php index 9f5699b..539354c 100644 --- a/attendance.php +++ b/attendance.php @@ -18,7 +18,7 @@ * Prints attendance info for particular user * * @package mod - * @subpackage attforblock + * @subpackage attendance * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ @@ -34,37 +34,37 @@ $attendance_session_id = required_param('sessid', PARAM_INT); $attforsession = $DB->get_record('attendance_sessions', array('id' => $id), '*', MUST_EXIST); -$attforblock = $DB->get_record('attforblock', array('id' => $attforsession->attendanceid), '*', MUST_EXIST); -$cm = get_coursemodule_from_instance('attforblock', $attforblock->id, 0, false, MUST_EXIST); +$attendance = $DB->get_record('attendance', array('id' => $attforsession->attendanceid), '*', MUST_EXIST); +$cm = get_coursemodule_from_instance('attendance', $attendance->id, 0, false, MUST_EXIST); $course = $DB->get_record('course', array('id' => $cm->course), '*', MUST_EXIST); // Require the user is logged in. require_login($course, true, $cm); $pageparams->sessionid = $id; -$att = new attforblock($attforblock, $cm, $course, $PAGE->context, $pageparams); +$att = new attendance($attendance, $cm, $course, $PAGE->context, $pageparams); // Require that a session key is passed to this page. require_sesskey(); // Create the form. -$mform = new mod_attforblock_student_attendance_form(null, +$mform = new mod_attendance_student_attendance_form(null, array('course' => $course, 'cm' => $cm, 'modcontext' => $PAGE->context, 'session' => $attforsession, 'attendance' => $att)); if ($mform->is_cancelled()) { // The user cancelled the form, so redirect them to the view page. - $url = new moodle_url('/mod/attforblock/view.php', array('id' => $cm->id)); + $url = new moodle_url('/mod/attendance/view.php', array('id' => $cm->id)); redirect($url); } else if ($fromform = $mform->get_data()) { if (!empty($fromform->status)) { $success = $att->take_from_student($fromform); - $url = new moodle_url('/mod/attforblock/view.php', array('id' => $cm->id)); + $url = new moodle_url('/mod/attendance/view.php', array('id' => $cm->id)); if ($success) { // Redirect back to the view page for the block. redirect($url); } else { - print_error ('attendance_already_submitted', 'mod_attforblock', $url); + print_error ('attendance_already_submitted', 'mod_attendance', $url); } } @@ -78,7 +78,7 @@ $PAGE->set_heading($course->fullname); $PAGE->set_cacheable(true); $PAGE->navbar->add($att->name); -$output = $PAGE->get_renderer('mod_attforblock'); +$output = $PAGE->get_renderer('mod_attendance'); echo $output->header(); $mform->display(); echo $output->footer(); diff --git a/backup/moodle2/backup_attendance_activity_task.class.php b/backup/moodle2/backup_attendance_activity_task.class.php index 87b5c89..df3b4a0 100644 --- a/backup/moodle2/backup_attendance_activity_task.class.php +++ b/backup/moodle2/backup_attendance_activity_task.class.php @@ -60,11 +60,11 @@ class backup_attendance_activity_task extends backup_activity_task { // Link to attendance view by moduleid. $search = "/(" . $base . "\/mod\/attendance\/view.php\?id\=)([0-9]+)/"; - $content= preg_replace($search, '$@ATTFORBLOCKVIEWBYID*$2@$', $content); + $content= preg_replace($search, '$@ATTENDANCEVIEWBYID*$2@$', $content); // Link to attendance view by moduleid and studentid. $search = "/(" . $base . "\/mod\/attendance\/view.php\?id\=)([0-9]+)\&studentid\=([0-9]+)/"; - $content= preg_replace($search, '$@ATTFORBLOCKVIEWBYIDSTUD*$2*$3@$', $content); + $content= preg_replace($search, '$@ATTENDANCEVIEWBYIDSTUD*$2*$3@$', $content); return $content; } diff --git a/backup/moodle2/restore_attendance_activity_task.class.php b/backup/moodle2/restore_attendance_activity_task.class.php index 5ca7794..629cecd 100644 --- a/backup/moodle2/restore_attendance_activity_task.class.php +++ b/backup/moodle2/restore_attendance_activity_task.class.php @@ -67,9 +67,9 @@ class restore_attendance_activity_task extends restore_activity_task { static public function define_decode_rules() { $rules = array(); - $rules[] = new restore_decode_rule('ATTFORBLOCKVIEWBYID', + $rules[] = new restore_decode_rule('ATTENDANCEVIEWBYID', '/mod/attendance/view.php?id=$1', 'course_module'); - $rules[] = new restore_decode_rule('ATTFORBLOCKVIEWBYIDSTUD', + $rules[] = new restore_decode_rule('ATTENDANCEVIEWBYIDSTUD', '/mod/attendance/view.php?id=$1&studentid=$2', array('course_module', 'user')); return $rules; diff --git a/locallib.php b/locallib.php index d5d2d79..ce2e3c8 100644 --- a/locallib.php +++ b/locallib.php @@ -854,7 +854,7 @@ class attendance { $record->studentid = $USER->id; $record->statusid = $mformdata->status; $record->statusset = $statuses; - $record->remarks = get_string('set_by_student', 'mod_attforblock'); + $record->remarks = get_string('set_by_student', 'mod_attendance'); $record->sessionid = $mformdata->sessid; $record->timetaken = $now; $record->takenby = $USER->id; @@ -882,8 +882,8 @@ class attendance { $params = array( 'sessionid' => $mformdata->sessid); $url = $this->url_take($params); - $this->log('attendance taked', $url, $USER->firstname.' '.$USER->lastname); - + add_to_log($this->course->id, 'attendance', 'taken', $url, '', $USER->id); + return true; } diff --git a/renderer.php b/renderer.php index 7ec3216..537b75d 100644 --- a/renderer.php +++ b/renderer.php @@ -174,7 +174,7 @@ class mod_attendance_renderer extends plugin_renderer_base { $views[ATT_VIEW_ALL] = get_string('all', 'attendance'); $views[ATT_VIEW_ALLPAST] = get_string('allpast', 'attendance'); if ($fcontrols->reportcontrol) { - $views[ATT_VIEW_NOTPRESENT] = get_string('lowgrade', 'attforblock'); + $views[ATT_VIEW_NOTPRESENT] = get_string('lowgrade', 'attendance'); } $views[ATT_VIEW_MONTHS] = get_string('months', 'attendance'); $views[ATT_VIEW_WEEKS] = get_string('weeks', 'attendance'); @@ -739,9 +739,9 @@ class mod_attendance_renderer extends plugin_renderer_base { } else { if (!empty($sess->studentscanmark)) { // Student can mark their own attendance. // URL to the page that lets the student modify their attendance. - $url = new moodle_url('/mod/attforblock/attendance.php', + $url = new moodle_url('/mod/attendance/attendance.php', array('sessid' => $sess->id, 'sesskey' => sesskey())); - $cell = new html_table_cell(html_writer::link($url, get_string('submitattendance', 'attforblock'))); + $cell = new html_table_cell(html_writer::link($url, get_string('submitattendance', 'attendance'))); $cell->colspan = 2; $row->cells[] = $cell; } else { // Student cannot mark their own attendace. @@ -766,7 +766,7 @@ class mod_attendance_renderer extends plugin_renderer_base { global $PAGE; // Initilise Javascript used to (un)check all checkboxes. - $this->page->requires->js_init_call('M.mod_attforblock.init_manage'); + $this->page->requires->js_init_call('M.mod_attendance.init_manage'); // Check if the user should be able to bulk send messages to other users on the course. $bulkmessagecapability = has_capability('moodle/course:bulkmessaging', $PAGE->context); diff --git a/student_attenance_form.php b/student_attenance_form.php index 7089b39..5f7d7d7 100644 --- a/student_attenance_form.php +++ b/student_attenance_form.php @@ -16,7 +16,7 @@ require_once($CFG->libdir.'/formslib.php'); -class mod_attforblock_student_attendance_form extends moodleform { +class mod_attendance_student_attendance_form extends moodleform { public function definition() { global $CFG, $USER; @@ -40,7 +40,7 @@ class mod_attforblock_student_attendance_form extends moodleform { // Set a title as the date and time of the session. $sesstiontitle = userdate($attforsession->sessdate, get_string('strftimedate')).' ' - .userdate($attforsession->sessdate, get_string('strftimehm', 'mod_attforblock')); + .userdate($attforsession->sessdate, get_string('strftimehm', 'mod_attendance')); $mform->addElement('header', 'session', $sesstiontitle); @@ -56,7 +56,7 @@ class mod_attforblock_student_attendance_form extends moodleform { } // Add the radio buttons as a control with the user's name in front. $mform->addGroup($radioarray, 'statusarray', $USER->firstname.' '.$USER->lastname.':', array(''), false); - $mform->addRule('statusarray', get_string('attendancenotset', 'attforblock'), 'required', '', 'client', false, false); + $mform->addRule('statusarray', get_string('attendancenotset', 'attendance'), 'required', '', 'client', false, false); $this->add_action_buttons(); } From ba31d7ad831d4163c8211f6ee1068f6ccbaac953 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Wed, 21 May 2014 16:41:34 +0100 Subject: [PATCH 56/75] fix for log page link --- locallib.php | 32 +++++++++++++++++++++++++++----- 1 file changed, 27 insertions(+), 5 deletions(-) diff --git a/locallib.php b/locallib.php index ce2e3c8..a8a49b7 100644 --- a/locallib.php +++ b/locallib.php @@ -878,10 +878,23 @@ class attendance { // Update the users grade. $this->update_users_grade(array($USER->id)); - // Log the change. + /* create url for link in log screen + * need to set grouptype to 0 to allow take attendance page to be called + * from report/log page */ + $params = array( - 'sessionid' => $mformdata->sessid); - $url = $this->url_take($params); + 'sessionid' => $this->pageparams->sessionid, + 'grouptype' => 0, + 'id' => $this->cm->id); + + $url = 'take.php?'; + foreach ($params as $param => $value) { + $url = $url . $param . '=' . $value . '&'; + } + + $url = rtrim($url,'&'); + + // Log the change. add_to_log($this->course->id, 'attendance', 'taken', $url, '', $USER->id); return true; @@ -934,10 +947,19 @@ class attendance { $this->update_users_grade(array_keys($sesslog)); } + // create url for link in log screen $params = array( 'sessionid' => $this->pageparams->sessionid, - 'grouptype' => $this->pageparams->grouptype); - $url = $this->url_take($params); + 'grouptype' => $this->pageparams->grouptype, + 'id' => $this->cm->id); + + $url = 'take.php?'; + foreach ($params as $param => $value) { + $url = $url . $param . '=' . $value . '&'; + } + + $url = rtrim($url,'&'); + add_to_log($this->course->id, 'attendance', 'taken', $url, '', $this->cm->id); $group = 0; From 3272e7f45d408a2bf99082ea784deafb12a550db Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Thu, 22 May 2014 10:05:00 +0100 Subject: [PATCH 57/75] low grade report fix --- report.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/report.php b/report.php index a0503f5..b9d37eb 100644 --- a/report.php +++ b/report.php @@ -57,8 +57,8 @@ $PAGE->navbar->add(get_string('report', 'attendance')); $output = $PAGE->get_renderer('mod_attendance'); $tabs = new attendance_tabs($att, attendance_tabs::TAB_REPORT); -$filtercontrols = new attendance_filter_controls($att); -$reportdata = new attendance_report_data($att, true); +$filtercontrols = new attendance_filter_controls($att, true); +$reportdata = new attendance_report_data($att); add_to_log($course->id, 'attendance', 'report viewed', '/mod/attendance/report.php?id='.$id, '', $cm->id); From e5a4dbb12c57d3b7f04ccd85e3a4bb6c092530da Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Thu, 22 May 2014 10:41:57 +0100 Subject: [PATCH 58/75] found log function in attforblock --- locallib.php | 46 +++++++++++++++++----------------------------- 1 file changed, 17 insertions(+), 29 deletions(-) diff --git a/locallib.php b/locallib.php index a8a49b7..e5df5ca 100644 --- a/locallib.php +++ b/locallib.php @@ -810,8 +810,8 @@ class attendance { } $i++; } - add_to_log($this->course->id, 'attendance', 'sessions added', $this->url_manage(), - implode(',', $info_array), $this->cm->id); + + $this->log('sessions added', $this->url_manage(), implode(', ', $info_array)); } public function update_session_from_form_data($formdata, $sessionid) { @@ -833,7 +833,7 @@ class attendance { $url = $this->url_sessions(array('sessionid' => $sessionid, 'action' => att_sessions_page_params::ACTION_UPDATE)); $info = construct_session_full_date_time($sess->sessdate, $sess->duration); - add_to_log($this->course->id, 'attendance', 'session updated', $url, $info, $this->cm->id); + $this->log('session updated', $url, $info); } /** @@ -884,18 +884,12 @@ class attendance { $params = array( 'sessionid' => $this->pageparams->sessionid, - 'grouptype' => 0, - 'id' => $this->cm->id); - - $url = 'take.php?'; - foreach ($params as $param => $value) { - $url = $url . $param . '=' . $value . '&'; - } - - $url = rtrim($url,'&'); + 'grouptype' => 0); + + $url = $this->url_take($params); // Log the change. - add_to_log($this->course->id, 'attendance', 'taken', $url, '', $USER->id); + $this->log('attendance taken', $url, $USER->firstname.' '.$USER->lastname); return true; } @@ -950,17 +944,12 @@ class attendance { // create url for link in log screen $params = array( 'sessionid' => $this->pageparams->sessionid, - 'grouptype' => $this->pageparams->grouptype, - 'id' => $this->cm->id); - - $url = 'take.php?'; - foreach ($params as $param => $value) { - $url = $url . $param . '=' . $value . '&'; - } - - $url = rtrim($url,'&'); + 'grouptype' => $this->pageparams->grouptype); + + $url = $this->url_take($params); - add_to_log($this->course->id, 'attendance', 'taken', $url, '', $this->cm->id); + // Log the change. + $this->log('attendance taken', $url, $USER->firstname.' '.$USER->lastname); $group = 0; if ($this->pageparams->grouptype != attendance::SESSION_COMMON) { @@ -1392,8 +1381,7 @@ class attendance { list($sql, $params) = $DB->get_in_or_equal($sessionsids); $DB->delete_records_select('attendance_log', "sessionid $sql", $params); $DB->delete_records_list('attendance_sessions', 'id', $sessionsids); - add_to_log($this->course->id, 'attendance', 'sessions deleted', $this->url_manage(), - get_string('sessionsids', 'attendance').implode(', ', $sessionsids), $this->cm->id); + $this->log('sessions deleted', null, get_string('sessionsids', 'attforblock').implode(', ', $sessionsids)); } public function update_sessions_duration($sessionsids, $duration) { @@ -1409,6 +1397,8 @@ class attendance { $sessions->close(); add_to_log($this->course->id, 'attendance', 'sessions duration updated', $this->url_manage(), get_string('sessionsids', 'attendance').implode(', ', $sessionsids), $this->cm->id); + + $this->log('sessions duration updated', $this->url_manage(), get_string('sessionsids', 'attforblock').implode(', ', $sessionsids)); } public function remove_status($statusid) { @@ -1429,8 +1419,7 @@ class attendance { $rec->grade = $grade; $DB->insert_record('attendance_statuses', $rec); - add_to_log($this->course->id, 'attendance', 'status added', $this->url_preferences(), - $acronym.': '.$description.' ('.$grade.')', $this->cm->id); + $this->log('status added', $this->url_preferences(), $acronym.': '.$description.' ('.$grade.')'); } else { print_error('cantaddstatus', 'attendance', $this->url_preferences()); } @@ -1461,8 +1450,7 @@ class attendance { } $DB->update_record('attendance_statuses', $status); - add_to_log($this->course->id, 'attendance', 'status updated', $this->url_preferences(), - implode(' ', $updated), $this->cm->id); + $this->log('status updated', $this->url_preferences(), implode(' ', $updated)); } } From 11660b237977f395b14a0467b08f00b7ce35c980 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Thu, 22 May 2014 10:57:08 +0100 Subject: [PATCH 59/75] removed duplicate log word --- locallib.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/locallib.php b/locallib.php index e5df5ca..ed78519 100644 --- a/locallib.php +++ b/locallib.php @@ -889,7 +889,7 @@ class attendance { $url = $this->url_take($params); // Log the change. - $this->log('attendance taken', $url, $USER->firstname.' '.$USER->lastname); + $this->log('taken by student', $url, $USER->firstname.' '.$USER->lastname); return true; } @@ -949,7 +949,7 @@ class attendance { $url = $this->url_take($params); // Log the change. - $this->log('attendance taken', $url, $USER->firstname.' '.$USER->lastname); + $this->log('taken', $url, $USER->firstname.' '.$USER->lastname); $group = 0; if ($this->pageparams->grouptype != attendance::SESSION_COMMON) { From d217f7ed908175222509d6887520b638963f0a6c Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Fri, 23 May 2014 11:21:10 +0100 Subject: [PATCH 60/75] changes attforblock to attendance --- locallib.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/locallib.php b/locallib.php index ed78519..5e123fa 100644 --- a/locallib.php +++ b/locallib.php @@ -1381,7 +1381,7 @@ class attendance { list($sql, $params) = $DB->get_in_or_equal($sessionsids); $DB->delete_records_select('attendance_log', "sessionid $sql", $params); $DB->delete_records_list('attendance_sessions', 'id', $sessionsids); - $this->log('sessions deleted', null, get_string('sessionsids', 'attforblock').implode(', ', $sessionsids)); + $this->log('sessions deleted', null, get_string('sessionsids', 'attendance').implode(', ', $sessionsids)); } public function update_sessions_duration($sessionsids, $duration) { @@ -1398,7 +1398,7 @@ class attendance { add_to_log($this->course->id, 'attendance', 'sessions duration updated', $this->url_manage(), get_string('sessionsids', 'attendance').implode(', ', $sessionsids), $this->cm->id); - $this->log('sessions duration updated', $this->url_manage(), get_string('sessionsids', 'attforblock').implode(', ', $sessionsids)); + $this->log('sessions duration updated', $this->url_manage(), get_string('sessionsids', 'attendance').implode(', ', $sessionsids)); } public function remove_status($statusid) { From 127a72ed391d062416a5348801e2bbafb0cade15 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Fri, 23 May 2014 14:47:22 +0100 Subject: [PATCH 61/75] MOODLE-845 add idnumber to export --- export.php | 7 ++++++- export_form.php | 7 ++++--- locallib.php | 6 +++--- 3 files changed, 13 insertions(+), 7 deletions(-) diff --git a/export.php b/export.php index a0a690a..7185dd3 100644 --- a/export.php +++ b/export.php @@ -88,6 +88,9 @@ if ($mform->is_submitted()) { if (isset($formdata->ident['uname'])) { $data->tabhead[] = get_string('username'); } + if (isset($formdata->ident['idnumber'])) { + $data->tabhead[] = get_string('idnumber'); + } $data->tabhead[] = get_string('lastname'); $data->tabhead[] = get_string('firstname'); $groupmode = groups_get_activity_groupmode($cm, $course); @@ -95,7 +98,6 @@ if ($mform->is_submitted()) { $data->tabhead[] = get_string('groups'); } - if (count($reportdata->sessions) > 0) { foreach ($reportdata->sessions as $sess) { $text = userdate($sess->sessdate, get_string('strftimedmyhm', 'attendance')); @@ -122,6 +124,9 @@ if ($mform->is_submitted()) { if (isset($formdata->ident['uname'])) { $data->table[$i][] = $user->username; } + if (isset($formdata->ident['idnumber'])) { + $data->table[$i][] = $user->idnumber; + } $data->table[$i][] = $user->lastname; $data->table[$i][] = $user->firstname; if (!empty($groupmode)) { diff --git a/export_form.php b/export_form.php index 994c5e1..7e822d1 100644 --- a/export_form.php +++ b/export_form.php @@ -62,13 +62,14 @@ class mod_attendance_export_form extends moodleform { $ident = array(); $ident[] =& $mform->createElement('checkbox', 'id', '', get_string('studentid', 'attendance')); - $ident[] =& $mform->createElement('checkbox', 'uname', '', get_string('username')); + $ident[] =& $mform->createElement('checkbox', 'idnumber', '', get_string('idnumber')); $mform->addGroup($ident, 'ident', get_string('identifyby', 'attendance'), array('
'), true); - $mform->setDefaults(array('ident[id]' => true, 'ident[uname]' => true)); + $mform->setDefaults(array('ident[id]' => true, 'ident[uname]' => true, 'ident[idnumber]' => false)); $mform->setType('id', PARAM_INT); $mform->setType('uname', PARAM_INT); - + $mform->setType('idnumber', PARAM_NOTAGS); + $mform->addElement('checkbox', 'includeallsessions', get_string('includeall', 'attendance'), get_string('yes')); $mform->setDefault('includeallsessions', true); $mform->addElement('checkbox', 'includenottaken', get_string('includenottaken', 'attendance'), get_string('yes')); diff --git a/locallib.php b/locallib.php index 5e123fa..f352e16 100644 --- a/locallib.php +++ b/locallib.php @@ -981,12 +981,12 @@ class attendance { global $DB, $CFG; // Fields we need from the user table. - $userfields = user_picture::fields('u', array('username')); + $userfields = user_picture::fields('u').',u.username,u.idnumber'; if (isset($this->pageparams->sort) and ($this->pageparams->sort == ATT_SORT_FIRSTNAME)) { - $orderby = "u.firstname ASC, u.lastname ASC"; + $orderby = "u.firstname ASC, u.lastname ASC, u.idnumber ASC"; } else { - $orderby = "u.lastname ASC, u.firstname ASC"; + $orderby = "u.lastname ASC, u.firstname ASC, u.idnumber ASC"; } if ($page) { From 105f3598bada551bf3e0172bb1afb4bbc901119b Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Fri, 23 May 2014 15:12:51 +0100 Subject: [PATCH 62/75] MOODLE-845 add department and institution --- export.php | 12 ++++++++++++ export_form.php | 11 ++++++++--- locallib.php | 6 +++--- 3 files changed, 23 insertions(+), 6 deletions(-) diff --git a/export.php b/export.php index 7185dd3..a93e29f 100644 --- a/export.php +++ b/export.php @@ -91,6 +91,12 @@ if ($mform->is_submitted()) { if (isset($formdata->ident['idnumber'])) { $data->tabhead[] = get_string('idnumber'); } + if (isset($formdata->ident['institution'])) { + $data->tabhead[] = get_string('institution'); + } + if (isset($formdata->ident['department'])) { + $data->tabhead[] = get_string('department'); + } $data->tabhead[] = get_string('lastname'); $data->tabhead[] = get_string('firstname'); $groupmode = groups_get_activity_groupmode($cm, $course); @@ -127,6 +133,12 @@ if ($mform->is_submitted()) { if (isset($formdata->ident['idnumber'])) { $data->table[$i][] = $user->idnumber; } + if (isset($formdata->ident['institution'])) { + $data->table[$i][] = $user->institution; + } + if (isset($formdata->ident['department'])) { + $data->table[$i][] = $user->department; + } $data->table[$i][] = $user->lastname; $data->table[$i][] = $user->firstname; if (!empty($groupmode)) { diff --git a/export_form.php b/export_form.php index 7e822d1..52276ce 100644 --- a/export_form.php +++ b/export_form.php @@ -63,12 +63,17 @@ class mod_attendance_export_form extends moodleform { $ident = array(); $ident[] =& $mform->createElement('checkbox', 'id', '', get_string('studentid', 'attendance')); $ident[] =& $mform->createElement('checkbox', 'uname', '', get_string('username')); - $ident[] =& $mform->createElement('checkbox', 'idnumber', '', get_string('idnumber')); + + $optional = array('idnumber', 'institution', 'department'); + foreach ($optional as $opt) { + $ident[] =& $mform->createElement('checkbox', $opt, '', get_string($opt)); + $mform->setType($opt, PARAM_NOTAGS); + } + $mform->addGroup($ident, 'ident', get_string('identifyby', 'attendance'), array('
'), true); - $mform->setDefaults(array('ident[id]' => true, 'ident[uname]' => true, 'ident[idnumber]' => false)); + $mform->setDefaults(array('ident[id]' => true, 'ident[uname]' => true)); $mform->setType('id', PARAM_INT); $mform->setType('uname', PARAM_INT); - $mform->setType('idnumber', PARAM_NOTAGS); $mform->addElement('checkbox', 'includeallsessions', get_string('includeall', 'attendance'), get_string('yes')); $mform->setDefault('includeallsessions', true); diff --git a/locallib.php b/locallib.php index f352e16..31a388d 100644 --- a/locallib.php +++ b/locallib.php @@ -981,12 +981,12 @@ class attendance { global $DB, $CFG; // Fields we need from the user table. - $userfields = user_picture::fields('u').',u.username,u.idnumber'; + $userfields = user_picture::fields('u').',u.username,u.idnumber,u.institution,u.department'; if (isset($this->pageparams->sort) and ($this->pageparams->sort == ATT_SORT_FIRSTNAME)) { - $orderby = "u.firstname ASC, u.lastname ASC, u.idnumber ASC"; + $orderby = "u.firstname ASC, u.lastname ASC, u.idnumber ASC, u.institution ASC, u.department ASC"; } else { - $orderby = "u.lastname ASC, u.firstname ASC, u.idnumber ASC"; + $orderby = "u.lastname ASC, u.firstname ASC, u.idnumber ASC, u.institution ASC, u.department ASC"; } if ($page) { From 6dd38ca34fc9c3830ba6ececfe9bfd616a3dba0b Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Fri, 23 May 2014 15:43:18 +0100 Subject: [PATCH 63/75] tidy up --- export.php | 30 ++++++++++++++---------------- 1 file changed, 14 insertions(+), 16 deletions(-) diff --git a/export.php b/export.php index a93e29f..f5f61e4 100644 --- a/export.php +++ b/export.php @@ -88,15 +88,14 @@ if ($mform->is_submitted()) { if (isset($formdata->ident['uname'])) { $data->tabhead[] = get_string('username'); } - if (isset($formdata->ident['idnumber'])) { - $data->tabhead[] = get_string('idnumber'); - } - if (isset($formdata->ident['institution'])) { - $data->tabhead[] = get_string('institution'); - } - if (isset($formdata->ident['department'])) { - $data->tabhead[] = get_string('department'); + + $optional = array('idnumber', 'institution', 'department'); + foreach ($optional as $opt) { + if (isset($formdata->ident[$opt])) { + $data->tabhead[] = get_string($opt); + } } + $data->tabhead[] = get_string('lastname'); $data->tabhead[] = get_string('firstname'); $groupmode = groups_get_activity_groupmode($cm, $course); @@ -130,15 +129,14 @@ if ($mform->is_submitted()) { if (isset($formdata->ident['uname'])) { $data->table[$i][] = $user->username; } - if (isset($formdata->ident['idnumber'])) { - $data->table[$i][] = $user->idnumber; - } - if (isset($formdata->ident['institution'])) { - $data->table[$i][] = $user->institution; - } - if (isset($formdata->ident['department'])) { - $data->table[$i][] = $user->department; + + $optional_row = array('idnumber', 'institution', 'department'); + foreach ($$optional_row as $opt) { + if (isset($formdata->ident[$opt])) { + $data->table[$i][] = $user->$opt; + } } + $data->table[$i][] = $user->lastname; $data->table[$i][] = $user->firstname; if (!empty($groupmode)) { From 48f4d81618621f29f01c0d7521a61e43eca61153 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Fri, 23 May 2014 15:45:20 +0100 Subject: [PATCH 64/75] typo --- export.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/export.php b/export.php index f5f61e4..9b6fb99 100644 --- a/export.php +++ b/export.php @@ -131,7 +131,7 @@ if ($mform->is_submitted()) { } $optional_row = array('idnumber', 'institution', 'department'); - foreach ($$optional_row as $opt) { + foreach ($optional_row as $opt) { if (isset($formdata->ident[$opt])) { $data->table[$i][] = $user->$opt; } From c3383a6d86894c971a40f8c8e0ea58e84c46e1f7 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Tue, 27 May 2014 08:55:04 +0100 Subject: [PATCH 65/75] code review: removed new line --- export_form.php | 1 - 1 file changed, 1 deletion(-) diff --git a/export_form.php b/export_form.php index 52276ce..7789a33 100644 --- a/export_form.php +++ b/export_form.php @@ -74,7 +74,6 @@ class mod_attendance_export_form extends moodleform { $mform->setDefaults(array('ident[id]' => true, 'ident[uname]' => true)); $mform->setType('id', PARAM_INT); $mform->setType('uname', PARAM_INT); - $mform->addElement('checkbox', 'includeallsessions', get_string('includeall', 'attendance'), get_string('yes')); $mform->setDefault('includeallsessions', true); $mform->addElement('checkbox', 'includenottaken', get_string('includenottaken', 'attendance'), get_string('yes')); From 55856e6d4ee66e19af26814701b7fdc4a7fe2237 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Tue, 27 May 2014 08:59:22 +0100 Subject: [PATCH 66/75] code review change new line without whitespace --- export_form.php | 1 + 1 file changed, 1 insertion(+) diff --git a/export_form.php b/export_form.php index 7789a33..52276ce 100644 --- a/export_form.php +++ b/export_form.php @@ -74,6 +74,7 @@ class mod_attendance_export_form extends moodleform { $mform->setDefaults(array('ident[id]' => true, 'ident[uname]' => true)); $mform->setType('id', PARAM_INT); $mform->setType('uname', PARAM_INT); + $mform->addElement('checkbox', 'includeallsessions', get_string('includeall', 'attendance'), get_string('yes')); $mform->setDefault('includeallsessions', true); $mform->addElement('checkbox', 'includenottaken', get_string('includenottaken', 'attendance'), get_string('yes')); From d4fd1f4b4db9615b04655e03ee652aadf452ca1b Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Tue, 27 May 2014 09:07:04 +0100 Subject: [PATCH 67/75] fixing whitespce --- export_form.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/export_form.php b/export_form.php index 52276ce..766e863 100644 --- a/export_form.php +++ b/export_form.php @@ -74,7 +74,7 @@ class mod_attendance_export_form extends moodleform { $mform->setDefaults(array('ident[id]' => true, 'ident[uname]' => true)); $mform->setType('id', PARAM_INT); $mform->setType('uname', PARAM_INT); - + $mform->addElement('checkbox', 'includeallsessions', get_string('includeall', 'attendance'), get_string('yes')); $mform->setDefault('includeallsessions', true); $mform->addElement('checkbox', 'includenottaken', get_string('includenottaken', 'attendance'), get_string('yes')); From ba1d8545bf7a6c7514b6fcbb4f6261ff3f0654d1 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Tue, 3 Jun 2014 14:59:47 +0100 Subject: [PATCH 68/75] fixes: log url and report column order --- locallib.php | 2 +- renderer.php | 21 +++++++++++---------- version.php | 2 +- 3 files changed, 13 insertions(+), 12 deletions(-) diff --git a/locallib.php b/locallib.php index a681e92..1d829e5 100644 --- a/locallib.php +++ b/locallib.php @@ -1467,7 +1467,7 @@ class attendance { } $logurl = att_log_convert_url($url); - add_to_log($this->course->id, 'attforblock', $action, $logurl, $info, $this->cm->id); + add_to_log($this->course->id, 'attendance', $action, $logurl, $info, $this->cm->id); } } diff --git a/renderer.php b/renderer.php index 02561f9..ee3fbf7 100644 --- a/renderer.php +++ b/renderer.php @@ -813,6 +813,12 @@ class mod_attendance_renderer extends plugin_renderer_base { $table->size[] = '1px'; } + if ($reportdata->sessionslog) { + $table->head[] = get_string('remarks', 'attendance'); + $table->align[] = 'center'; + $table->size[] = '200px'; + } + if ($bulkmessagecapability) { // Display the table header for bulk messaging. // The checkbox must have an id of cb_selector so that the JavaScript will pick it up. $table->head[] = html_writer::checkbox('cb_selector', 0, false, '', array('id' => 'cb_selector')); @@ -820,12 +826,6 @@ class mod_attendance_renderer extends plugin_renderer_base { $table->size[] = '1px'; } - if ($reportdata->sessionslog) { - $table->head[] = get_string('remarks', 'attendance'); - $table->align[] = 'center'; - $table->size[] = '200px'; - } - foreach ($reportdata->users as $user) { $row = new html_table_row(); @@ -847,10 +847,6 @@ class mod_attendance_renderer extends plugin_renderer_base { $row->cells[] = $reportdata->grades[$user->id].' / '.$reportdata->maxgrades[$user->id]; } - if ($bulkmessagecapability) { // Create the checkbox for bulk messaging. - $row->cells[] = html_writer::checkbox('user'.$user->id, 'on', false); - } - if ($reportdata->sessionslog) { if (isset($sess) && isset($reportdata->sessionslog[$user->id][$sess->id]->remarks)) { $row->cells[] = $reportdata->sessionslog[$user->id][$sess->id]->remarks; @@ -858,6 +854,11 @@ class mod_attendance_renderer extends plugin_renderer_base { $row->cells[] = ''; } } + + if ($bulkmessagecapability) { // Create the checkbox for bulk messaging. + $row->cells[] = html_writer::checkbox('user'.$user->id, 'on', false); + } + $table->data[] = $row; } diff --git a/version.php b/version.php index ae31eea..28aaec1 100644 --- a/version.php +++ b/version.php @@ -22,7 +22,7 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -$plugin->version = 2014022801; +$plugin->version = 2014060314; $plugin->requires = 2013040500; $plugin->release = '2.6.1'; $plugin->maturity = MATURITY_STABLE; From 5b1f3b2390eec06624e7c94f3c9ceb1e464cdf05 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Tue, 3 Jun 2014 15:28:54 +0100 Subject: [PATCH 69/75] get_filtered_sessions and get_user_statuses_stat as per community --- locallib.php | 32 +++++++------------------------- 1 file changed, 7 insertions(+), 25 deletions(-) diff --git a/locallib.php b/locallib.php index 1d829e5..5a4cc8f 100644 --- a/locallib.php +++ b/locallib.php @@ -702,8 +702,6 @@ class attendance { if ($this->pageparams->startdate && $this->pageparams->enddate) { $where = "attendanceid = :aid AND sessdate >= :csdate AND sessdate >= :sdate AND sessdate < :edate"; - } else if ($this->pageparams->enddate) { - $where = "attendanceid = :aid AND sessdate >= :csdate AND sessdate < :edate"; } else { $where = "attendanceid = :aid AND sessdate >= :csdate"; } @@ -1188,32 +1186,16 @@ class attendance { ats.sessdate >= :cstartdate AND al.studentid = :uid".$period." GROUP BY al.statusid"; - + } - } - // Make the filter array into a SQL string. - if (!empty($processed_filters)) { - $processed_filters = 'AND '.implode(' AND ', $processed_filters); - } else { - $processed_filters = ''; - } + if ($filters !== null) { // We do not want to cache, or use a cached version of the results when a filter is set. + return $DB->get_records_sql($qry, $params); + } else if (!array_key_exists($userid, $this->userstatusesstat)) { + // Not filtered so if we do not already have them do the query. + $this->userstatusesstat[$userid] = $DB->get_records_sql($qry, $params); + } - $qry = "SELECT al.statusid, count(al.statusid) AS stcnt - FROM {attendance_log} al - JOIN {attendance_sessions} ats - ON al.sessionid = ats.id - WHERE ats.attendanceid = :aid AND - ats.sessdate >= :cstartdate AND - al.studentid = :uid - $processed_filters - GROUP BY al.statusid"; - - if ($filters !== null) { // We do not want to cache, or use a cached version of the results when a filter is set. - return $DB->get_records_sql($qry, $params); - } else if (!array_key_exists($userid, $this->userstatusesstat)) { - // Not filtered so if we do not already have them do the query. - $this->userstatusesstat[$userid] = $DB->get_records_sql($qry, $params); } // Return the cached stats. From b2e962afae2c841fd77aea2581c8306be2e55bab Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Tue, 3 Jun 2014 15:29:43 +0100 Subject: [PATCH 70/75] removed unecessary line --- locallib.php | 1 - 1 file changed, 1 deletion(-) diff --git a/locallib.php b/locallib.php index 5a4cc8f..5bba8fe 100644 --- a/locallib.php +++ b/locallib.php @@ -1186,7 +1186,6 @@ class attendance { ats.sessdate >= :cstartdate AND al.studentid = :uid".$period." GROUP BY al.statusid"; - } if ($filters !== null) { // We do not want to cache, or use a cached version of the results when a filter is set. From bc9a079d387682b89e31aca34b956afaf1ce3556 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Thu, 5 Jun 2014 09:43:03 +0100 Subject: [PATCH 71/75] code review changes --- locallib.php | 125 ++++++++++++++++++++++++++------------------------- renderer.php | 3 +- 2 files changed, 65 insertions(+), 63 deletions(-) diff --git a/locallib.php b/locallib.php index 5bba8fe..f30c292 100644 --- a/locallib.php +++ b/locallib.php @@ -702,6 +702,8 @@ class attendance { if ($this->pageparams->startdate && $this->pageparams->enddate) { $where = "attendanceid = :aid AND sessdate >= :csdate AND sessdate >= :sdate AND sessdate < :edate"; + } else if ($this->pageparams->enddate) { + $where = "attendanceid = :aid AND sessdate >= :csdate AND sessdate < :edate"; } else { $where = "attendanceid = :aid AND sessdate >= :csdate"; } @@ -809,7 +811,8 @@ class attendance { $i++; } - $this->log('sessions added', $this->url_manage(), implode(', ', $info_array)); + add_to_log($this->course->id, 'attendance', 'sessions added', $this->url_manage(), + implode(',', $info_array), $this->cm->id); } public function update_session_from_form_data($formdata, $sessionid) { @@ -831,7 +834,7 @@ class attendance { $url = $this->url_sessions(array('sessionid' => $sessionid, 'action' => att_sessions_page_params::ACTION_UPDATE)); $info = construct_session_full_date_time($sess->sessdate, $sess->duration); - $this->log('session updated', $url, $info); + add_to_log($this->course->id, 'attendance', 'session updated', $url, $info, $this->cm->id); } /** @@ -885,10 +888,11 @@ class attendance { 'grouptype' => 0); $url = $this->url_take($params); - + $logurl = att_log_convert_url($url); + // Log the change. - $this->log('taken by student', $url, $USER->firstname.' '.$USER->lastname); - + add_to_log($this->course->id, 'attendance', 'taken by student', $logurl, '', $this->cm->id); + return true; } @@ -945,9 +949,10 @@ class attendance { 'grouptype' => $this->pageparams->grouptype); $url = $this->url_take($params); - + $logurl = att_log_convert_url($url); + // Log the change. - $this->log('taken', $url, $USER->firstname.' '.$USER->lastname); + add_to_log($this->course->id, 'attendance', 'taken', $logurl, '', $this->cm->id); $group = 0; if ($this->pageparams->grouptype != attendance::SESSION_COMMON) { @@ -979,7 +984,7 @@ class attendance { global $DB, $CFG; // Fields we need from the user table. - $userfields = user_picture::fields('u').',u.username,u.idnumber,u.institution,u.department'; + $userfields = user_picture::fields('u', array('username' , 'idnumber' , 'institution' , 'department')); if (isset($this->pageparams->sort) and ($this->pageparams->sort == ATT_SORT_FIRSTNAME)) { $orderby = "u.firstname ASC, u.lastname ASC, u.idnumber ASC, u.institution ASC, u.department ASC"; @@ -1159,6 +1164,22 @@ class attendance { 'cstartdate' => $this->course->startdate, 'uid' => $userid); + $processed_filters = array(); + + // We test for any valid filters sent. + if (isset($filters['enddate'])) { + $processed_filters[] = 'ats.sessdate <= :enddate'; + $params['enddate'] = $filters['enddate']; + } + + // Make the filter array into a SQL string. + if (!empty($processed_filters)) { + $processed_filters = ' AND '.implode(' AND ', $processed_filters); + } else { + $processed_filters = ''; + } + + $period = ''; if (!empty($this->pageparams->startdate) && !empty($this->pageparams->enddate)) { $period = ' AND ats.sessdate >= :sdate AND ats.sessdate < :edate '; @@ -1166,35 +1187,33 @@ class attendance { $params['edate'] = $this->pageparams->enddate; } - if (!array_key_exists($userid, $this->userstatusesstat)) { - if ($this->get_group_mode()) { - $qry = "SELECT al.statusid, count(al.statusid) AS stcnt - FROM {attendance_log} al - JOIN {attendance_sessions} ats ON al.sessionid = ats.id - LEFT JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid - WHERE ats.attendanceid = :aid AND - ats.sessdate >= :cstartdate AND - al.studentid = :uid AND - (ats.groupid = 0 or gm.id is NOT NULL)".$period." - GROUP BY al.statusid"; - } else { - $qry = "SELECT al.statusid, count(al.statusid) AS stcnt - FROM {attendance_log} al - JOIN {attendance_sessions} ats - ON al.sessionid = ats.id - WHERE ats.attendanceid = :aid AND - ats.sessdate >= :cstartdate AND - al.studentid = :uid".$period." - GROUP BY al.statusid"; - } - - if ($filters !== null) { // We do not want to cache, or use a cached version of the results when a filter is set. - return $DB->get_records_sql($qry, $params); - } else if (!array_key_exists($userid, $this->userstatusesstat)) { - // Not filtered so if we do not already have them do the query. - $this->userstatusesstat[$userid] = $DB->get_records_sql($qry, $params); - } + if ($this->get_group_mode()) { + $qry = "SELECT al.statusid, count(al.statusid) AS stcnt + FROM {attendance_log} al + JOIN {attendance_sessions} ats ON al.sessionid = ats.id + LEFT JOIN {groups_members} gm ON gm.userid = al.studentid AND gm.groupid = ats.groupid + WHERE ats.attendanceid = :aid AND + ats.sessdate >= :cstartdate AND + al.studentid = :uid AND + (ats.groupid = 0 or gm.id is NOT NULL)".$period.$processed_filters." + GROUP BY al.statusid"; + } else { + $qry = "SELECT al.statusid, count(al.statusid) AS stcnt + FROM {attendance_log} al + JOIN {attendance_sessions} ats + ON al.sessionid = ats.id + WHERE ats.attendanceid = :aid AND + ats.sessdate >= :cstartdate AND + al.studentid = :uid".$period.$processed_filters." + GROUP BY al.statusid"; + } + // We do not want to cache, or use a cached version of the results when a filter is set. + if ($filters !== null) { + return $DB->get_records_sql($qry, $params); + } else if (!array_key_exists($userid, $this->userstatusesstat)) { + // Not filtered so if we do not already have them do the query. + $this->userstatusesstat[$userid] = $DB->get_records_sql($qry, $params); } // Return the cached stats. @@ -1362,7 +1381,8 @@ class attendance { list($sql, $params) = $DB->get_in_or_equal($sessionsids); $DB->delete_records_select('attendance_log', "sessionid $sql", $params); $DB->delete_records_list('attendance_sessions', 'id', $sessionsids); - $this->log('sessions deleted', null, get_string('sessionsids', 'attendance').implode(', ', $sessionsids)); + add_to_log($this->course->id, 'attendance', 'sessions deleted', $this->url_manage(), + get_string('sessionsids', 'attendance').implode(', ', $sessionsids), $this->cm->id); } public function update_sessions_duration($sessionsids, $duration) { @@ -1376,7 +1396,8 @@ class attendance { $DB->update_record('attendance_sessions', $sess); } $sessions->close(); - $this->log('sessions duration updated', $this->url_manage(), get_string('sessionsids', 'attendance').implode(', ', $sessionsids)); + add_to_log($this->course->id, 'attendance', 'sessions duration updated', $this->url_manage(), + get_string('sessionsids', 'attendance').implode(', ', $sessionsids), $this->cm->id); } public function remove_status($statusid) { @@ -1397,7 +1418,8 @@ class attendance { $rec->grade = $grade; $DB->insert_record('attendance_statuses', $rec); - $this->log('status added', $this->url_preferences(), $acronym.': '.$description.' ('.$grade.')'); + add_to_log($this->course->id, 'attendance', 'status added', $this->url_preferences(), + $acronym.': '.$description.' ('.$grade.')', $this->cm->id); } else { print_error('cantaddstatus', 'attendance', $this->url_preferences()); } @@ -1428,31 +1450,12 @@ class attendance { } $DB->update_record('attendance_statuses', $status); - $this->log('status updated', $this->url_preferences(), implode(' ', $updated)); - } - - /** - * wrapper around {@see add_to_log()} - * - * @param string $action to be logged - * @param moodle_url $url absolute url, if null will be used $this->url_manage() - * @param mixed $info additional info, usually id in a table - */ - public function log($action, moodle_url $url = null, $info = null) { - if (is_null($url)) { - $url = $this->url_manage(); - } - - if (is_null($info)) { - $info = $this->id; - } - - $logurl = att_log_convert_url($url); - add_to_log($this->course->id, 'attendance', $action, $logurl, $info, $this->cm->id); + add_to_log($this->course->id, 'attendance', 'status updated', $this->url_preferences(), + implode(' ', $updated), $this->cm->id); } + } - function att_get_statuses($attid, $onlyvisible=true) { global $DB; diff --git a/renderer.php b/renderer.php index ee3fbf7..b506c2b 100644 --- a/renderer.php +++ b/renderer.php @@ -888,12 +888,11 @@ class mod_attendance_renderer extends plugin_renderer_base { $output .= html_writer::empty_tag('input', array('name' => 'formaction', 'type' => 'hidden', 'value' => 'messageselect.php')); $output .= html_writer::empty_tag('input', array('name' => 'id', 'type' => 'hidden', 'value' => $GLOBALS['COURSE']->id)); $output .= html_writer::empty_tag('input', array('name' => 'returnto', 'type' => 'hidden', 'value' => s(me()))); - $output .= html_writer::table($table); + $output .= html_writer::table($table).html_writer::tag('div', get_string('users').': '.count($reportdata->users));; $output .= html_writer::tag('div', html_writer::empty_tag('input', array('type' => 'submit', 'value' => get_string('messageselectadd'))), array('class' => 'buttons')); $url = new moodle_url('/user/action_redir.php'); - html_writer::tag('div', get_string('users').': '.count($reportdata->users)); return html_writer::tag('form', $output, array('action' => $url->out(), 'method' => 'post')); } else { return html_writer::table($table).html_writer::tag('div', get_string('users').': '.count($reportdata->users)); From 39f47348aee69f2f8630aa0512d6f3b8af40038c Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Thu, 5 Jun 2014 12:23:19 +0100 Subject: [PATCH 72/75] code review: use same version as community --- version.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.php b/version.php index 28aaec1..ae31eea 100644 --- a/version.php +++ b/version.php @@ -22,7 +22,7 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -$plugin->version = 2014060314; +$plugin->version = 2014022801; $plugin->requires = 2013040500; $plugin->release = '2.6.1'; $plugin->maturity = MATURITY_STABLE; From c221a04459bb2820235b2e9946efede1453a1fd2 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Thu, 5 Jun 2014 17:16:04 +0100 Subject: [PATCH 73/75] bug fix for issue on community branch - no per page param for students --- renderer.php | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/renderer.php b/renderer.php index b506c2b..a14a9ce 100644 --- a/renderer.php +++ b/renderer.php @@ -104,7 +104,14 @@ class mod_attendance_renderer extends plugin_renderer_base { } $totalusers = count_enrolled_users(context_module::instance($fcontrols->cm->id), 'mod/attendance:canbelisted', $group); - $usersperpage = $fcontrols->pageparams->perpage; + + // No per page param on student view. + if (!empty($fcontrols->pageparams->perpage)) { + $usersperpage = $fcontrols->pageparams->perpage; + } else { + $usersperpage = 0; + } + if (empty($fcontrols->pageparams->page) || !$fcontrols->pageparams->page || !$totalusers || !$usersperpage) { return $paging_controls; } From 717208e0f81bc16ec32fd3eca38d035e98be683b Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Fri, 6 Jun 2014 09:33:39 +0100 Subject: [PATCH 74/75] rework of previous fix --- renderer.php | 11 ++--------- 1 file changed, 2 insertions(+), 9 deletions(-) diff --git a/renderer.php b/renderer.php index a14a9ce..5194b24 100644 --- a/renderer.php +++ b/renderer.php @@ -105,18 +105,11 @@ class mod_attendance_renderer extends plugin_renderer_base { $totalusers = count_enrolled_users(context_module::instance($fcontrols->cm->id), 'mod/attendance:canbelisted', $group); - // No per page param on student view. - if (!empty($fcontrols->pageparams->perpage)) { - $usersperpage = $fcontrols->pageparams->perpage; - } else { - $usersperpage = 0; - } - - if (empty($fcontrols->pageparams->page) || !$fcontrols->pageparams->page || !$totalusers || !$usersperpage) { + if (empty($fcontrols->pageparams->page) || !$fcontrols->pageparams->page || !$totalusers || empty($fcontrols->pageparams->perpage)) { return $paging_controls; } - $numberofpages = ceil($totalusers / $usersperpage); + $numberofpages = ceil($totalusers / $fcontrols->pageparams->perpage); if ($fcontrols->pageparams->page > 1) { $paging_controls .= html_writer::link($fcontrols->url(array('curdate' => $fcontrols->nextcur, 'page' => $fcontrols->pageparams->page - 1)), From b9ed00d3a84aabba7cfa3077ac03a12176275309 Mon Sep 17 00:00:00 2001 From: Joseph Baxter Date: Fri, 6 Jun 2014 09:47:03 +0100 Subject: [PATCH 75/75] bug fix for community issue: reportdata session log offset non existant --- renderer.php | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/renderer.php b/renderer.php index 5194b24..9f43f0d 100644 --- a/renderer.php +++ b/renderer.php @@ -869,7 +869,9 @@ class mod_attendance_renderer extends plugin_renderer_base { foreach ($reportdata->sessions as $sess) { foreach ($reportdata->users as $user) { foreach($reportdata->statuses as $status) { - if ($reportdata->sessionslog[$user->id][$sess->id]->statusid == $status->id) $sessionstats[$status->id]++; + if (!empty($reportdata->sessionslog[$user->id][$sess->id])) { + if ($reportdata->sessionslog[$user->id][$sess->id]->statusid == $status->id) $sessionstats[$status->id]++; + } } }