Moodle

All or nothing scoring for multiple choice-multiple response

Details

  • Type: New Feature New Feature
  • Status: Open Open
  • Priority: Minor Minor
  • Resolution: Unresolved
  • Affects Version/s: 1.5
  • Fix Version/s: None
  • Component/s: Quiz
  • Labels:
    None
  • Environment:
    All
  • Database:
    MySQL
  • Affected Branches:
    MOODLE_15_STABLE

Description

The problem:

if I have a multiple choiche quiz containing 5 possible answer, if 4 answer are all needed to make the quiz correct, according to your suggestion I set up in this way:

correct answer 1: 25%

correct answer 2: 25%

correct answer 3: 25%

correct answer 4: 25%

wrong answer 1: -100%

I want to have a score of 0 if at least 1 answer is wrong, while I want a full score if all the four correct answer are selected. A question must be considered wrong with a score of 0 also if only 1 correct answer is missing.

Attempting the quiz, the decimal percentage is mantained: for example with a question score of 1, selecting the first three answer I get 0.75/1 instead of 0. I'm able to get 0 only if I select also the wrong answer.

Possible solution:

new setting like all positive answers MUST be chosen to get anything (yes/no). This needs to be added to the multichoice table as a new column, and the grading routines need to check for it and use it appropriately when calculating grades.

Issue Links

Activity

Hide
Richard Rode added a comment -

It is not very difficult to add the all or nothing flag to your Moodle. Just change the code as follows:

Open the language file:
lang/en_utf8/qtype_multichoice.php

and add the string:

$string['allornothing'] = 'All or nothing';

If you have a german language pack to the same and add 'Alles oder nichts'.

Write a help file and describe what the all or nothing flag does. Save it as:
lang/en_utf8/help/qtype_multichoice/allornothing.html

If you want a german version you can take the one in the attached zip. If you want a correct english version, it would be a better idea to write your own.

In your Moodle database change the table 'question_multichoice'. Add the field 'allornothing' (type int, default 1).

Now open the following files and add the lines with the plus (but not the plus):

question/type/multichoice/edit_multichoice_form.php
:

$menu = array(get_string('answersingleno', 'qtype_multichoice'), get_string('answersingleyes', 'qtype_multichoice'));

        $mform->addElement('select', 'single', get_string('answerhowmany', 'qtype_multichoice'), $menu);

        $mform->setDefault('single', 1);



+        $mform->addElement('advcheckbox', 'allornothing', get_string('allornothing', 'qtype_multichoice'), null, null, array(0,1));

+        $mform->setDefault('allornothing', 1);



        $mform->addElement('advcheckbox', 'shuffleanswers', get_string('shuffleanswers', 'qtype_multichoice'), null, null, array(0,1));

        $mform->setHelpButton('shuffleanswers', array('multichoiceshuffle', get_string('shuffleanswers','qtype_multichoice'), 'quiz'));

        $mform->setDefault('shuffleanswers', 1);

and same file:

$default_values['single'] =  $question->options->single;

+            $default_values['allornothing'] =  $question->options->allornothing;

            $default_values['answernumbering'] =  $question->options->answernumbering;

question/type/multichoice/questiontype.php
:

$options->answernumbering = $question->answernumbering;

        $options->shuffleanswers = $question->shuffleanswers;

+        if (isset($question->allornothing)) {

+            $options->allornothing = $question->allornothing;

+        }

        $options->correctfeedback = trim($question->correctfeedback);

        $options->partiallycorrectfeedback = trim($question->partiallycorrectfeedback);

Same file in the function grade_resposes:

} else {

            foreach ($state->responses as $response) {

                if ($response) {

                    $state->raw_grade += $question->options->answers[$response]->fraction;

                }

            }

+            if ($question->options->allornothing && $state->raw_grade < 0.9999) {

+                $state->raw_grade = 0;

+            }

        }

