Search moodle.org's
Developer Documentation


  • Bug fixes for general core bugs in 2.8.x ended 9 November 2015 (12 months).
  • Bug fixes for security issues in 2.8.x ended 9 May 2016 (18 months).
  • minimum PHP 5.4.4 (always use latest PHP 5.4.x or 5.5.x on Windows - http://windows.php.net/download/), PHP 7 is NOT supported
  • /user/ -> index.php (source)

    Differences Between: [Versions 28 and 29] [Versions 28 and 30] [Versions 28 and 31] [Versions 28 and 32] [Versions 28 and 33] [Versions 28 and 34] [Versions 28 and 35] [Versions 28 and 36] [Versions 28 and 37]

       1  <?php
       2  // This file is part of Moodle - http://moodle.org/
       3  //
       4  // Moodle is free software: you can redistribute it and/or modify
       5  // it under the terms of the GNU General Public License as published by
       6  // the Free Software Foundation, either version 3 of the License, or
       7  // (at your option) any later version.
       8  //
       9  // Moodle is distributed in the hope that it will be useful,
      10  // but WITHOUT ANY WARRANTY; without even the implied warranty of
      11  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      12  // GNU General Public License for more details.
      13  //
      14  // You should have received a copy of the GNU General Public License
      15  // along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
      16  
      17  /**
      18   * Lists all the users within a given course.
      19   *
      20   * @copyright 1999 Martin Dougiamas  http://dougiamas.com
      21   * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
      22   * @package core_user
      23   */
      24  
      25  require_once('../config.php');
      26  require_once($CFG->libdir.'/tablelib.php');
      27  require_once($CFG->libdir.'/filelib.php');
      28  
      29  define('USER_SMALL_CLASS', 20);   // Below this is considered small.
      30  define('USER_LARGE_CLASS', 200);  // Above this is considered large.
      31  define('DEFAULT_PAGE_SIZE', 20);
      32  define('SHOW_ALL_PAGE_SIZE', 5000);
      33  define('MODE_BRIEF', 0);
      34  define('MODE_USERDETAILS', 1);
      35  
      36  $page         = optional_param('page', 0, PARAM_INT); // Which page to show.
      37  $perpage      = optional_param('perpage', DEFAULT_PAGE_SIZE, PARAM_INT); // How many per page.
      38  $mode         = optional_param('mode', null, PARAM_INT); // Use the MODE_ constants.
      39  $accesssince  = optional_param('accesssince', 0, PARAM_INT); // Filter by last access. -1 = never.
      40  $search       = optional_param('search', '', PARAM_RAW); // Make sure it is processed with p() or s() when sending to output!
      41  $roleid       = optional_param('roleid', 0, PARAM_INT); // Optional roleid, 0 means all enrolled users (or all on the frontpage).
      42  $contextid    = optional_param('contextid', 0, PARAM_INT); // One of this or.
      43  $courseid     = optional_param('id', 0, PARAM_INT); // This are required.
      44  
      45  $PAGE->set_url('/user/index.php', array(
      46          'page' => $page,
      47          'perpage' => $perpage,
      48          'mode' => $mode,
      49          'accesssince' => $accesssince,
      50          'search' => $search,
      51          'roleid' => $roleid,
      52          'contextid' => $contextid,
      53          'id' => $courseid));
      54  
      55  if ($contextid) {
      56      $context = context::instance_by_id($contextid, MUST_EXIST);
      57      if ($context->contextlevel != CONTEXT_COURSE) {
      58          print_error('invalidcontext');
      59      }
      60      $course = $DB->get_record('course', array('id' => $context->instanceid), '*', MUST_EXIST);
      61  } else {
      62      $course = $DB->get_record('course', array('id' => $courseid), '*', MUST_EXIST);
      63      $context = context_course::instance($course->id, MUST_EXIST);
      64  }
      65  // Not needed anymore.
      66  unset($contextid);
      67  unset($courseid);
      68  
      69  require_login($course);
      70  
      71  $systemcontext = context_system::instance();
      72  $isfrontpage = ($course->id == SITEID);
      73  
      74  $frontpagectx = context_course::instance(SITEID);
      75  
      76  if ($isfrontpage) {
      77      $PAGE->set_pagelayout('admin');
      78      require_capability('moodle/site:viewparticipants', $systemcontext);
      79  } else {
      80      $PAGE->set_pagelayout('incourse');
      81      require_capability('moodle/course:viewparticipants', $context);
      82  }
      83  
      84  $rolenamesurl = new moodle_url("$CFG->wwwroot/user/index.php?contextid=$context->id&sifirst=&silast=");
      85  
      86  $rolenames = role_fix_names(get_profile_roles($context), $context, ROLENAME_ALIAS, true);
      87  if ($isfrontpage) {
      88      $rolenames[0] = get_string('allsiteusers', 'role');
      89  } else {
      90      $rolenames[0] = get_string('allparticipants');
      91  }
      92  
      93  // Make sure other roles may not be selected by any means.
      94  if (empty($rolenames[$roleid])) {
      95      print_error('noparticipants');
      96  }
      97  
      98  // No roles to display yet?
      99  // frontpage course is an exception, on the front page course we should display all users.
     100  if (empty($rolenames) && !$isfrontpage) {
     101      if (has_capability('moodle/role:assign', $context)) {
     102          redirect($CFG->wwwroot.'/'.$CFG->admin.'/roles/assign.php?contextid='.$context->id);
     103      } else {
     104          print_error('noparticipants');
     105      }
     106  }
     107  
     108  $event = \core\event\user_list_viewed::create(array(
     109      'objectid' => $course->id,
     110      'courseid' => $course->id,
     111      'context' => $context,
     112      'other' => array(
     113          'courseshortname' => $course->shortname,
     114          'coursefullname' => $course->fullname
     115      )
     116  ));
     117  $event->trigger();
     118  
     119  $bulkoperations = has_capability('moodle/course:bulkmessaging', $context);
     120  
     121  $countries = get_string_manager()->get_list_of_countries();
     122  
     123  $strnever = get_string('never');
     124  
     125  $datestring = new stdClass();
     126  $datestring->year  = get_string('year');
     127  $datestring->years = get_string('years');
     128  $datestring->day   = get_string('day');
     129  $datestring->days  = get_string('days');
     130  $datestring->hour  = get_string('hour');
     131  $datestring->hours = get_string('hours');
     132  $datestring->min   = get_string('min');
     133  $datestring->mins  = get_string('mins');
     134  $datestring->sec   = get_string('sec');
     135  $datestring->secs  = get_string('secs');
     136  
     137  if ($mode !== null) {
     138      $mode = (int)$mode;
     139      $SESSION->userindexmode = $mode;
     140  } else if (isset($SESSION->userindexmode)) {
     141      $mode = (int)$SESSION->userindexmode;
     142  } else {
     143      $mode = MODE_BRIEF;
     144  }
     145  
     146  // Check to see if groups are being used in this course
     147  // and if so, set $currentgroup to reflect the current group.
     148  
     149  $groupmode    = groups_get_course_groupmode($course);   // Groups are being used.
     150  $currentgroup = groups_get_course_group($course, true);
     151  
     152  if (!$currentgroup) {      // To make some other functions work better later.
     153      $currentgroup  = null;
     154  }
     155  
     156  $isseparategroups = ($course->groupmode == SEPARATEGROUPS and !has_capability('moodle/site:accessallgroups', $context));
     157  
     158  $PAGE->set_title("$course->shortname: ".get_string('participants'));
     159  $PAGE->set_heading($course->fullname);
     160  $PAGE->set_pagetype('course-view-' . $course->format);
     161  $PAGE->add_body_class('path-user');                     // So we can style it independently.
     162  $PAGE->set_other_editing_capability('moodle/course:manageactivities');
     163  
     164  echo $OUTPUT->header();
     165  
     166  echo '<div class="userlist">';
     167  
     168  if ($isseparategroups and (!$currentgroup) ) {
     169      // The user is not in the group so show message and exit.
     170      echo $OUTPUT->heading(get_string("notingroup"));
     171      echo $OUTPUT->footer();
     172      exit;
     173  }
     174  
     175  
     176  // Should use this variable so that we don't break stuff every time a variable is added or changed.
     177  $baseurl = new moodle_url('/user/index.php', array(
     178          'contextid' => $context->id,
     179          'roleid' => $roleid,
     180          'id' => $course->id,
     181          'perpage' => $perpage,
     182          'accesssince' => $accesssince,
     183          'search' => s($search)));
     184  
     185  // Setting up tags.
     186  if ($course->id == SITEID) {
     187      $filtertype = 'site';
     188  } else if ($course->id && !$currentgroup) {
     189      $filtertype = 'course';
     190      $filterselect = $course->id;
     191  } else {
     192      $filtertype = 'group';
     193      $filterselect = $currentgroup;
     194  }
     195  
     196  
     197  
     198  // Get the hidden field list.
     199  if (has_capability('moodle/course:viewhiddenuserfields', $context)) {
     200      $hiddenfields = array();  // Teachers and admins are allowed to see everything.
     201  } else {
     202      $hiddenfields = array_flip(explode(',', $CFG->hiddenuserfields));
     203  }
     204  
     205  if (isset($hiddenfields['lastaccess'])) {
     206      // Do not allow access since filtering.
     207      $accesssince = 0;
     208  }
     209  
     210  // Print settings and things in a table across the top.
     211  $controlstable = new html_table();
     212  $controlstable->attributes['class'] = 'controls';
     213  $controlstable->cellspacing = 0;
     214  $controlstable->data[] = new html_table_row();
     215  
     216  // Print my course menus.
     217  if ($mycourses = enrol_get_my_courses()) {
     218      $courselist = array();
     219      $popupurl = new moodle_url('/user/index.php?roleid='.$roleid.'&sifirst=&silast=');
     220      foreach ($mycourses as $mycourse) {
     221          $coursecontext = context_course::instance($mycourse->id);
     222          $courselist[$mycourse->id] = format_string($mycourse->shortname, true, array('context' => $coursecontext));
     223      }
     224      if (has_capability('moodle/site:viewparticipants', $systemcontext)) {
     225          unset($courselist[SITEID]);
     226          $courselist = array(SITEID => format_string($SITE->shortname, true, array('context' => $systemcontext))) + $courselist;
     227      }
     228      $select = new single_select($popupurl, 'id', $courselist, $course->id, null, 'courseform');
     229      $select->set_label(get_string('mycourses'));
     230      $controlstable->data[0]->cells[] = $OUTPUT->render($select);
     231  }
     232  
     233  if ($groupmenu = groups_print_course_menu($course, $baseurl->out(), true)) {
     234      $controlstable->data[0]->cells[] = $groupmenu;
     235  }
     236  
     237  if (!isset($hiddenfields['lastaccess'])) {
     238      // Get minimum lastaccess for this course and display a dropbox to filter by lastaccess going back this far.
     239      // We need to make it diferently for normal courses and site course.
     240      if (!$isfrontpage) {
     241          $minlastaccess = $DB->get_field_sql('SELECT min(timeaccess)
     242                                                 FROM {user_lastaccess}
     243                                                WHERE courseid = ?
     244                                                      AND timeaccess != 0', array($course->id));
     245          $lastaccess0exists = $DB->record_exists('user_lastaccess', array('courseid' => $course->id, 'timeaccess' => 0));
     246      } else {
     247          $minlastaccess = $DB->get_field_sql('SELECT min(lastaccess)
     248                                                 FROM {user}
     249                                                WHERE lastaccess != 0');
     250          $lastaccess0exists = $DB->record_exists('user', array('lastaccess' => 0));
     251      }
     252  
     253      $now = usergetmidnight(time());
     254      $timeaccess = array();
     255      $baseurl->remove_params('accesssince');
     256  
     257      // Makes sense for this to go first.
     258      $timeoptions[0] = get_string('selectperiod');
     259  
     260      // Days.
     261      for ($i = 1; $i < 7; $i++) {
     262          if (strtotime('-'.$i.' days', $now) >= $minlastaccess) {
     263              $timeoptions[strtotime('-'.$i.' days', $now)] = get_string('numdays', 'moodle', $i);
     264          }
     265      }
     266      // Weeks.
     267      for ($i = 1; $i < 10; $i++) {
     268          if (strtotime('-'.$i.' weeks', $now) >= $minlastaccess) {
     269              $timeoptions[strtotime('-'.$i.' weeks', $now)] = get_string('numweeks', 'moodle', $i);
     270          }
     271      }
     272      // Months.
     273      for ($i = 2; $i < 12; $i++) {
     274          if (strtotime('-'.$i.' months', $now) >= $minlastaccess) {
     275              $timeoptions[strtotime('-'.$i.' months', $now)] = get_string('nummonths', 'moodle', $i);
     276          }
     277      }
     278      // Try a year.
     279      if (strtotime('-1 year', $now) >= $minlastaccess) {
     280          $timeoptions[strtotime('-1 year', $now)] = get_string('lastyear');
     281      }
     282  
     283      if (!empty($lastaccess0exists)) {
     284          $timeoptions[-1] = get_string('never');
     285      }
     286  
     287      if (count($timeoptions) > 1) {
     288          $select = new single_select($baseurl, 'accesssince', $timeoptions, $accesssince, null, 'timeoptions');
     289          $select->set_label(get_string('usersnoaccesssince'));
     290          $controlstable->data[0]->cells[] = $OUTPUT->render($select);
     291      }
     292  }
     293  
     294  $formatmenu = array( '0' => get_string('brief'),
     295                       '1' => get_string('userdetails'));
     296  $select = new single_select($baseurl, 'mode', $formatmenu, $mode, null, 'formatmenu');
     297  $select->set_label(get_string('userlist'));
     298  $userlistcell = new html_table_cell();
     299  $userlistcell->attributes['class'] = 'right';
     300  $userlistcell->text = $OUTPUT->render($select);
     301  $controlstable->data[0]->cells[] = $userlistcell;
     302  
     303  echo html_writer::table($controlstable);
     304  
     305  if ($currentgroup and (!$isseparategroups or has_capability('moodle/site:accessallgroups', $context))) {
     306      // Display info about the group.
     307      if ($group = groups_get_group($currentgroup)) {
     308          if (!empty($group->description) or (!empty($group->picture) and empty($group->hidepicture))) {
     309              $groupinfotable = new html_table();
     310              $groupinfotable->attributes['class'] = 'groupinfobox';
     311              $picturecell = new html_table_cell();
     312              $picturecell->attributes['class'] = 'left side picture';
     313              $picturecell->text = print_group_picture($group, $course->id, true, true, false);
     314  
     315              $contentcell = new html_table_cell();
     316              $contentcell->attributes['class'] = 'content';
     317  
     318              $contentheading = $group->name;
     319              if (has_capability('moodle/course:managegroups', $context)) {
     320                  $aurl = new moodle_url('/group/group.php', array('id' => $group->id, 'courseid' => $group->courseid));
     321                  $contentheading .= '&nbsp;' . $OUTPUT->action_icon($aurl, new pix_icon('t/edit', get_string('editgroupprofile')));
     322              }
     323  
     324              $group->description = file_rewrite_pluginfile_urls($group->description, 'pluginfile.php', $context->id, 'group',
     325                  'description', $group->id);
     326              if (!isset($group->descriptionformat)) {
     327                  $group->descriptionformat = FORMAT_MOODLE;
     328              }
     329              $options = array('overflowdiv' => true);
     330              $formatteddesc = format_text($group->description, $group->descriptionformat, $options);
     331              $contentcell->text = $OUTPUT->heading($contentheading, 3) . $formatteddesc;
     332              $groupinfotable->data[] = new html_table_row(array($picturecell, $contentcell));
     333              echo html_writer::table($groupinfotable);
     334          }
     335      }
     336  }
     337  
     338  // Define a table showing a list of users in the current role selection.
     339  $tablecolumns = array();
     340  $tableheaders = array();
     341  if ($bulkoperations && $mode === MODE_BRIEF) {
     342      $tablecolumns[] = 'select';
     343      $tableheaders[] = get_string('select');
     344  }
     345  $tablecolumns[] = 'userpic';
     346  $tablecolumns[] = 'fullname';
     347  
     348  $extrafields = get_extra_user_fields($context);
     349  $tableheaders[] = get_string('userpic');
     350  $tableheaders[] = get_string('fullnameuser');
     351  
     352  if ($mode === MODE_BRIEF) {
     353      foreach ($extrafields as $field) {
     354          $tablecolumns[] = $field;
     355          $tableheaders[] = get_user_field_name($field);
     356      }
     357  }
     358  if ($mode === MODE_BRIEF && !isset($hiddenfields['city'])) {
     359      $tablecolumns[] = 'city';
     360      $tableheaders[] = get_string('city');
     361  }
     362  if ($mode === MODE_BRIEF && !isset($hiddenfields['country'])) {
     363      $tablecolumns[] = 'country';
     364      $tableheaders[] = get_string('country');
     365  }
     366  if (!isset($hiddenfields['lastaccess'])) {
     367      $tablecolumns[] = 'lastaccess';
     368      if ($course->id == SITEID) {
     369          // Exception case for viewing participants on site home.
     370          $tableheaders[] = get_string('lastsiteaccess');
     371      } else {
     372          $tableheaders[] = get_string('lastcourseaccess');
     373      }
     374  }
     375  
     376  if ($bulkoperations && $mode === MODE_USERDETAILS) {
     377      $tablecolumns[] = 'select';
     378      $tableheaders[] = get_string('select');
     379  }
     380  
     381  $table = new flexible_table('user-index-participants-'.$course->id);
     382  $table->define_columns($tablecolumns);
     383  $table->define_headers($tableheaders);
     384  $table->define_baseurl($baseurl->out());
     385  
     386  if (!isset($hiddenfields['lastaccess'])) {
     387      $table->sortable(true, 'lastaccess', SORT_DESC);
     388  } else {
     389      $table->sortable(true, 'firstname', SORT_ASC);
     390  }
     391  
     392  $table->no_sorting('roles');
     393  $table->no_sorting('groups');
     394  $table->no_sorting('groupings');
     395  $table->no_sorting('select');
     396  
     397  $table->set_attribute('cellspacing', '0');
     398  $table->set_attribute('id', 'participants');
     399  $table->set_attribute('class', 'generaltable generalbox');
     400  
     401  $table->set_control_variables(array(
     402              TABLE_VAR_SORT    => 'ssort',
     403              TABLE_VAR_HIDE    => 'shide',
     404              TABLE_VAR_SHOW    => 'sshow',
     405              TABLE_VAR_IFIRST  => 'sifirst',
     406              TABLE_VAR_ILAST   => 'silast',
     407              TABLE_VAR_PAGE    => 'spage'
     408              ));
     409  $table->setup();
     410  
     411  list($esql, $params) = get_enrolled_sql($context, null, $currentgroup, true);
     412  $joins = array("FROM {user} u");
     413  $wheres = array();
     414  
     415  $userfields = array('username', 'email', 'city', 'country', 'lang', 'timezone', 'maildisplay');
     416  $mainuserfields = user_picture::fields('u', $userfields);
     417  $extrasql = get_extra_user_fields_sql($context, 'u', '', $userfields);
     418  
     419  if ($isfrontpage) {
     420      $select = "SELECT $mainuserfields, u.lastaccess$extrasql";
     421      $joins[] = "JOIN ($esql) e ON e.id = u.id"; // Everybody on the frontpage usually.
     422      if ($accesssince) {
     423          $wheres[] = get_user_lastaccess_sql($accesssince);
     424      }
     425  
     426  } else {
     427      $select = "SELECT $mainuserfields, COALESCE(ul.timeaccess, 0) AS lastaccess$extrasql";
     428      $joins[] = "JOIN ($esql) e ON e.id = u.id"; // Course enrolled users only.
     429      $joins[] = "LEFT JOIN {user_lastaccess} ul ON (ul.userid = u.id AND ul.courseid = :courseid)"; // Not everybody accessed course yet.
     430      $params['courseid'] = $course->id;
     431      if ($accesssince) {
     432          $wheres[] = get_course_lastaccess_sql($accesssince);
     433      }
     434  }
     435  
     436  // Performance hacks - we preload user contexts together with accounts.
     437  $ccselect = ', ' . context_helper::get_preload_record_columns_sql('ctx');
     438  $ccjoin = "LEFT JOIN {context} ctx ON (ctx.instanceid = u.id AND ctx.contextlevel = :contextlevel)";
     439  $params['contextlevel'] = CONTEXT_USER;
     440  $select .= $ccselect;
     441  $joins[] = $ccjoin;
     442  
     443  
     444  // Limit list to users with some role only.
     445  if ($roleid) {
     446      // We want to query both the current context and parent contexts.
     447      list($relatedctxsql, $relatedctxparams) = $DB->get_in_or_equal($context->get_parent_context_ids(true), SQL_PARAMS_NAMED, 'relatedctx');
     448  
     449      $wheres[] = "u.id IN (SELECT userid FROM {role_assignments} WHERE roleid = :roleid AND contextid $relatedctxsql)";
     450      $params = array_merge($params, array('roleid' => $roleid), $relatedctxparams);
     451  }
     452  
     453  $from = implode("\n", $joins);
     454  if ($wheres) {
     455      $where = "WHERE " . implode(" AND ", $wheres);
     456  } else {
     457      $where = "";
     458  }
     459  
     460  $totalcount = $DB->count_records_sql("SELECT COUNT(u.id) $from $where", $params);
     461  
     462  if (!empty($search)) {
     463      $fullname = $DB->sql_fullname('u.firstname', 'u.lastname');
     464      $wheres[] = "(". $DB->sql_like($fullname, ':search1', false, false) .
     465                  " OR ". $DB->sql_like('email', ':search2', false, false) .
     466                  " OR ". $DB->sql_like('idnumber', ':search3', false, false) .") ";
     467      $params['search1'] = "%$search%";
     468      $params['search2'] = "%$search%";
     469      $params['search3'] = "%$search%";
     470  }
     471  
     472  list($twhere, $tparams) = $table->get_sql_where();
     473  if ($twhere) {
     474      $wheres[] = $twhere;
     475      $params = array_merge($params, $tparams);
     476  }
     477  
     478  $from = implode("\n", $joins);
     479  if ($wheres) {
     480      $where = "WHERE " . implode(" AND ", $wheres);
     481  } else {
     482      $where = "";
     483  }
     484  
     485  if ($table->get_sql_sort()) {
     486      $sort = ' ORDER BY '.$table->get_sql_sort();
     487  } else {
     488      $sort = '';
     489  }
     490  
     491  $matchcount = $DB->count_records_sql("SELECT COUNT(u.id) $from $where", $params);
     492  
     493  $table->initialbars(true);
     494  $table->pagesize($perpage, $matchcount);
     495  
     496  // List of users at the current visible page - paging makes it relatively short.
     497  $userlist = $DB->get_recordset_sql("$select $from $where $sort", $params, $table->get_page_start(), $table->get_page_size());
     498  
     499  // If there are multiple Roles in the course, then show a drop down menu for switching.
     500  if (count($rolenames) > 1) {
     501      echo '<div class="rolesform">';
     502      echo '<label for="rolesform_jump">'.get_string('currentrole', 'role').'&nbsp;</label>';
     503      echo $OUTPUT->single_select($rolenamesurl, 'roleid', $rolenames, $roleid, null, 'rolesform');
     504      echo '</div>';
     505  
     506  } else if (count($rolenames) == 1) {
     507      // When all users with the same role - print its name.
     508      echo '<div class="rolesform">';
     509      echo get_string('role').get_string('labelsep', 'langconfig');
     510      $rolename = reset($rolenames);
     511      echo $rolename;
     512      echo '</div>';
     513  }
     514  
     515  if ($roleid > 0) {
     516      $a = new stdClass();
     517      $a->number = $totalcount;
     518      $a->role = $rolenames[$roleid];
     519      $heading = format_string(get_string('xuserswiththerole', 'role', $a));
     520  
     521      if ($currentgroup and $group) {
     522          $a->group = $group->name;
     523          $heading .= ' ' . format_string(get_string('ingroup', 'role', $a));
     524      }
     525  
     526      if ($accesssince) {
     527          $a->timeperiod = $timeoptions[$accesssince];
     528          $heading .= ' ' . format_string(get_string('inactiveformorethan', 'role', $a));
     529      }
     530  
     531      $heading .= ": $a->number";
     532  
     533      if (user_can_assign($context, $roleid)) {
     534          $headingurl = new moodle_url($CFG->wwwroot . '/' . $CFG->admin . '/roles/assign.php',
     535                  array('roleid' => $roleid, 'contextid' => $context->id));
     536          $heading .= $OUTPUT->action_icon($headingurl, new pix_icon('t/edit', get_string('edit')));
     537      }
     538      echo $OUTPUT->heading($heading, 3);
     539  } else {
     540      if ($course->id != SITEID && has_capability('moodle/course:enrolreview', $context)) {
     541          $editlink = $OUTPUT->action_icon(new moodle_url('/enrol/users.php', array('id' => $course->id)),
     542                                           new pix_icon('t/edit', get_string('edit')));
     543      } else {
     544          $editlink = '';
     545      }
     546      if ($course->id == SITEID and $roleid < 0) {
     547          $strallparticipants = get_string('allsiteusers', 'role');
     548      } else {
     549          $strallparticipants = get_string('allparticipants');
     550      }
     551      if ($matchcount < $totalcount) {
     552          echo $OUTPUT->heading($strallparticipants.get_string('labelsep', 'langconfig').$matchcount.'/'.$totalcount . $editlink, 3);
     553      } else {
     554          echo $OUTPUT->heading($strallparticipants.get_string('labelsep', 'langconfig').$matchcount . $editlink, 3);
     555      }
     556  }
     557  
     558  
     559  if ($bulkoperations) {
     560      echo '<form action="action_redir.php" method="post" id="participantsform">';
     561      echo '<div>';
     562      echo '<input type="hidden" name="sesskey" value="'.sesskey().'" />';
     563      echo '<input type="hidden" name="returnto" value="'.s($PAGE->url->out(false)).'" />';
     564  }
     565  
     566  if ($mode === MODE_USERDETAILS) {    // Print simple listing.
     567      if ($totalcount < 1) {
     568          echo $OUTPUT->heading(get_string('nothingtodisplay'));
     569      } else {
     570          if ($totalcount > $perpage) {
     571  
     572              $firstinitial = $table->get_initial_first();
     573              $lastinitial  = $table->get_initial_last();
     574              $strall = get_string('all');
     575              $alpha  = explode(',', get_string('alphabet', 'langconfig'));
     576  
     577              // Bar of first initials.
     578  
     579              echo '<div class="initialbar firstinitial">'.get_string('firstname').' : ';
     580              if (!empty($firstinitial)) {
     581                  echo '<a href="'.$baseurl->out().'&amp;sifirst=">'.$strall.'</a>';
     582              } else {
     583                  echo '<strong>'.$strall.'</strong>';
     584              }
     585              foreach ($alpha as $letter) {
     586                  if ($letter == $firstinitial) {
     587                      echo ' <strong>'.$letter.'</strong>';
     588                  } else {
     589                      echo ' <a href="'.$baseurl->out().'&amp;sifirst='.$letter.'">'.$letter.'</a>';
     590                  }
     591              }
     592              echo '</div>';
     593  
     594              // Bar of last initials.
     595  
     596              echo '<div class="initialbar lastinitial">'.get_string('lastname').' : ';
     597              if (!empty($lastinitial)) {
     598                  echo '<a href="'.$baseurl->out().'&amp;silast=">'.$strall.'</a>';
     599              } else {
     600                  echo '<strong>'.$strall.'</strong>';
     601              }
     602              foreach ($alpha as $letter) {
     603                  if ($letter == $lastinitial) {
     604                      echo ' <strong>'.$letter.'</strong>';
     605                  } else {
     606                      echo ' <a href="'.$baseurl->out().'&amp;silast='.$letter.'">'.$letter.'</a>';
     607                  }
     608              }
     609              echo '</div>';
     610  
     611              $pagingbar = new paging_bar($matchcount, intval($table->get_page_start() / $perpage), $perpage, $baseurl);
     612              $pagingbar->pagevar = 'spage';
     613              echo $OUTPUT->render($pagingbar);
     614          }
     615  
     616          if ($matchcount > 0) {
     617              $usersprinted = array();
     618              foreach ($userlist as $user) {
     619                  if (in_array($user->id, $usersprinted)) { // Prevent duplicates by r.hidden - MDL-13935.
     620                      continue;
     621                  }
     622                  $usersprinted[] = $user->id; // Add new user to the array of users printed.
     623  
     624                  context_helper::preload_from_record($user);
     625  
     626                  $context = context_course::instance($course->id);
     627                  $usercontext = context_user::instance($user->id);
     628  
     629                  $countries = get_string_manager()->get_list_of_countries();
     630  
     631                  // Get the hidden field list.
     632                  if (has_capability('moodle/course:viewhiddenuserfields', $context)) {
     633                      $hiddenfields = array();
     634                  } else {
     635                      $hiddenfields = array_flip(explode(',', $CFG->hiddenuserfields));
     636                  }
     637                  $table = new html_table();
     638                  $table->attributes['class'] = 'userinfobox';
     639  
     640                  $row = new html_table_row();
     641                  $row->cells[0] = new html_table_cell();
     642                  $row->cells[0]->attributes['class'] = 'left side';
     643  
     644                  $row->cells[0]->text = $OUTPUT->user_picture($user, array('size' => 100, 'courseid' => $course->id));
     645                  $row->cells[1] = new html_table_cell();
     646                  $row->cells[1]->attributes['class'] = 'content';
     647  
     648                  $row->cells[1]->text = $OUTPUT->container(fullname($user, has_capability('moodle/site:viewfullnames', $context)), 'username');
     649                  $row->cells[1]->text .= $OUTPUT->container_start('info');
     650  
     651                  if (!empty($user->role)) {
     652                      $row->cells[1]->text .= get_string('role').get_string('labelsep', 'langconfig').$user->role.'<br />';
     653                  }
     654                  if ($user->maildisplay == 1 or ($user->maildisplay == 2 and ($course->id != SITEID) and !isguestuser()) or
     655                              in_array('email', $extrafields) or ($user->id == $USER->id)) {
     656                      $row->cells[1]->text .= get_string('email').get_string('labelsep', 'langconfig').html_writer::link("mailto:$user->email", $user->email) . '<br />';
     657                  }
     658                  foreach ($extrafields as $field) {
     659                      if ($field === 'email') {
     660                          // Skip email because it was displayed with different logic above
     661                          // because this page is intended for students too.
     662                          continue;
     663                      }
     664                      $row->cells[1]->text .= get_user_field_name($field) .
     665                              get_string('labelsep', 'langconfig') . s($user->{$field}) . '<br />';
     666                  }
     667                  if (($user->city or $user->country) and (!isset($hiddenfields['city']) or !isset($hiddenfields['country']))) {
     668                      $row->cells[1]->text .= get_string('city').get_string('labelsep', 'langconfig');
     669                      if ($user->city && !isset($hiddenfields['city'])) {
     670                          $row->cells[1]->text .= $user->city;
     671                      }
     672                      if (!empty($countries[$user->country]) && !isset($hiddenfields['country'])) {
     673                          if ($user->city && !isset($hiddenfields['city'])) {
     674                              $row->cells[1]->text .= ', ';
     675                          }
     676                          $row->cells[1]->text .= $countries[$user->country];
     677                      }
     678                      $row->cells[1]->text .= '<br />';
     679                  }
     680  
     681                  if (!isset($hiddenfields['lastaccess'])) {
     682                      if ($user->lastaccess) {
     683                          $row->cells[1]->text .= get_string('lastaccess').get_string('labelsep', 'langconfig').userdate($user->lastaccess);
     684                          $row->cells[1]->text .= '&nbsp; ('. format_time(time() - $user->lastaccess, $datestring) .')';
     685                      } else {
     686                          $row->cells[1]->text .= get_string('lastaccess').get_string('labelsep', 'langconfig').get_string('never');
     687                      }
     688                  }
     689  
     690                  $row->cells[1]->text .= $OUTPUT->container_end();
     691  
     692                  $row->cells[2] = new html_table_cell();
     693                  $row->cells[2]->attributes['class'] = 'links';
     694                  $row->cells[2]->text = '';
     695  
     696                  $links = array();
     697  
     698                  if ($CFG->enableblogs && ($CFG->bloglevel != BLOG_USER_LEVEL || $USER->id == $user->id)) {
     699                      $links[] = html_writer::link(new moodle_url('/blog/index.php?userid='.$user->id), get_string('blogs', 'blog'));
     700                  }
     701  
     702                  if (!empty($CFG->enablenotes) and (has_capability('moodle/notes:manage', $context) || has_capability('moodle/notes:view', $context))) {
     703                      $links[] = html_writer::link(new moodle_url('/notes/index.php?course=' . $course->id. '&user='.$user->id), get_string('notes', 'notes'));
     704                  }
     705  
     706                  if (has_capability('moodle/site:viewreports', $context) or has_capability('moodle/user:viewuseractivitiesreport', $usercontext)) {
     707                      $links[] = html_writer::link(new moodle_url('/course/user.php?id='. $course->id .'&user='. $user->id), get_string('activity'));
     708                  }
     709  
     710                  if ($USER->id != $user->id && !\core\session\manager::is_loggedinas() && has_capability('moodle/user:loginas', $context) && !is_siteadmin($user->id)) {
     711                      $links[] = html_writer::link(new moodle_url('/course/loginas.php?id='. $course->id .'&user='. $user->id .'&sesskey='. sesskey()), get_string('loginas'));
     712                  }
     713  
     714                  $links[] = html_writer::link(new moodle_url('/user/view.php?id='. $user->id .'&course='. $course->id), get_string('fullprofile') . '...');
     715  
     716                  $row->cells[2]->text .= implode('', $links);
     717  
     718                  if ($bulkoperations) {
     719                      $row->cells[2]->text .= '<br /><input type="checkbox" class="usercheckbox" name="user'.$user->id.'" /> ';
     720                  }
     721                  $table->data = array($row);
     722                  echo html_writer::table($table);
     723              }
     724  
     725          } else {
     726              echo $OUTPUT->heading(get_string('nothingtodisplay'));
     727          }
     728      }
     729  
     730  } else {
     731      $countrysort = (strpos($sort, 'country') !== false);
     732      $timeformat = get_string('strftimedate');
     733  
     734  
     735      if ($userlist) {
     736  
     737          $usersprinted = array();
     738          foreach ($userlist as $user) {
     739              if (in_array($user->id, $usersprinted)) { // Prevent duplicates by r.hidden - MDL-13935.
     740                  continue;
     741              }
     742              $usersprinted[] = $user->id; // Add new user to the array of users printed.
     743  
     744              context_helper::preload_from_record($user);
     745  
     746              if ($user->lastaccess) {
     747                  $lastaccess = format_time(time() - $user->lastaccess, $datestring);
     748              } else {
     749                  $lastaccess = $strnever;
     750              }
     751  
     752              if (empty($user->country)) {
     753                  $country = '';
     754  
     755              } else {
     756                  if ($countrysort) {
     757                      $country = '('.$user->country.') '.$countries[$user->country];
     758                  } else {
     759                      $country = $countries[$user->country];
     760                  }
     761              }
     762  
     763              $usercontext = context_user::instance($user->id);
     764  
     765              if ($piclink = ($USER->id == $user->id || has_capability('moodle/user:viewdetails', $context) || has_capability('moodle/user:viewdetails', $usercontext))) {
     766                  $profilelink = '<strong><a href="'.$CFG->wwwroot.'/user/view.php?id='.$user->id.'&amp;course='.$course->id.'">'.fullname($user).'</a></strong>';
     767              } else {
     768                  $profilelink = '<strong>'.fullname($user).'</strong>';
     769              }
     770  
     771              $data = array();
     772              if ($bulkoperations) {
     773                  $data[] = '<input type="checkbox" class="usercheckbox" name="user'.$user->id.'" />';
     774              }
     775              $data[] = $OUTPUT->user_picture($user, array('size' => 35, 'courseid' => $course->id));
     776              $data[] = $profilelink;
     777  
     778              if ($mode === MODE_BRIEF) {
     779                  foreach ($extrafields as $field) {
     780                      $data[] = $user->{$field};
     781                  }
     782              }
     783              if ($mode === MODE_BRIEF && !isset($hiddenfields['city'])) {
     784                  $data[] = $user->city;
     785              }
     786              if ($mode === MODE_BRIEF && !isset($hiddenfields['country'])) {
     787                  $data[] = $country;
     788              }
     789              if (!isset($hiddenfields['lastaccess'])) {
     790                  $data[] = $lastaccess;
     791              }
     792  
     793              $table->add_data($data);
     794          }
     795      }
     796  
     797      $table->print_html();
     798  
     799  }
     800  
     801  if ($bulkoperations) {
     802      echo '<br /><div class="buttons">';
     803      echo '<input type="button" id="checkall" value="'.get_string('selectall').'" /> ';
     804      echo '<input type="button" id="checknone" value="'.get_string('deselectall').'" /> ';
     805      $displaylist = array();
     806      $displaylist['messageselect.php'] = get_string('messageselectadd');
     807      if (!empty($CFG->enablenotes) && has_capability('moodle/notes:manage', $context) && $context->id != $frontpagectx->id) {
     808          $displaylist['addnote.php'] = get_string('addnewnote', 'notes');
     809          $displaylist['groupaddnote.php'] = get_string('groupaddnewnote', 'notes');
     810      }
     811  
     812      echo $OUTPUT->help_icon('withselectedusers');
     813      echo html_writer::tag('label', get_string("withselectedusers"), array('for' => 'formactionid'));
     814      echo html_writer::select($displaylist, 'formaction', '', array('' => 'choosedots'), array('id' => 'formactionid'));
     815  
     816      echo '<input type="hidden" name="id" value="'.$course->id.'" />';
     817      echo '<noscript style="display:inline">';
     818      echo '<div><input type="submit" value="'.get_string('ok').'" /></div>';
     819      echo '</noscript>';
     820      echo '</div></div>';
     821      echo '</form>';
     822  
     823      $module = array('name' => 'core_user', 'fullpath' => '/user/module.js');
     824      $PAGE->requires->js_init_call('M.core_user.init_participation', null, false, $module);
     825  }
     826  
     827  // Show a search box if all participants don't fit on a single screen.
     828  if ($totalcount > $perpage) {
     829      echo '<form action="index.php" class="searchform"><div><input type="hidden" name="id" value="'.$course->id.'" />';
     830      echo '<label for="search">' . get_string('search', 'search') . ' </label>';
     831      echo '<input type="text" id="search" name="search" value="'.s($search).'" />&nbsp;<input type="submit" value="'.get_string('search').'" /></div></form>'."\n";
     832  }
     833  
     834  $perpageurl = clone($baseurl);
     835  $perpageurl->remove_params('perpage');
     836  if ($perpage == SHOW_ALL_PAGE_SIZE) {
     837      $perpageurl->param('perpage', DEFAULT_PAGE_SIZE);
     838      echo $OUTPUT->container(html_writer::link($perpageurl, get_string('showperpage', '', DEFAULT_PAGE_SIZE)), array(), 'showall');
     839  
     840  } else if ($matchcount > 0 && $perpage < $matchcount) {
     841      $perpageurl->param('perpage', SHOW_ALL_PAGE_SIZE);
     842      echo $OUTPUT->container(html_writer::link($perpageurl, get_string('showall', '', $matchcount)), array(), 'showall');
     843  }
     844  
     845  echo '</div>';  // Userlist.
     846  
     847  echo $OUTPUT->footer();
     848  
     849  if ($userlist) {
     850      $userlist->close();
     851  }
     852  
     853  /**
     854   * Returns SQL that can be used to limit a query to a period where the user last accessed a course..
     855   *
     856   * @param string $accesssince
     857   * @return string
     858   */
     859  function get_course_lastaccess_sql($accesssince='') {
     860      if (empty($accesssince)) {
     861          return '';
     862      }
     863      if ($accesssince == -1) { // Never.
     864          return 'ul.timeaccess = 0';
     865      } else {
     866          return 'ul.timeaccess != 0 AND ul.timeaccess < '.$accesssince;
     867      }
     868  }
     869  
     870  /**
     871   * Returns SQL that can be used to limit a query to a period where the user last accessed the system.
     872   *
     873   * @param string $accesssince
     874   * @return string
     875   */
     876  function get_user_lastaccess_sql($accesssince='') {
     877      if (empty($accesssince)) {
     878          return '';
     879      }
     880      if ($accesssince == -1) { // Never.
     881          return 'u.lastaccess = 0';
     882      } else {
     883          return 'u.lastaccess != 0 AND u.lastaccess < '.$accesssince;
     884      }
     885  }
    

    Search This Site: