[ Index ]

PHP Cross Reference of Unnamed Project

title

Body

[close]

/mod/quiz/report/overview/ -> overview_table.php (source)

   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   * This file defines the quiz grades table.
  19   *
  20   * @package   quiz_overview
  21   * @copyright 2008 Jamie Pratt
  22   * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  23   */
  24  
  25  
  26  defined('MOODLE_INTERNAL') || die();
  27  
  28  require_once($CFG->dirroot . '/mod/quiz/report/attemptsreport_table.php');
  29  
  30  
  31  /**
  32   * This is a table subclass for displaying the quiz grades report.
  33   *
  34   * @copyright 2008 Jamie Pratt
  35   * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  36   */
  37  class quiz_overview_table extends quiz_attempts_report_table {
  38  
  39      protected $regradedqs = array();
  40  
  41      /**
  42       * Constructor
  43       * @param object $quiz
  44       * @param context $context
  45       * @param string $qmsubselect
  46       * @param quiz_overview_options $options
  47       * @param array $groupstudents
  48       * @param array $students
  49       * @param array $questions
  50       * @param moodle_url $reporturl
  51       */
  52      public function __construct($quiz, $context, $qmsubselect,
  53              quiz_overview_options $options, $groupstudents, $students, $questions, $reporturl) {
  54          parent::__construct('mod-quiz-report-overview-report', $quiz , $context,
  55                  $qmsubselect, $options, $groupstudents, $students, $questions, $reporturl);
  56      }
  57  
  58      public function build_table() {
  59          global $DB;
  60  
  61          if (!$this->rawdata) {
  62              return;
  63          }
  64  
  65          $this->strtimeformat = str_replace(',', ' ', get_string('strftimedatetime'));
  66          parent::build_table();
  67  
  68          // End of adding the data from attempts. Now add averages at bottom.
  69          $this->add_separator();
  70  
  71          if ($this->groupstudents) {
  72              $this->add_average_row(get_string('groupavg', 'grades'), $this->groupstudents);
  73          }
  74  
  75          if ($this->students) {
  76              $this->add_average_row(get_string('overallaverage', 'grades'), $this->students);
  77          }
  78      }
  79  
  80      /**
  81       * Add an average grade over the attempts of a set of users.
  82       * @param string $label the title ot use for this row.
  83       * @param array $users the users to average over.
  84       */
  85      protected function add_average_row($label, $users) {
  86          global $DB;
  87  
  88          list($fields, $from, $where, $params) = $this->base_sql($users);
  89          $record = $DB->get_record_sql("
  90                  SELECT AVG(quiza.sumgrades) AS grade, COUNT(quiza.sumgrades) AS numaveraged
  91                    FROM $from
  92                   WHERE $where", $params);
  93          $record->grade = quiz_rescale_grade($record->grade, $this->quiz, false);
  94  
  95          if ($this->is_downloading()) {
  96              $namekey = 'lastname';
  97          } else {
  98              $namekey = 'fullname';
  99          }
 100          $averagerow = array(
 101              $namekey    => $label,
 102              'sumgrades' => $this->format_average($record),
 103              'feedbacktext'=> strip_tags(quiz_report_feedback_for_grade(
 104                                          $record->grade, $this->quiz->id, $this->context))
 105          );
 106  
 107          if ($this->options->slotmarks) {
 108              $dm = new question_engine_data_mapper();
 109              $qubaids = new qubaid_join($from, 'quiza.uniqueid', $where, $params);
 110              $avggradebyq = $dm->load_average_marks($qubaids, array_keys($this->questions));
 111  
 112              $averagerow += $this->format_average_grade_for_questions($avggradebyq);
 113          }
 114  
 115          $this->add_data_keyed($averagerow);
 116      }
 117  
 118      /**
 119       * Helper userd by {@link add_average_row()}.
 120       * @param array $gradeaverages the raw grades.
 121       * @return array the (partial) row of data.
 122       */
 123      protected function format_average_grade_for_questions($gradeaverages) {
 124          $row = array();
 125  
 126          if (!$gradeaverages) {
 127              $gradeaverages = array();
 128          }
 129  
 130          foreach ($this->questions as $question) {
 131              if (isset($gradeaverages[$question->slot]) && $question->maxmark > 0) {
 132                  $record = $gradeaverages[$question->slot];
 133                  $record->grade = quiz_rescale_grade(
 134                          $record->averagefraction * $question->maxmark, $this->quiz, false);
 135  
 136              } else {
 137                  $record = new stdClass();
 138                  $record->grade = null;
 139                  $record->numaveraged = 0;
 140              }
 141  
 142              $row['qsgrade' . $question->slot] = $this->format_average($record, true);
 143          }
 144  
 145          return $row;
 146      }
 147  
 148      /**
 149       * Format an entry in an average row.
 150       * @param object $record with fields grade and numaveraged
 151       */
 152      protected function format_average($record, $question = false) {
 153          if (is_null($record->grade)) {
 154              $average = '-';
 155          } else if ($question) {
 156              $average = quiz_format_question_grade($this->quiz, $record->grade);
 157          } else {
 158              $average = quiz_format_grade($this->quiz, $record->grade);
 159          }
 160  
 161          if ($this->download) {
 162              return $average;
 163          } else if (is_null($record->numaveraged) || $record->numaveraged == 0) {
 164              return html_writer::tag('span', html_writer::tag('span',
 165                      $average, array('class' => 'average')), array('class' => 'avgcell'));
 166          } else {
 167              return html_writer::tag('span', html_writer::tag('span',
 168                      $average, array('class' => 'average')) . ' ' . html_writer::tag('span',
 169                      '(' . $record->numaveraged . ')', array('class' => 'count')),
 170                      array('class' => 'avgcell'));
 171          }
 172      }
 173  
 174      protected function submit_buttons() {
 175          if (has_capability('mod/quiz:regrade', $this->context)) {
 176              echo '<input type="submit" name="regrade" value="' .
 177                      get_string('regradeselected', 'quiz_overview') . '"/>';
 178          }
 179          parent::submit_buttons();
 180      }
 181  
 182      public function col_sumgrades($attempt) {
 183          if ($attempt->state != quiz_attempt::FINISHED) {
 184              return '-';
 185          }
 186  
 187          $grade = quiz_rescale_grade($attempt->sumgrades, $this->quiz);
 188          if ($this->is_downloading()) {
 189              return $grade;
 190          }
 191  
 192          if (isset($this->regradedqs[$attempt->usageid])) {
 193              $newsumgrade = 0;
 194              $oldsumgrade = 0;
 195              foreach ($this->questions as $question) {
 196                  if (isset($this->regradedqs[$attempt->usageid][$question->slot])) {
 197                      $newsumgrade += $this->regradedqs[$attempt->usageid]
 198                              [$question->slot]->newfraction * $question->maxmark;
 199                      $oldsumgrade += $this->regradedqs[$attempt->usageid]
 200                              [$question->slot]->oldfraction * $question->maxmark;
 201                  } else {
 202                      $newsumgrade += $this->lateststeps[$attempt->usageid]
 203                              [$question->slot]->fraction * $question->maxmark;
 204                      $oldsumgrade += $this->lateststeps[$attempt->usageid]
 205                              [$question->slot]->fraction * $question->maxmark;
 206                  }
 207              }
 208              $newsumgrade = quiz_rescale_grade($newsumgrade, $this->quiz);
 209              $oldsumgrade = quiz_rescale_grade($oldsumgrade, $this->quiz);
 210              $grade = html_writer::tag('del', $oldsumgrade) . '/' .
 211                      html_writer::empty_tag('br') . $newsumgrade;
 212          }
 213          return html_writer::link(new moodle_url('/mod/quiz/review.php',
 214                  array('attempt' => $attempt->attempt)), $grade,
 215                  array('title' => get_string('reviewattempt', 'quiz')));
 216      }
 217  
 218      /**
 219       * @param string $colname the name of the column.
 220       * @param object $attempt the row of data - see the SQL in display() in
 221       * mod/quiz/report/overview/report.php to see what fields are present,
 222       * and what they are called.
 223       * @return string the contents of the cell.
 224       */
 225      public function other_cols($colname, $attempt) {
 226          if (!preg_match('/^qsgrade(\d+)$/', $colname, $matches)) {
 227              return null;
 228          }
 229          $slot = $matches[1];
 230  
 231          $question = $this->questions[$slot];
 232          if (!isset($this->lateststeps[$attempt->usageid][$slot])) {
 233              return '-';
 234          }
 235  
 236          $stepdata = $this->lateststeps[$attempt->usageid][$slot];
 237          $state = question_state::get($stepdata->state);
 238  
 239          if ($question->maxmark == 0) {
 240              $grade = '-';
 241          } else if (is_null($stepdata->fraction)) {
 242              if ($state == question_state::$needsgrading) {
 243                  $grade = get_string('requiresgrading', 'question');
 244              } else {
 245                  $grade = '-';
 246              }
 247          } else {
 248              $grade = quiz_rescale_grade(
 249                      $stepdata->fraction * $question->maxmark, $this->quiz, 'question');
 250          }
 251  
 252          if ($this->is_downloading()) {
 253              return $grade;
 254          }
 255  
 256          if (isset($this->regradedqs[$attempt->usageid][$slot])) {
 257              $gradefromdb = $grade;
 258              $newgrade = quiz_rescale_grade(
 259                      $this->regradedqs[$attempt->usageid][$slot]->newfraction * $question->maxmark,
 260                      $this->quiz, 'question');
 261              $oldgrade = quiz_rescale_grade(
 262                      $this->regradedqs[$attempt->usageid][$slot]->oldfraction * $question->maxmark,
 263                      $this->quiz, 'question');
 264  
 265              $grade = html_writer::tag('del', $oldgrade) . '/' .
 266                      html_writer::empty_tag('br') . $newgrade;
 267          }
 268  
 269          return $this->make_review_link($grade, $attempt, $slot);
 270      }
 271  
 272      public function col_regraded($attempt) {
 273          if ($attempt->regraded == '') {
 274              return '';
 275          } else if ($attempt->regraded == 0) {
 276              return get_string('needed', 'quiz_overview');
 277          } else if ($attempt->regraded == 1) {
 278              return get_string('done', 'quiz_overview');
 279          }
 280      }
 281  
 282      protected function requires_latest_steps_loaded() {
 283          return $this->options->slotmarks;
 284      }
 285  
 286      protected function is_latest_step_column($column) {
 287          if (preg_match('/^qsgrade([0-9]+)/', $column, $matches)) {
 288              return $matches[1];
 289          }
 290          return false;
 291      }
 292  
 293      protected function get_required_latest_state_fields($slot, $alias) {
 294          return "$alias.fraction * $alias.maxmark AS qsgrade$slot";
 295      }
 296  
 297      public function query_db($pagesize, $useinitialsbar = true) {
 298          parent::query_db($pagesize, $useinitialsbar);
 299  
 300          if ($this->options->slotmarks && has_capability('mod/quiz:regrade', $this->context)) {
 301              $this->regradedqs = $this->get_regraded_questions();
 302          }
 303      }
 304  
 305      /**
 306       * Get all the questions in all the attempts being displayed that need regrading.
 307       * @return array A two dimensional array $questionusageid => $slot => $regradeinfo.
 308       */
 309      protected function get_regraded_questions() {
 310          global $DB;
 311  
 312          $qubaids = $this->get_qubaids_condition();
 313          $regradedqs = $DB->get_records_select('quiz_overview_regrades',
 314                  'questionusageid ' . $qubaids->usage_id_in(), $qubaids->usage_id_in_params());
 315          return quiz_report_index_by_keys($regradedqs, array('questionusageid', 'slot'));
 316      }
 317  }


Generated: Thu Aug 11 10:00:09 2016 Cross-referenced by PHPXref 0.7.1