Same file in the function backup:

fwrite ($bf,full_tag("SHUFFLEANSWERS",$level+1,false,$multichoice->shuffleanswers));

+                fwrite ($bf,full_tag("ALLORNOTHING",$level+1,false,$multichoice->allornothing));

                fwrite ($bf,full_tag("CORRECTFEEDBACK",$level+1,false,$multichoice->correctfeedback));

And in the function restore:

$multichoice->single = backup_todb($mul_info['#']['SINGLE']['0']['#']);

+            $multichoice->allornothing = backup_todb($mul_info['#']['ALLORNOTHING']['0']['#']);

            $multichoice->shuffleanswers = isset($mul_info['#']['SHUFFLEANSWERS']['0']['#'])?backup_todb($mul_info['#']['SHUFFLEANSWERS']['0']['#']):'';

To make sure that Moodle-XML-format works with the new flag open question/format/xml/format.php
and add:

$qo->answernumbering = $this->getpath( $question, array('#','answernumbering',0,'#'), 'abc' );

        $qo->shuffleanswers = $this->trans_single($shuffleanswers);

+        $allornothing = $this->getpath( $question, array('#','allornothing',0,'#'), 'false' );

+        $qo->allornothing = $this->trans_single($allornothing);

        $qo->correctfeedback = $this->getpath( $question, array('#','correctfeedback',0,'#','text',0,'#'), '', true );

And in the same file:

case MULTICHOICE:

            $expout .= "    <single>".$this->get_single($question->options->single)."</single>\n";

            $expout .= "    <shuffleanswers>".$this->get_single($question->options->shuffleanswers)."</shuffleanswers>\n";

+            $expout .= "    <allornothing>".$this->get_single($question->options->allornothing)."</allornothing>\n";

            $expout .= "    <correctfeedback>".$this->writetext($question->options->correctfeedback, 3)."</correctfeedback>\n";

You can also set a new option in the import form to overrule this flag if someone has a format without allornothing (like GIFT) and doesn't like your default value. To do this change:

question/import_form.php
:

$mform->disabledIf('categorygroup', 'catfromfile', 'notchecked');

        $mform->setDefault('catfromfile', 1);

        $mform->setDefault('contextfromfile', 1);



+        $allornothing = array();

+        $allornothing['default'] = get_string('default');

+        $allornothing['true'] = get_string('yes');

+        $allornothing['false'] = get_string('no');

+        $mform->addElement('select', 'allornothing', get_string('allornothing','qtype_multichoice'), $allornothing);

+        $mform->setHelpButton('allornothing', array('allornothing', get_string('allornothing','qtype_multichoice'), 'qtype_multichoice'));




        $matchgrades = array();

        $matchgrades['error'] = get_string('matchgradeserror','quiz');

question/import.php:

$qformat->setRealfilename($realfilename);

            $qformat->setMatchgrades($form->matchgrades);

+            $qformat->setAllornothing($form->allornothing);

            $qformat->setCatfromfile(!empty($form->catfromfile));

            $qformat->setContextfromfile(!empty($form->contextfromfile));

question/format.php

function setMatchgrades( $matchgrades ) {

        $this->matchgrades = $matchgrades;

    }



+    /**

+     * set allornothing

+     * @param string allornothing

+     */

+    function setAllornothing( $allornothing ) {

+        if ($allornothing == 'true') {

+            $this->allornothing = true;

+        } else if ($allornothing == 'false') {

+            $this->allornothing = false;

+        }

+    }

This is all. If it doesn't work, feel free to contact me and complain. The files I attached should be compatible with 1.9.4 but be careful, there could be other local changes in them.

