MDL-32523 Duplicate questions in question bank

This commit is contained in:
M Kassaei 2013-11-04 16:35:27 +00:00 committed by Tim Hunt
parent f05e25d208
commit e0c41591e1
6 changed files with 98 additions and 10 deletions

View File

@ -380,6 +380,7 @@ $string['questionbehavioursorder'] = 'Question behaviours order';
$string['questionbehavioursorderexplained'] = 'Enter a comma separated list of behaviours in the order you want them to appear in dropdown menu';
$string['questionidmismatch'] = 'Question ids mismatch';
$string['questionname'] = 'Question name';
$string['questionnamecopy'] = '{$a} (copy)';
$string['questionpreviewdefaults'] = 'Question preview defaults';
$string['questionpreviewdefaults_desc'] = 'These defaults are used when a user first previews a question in the question bank. Once a user has previewed a question, their personal preferences are stored as user preferences.';
$string['questions'] = 'Questions';

View File

@ -1136,7 +1136,7 @@ class quiz_question_bank_view extends question_bank_view {
protected function wanted_columns() {
return array('addtoquizaction', 'checkbox', 'qtype', 'questionnametext',
'editaction', 'previewaction');
'editaction', 'copyaction', 'previewaction');
}
/**

View File

@ -691,6 +691,35 @@ class question_bank_edit_action_column extends question_bank_action_column_base
}
}
/**
* Question bank column for the duplicate action icon.
*
* @copyright 2013 The Open University
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_bank_copy_action_column extends question_bank_action_column_base {
/** @var string avoids repeated calls to get_string('duplicate'). */
protected $strcopy;
public function init() {
parent::init();
$this->strcopy = get_string('duplicate');
}
public function get_name() {
return 'copyaction';
}
protected function display_content($question, $rowclasses) {
// To copy a question, you need permission to add a question in the same
// category as the existing question, and ability to access the details of
// the question being copied.
if (question_has_capability_on($question, 'add') &&
(question_has_capability_on($question, 'edit') || question_has_capability_on($question, 'view'))) {
$this->print_icon('t/copy', $this->strcopy, $this->qbank->copy_question_url($question->id));
}
}
}
/**
* Question bank columns for the preview action icon.
@ -957,7 +986,7 @@ class question_bank_view {
}
protected function wanted_columns() {
$columns = array('checkbox', 'qtype', 'questionname', 'editaction',
$columns = array('checkbox', 'qtype', 'questionname', 'editaction', 'copyaction',
'previewaction', 'moveaction', 'deleteaction', 'creatorname',
'modifiername');
if (question_get_display_preference('qbshowtext', 0, PARAM_BOOL, new moodle_url(''))) {
@ -983,6 +1012,7 @@ class question_bank_view {
new question_bank_creator_name_column($this),
new question_bank_modifier_name_column($this),
new question_bank_edit_action_column($this),
new question_bank_copy_action_column($this),
new question_bank_preview_action_column($this),
new question_bank_move_action_column($this),
new question_bank_delete_action_column($this),
@ -1253,6 +1283,15 @@ class question_bank_view {
return $this->editquestionurl->out(true, array('id' => $questionid));
}
/**
* Get the URL for duplicating a given question.
* @param int $questionid the question id.
* @return moodle_url the URL.
*/
public function copy_question_url($questionid) {
return $this->editquestionurl->out(true, array('id' => $questionid, 'makecopy' => 1));
}
public function move_question_url($questionid) {
return $this->editquestionurl->out(true, array('id' => $questionid, 'movecontext' => 1));
}

View File

