Differences Between: [Versions 310 and 400] [Versions 311 and 400] [Versions 39 and 400] [Versions 400 and 401] [Versions 400 and 402] [Versions 400 and 403]
1 <?php 2 3 // This file is part of Moodle - http://moodle.org/ 4 // 5 // Moodle is free software: you can redistribute it and/or modify 6 // it under the terms of the GNU General Public License as published by 7 // the Free Software Foundation, either version 3 of the License, or 8 // (at your option) any later version. 9 // 10 // Moodle is distributed in the hope that it will be useful, 11 // but WITHOUT ANY WARRANTY; without even the implied warranty of 12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 // GNU General Public License for more details. 14 // 15 // You should have received a copy of the GNU General Public License 16 // along with Moodle. If not, see <http://www.gnu.org/licenses/>. 17 18 /** 19 * This file is part of the Database module for Moodle 20 * 21 * @copyright 2005 Martin Dougiamas http://dougiamas.com 22 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later 23 * @package mod_data 24 */ 25 26 require_once('../../config.php'); 27 require_once ('lib.php'); 28 require_once($CFG->dirroot.'/mod/data/preset_form.php'); 29 30 $id = optional_param('id', 0, PARAM_INT); // course module id 31 $d = optional_param('d', 0, PARAM_INT); // database id 32 $fid = optional_param('fid', 0 , PARAM_INT); // update field id 33 $newtype = optional_param('newtype','',PARAM_ALPHA); // type of the new field 34 $mode = optional_param('mode','',PARAM_ALPHA); 35 $action = optional_param('action', '', PARAM_ALPHA); 36 $fullname = optional_param('fullname', '', PARAM_PATH); // Directory the preset is in. 37 $defaultsort = optional_param('defaultsort', 0, PARAM_INT); 38 $defaultsortdir = optional_param('defaultsortdir', 0, PARAM_INT); 39 $cancel = optional_param('cancel', 0, PARAM_BOOL); 40 41 if ($cancel) { 42 $mode = 'list'; 43 } 44 45 $url = new moodle_url('/mod/data/field.php'); 46 if ($fid !== 0) { 47 $url->param('fid', $fid); 48 } 49 if ($newtype !== '') { 50 $url->param('newtype', $newtype); 51 } 52 if ($mode !== '') { 53 $url->param('mode', $mode); 54 } 55 if ($defaultsort !== 0) { 56 $url->param('defaultsort', $defaultsort); 57 } 58 if ($defaultsortdir !== 0) { 59 $url->param('defaultsortdir', $defaultsortdir); 60 } 61 if ($cancel !== 0) { 62 $url->param('cancel', $cancel); 63 } 64 if ($action !== '') { 65 $url->param('action', $action); 66 } 67 68 if ($id) { 69 $url->param('id', $id); 70 $PAGE->set_url($url); 71 if (! $cm = get_coursemodule_from_id('data', $id)) { 72 print_error('invalidcoursemodule'); 73 } 74 if (! $course = $DB->get_record('course', array('id'=>$cm->course))) { 75 print_error('coursemisconf'); 76 } 77 if (! $data = $DB->get_record('data', array('id'=>$cm->instance))) { 78 print_error('invalidcoursemodule'); 79 } 80 81 } else { 82 $url->param('d', $d); 83 $PAGE->set_url($url); 84 if (! $data = $DB->get_record('data', array('id'=>$d))) { 85 print_error('invalidid', 'data'); 86 } 87 if (! $course = $DB->get_record('course', array('id'=>$data->course))) { 88 print_error('invalidcoursemodule'); 89 } 90 if (! $cm = get_coursemodule_from_instance('data', $data->id, $course->id)) { 91 print_error('invalidcoursemodule'); 92 } 93 } 94 95 require_login($course, true, $cm); 96 97 $context = context_module::instance($cm->id); 98 require_capability('mod/data:managetemplates', $context); 99 100 $formimportzip = new data_import_preset_zip_form(); 101 $formimportzip->set_data(array('d' => $data->id)); 102 103 $actionbar = new \mod_data\output\action_bar($data->id, $PAGE->url); 104 105 $PAGE->set_title(get_string('course') . ': ' . $course->fullname); 106 $PAGE->set_heading($course->fullname); 107 $PAGE->activityheader->disable(); 108 109 // Fill in missing properties needed for updating of instance. 110 $data->course = $cm->course; 111 $data->cmidnumber = $cm->idnumber; 112 $data->instance = $cm->instance; 113 114 /************************************ 115 * Data Processing * 116 ***********************************/ 117 $renderer = $PAGE->get_renderer('mod_data'); 118 119 if ($formimportzip->is_cancelled()) { 120 redirect(new moodle_url('/mod/data/field.php', ['d' => $data->id])); 121 } else if ($formdata = $formimportzip->get_data()) { 122 $fieldactionbar = $actionbar->get_fields_action_bar(); 123 data_print_header($course, $cm, $data, false, $fieldactionbar); 124 echo $OUTPUT->heading(get_string('importpreset', 'data'), 2, 'mb-4'); 125 $file = new stdClass; 126 $file->name = $formimportzip->get_new_filename('importfile'); 127 $file->path = $formimportzip->save_temp_file('importfile'); 128 $importer = new data_preset_upload_importer($course, $cm, $data, $file->path); 129 echo $renderer->import_setting_mappings($data, $importer); 130 echo $OUTPUT->footer(); 131 exit(0); 132 } 133 134 if ($action == 'finishimport' && confirm_sesskey()) { 135 data_print_header($course, $cm, $data, false); 136 $overwritesettings = optional_param('overwritesettings', false, PARAM_BOOL); 137 138 if (!$fullname) { 139 $presetdir = $CFG->tempdir . '/forms/' . required_param('directory', PARAM_FILE); 140 if (!file_exists($presetdir) || !is_dir($presetdir)) { 141 throw new moodle_exception('cannotimport', 'error'); 142 } 143 $importer = new data_preset_upload_importer($course, $cm, $data, $presetdir); 144 } else { 145 $importer = new data_preset_existing_importer($course, $cm, $data, $fullname); 146 } 147 148 $importer->import($overwritesettings); 149 $strimportsuccess = get_string('importsuccess', 'data'); 150 $straddentries = get_string('addentries', 'data'); 151 $strtodatabase = get_string('todatabase', 'data'); 152 153 if (!$DB->get_records('data_records', array('dataid' => $data->id))) { 154 echo $OUTPUT->notification("$strimportsuccess <a href='edit.php?d=$data->id'>$straddentries</a> $strtodatabase", 155 'notifysuccess'); 156 } else { 157 echo $OUTPUT->notification("$strimportsuccess", 'notifysuccess'); 158 } 159 160 echo $OUTPUT->continue_button(new moodle_url('/mod/data/field.php', ['d' => $data->id])); 161 echo $OUTPUT->footer(); 162 exit; 163 } 164 165 switch ($mode) { 166 167 case 'add': ///add a new field 168 if (confirm_sesskey() and $fieldinput = data_submitted()){ 169 170 //$fieldinput->name = data_clean_field_name($fieldinput->name); 171 172 /// Only store this new field if it doesn't already exist. 173 if (($fieldinput->name == '') or data_fieldname_exists($fieldinput->name, $data->id)) { 174 175 $displaynoticebad = get_string('invalidfieldname','data'); 176 177 } else { 178 179 /// Check for arrays and convert to a comma-delimited string 180 data_convert_arrays_to_strings($fieldinput); 181 182 /// Create a field object to collect and store the data safely 183 $type = required_param('type', PARAM_FILE); 184 $field = data_get_field_new($type, $data); 185 186 if (!empty($validationerrors = $field->validate($fieldinput))) { 187 $displaynoticebad = html_writer::alist($validationerrors); 188 $mode = 'new'; 189 $newtype = $type; 190 break; 191 } 192 193 $field->define_field($fieldinput); 194 $field->insert_field(); 195 196 /// Update some templates 197 data_append_new_field_to_templates($data, $fieldinput->name); 198 199 $displaynoticegood = get_string('fieldadded','data'); 200 } 201 } 202 break; 203 204 205 case 'update': ///update a field 206 if (confirm_sesskey() and $fieldinput = data_submitted()){ 207 208 //$fieldinput->name = data_clean_field_name($fieldinput->name); 209 210 if (($fieldinput->name == '') or data_fieldname_exists($fieldinput->name, $data->id, $fieldinput->fid)) { 211 212 $displaynoticebad = get_string('invalidfieldname','data'); 213 214 } else { 215 /// Check for arrays and convert to a comma-delimited string 216 data_convert_arrays_to_strings($fieldinput); 217 218 /// Create a field object to collect and store the data safely 219 $field = data_get_field_from_id($fid, $data); 220 if (!empty($validationerrors = $field->validate($fieldinput))) { 221 $displaynoticebad = html_writer::alist($validationerrors); 222 $mode = 'display'; 223 break; 224 } 225 $oldfieldname = $field->field->name; 226 227 $field->field->name = $fieldinput->name; 228 $field->field->description = $fieldinput->description; 229 $field->field->required = !empty($fieldinput->required) ? 1 : 0; 230 231 for ($i=1; $i<=10; $i++) { 232 if (isset($fieldinput->{'param'.$i})) { 233 $field->field->{'param'.$i} = $fieldinput->{'param'.$i}; 234 } else { 235 $field->field->{'param'.$i} = ''; 236 } 237 } 238 239 $field->update_field(); 240 241 /// Update the templates. 242 data_replace_field_in_templates($data, $oldfieldname, $field->field->name); 243 244 $displaynoticegood = get_string('fieldupdated','data'); 245 } 246 } 247 break; 248 249 250 case 'delete': // Delete a field 251 if (confirm_sesskey()){ 252 253 if ($confirm = optional_param('confirm', 0, PARAM_INT)) { 254 255 256 // Delete the field completely 257 if ($field = data_get_field_from_id($fid, $data)) { 258 $field->delete_field(); 259 260 // Update the templates. 261 data_replace_field_in_templates($data, $field->field->name, ''); 262 263 // Update the default sort field 264 if ($fid == $data->defaultsort) { 265 $rec = new stdClass(); 266 $rec->id = $data->id; 267 $rec->defaultsort = 0; 268 $rec->defaultsortdir = 0; 269 $DB->update_record('data', $rec); 270 } 271 272 $displaynoticegood = get_string('fielddeleted', 'data'); 273 } 274 275 } else { 276 277 data_print_header($course,$cm,$data, false); 278 echo $OUTPUT->heading(get_string('deletefield', 'data'), 2, 'mb-4'); 279 280 // Print confirmation message. 281 $field = data_get_field_from_id($fid, $data); 282 283 if ($field->type === 'unknown') { 284 $fieldtypename = get_string('unknown', 'data'); 285 } else { 286 $fieldtypename = $field->name(); 287 } 288 echo $OUTPUT->confirm('<strong>'.$fieldtypename.': '.$field->field->name.'</strong><br /><br />'. 289 get_string('confirmdeletefield', 'data'), 290 'field.php?d='.$data->id.'&mode=delete&fid='.$fid.'&confirm=1', 291 'field.php?d='.$data->id); 292 293 echo $OUTPUT->footer(); 294 exit; 295 } 296 } 297 break; 298 299 300 case 'sort': // Set the default sort parameters 301 if (confirm_sesskey()) { 302 $rec = new stdClass(); 303 $rec->id = $data->id; 304 $rec->defaultsort = $defaultsort; 305 $rec->defaultsortdir = $defaultsortdir; 306 307 $DB->update_record('data', $rec); 308 redirect($CFG->wwwroot.'/mod/data/field.php?d='.$data->id, get_string('changessaved'), 2); 309 exit; 310 } 311 break; 312 313 case 'import': 314 $PAGE->navbar->add(get_string('importpreset', 'data')); 315 $fieldactionbar = $actionbar->get_fields_action_bar(); 316 data_print_header($course, $cm, $data, false, $fieldactionbar); 317 318 echo $OUTPUT->heading(get_string('importpreset', 'data'), 2, 'mb-4'); 319 echo $formimportzip->display(); 320 echo $OUTPUT->footer(); 321 exit; 322 323 case 'usepreset': 324 $PAGE->navbar->add(get_string('usestandard', 'data')); 325 $fieldactionbar = $actionbar->get_fields_action_bar(); 326 data_print_header($course, $cm, $data, false, $fieldactionbar); 327 328 if ($action === 'select') { 329 if (!empty($fullname)) { 330 echo $OUTPUT->heading(get_string('usestandard', 'data'), 2, 'mb-4'); 331 $importer = new data_preset_existing_importer($course, $cm, $data, $fullname); 332 echo $renderer->import_setting_mappings($data, $importer); 333 } 334 } else { 335 echo $OUTPUT->heading(get_string('presets', 'data'), 2, 'mb-4'); 336 $presets = data_get_available_presets($context); 337 $presetstable = new \mod_data\output\presets($data->id, $presets, 338 new \moodle_url('/mod/data/field.php')); 339 echo $renderer->render_presets($presetstable, false); 340 } 341 echo $OUTPUT->footer(); 342 exit; 343 344 default: 345 break; 346 } 347 348 349 350 /// Print the browsing interface 351 352 ///get the list of possible fields (plugins) 353 $plugins = core_component::get_plugin_list('datafield'); 354 $menufield = array(); 355 356 foreach ($plugins as $plugin=>$fulldir){ 357 if (!is_dir($fulldir)) { 358 continue; 359 } 360 $menufield[$plugin] = get_string('pluginname', 'datafield_'.$plugin); //get from language files 361 } 362 asort($menufield); //sort in alphabetical order 363 $PAGE->force_settings_menu(true); 364 365 $PAGE->set_pagetype('mod-data-field-' . $newtype); 366 if (($mode == 'new') && (!empty($newtype))) { // Adding a new field. 367 data_print_header($course, $cm, $data,'fields'); 368 echo $OUTPUT->heading(get_string('newfield', 'data')); 369 370 $field = data_get_field_new($newtype, $data); 371 $field->display_edit_field(); 372 373 } else if ($mode == 'display' && confirm_sesskey()) { /// Display/edit existing field 374 data_print_header($course, $cm, $data,'fields'); 375 echo $OUTPUT->heading(get_string('editfield', 'data')); 376 377 $field = data_get_field_from_id($fid, $data); 378 $field->display_edit_field(); 379 380 } else { /// Display the main listing of all fields 381 $fieldactionbar = $actionbar->get_fields_action_bar(true, true, true); 382 data_print_header($course, $cm, $data, 'fields', $fieldactionbar); 383 echo $OUTPUT->heading(get_string('managefields', 'data'), 2, 'mb-4'); 384 385 if (!$DB->record_exists('data_fields', array('dataid'=>$data->id))) { 386 echo $OUTPUT->notification(get_string('nofieldindatabase','data')); // nothing in database 387 echo $OUTPUT->notification(get_string('pleaseaddsome','data', 'preset.php?id='.$cm->id)); // link to presets 388 389 } else { //else print quiz style list of fields 390 391 $table = new html_table(); 392 $table->head = array( 393 get_string('fieldname', 'data'), 394 get_string('type', 'data'), 395 get_string('required', 'data'), 396 get_string('fielddescription', 'data'), 397 get_string('action', 'data'), 398 ); 399 $table->align = array('left', 'left', 'left', 'left'); 400 $table->wrap = array(false,false,false,false); 401 402 if ($fff = $DB->get_records('data_fields', array('dataid'=>$data->id),'id')){ 403 $missingfieldtypes = []; 404 foreach ($fff as $ff) { 405 406 $field = data_get_field($ff, $data); 407 408 $baseurl = new moodle_url('/mod/data/field.php', array( 409 'd' => $data->id, 410 'fid' => $field->field->id, 411 'sesskey' => sesskey(), 412 )); 413 414 $displayurl = new moodle_url($baseurl, array( 415 'mode' => 'display', 416 )); 417 418 $deleteurl = new moodle_url($baseurl, array( 419 'mode' => 'delete', 420 )); 421 422 // It display a notification when the field type does not exist. 423 $deletelink = html_writer::link($deleteurl, $OUTPUT->pix_icon('t/delete', get_string('delete'))); 424 $editlink = html_writer::link($displayurl, $OUTPUT->pix_icon('t/edit', get_string('edit'))); 425 if ($field->type === 'unknown') { 426 $missingfieldtypes[] = $field->field->name; 427 $fieldnamedata = $field->field->name; 428 $fieltypedata = $field->field->type; 429 $fieldlinkdata = $deletelink; 430 } else { 431 $fieldnamedata = html_writer::link($displayurl, $field->field->name); 432 $fieltypedata = $field->image() . ' ' . $field->name(); 433 $fieldlinkdata = $editlink . ' ' . $deletelink; 434 } 435 436 $table->data[] = [ 437 $fieldnamedata, 438 $fieltypedata, 439 $field->field->required ? get_string('yes') : get_string('no'), 440 shorten_text($field->field->description, 30), 441 $fieldlinkdata 442 ]; 443 } 444 if (!empty($missingfieldtypes)) { 445 echo $OUTPUT->notification(get_string('missingfieldtypes', 'data') . html_writer::alist($missingfieldtypes)); 446 } 447 } 448 echo html_writer::table($table); 449 } 450 451 echo '<div class="sortdefault">'; 452 echo '<form id="sortdefault" action="'.$CFG->wwwroot.'/mod/data/field.php" method="get">'; 453 echo '<div>'; 454 echo '<input type="hidden" name="d" value="'.$data->id.'" />'; 455 echo '<input type="hidden" name="mode" value="sort" />'; 456 echo '<input type="hidden" name="sesskey" value="'.sesskey().'" />'; 457 echo '<label for="defaultsort">'.get_string('defaultsortfield','data').'</label>'; 458 echo '<select id="defaultsort" name="defaultsort" class="custom-select">'; 459 if ($fields = $DB->get_records('data_fields', array('dataid'=>$data->id))) { 460 echo '<optgroup label="'.get_string('fields', 'data').'">'; 461 foreach ($fields as $field) { 462 if ($data->defaultsort == $field->id) { 463 echo '<option value="'.$field->id.'" selected="selected">'.$field->name.'</option>'; 464 } else { 465 echo '<option value="'.$field->id.'">'.$field->name.'</option>'; 466 } 467 } 468 echo '</optgroup>'; 469 } 470 $options = array(); 471 $options[DATA_TIMEADDED] = get_string('timeadded', 'data'); 472 // TODO: we will need to change defaultsort db to unsinged to make these work in 2.0 473 /* $options[DATA_TIMEMODIFIED] = get_string('timemodified', 'data'); 474 $options[DATA_FIRSTNAME] = get_string('authorfirstname', 'data'); 475 $options[DATA_LASTNAME] = get_string('authorlastname', 'data'); 476 if ($data->approval and has_capability('mod/data:approve', $context)) { 477 $options[DATA_APPROVED] = get_string('approved', 'data'); 478 }*/ 479 echo '<optgroup label="'.get_string('other', 'data').'">'; 480 foreach ($options as $key => $name) { 481 if ($data->defaultsort == $key) { 482 echo '<option value="'.$key.'" selected="selected">'.$name.'</option>'; 483 } else { 484 echo '<option value="'.$key.'">'.$name.'</option>'; 485 } 486 } 487 echo '</optgroup>'; 488 echo '</select>'; 489 490 $options = array(0 => get_string('ascending', 'data'), 491 1 => get_string('descending', 'data')); 492 echo html_writer::label(get_string('sortby'), 'menudefaultsortdir', false, array('class' => 'accesshide')); 493 echo html_writer::select($options, 'defaultsortdir', $data->defaultsortdir, false, array('class' => 'custom-select')); 494 echo '<input type="submit" class="btn btn-secondary ml-1" value="'.get_string('save', 'data').'" />'; 495 echo '</div>'; 496 echo '</form>'; 497 echo '</div>'; 498 499 } 500 501 /// Finish the page 502 echo $OUTPUT->footer(); 503
title
Description
Body
title
Description
Body
title
Description
Body
title
Body