Show
Richard Rode added a comment - It is not very difficult to add the all or nothing flag to your Moodle. Just change the code as follows: Open the language file: lang/en_utf8/qtype_multichoice.php and add the string:
$string['allornothing'] = 'All or nothing';
If you have a german language pack to the same and add 'Alles oder nichts'. Write a help file and describe what the all or nothing flag does. Save it as: lang/en_utf8/help/qtype_multichoice/allornothing.html If you want a german version you can take the one in the attached zip. If you want a correct english version, it would be a better idea to write your own. In your Moodle database change the table 'question_multichoice'. Add the field 'allornothing' (type int, default 1). Now open the following files and add the lines with the plus (but not the plus): question/type/multichoice/edit_multichoice_form.php :
$menu = array(get_string('answersingleno', 'qtype_multichoice'), get_string('answersingleyes', 'qtype_multichoice'));

        $mform->addElement('select', 'single', get_string('answerhowmany', 'qtype_multichoice'), $menu);

        $mform->setDefault('single', 1);



+        $mform->addElement('advcheckbox', 'allornothing', get_string('allornothing', 'qtype_multichoice'), null, null, array(0,1));

+        $mform->setDefault('allornothing', 1);



        $mform->addElement('advcheckbox', 'shuffleanswers', get_string('shuffleanswers', 'qtype_multichoice'), null, null, array(0,1));

        $mform->setHelpButton('shuffleanswers', array('multichoiceshuffle', get_string('shuffleanswers','qtype_multichoice'), 'quiz'));

        $mform->setDefault('shuffleanswers', 1);
and same file:
$default_values['single'] =  $question->options->single;

+            $default_values['allornothing'] =  $question->options->allornothing;

            $default_values['answernumbering'] =  $question->options->answernumbering;
question/type/multichoice/questiontype.php :
$options->answernumbering = $question->answernumbering;

        $options->shuffleanswers = $question->shuffleanswers;

+        if (isset($question->allornothing)) {

+            $options->allornothing = $question->allornothing;

+        }

        $options->correctfeedback = trim($question->correctfeedback);

        $options->partiallycorrectfeedback = trim($question->partiallycorrectfeedback);
Same file in the function grade_resposes:
} else {

            foreach ($state->responses as $response) {

                if ($response) {

                    $state->raw_grade += $question->options->answers[$response]->fraction;

                }

            }

+            if ($question->options->allornothing && $state->raw_grade < 0.9999) {

+                $state->raw_grade = 0;

+            }

        }
Same file in the function backup:
fwrite ($bf,full_tag("SHUFFLEANSWERS",$level+1,false,$multichoice->shuffleanswers));

+                fwrite ($bf,full_tag("ALLORNOTHING",$level+1,false,$multichoice->allornothing));

                fwrite ($bf,full_tag("CORRECTFEEDBACK",$level+1,false,$multichoice->correctfeedback));
And in the function restore:
$multichoice->single = backup_todb($mul_info['#']['SINGLE']['0']['#']);

+            $multichoice->allornothing = backup_todb($mul_info['#']['ALLORNOTHING']['0']['#']);

            $multichoice->shuffleanswers = isset($mul_info['#']['SHUFFLEANSWERS']['0']['#'])?backup_todb($mul_info['#']['SHUFFLEANSWERS']['0']['#']):'';
To make sure that Moodle-XML-format works with the new flag open question/format/xml/format.php and add:
$qo->answernumbering = $this->getpath( $question, array('#','answernumbering',0,'#'), 'abc' );

        $qo->shuffleanswers = $this->trans_single($shuffleanswers);

+        $allornothing = $this->getpath( $question, array('#','allornothing',0,'#'), 'false' );

+        $qo->allornothing = $this->trans_single($allornothing);

        $qo->correctfeedback = $this->getpath( $question, array('#','correctfeedback',0,'#','text',0,'#'), '', true );
And in the same file:
case MULTICHOICE:

            $expout .= "    <single>".$this->get_single($question->options->single)."</single>\n";

            $expout .= "    <shuffleanswers>".$this->get_single($question->options->shuffleanswers)."</shuffleanswers>\n";