@ -31,6 +31,7 @@ require_once($CFG->libdir . '/formslib.php');
// Read URL parameters telling us which question to edit.
$id = optional_param('id', 0, PARAM_INT); // question id
$makecopy = optional_param('makecopy', 0, PARAM_INT);
$qtype = optional_param('qtype', '', PARAM_FILE);
$categoryid = optional_param('category', 0, PARAM_INT);
$cmid = optional_param('cmid', 0, PARAM_INT);
@ -47,6 +48,9 @@ $url = new moodle_url('/question/question.php');
if ($id !== 0) {
$url->param('id', $id);
}
if ($makecopy !== 0) {
$url->param('makecopy', $makecopy);
}
if ($qtype !== '') {
$url->param('qtype', $qtype);
}
@ -177,6 +181,10 @@ if ($id) {
if (!$formeditable) {
question_require_capability_on($question, 'view');
}
if ($makecopy) {
// If we are duplicating a question, add some indication to the question name.
$question->name = get_string('questionnamecopy', 'question', $question->name);
}
}
} else { // creating a new question
@ -209,6 +217,7 @@ if ($formeditable && $id){
$toform->appendqnumstring = $appendqnumstring;
$toform->returnurl = $originalreturnurl;
$toform->movecontext = $movecontext;
$toform->makecopy = $makecopy;
if ($cm !== null){
$toform->cmid = $cm->id;
$toform->courseid = $cm->course;
@ -228,10 +237,10 @@ if ($mform->is_cancelled()) {
}
} else if ($fromform = $mform->get_data()) {
/// If we are saving as a copy, break the connection to the old question.
if (!empty($fromform->makecopy)) {
// If we are saving as a copy, break the connection to the old question.
if ($makecopy) {
$question->id = 0;
$question->hidden = 0; // Copies should not be hidden
$question->hidden = 0; // Copies should not be hidden.
}
/// Process the combination of usecurrentcat, categorymoveto and category form

View File

@ -0,0 +1,40 @@
@core @core_question
Feature: A teacher can duplicate questions in the question bank
In order to reuse questions and modify duplicated questions
As a teacher
I need to duplicate questions
@javascript
Scenario: copy a previously created question
Given the following "users" exists:
| username | firstname | lastname | email |
| teacher1 | Teacher | 1 | teacher1@asd.com |
And the following "courses" exists:
| fullname | shortname | format |
| Course 1 | C1 | weeks |
And the following "course enrolments" exists:
| user | course | role |
| teacher1 | C1 | editingteacher |
And I log in as "admin"
And I follow "Course 1"
And I add a "Essay" question filling the form with:
| Question name | Test question to be copied |
| Question text | Write about whatever you want |
And I log out
And I log in as "teacher1"
And I follow "Course 1"
And I follow "Question bank"
When I click on "Duplicate" "link" in the "Test question to be copied" "table_row"
And I fill the moodle form with:
| Question name | Duplicated question name |
| Question text | Write a lot about duplicating questions |
And I press "Save changes"
Then I should see "Duplicated question name"
And I should see "Test question to be copied"
And I should see "Teacher 1" in the ".categoryquestionscontainer tbody tr.r0 .creatorname" "css_element"
And I should see "Admin User" in the ".categoryquestionscontainer tbody tr.r1 .creatorname" "css_element"
And I click on "Duplicate" "link" in the "Duplicated question name" "table_row"
And the "Question name" field should match "Duplicated question name (copy)" value
And I press "Cancel"
Then I should see "Duplicated question name"
And I should see "Test question to be copied"

View File

@ -241,6 +241,9 @@ abstract class question_edit_form extends question_wizard_form {
$mform->addElement('hidden', 'qtype');
$mform->setType('qtype', PARAM_ALPHA);
$mform->addElement('hidden', 'makecopy');
$mform->setType('makecopy', PARAM_INT);
$buttonarray = array();
if (!empty($this->question->id)) {
// Editing / moving question.
@ -251,10 +254,6 @@ abstract class question_edit_form extends question_wizard_form {
$buttonarray[] = $mform->createElement('submit', 'submitbutton',
get_string('savechanges'));
}
if ($this->question->formoptions->cansaveasnew) {
$buttonarray[] = $mform->createElement('submit', 'makecopy',
get_string('makecopy', 'question'));
}
$buttonarray[] = $mform->createElement('cancel');
} else {
// Adding new question.
@ -361,7 +360,7 @@ abstract class question_edit_form extends question_wizard_form {
array('rows' => 5), $this->editoroptions);
$mform->setType($feedbackname, PARAM_RAW);
// Using setValue() as setDefault() does not work for the editor class.
$element->setValue(array('text'=>get_string($feedbackname.'default', 'question')));
$element->setValue(array('text' => get_string($feedbackname.'default', 'question')));
if ($withshownumpartscorrect && $feedbackname == 'partiallycorrectfeedback') {
$mform->addElement('advcheckbox', 'shownumcorrect',