+            $expout .= "    <allornothing>".$this->get_single($question->options->allornothing)."</allornothing>\n";

            $expout .= "    <correctfeedback>".$this->writetext($question->options->correctfeedback, 3)."</correctfeedback>\n";
You can also set a new option in the import form to overrule this flag if someone has a format without allornothing (like GIFT) and doesn't like your default value. To do this change: question/import_form.php :
$mform->disabledIf('categorygroup', 'catfromfile', 'notchecked');

        $mform->setDefault('catfromfile', 1);

        $mform->setDefault('contextfromfile', 1);



+        $allornothing = array();

+        $allornothing['default'] = get_string('default');

+        $allornothing['true'] = get_string('yes');

+        $allornothing['false'] = get_string('no');

+        $mform->addElement('select', 'allornothing', get_string('allornothing','qtype_multichoice'), $allornothing);

+        $mform->setHelpButton('allornothing', array('allornothing', get_string('allornothing','qtype_multichoice'), 'qtype_multichoice'));




        $matchgrades = array();

        $matchgrades['error'] = get_string('matchgradeserror','quiz');
question/import.php:
$qformat->setRealfilename($realfilename);

            $qformat->setMatchgrades($form->matchgrades);

+            $qformat->setAllornothing($form->allornothing);

            $qformat->setCatfromfile(!empty($form->catfromfile));

            $qformat->setContextfromfile(!empty($form->contextfromfile));
question/format.php
function setMatchgrades( $matchgrades ) {

        $this->matchgrades = $matchgrades;

    }



+    /**

+     * set allornothing

+     * @param string allornothing

+     */

+    function setAllornothing( $allornothing ) {

+        if ($allornothing == 'true') {

+            $this->allornothing = true;

+        } else if ($allornothing == 'false') {

+            $this->allornothing = false;

+        }

+    }
This is all. If it doesn't work, feel free to contact me and complain. The files I attached should be compatible with 1.9.4 but be careful, there could be other local changes in them.
Hide
Tim Hunt added a comment -

This looks like good work, but it needs a little more improvement before it could be included in Moodle.

1. Would it be possible for you to create a patch file with these changes? That would make them much easier to work with. Please see http://docs.moodle.org/en/Development:How_to_create_a_patch.

2. Instead of telling people to edit the database themselves, you should use Moodle's self-update mechanism, which involves editing question/type/multichoice/db/install.xml, and adding a chunk of code to .../db/upgrade.xml. Both of those two steps should be done using Moodle's built in XMLDB editor. Then you need to update the version number in .../version.php. See http://docs.moodle.org/en/Development:Installing_and_upgrading_plugin_database_tables.

3. I think the default in the database should be 0.

4. I think you need to disable the all-or-nothing scoring option on the form if it is a single choice question. Look up the disabledIf method.

5. I don't think we should have question-type specific UI on the question import form. Is there another way to handle this?

Also, please could I ask you to introduce yourself. I like to know who I am working with, and as far as I can see, you don't have a profile on the main http://moodle.org/ site.

Thanks for contributing to Moodle. Tim (quiz maintainer)

Show
Tim Hunt added a comment - This looks like good work, but it needs a little more improvement before it could be included in Moodle. 1. Would it be possible for you to create a patch file with these changes? That would make them much easier to work with. Please see http://docs.moodle.org/en/Development:How_to_create_a_patch. 2. Instead of telling people to edit the database themselves, you should use Moodle's self-update mechanism, which involves editing question/type/multichoice/db/install.xml, and adding a chunk of code to .../db/upgrade.xml. Both of those two steps should be done using Moodle's built in XMLDB editor. Then you need to update the version number in .../version.php. See http://docs.moodle.org/en/Development:Installing_and_upgrading_plugin_database_tables. 3. I think the default in the database should be 0. 4. I think you need to disable the all-or-nothing scoring option on the form if it is a single choice question. Look up the disabledIf method. 5. I don't think we should have question-type specific UI on the question import form. Is there another way to handle this? Also, please could I ask you to introduce yourself. I like to know who I am working with, and as far as I can see, you don't have a profile on the main http://moodle.org/ site. Thanks for contributing to Moodle. Tim (quiz maintainer)
Hide
Richard Rode added a comment -

Good morning Tim,

You can find my profile at:

http://moodle.org/user/view.php?id=570753&course=5

We are using Moodle as a second LMS here at the University of Vienna, so it's a smaller installation, but this all-or-nothing code is tested and no one ever complained.

I can create the patch. Point 1 to 4 is clear and logical. The only problem I have is point 5. This is something I recently added. I can think of three possible solutions:

1. Take the default value: This is what we had before and it wasn't very handy. People imported their questions and then they called the support to change the value in the database (doesn't matter if the default is 0 or 1).

2. Add the flag to the import and export formats: This is what I did for Moodle-XML. It is easy to extend XML, but how should I add it to GIFT?

3. Add a flag to the UI on the import form as described: I added this because it is needed. When you import 50 questions you don't want to set the flag for all these questions after the import just because you don't want the default value.

My question is: Is there a possibility to add the flag to the GIFT format? I could create the code but who defines the standards? Using the default value was the easiest way, adding the flag to the import UI is maybe another lousy solution. I could dig through all the import/export formats and try to find out if they have the flag but I think GIFT is the most important, many people use it and we should have a solution for this first.

Kind regards
Richard

Show
Richard Rode added a comment - Good morning Tim, You can find my profile at: http://moodle.org/user/view.php?id=570753&course=5 We are using Moodle as a second LMS here at the University of Vienna, so it's a smaller installation, but this all-or-nothing code is tested and no one ever complained. I can create the patch. Point 1 to 4 is clear and logical. The only problem I have is point 5. This is something I recently added. I can think of three possible solutions: 1. Take the default value: This is what we had before and it wasn't very handy. People imported their questions and then they called the support to change the value in the database (doesn't matter if the default is 0 or 1). 2. Add the flag to the import and export formats: This is what I did for Moodle-XML. It is easy to extend XML, but how should I add it to GIFT? 3. Add a flag to the UI on the import form as described: I added this because it is needed. When you import 50 questions you don't want to set the flag for all these questions after the import just because you don't want the default value. My question is: Is there a possibility to add the flag to the GIFT format? I could create the code but who defines the standards? Using the default value was the easiest way, adding the flag to the import UI is maybe another lousy solution. I could dig through all the import/export formats and try to find out if they have the flag but I think GIFT is the most important, many people use it and we should have a solution for this first. Kind regards Richard
Hide
Tim Hunt added a comment -

Actually, the issue you identify is already a problem with some other options, for example shuffle answers for MC, matching and so on. So I suppose there is an alternate point of view that says we should have more question type specific UI in the import process.

And thinking about it, in an ideal world, the import process would have a wizard user interface, so
1. On the first page you select the format to import.
2. On the second page, you select the file to import, and we can now only show files of the type you are interested in.
... Moodle then scans the file you selected, to see which types of questions it contains, and as a result, which questions the user should be asked, so that the user does not get asked about irrelevant options.
3. The user is presented with a list of options that might affect the import.

That is, of course, quite a big change. I just started dreaming.

In the mean time, it is probably OK to add some options to the import form, particularly if we cover options like shuffleanswers too.

About the formats. Moodle XML format should always contain full information about the question to be imported and exported, so you were right to add the new option. However, in your code, it must still work on import if that bit of XML is missing, in order to be backwards compatible. You will find other examples of that in the code that you can copy.

GIFT is defined by Moodle. It is OK to propose a change, but again it is very important that the change is forwards and backwards compatible. The best way to propose it is to post in the quiz forum: moodle.org/mod/forum/view.php?f=121

Show
Tim Hunt added a comment - Actually, the issue you identify is already a problem with some other options, for example shuffle answers for MC, matching and so on. So I suppose there is an alternate point of view that says we should have more question type specific UI in the import process. And thinking about it, in an ideal world, the import process would have a wizard user interface, so 1. On the first page you select the format to import. 2. On the second page, you select the file to import, and we can now only show files of the type you are interested in. ... Moodle then scans the file you selected, to see which types of questions it contains, and as a result, which questions the user should be asked, so that the user does not get asked about irrelevant options. 3. The user is presented with a list of options that might affect the import. That is, of course, quite a big change. I just started dreaming. In the mean time, it is probably OK to add some options to the import form, particularly if we cover options like shuffleanswers too. About the formats. Moodle XML format should always contain full information about the question to be imported and exported, so you were right to add the new option. However, in your code, it must still work on import if that bit of XML is missing, in order to be backwards compatible. You will find other examples of that in the code that you can copy. GIFT is defined by Moodle. It is OK to propose a change, but again it is very important that the change is forwards and backwards compatible. The best way to propose it is to post in the quiz forum: moodle.org/mod/forum/view.php?f=121
Hide
Richard Rode added a comment -

I think, the only thing in a GIFT file that will be ignored by older Moodle versions is a comment line, so I added three different comments to my GIFT encodings:

//shuffleanswers:
//usecase:
//allornothing:

These comments can be followed by yes or no. I think the risk that someone writes a comment like this by accident is very small. All these flags can be overruled in the import form. The default value for allornothing is 0 now, so older import packages and new export packages on older Moodle installations should work as before. I have tested this for Moodle-XML and GIFT.

I have commented out the line for disabledif in edit_multichoice_form.php for two reasons: It didn't work with advcheckbox, I think there is a bug in the QuickForm code, the function getPrivateName() should be removed. And it does no harm. Questions with only one correct answer are always all or nothing, no matter if you click the flag or not. This is logical, but not for every one. Having this option disabled will lead to unnecessary support (there is something wrong with my computer, I cannot click this option...).

Database update is in the attached cvs patch. If you are still missing something, just let me know.

Best regards from Vienna
Richard

Show
Richard Rode added a comment - I think, the only thing in a GIFT file that will be ignored by older Moodle versions is a comment line, so I added three different comments to my GIFT encodings: //shuffleanswers: //usecase: //allornothing: These comments can be followed by yes or no. I think the risk that someone writes a comment like this by accident is very small. All these flags can be overruled in the import form. The default value for allornothing is 0 now, so older import packages and new export packages on older Moodle installations should work as before. I have tested this for Moodle-XML and GIFT. I have commented out the line for disabledif in edit_multichoice_form.php for two reasons: It didn't work with advcheckbox, I think there is a bug in the QuickForm code, the function getPrivateName() should be removed. And it does no harm. Questions with only one correct answer are always all or nothing, no matter if you click the flag or not. This is logical, but not for every one. Having this option disabled will lead to unnecessary support (there is something wrong with my computer, I cannot click this option...). Database update is in the attached cvs patch. If you are still missing something, just let me know. Best regards from Vienna Richard
Hide
Tim Hunt added a comment -

Thanks for the patch.

We cannot start making comments significant in the GIFT format. That way lies madness, and bugs.

Please can you post about this in the quiz forum, becuase there are people there who know much more about the format than I do. They may have a good idea. Also, people in the forum may be interesting in helping to test this.

Thanks.

Show
Tim Hunt added a comment - Thanks for the patch. We cannot start making comments significant in the GIFT format. That way lies madness, and bugs. Please can you post about this in the quiz forum, becuase there are people there who know much more about the format than I do. They may have a good idea. Also, people in the forum may be interesting in helping to test this. Thanks.

People

Vote (5)
Watch (4)

Dates

  • Created:
    Updated: