Proyectos de Subversion Moodle

Rev

Rev 11 | | Comparar con el anterior | Ultima modificación | Ver Log |

Rev Autor Línea Nro. Línea
1 efrain 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
namespace qtype_ddimageortext;
18
 
19
use question_display_options;
20
use question_hint_with_parts;
21
use question_state;
22
 
23
defined('MOODLE_INTERNAL') || die();
24
 
25
global $CFG;
26
require_once($CFG->dirroot . '/question/engine/tests/helpers.php');
27
require_once($CFG->dirroot . '/question/type/ddimageortext/tests/helper.php');
28
 
29
 
30
/**
31
 * Unit tests for the drag-and-drop onto image question type.
32
 *
33
 * @package   qtype_ddimageortext
34
 * @copyright 2010 The Open University
35
 * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
36
 */
1441 ariadna 37
final class walkthrough_test extends \qbehaviour_walkthrough_test_base {
1 efrain 38
 
39
    /**
40
     * Get an expectation that the output contains an item ready to drag.
41
     * @param int $dragitemno the item number.
42
     * @param int $choice which choice this is.
43
     * @param int $group which drag group it belongs to.
44
     * @return \question_contains_tag_with_attributes the required expectation.
45
     */
46
    protected function get_contains_drag_image_home_expectation($dragitemno, $choice, $group) {
47
        $class = 'group' . $group . ' draghome choice' . $choice;
48
 
49
        $expectedattrs = array();
50
        $expectedattrs['class'] = $class;
51
 
52
        return new \question_contains_tag_with_attributes('div', $expectedattrs);
53
    }
54
 
11 efrain 55
    public function test_interactive_behaviour(): void {
1 efrain 56
 
57
        // Create a drag-and-drop question.
58
        $dd = \test_question_maker::make_question('ddimageortext');
59
        $dd->hints = array(
60
            new question_hint_with_parts(13, 'This is the first hint.', FORMAT_HTML, false, false),
61
            new question_hint_with_parts(14, 'This is the second hint.', FORMAT_HTML, true, true),
62
        );
63
        $dd->shufflechoices = false;
64
        $this->start_attempt_at_question($dd, 'interactive', 12);
65
 
66
        // Check the initial state.
67
        $this->check_current_state(question_state::$todo);
68
        $this->check_current_mark(null);
69
 
70
        $this->check_current_output(
71
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
72
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
73
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
74
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
75
            $this->get_contains_hidden_expectation(
76
                $this->quba->get_field_prefix($this->slot) . 'p1'),
77
            $this->get_contains_hidden_expectation(
78
                $this->quba->get_field_prefix($this->slot) . 'p2'),
79
            $this->get_contains_hidden_expectation(
80
                $this->quba->get_field_prefix($this->slot) . 'p3'),
81
            $this->get_contains_hidden_expectation(
82
                $this->quba->get_field_prefix($this->slot) . 'p4'),
83
            $this->get_contains_submit_button_expectation(true),
84
            $this->get_does_not_contain_feedback_expectation(),
85
            $this->get_tries_remaining_expectation(3),
86
            $this->get_no_hint_visible_expectation());
87
 
88
        // Save the wrong answer.
89
        $this->process_submission(array('p1' => '2', 'p2' => '1', 'p3' => '2', 'p4' => '1'));
90
        // Verify.
91
        $this->check_current_state(question_state::$todo);
92
        $this->check_current_mark(null);
93
 
94
        $this->check_current_output(
95
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
96
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
97
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
98
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
99
            $this->get_contains_hidden_expectation(
100
                $this->quba->get_field_prefix($this->slot) . 'p1', 2),
101
            $this->get_contains_hidden_expectation(
102
                $this->quba->get_field_prefix($this->slot) . 'p2', 1),
103
            $this->get_contains_hidden_expectation(
104
                $this->quba->get_field_prefix($this->slot) . 'p3', 2),
105
            $this->get_contains_hidden_expectation(
106
                $this->quba->get_field_prefix($this->slot) . 'p4', 1),
107
            $this->get_contains_submit_button_expectation(true),
108
            $this->get_does_not_contain_feedback_expectation(),
109
            $this->get_tries_remaining_expectation(3),
110
            $this->get_no_hint_visible_expectation());
111
        // Submit the wrong answer.
112
        $this->process_submission(
113
            array('p1' => '2', 'p2' => '1', 'p3' => '2', 'p4' => '1', '-submit' => 1));
114
 
115
        // Verify.
116
        $this->check_current_state(question_state::$todo);
117
        $this->check_current_mark(null);
118
        $this->check_current_output(
119
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
120
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
121
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
122
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
123
            $this->get_contains_hidden_expectation(
124
                $this->quba->get_field_prefix($this->slot) . 'p1', 2),
125
            $this->get_contains_hidden_expectation(
126
                $this->quba->get_field_prefix($this->slot) . 'p2', 1),
127
            $this->get_contains_hidden_expectation(
128
                $this->quba->get_field_prefix($this->slot) . 'p3', 2),
129
            $this->get_contains_hidden_expectation(
130
                $this->quba->get_field_prefix($this->slot) . 'p4', 1),
131
            $this->get_contains_try_again_button_expectation(true),
132
            $this->get_contains_hint_expectation('This is the first hint'));
133
 
134
        // Do try again.
135
        $this->process_submission(array('-tryagain' => 1));
136
 
137
        // Verify.
138
        $this->check_current_state(question_state::$todo);
139
        $this->check_current_mark(null);
140
 
141
        $this->check_current_output(
142
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
143
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
144
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
145
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
146
            $this->get_contains_hidden_expectation(
147
                $this->quba->get_field_prefix($this->slot) . 'p1', '2'),
148
            $this->get_contains_hidden_expectation(
149
                $this->quba->get_field_prefix($this->slot) . 'p2', '1'),
150
            $this->get_contains_hidden_expectation(
151
                $this->quba->get_field_prefix($this->slot) . 'p3', '2'),
152
            $this->get_contains_hidden_expectation(
153
                $this->quba->get_field_prefix($this->slot) . 'p4', '1'),
154
            $this->get_contains_submit_button_expectation(true),
155
            $this->get_does_not_contain_correctness_expectation(),
156
            $this->get_does_not_contain_feedback_expectation(),
157
            $this->get_tries_remaining_expectation(2),
158
            $this->get_no_hint_visible_expectation());
159
 
160
        // Submit the right answer.
161
        $this->process_submission(
162
            array('p1' => '1', 'p2' => '2', 'p3' => '1', 'p4' => '2', '-submit' => 1));
163
 
164
        // Verify.
165
        $this->check_current_state(question_state::$gradedright);
166
        $this->check_current_mark(8);
167
        $this->check_current_output(
168
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
169
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
170
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
171
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
172
            $this->get_contains_hidden_expectation(
173
                $this->quba->get_field_prefix($this->slot) . 'p1', '1'),
174
            $this->get_contains_hidden_expectation(
175
                $this->quba->get_field_prefix($this->slot) . 'p2', '2'),
176
            $this->get_contains_hidden_expectation(
177
                $this->quba->get_field_prefix($this->slot) . 'p3', '1'),
178
            $this->get_contains_hidden_expectation(
179
                $this->quba->get_field_prefix($this->slot) . 'p4', '2'),
180
            $this->get_does_not_contain_submit_button_expectation(),
181
            $this->get_contains_correct_expectation(),
182
            $this->get_no_hint_visible_expectation());
183
 
184
        // Check regrading does not mess anything up.
185
        $this->quba->regrade_all_questions();
186
 
187
        // Verify.
188
        $this->check_current_state(question_state::$gradedright);
189
        $this->check_current_mark(8);
190
    }
191
 
11 efrain 192
    public function test_deferred_feedback(): void {
1 efrain 193
 
194
        // Create a drag-and-drop question.
195
        $dd = \test_question_maker::make_question('ddimageortext');
196
        $dd->shufflechoices = false;
197
        $this->start_attempt_at_question($dd, 'deferredfeedback', 12);
198
 
199
        // Check the initial state.
200
        $this->check_current_state(question_state::$todo);
201
        $this->check_current_mark(null);
202
 
203
        $this->check_current_output(
204
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
205
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
206
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
207
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
208
            $this->get_contains_hidden_expectation(
209
                $this->quba->get_field_prefix($this->slot) . 'p1'),
210
            $this->get_contains_hidden_expectation(
211
                $this->quba->get_field_prefix($this->slot) . 'p2'),
212
            $this->get_contains_hidden_expectation(
213
                $this->quba->get_field_prefix($this->slot) . 'p3'),
214
            $this->get_contains_hidden_expectation(
215
                $this->quba->get_field_prefix($this->slot) . 'p4'),
216
            $this->get_does_not_contain_feedback_expectation());
217
 
218
        // Save a partial answer.
219
        $this->process_submission(array('p1' => '2', 'p2' => '1'));
220
        // Verify.
221
        $this->check_current_state(question_state::$invalid);
222
        $this->check_current_mark(null);
223
 
224
        $this->check_current_output(
225
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
226
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
227
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
228
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
229
            $this->get_contains_hidden_expectation(
230
                $this->quba->get_field_prefix($this->slot) . 'p1', 2),
231
            $this->get_contains_hidden_expectation(
232
                $this->quba->get_field_prefix($this->slot) . 'p2', 1),
233
            $this->get_contains_hidden_expectation(
234
                $this->quba->get_field_prefix($this->slot) . 'p3', ''),
235
            $this->get_contains_hidden_expectation(
236
                $this->quba->get_field_prefix($this->slot) . 'p4', ''),
237
            $this->get_does_not_contain_correctness_expectation(),
238
            $this->get_does_not_contain_feedback_expectation());
239
        // Save the right answer.
240
        $this->process_submission(
241
            array('p1' => '1', 'p2' => '2', 'p3' => '1', 'p4' => '2'));
242
 
243
        // Verify.
244
        $this->check_current_state(question_state::$complete);
245
        $this->check_current_mark(null);
246
        $this->check_current_output(
247
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
248
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
249
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
250
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
251
            $this->get_contains_hidden_expectation(
252
                $this->quba->get_field_prefix($this->slot) . 'p1', 1),
253
            $this->get_contains_hidden_expectation(
254
                $this->quba->get_field_prefix($this->slot) . 'p2', 2),
255
            $this->get_contains_hidden_expectation(
256
                $this->quba->get_field_prefix($this->slot) . 'p3', 1),
257
            $this->get_contains_hidden_expectation(
258
                $this->quba->get_field_prefix($this->slot) . 'p4', 2),
259
            $this->get_does_not_contain_correctness_expectation(),
260
            $this->get_does_not_contain_feedback_expectation());
261
 
262
        // Finish the attempt.
263
        $this->quba->finish_all_questions();
264
 
265
        // Verify.
266
        $this->check_current_state(question_state::$gradedright);
267
        $this->check_current_mark(12);
268
 
269
        $this->check_current_output(
270
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
271
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
272
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
273
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
274
            $this->get_contains_hidden_expectation(
275
                $this->quba->get_field_prefix($this->slot) . 'p1', 1),
276
            $this->get_contains_hidden_expectation(
277
                $this->quba->get_field_prefix($this->slot) . 'p2', 2),
278
            $this->get_contains_hidden_expectation(
279
                $this->quba->get_field_prefix($this->slot) . 'p3', 1),
280
            $this->get_contains_hidden_expectation(
281
                $this->quba->get_field_prefix($this->slot) . 'p4', 2),
282
            $this->get_contains_correct_expectation());
283
 
284
        // Change the right answer a bit.
285
        $dd->rightchoices[2] = 1;
286
 
287
        // Check regrading does not mess anything up.
288
        $this->quba->regrade_all_questions();
289
 
290
        // Verify.
291
        $this->check_current_state(question_state::$gradedpartial);
292
        $this->check_current_mark(9);
293
    }
294
 
11 efrain 295
    public function test_deferred_feedback_unanswered(): void {
1 efrain 296
 
297
        // Create a drag-and-drop question.
298
        $dd = \test_question_maker::make_question('ddimageortext');
299
        $dd->shufflechoices = false;
300
        $this->start_attempt_at_question($dd, 'deferredfeedback', 12);
301
 
302
        // Check the initial state.
303
        $this->check_current_state(question_state::$todo);
304
        $this->check_current_mark(null);
305
        $this->check_current_output(
306
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
307
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
308
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
309
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
310
            $this->get_contains_hidden_expectation(
311
                $this->quba->get_field_prefix($this->slot) . 'p1'),
312
            $this->get_contains_hidden_expectation(
313
                $this->quba->get_field_prefix($this->slot) . 'p2'),
314
            $this->get_contains_hidden_expectation(
315
                $this->quba->get_field_prefix($this->slot) . 'p3'),
316
            $this->get_contains_hidden_expectation(
317
                $this->quba->get_field_prefix($this->slot) . 'p4'),
318
            $this->get_does_not_contain_correctness_expectation(),
319
            $this->get_does_not_contain_feedback_expectation());
320
        $this->check_step_count(1);
321
 
322
        // Save a blank response.
323
        $this->process_submission(array('p1' => '', 'p2' => '', 'p3' => '', 'p4' => ''));
324
 
325
        // Verify.
326
        $this->check_current_state(question_state::$todo);
327
        $this->check_current_mark(null);
328
        $this->check_current_output(
329
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
330
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
331
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
332
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
333
            $this->get_contains_hidden_expectation(
334
                $this->quba->get_field_prefix($this->slot) . 'p1', ''),
335
            $this->get_contains_hidden_expectation(
336
                $this->quba->get_field_prefix($this->slot) . 'p2', ''),
337
            $this->get_contains_hidden_expectation(
338
                $this->quba->get_field_prefix($this->slot) . 'p3', ''),
339
            $this->get_contains_hidden_expectation(
340
                $this->quba->get_field_prefix($this->slot) . 'p4', ''),
341
            $this->get_does_not_contain_correctness_expectation(),
342
            $this->get_does_not_contain_feedback_expectation());
343
        $this->check_step_count(1);
344
 
345
        // Finish the attempt.
346
        $this->quba->finish_all_questions();
347
 
348
        // Verify.
349
        $this->check_current_state(question_state::$gaveup);
350
        $this->check_current_mark(null);
351
        $this->check_current_output(
352
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
353
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
354
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
355
            $this->get_contains_drag_image_home_expectation(4, 2, 2));
356
    }
357
 
11 efrain 358
    public function test_deferred_feedback_partial_answer(): void {
1 efrain 359
 
360
        // Create a drag-and-drop question.
361
        $dd = \test_question_maker::make_question('ddimageortext');
362
        $dd->shufflechoices = false;
363
        $this->start_attempt_at_question($dd, 'deferredfeedback', 3);
364
 
365
        // Check the initial state.
366
        $this->check_current_state(question_state::$todo);
367
        $this->check_current_mark(null);
368
        $this->check_current_output(
369
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
370
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
371
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
372
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
373
            $this->get_contains_hidden_expectation(
374
                $this->quba->get_field_prefix($this->slot) . 'p1'),
375
            $this->get_contains_hidden_expectation(
376
                $this->quba->get_field_prefix($this->slot) . 'p2'),
377
            $this->get_contains_hidden_expectation(
378
                $this->quba->get_field_prefix($this->slot) . 'p3'),
379
            $this->get_contains_hidden_expectation(
380
                $this->quba->get_field_prefix($this->slot) . 'p4'),
381
            $this->get_does_not_contain_correctness_expectation(),
382
            $this->get_does_not_contain_feedback_expectation());
383
 
384
        // Save a partial response.
385
        $this->process_submission(array('p1' => '1', 'p2' => '2', 'p3' => '', 'p4' => ''));
386
 
387
        // Verify.
388
        $this->check_current_state(question_state::$invalid);
389
        $this->check_current_mark(null);
390
        $this->check_current_output(
391
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
392
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
393
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
394
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
395
            $this->get_contains_hidden_expectation(
396
                $this->quba->get_field_prefix($this->slot) . 'p1', 1),
397
            $this->get_contains_hidden_expectation(
398
                $this->quba->get_field_prefix($this->slot) . 'p2', 2),
399
            $this->get_contains_hidden_expectation(
400
                $this->quba->get_field_prefix($this->slot) . 'p3', 0),
401
            $this->get_contains_hidden_expectation(
402
                $this->quba->get_field_prefix($this->slot) . 'p4', 0),
403
            $this->get_does_not_contain_correctness_expectation(),
404
            $this->get_does_not_contain_feedback_expectation());
405
 
406
        // Finish the attempt.
407
        $this->quba->finish_all_questions();
408
 
409
        // Verify.
410
        $this->check_current_state(question_state::$gradedpartial);
411
        $this->check_current_mark(1.5);
412
        $this->check_current_output(
413
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
414
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
415
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
416
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
417
            $this->get_contains_partcorrect_expectation());
418
    }
419
 
11 efrain 420
    public function test_interactive_grading(): void {
1 efrain 421
 
422
        // Create a drag-and-drop question.
423
        $dd = \test_question_maker::make_question('ddimageortext');
424
        $dd->hints = array(
425
            new question_hint_with_parts(1, 'This is the first hint.',
426
                FORMAT_MOODLE, true, true),
427
            new question_hint_with_parts(2, 'This is the second hint.',
428
                FORMAT_MOODLE, true, true),
429
        );
430
        $dd->shufflechoices = false;
431
        $this->start_attempt_at_question($dd, 'interactive', 12);
432
 
433
        // Check the initial state.
434
        $this->check_current_state(question_state::$todo);
435
        $this->check_current_mark(null);
436
        $this->assertEquals('interactivecountback',
437
            $this->quba->get_question_attempt($this->slot)->get_behaviour_name());
438
        $this->check_current_output(
439
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
440
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
441
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
442
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
443
            $this->get_contains_hidden_expectation(
444
                $this->quba->get_field_prefix($this->slot) . 'p1'),
445
            $this->get_contains_hidden_expectation(
446
                $this->quba->get_field_prefix($this->slot) . 'p2'),
447
            $this->get_contains_hidden_expectation(
448
                $this->quba->get_field_prefix($this->slot) . 'p3'),
449
            $this->get_contains_hidden_expectation(
450
                $this->quba->get_field_prefix($this->slot) . 'p4'),
451
            $this->get_contains_submit_button_expectation(true),
452
            $this->get_does_not_contain_feedback_expectation(),
453
            $this->get_tries_remaining_expectation(3),
454
            $this->get_does_not_contain_num_parts_correct(),
455
            $this->get_no_hint_visible_expectation());
456
 
457
        // Submit an response with the first two parts right.
458
        $this->process_submission(
459
            array('p1' => '1', 'p2' => '2', 'p3' => '2', 'p4' => '1', '-submit' => 1));
460
 
461
        // Verify.
462
        $this->check_current_state(question_state::$todo);
463
        $this->check_current_mark(null);
464
        $this->check_current_output(
465
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
466
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
467
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
468
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
469
            $this->get_does_not_contain_submit_button_expectation(),
470
            $this->get_contains_try_again_button_expectation(true),
471
            $this->get_does_not_contain_correctness_expectation(),
472
            $this->get_contains_hint_expectation('This is the first hint'),
473
            $this->get_contains_num_parts_correct(2),
474
            $this->get_contains_standard_partiallycorrect_combined_feedback_expectation(),
475
            $this->get_contains_hidden_expectation(
476
                $this->quba->get_field_prefix($this->slot) . 'p1', 1),
477
            $this->get_contains_hidden_expectation(
478
                $this->quba->get_field_prefix($this->slot) . 'p2', 2),
479
            $this->get_contains_hidden_expectation(
480
                $this->quba->get_field_prefix($this->slot) . 'p3', 2),
481
            $this->get_contains_hidden_expectation(
482
                $this->quba->get_field_prefix($this->slot) . 'p4', 1));
483
 
484
        // Check that extract responses will return the reset data.
485
        $prefix = $this->quba->get_field_prefix($this->slot);
486
        $this->assertEquals(array('p1' => '1', 'p2' => '2'),
487
            $this->quba->extract_responses($this->slot,
488
                array($prefix . 'p1' => '1', $prefix . 'p2' => '2', '-tryagain' => 1)));
489
 
490
        // Do try again.
491
        // keys p3 and p4 are extra hidden fields to clear data.
492
        $this->process_submission(
493
            array('p1' => '1', 'p2' => '2', 'p3' => '', 'p4' => '', '-tryagain' => 1));
494
 
495
        // Verify.
496
        $this->check_current_state(question_state::$todo);
497
        $this->check_current_mark(null);
498
        $this->check_current_output(
499
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
500
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
501
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
502
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
503
            $this->get_contains_hidden_expectation(
504
                $this->quba->get_field_prefix($this->slot) . 'p1', 1),
505
            $this->get_contains_hidden_expectation(
506
                $this->quba->get_field_prefix($this->slot) . 'p2', 2),
507
            $this->get_contains_hidden_expectation(
508
                $this->quba->get_field_prefix($this->slot) . 'p3', 0),
509
            $this->get_contains_hidden_expectation(
510
                $this->quba->get_field_prefix($this->slot) . 'p4', 0),
511
            $this->get_contains_submit_button_expectation(true),
512
            $this->get_does_not_contain_try_again_button_expectation(),
513
            $this->get_does_not_contain_correctness_expectation(),
514
            $this->get_does_not_contain_feedback_expectation(),
515
            $this->get_tries_remaining_expectation(2),
516
            $this->get_no_hint_visible_expectation());
517
 
518
        // Submit an response with the first and last parts right.
519
        $this->process_submission(
520
            array('p1' => '1', 'p2' => '1', 'p3' => '2', 'p4' => '2', '-submit' => 1));
521
 
522
        // Verify.
523
        $this->check_current_state(question_state::$todo);
524
        $this->check_current_mark(null);
525
        $this->check_current_output(
526
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
527
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
528
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
529
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
530
            $this->get_does_not_contain_submit_button_expectation(),
531
            $this->get_contains_try_again_button_expectation(true),
532
            $this->get_does_not_contain_correctness_expectation(),
533
            $this->get_contains_hint_expectation('This is the second hint'),
534
            $this->get_contains_num_parts_correct(2),
535
            $this->get_contains_standard_partiallycorrect_combined_feedback_expectation(),
536
            $this->get_contains_hidden_expectation(
537
                $this->quba->get_field_prefix($this->slot) . 'p1', 1),
538
            $this->get_contains_hidden_expectation(
539
                $this->quba->get_field_prefix($this->slot) . 'p2', 1),
540
            $this->get_contains_hidden_expectation(
541
                $this->quba->get_field_prefix($this->slot) . 'p3', 2),
542
            $this->get_contains_hidden_expectation(
543
                $this->quba->get_field_prefix($this->slot) . 'p4', 2));
544
 
545
        // Do try again.
546
        $this->process_submission(
547
            array('p1' => '1', 'p2' => '', 'p3' => '', 'p4' => '2', '-tryagain' => 1));
548
 
549
        // Verify.
550
        $this->check_current_state(question_state::$todo);
551
        $this->check_current_mark(null);
552
        $this->check_current_output(
553
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
554
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
555
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
556
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
557
            $this->get_contains_hidden_expectation(
558
                $this->quba->get_field_prefix($this->slot) . 'p1', 1),
559
            $this->get_contains_hidden_expectation(
560
                $this->quba->get_field_prefix($this->slot) . 'p2', 0),
561
            $this->get_contains_hidden_expectation(
562
                $this->quba->get_field_prefix($this->slot) . 'p3', 0),
563
            $this->get_contains_hidden_expectation(
564
                $this->quba->get_field_prefix($this->slot) . 'p4', 2),
565
            $this->get_contains_submit_button_expectation(true),
566
            $this->get_does_not_contain_try_again_button_expectation(),
567
            $this->get_does_not_contain_correctness_expectation(),
568
            $this->get_does_not_contain_feedback_expectation(),
569
            $this->get_tries_remaining_expectation(1),
570
            $this->get_no_hint_visible_expectation());
571
 
572
        // Submit the right answer.
573
        $this->process_submission(
574
            array('p1' => '1', 'p2' => '2', 'p3' => '1', 'p4' => '2', '-submit' => 1));
575
 
576
        // Verify.
577
        $this->check_current_state(question_state::$gradedright);
578
        $this->check_current_mark(7);
579
        $this->check_current_output(
580
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
581
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
582
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
583
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
584
            $this->get_contains_hidden_expectation(
585
                $this->quba->get_field_prefix($this->slot) . 'p1', 1),
586
            $this->get_contains_hidden_expectation(
587
                $this->quba->get_field_prefix($this->slot) . 'p2', 2),
588
            $this->get_contains_hidden_expectation(
589
                $this->quba->get_field_prefix($this->slot) . 'p3', 1),
590
            $this->get_contains_hidden_expectation(
591
                $this->quba->get_field_prefix($this->slot) . 'p4', 2),
592
            $this->get_does_not_contain_submit_button_expectation(),
593
            $this->get_does_not_contain_try_again_button_expectation(),
594
            $this->get_contains_correct_expectation(),
595
            $this->get_no_hint_visible_expectation(),
596
            $this->get_does_not_contain_num_parts_correct(),
597
            $this->get_contains_standard_correct_combined_feedback_expectation());
598
    }
599
 
11 efrain 600
    public function test_interactive_correct_no_submit(): void {
1 efrain 601
 
602
        // Create a drag-and-drop question.
603
        $dd = \test_question_maker::make_question('ddimageortext');
604
        $dd->hints = array(
605
            new question_hint_with_parts(23, 'This is the first hint.',
606
                FORMAT_MOODLE, false, false),
607
            new question_hint_with_parts(24, 'This is the second hint.',
608
                FORMAT_MOODLE, true, true),
609
        );
610
        $dd->shufflechoices = false;
611
        $this->start_attempt_at_question($dd, 'interactive', 3);
612
 
613
        // Check the initial state.
614
        $this->check_current_state(question_state::$todo);
615
        $this->check_current_mark(null);
616
        $this->check_current_output(
617
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
618
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
619
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
620
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
621
            $this->get_contains_hidden_expectation(
622
                $this->quba->get_field_prefix($this->slot) . 'p1'),
623
            $this->get_contains_hidden_expectation(
624
                $this->quba->get_field_prefix($this->slot) . 'p2'),
625
            $this->get_contains_hidden_expectation(
626
                $this->quba->get_field_prefix($this->slot) . 'p3'),
627
            $this->get_contains_hidden_expectation(
628
                $this->quba->get_field_prefix($this->slot) . 'p4'),
629
            $this->get_contains_submit_button_expectation(true),
630
            $this->get_does_not_contain_feedback_expectation(),
631
            $this->get_tries_remaining_expectation(3),
632
            $this->get_no_hint_visible_expectation());
633
 
634
        // Save the right answer.
635
        $this->process_submission(array('p1' => '1', 'p2' => '2', 'p3' => '1', 'p4' => '2'));
636
 
637
        // Finish the attempt without clicking check.
638
        $this->quba->finish_all_questions();
639
 
640
        // Verify.
641
        $this->check_current_state(question_state::$gradedright);
642
        $this->check_current_mark(3);
643
        $this->check_current_output(
644
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
645
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
646
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
647
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
648
            $this->get_does_not_contain_submit_button_expectation(),
649
            $this->get_contains_correct_expectation(),
650
            $this->get_no_hint_visible_expectation());
651
 
652
        // Check regrading does not mess anything up.
653
        $this->quba->regrade_all_questions();
654
 
655
        // Verify.
656
        $this->check_current_state(question_state::$gradedright);
657
        $this->check_current_mark(3);
658
    }
659
 
11 efrain 660
    public function test_interactive_partial_no_submit(): void {
1 efrain 661
 
662
        // Create a drag-and-drop question.
663
        $dd = \test_question_maker::make_question('ddimageortext');
664
        $dd->hints = array(
665
            new question_hint_with_parts(23, 'This is the first hint.',
666
                FORMAT_MOODLE, false, false),
667
            new question_hint_with_parts(24, 'This is the second hint.',
668
                FORMAT_MOODLE, true, true),
669
        );
670
        $dd->shufflechoices = false;
671
        $this->start_attempt_at_question($dd, 'interactive', 4);
672
 
673
        // Check the initial state.
674
        $this->check_current_state(question_state::$todo);
675
        $this->check_current_mark(null);
676
 
677
        $this->check_current_output(
678
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
679
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
680
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
681
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
682
            $this->get_contains_hidden_expectation(
683
                $this->quba->get_field_prefix($this->slot) . 'p1'),
684
            $this->get_contains_hidden_expectation(
685
                $this->quba->get_field_prefix($this->slot) . 'p2'),
686
            $this->get_contains_hidden_expectation(
687
                $this->quba->get_field_prefix($this->slot) . 'p3'),
688
            $this->get_contains_hidden_expectation(
689
                $this->quba->get_field_prefix($this->slot) . 'p4'),
690
            $this->get_contains_submit_button_expectation(true),
691
            $this->get_does_not_contain_feedback_expectation(),
692
            $this->get_tries_remaining_expectation(3),
693
            $this->get_no_hint_visible_expectation());
694
 
695
        // Save the a partially right answer.
696
        $this->process_submission(array('p1' => '1', 'p2' => '1', 'p3' => '2', 'p4' => '1'));
697
 
698
        // Finish the attempt without clicking check.
699
        $this->quba->finish_all_questions();
700
 
701
        // Verify.
702
        $this->check_current_state(question_state::$gradedpartial);
703
        $this->check_current_mark(1);
704
 
705
        $this->check_current_output(
706
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
707
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
708
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
709
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
710
            $this->get_does_not_contain_submit_button_expectation(),
711
            $this->get_contains_partcorrect_expectation(),
712
            $this->get_no_hint_visible_expectation());
713
 
714
        // Check regrading does not mess anything up.
715
        $this->quba->regrade_all_questions();
716
 
717
        // Verify.
718
        $this->check_current_state(question_state::$gradedpartial);
719
        $this->check_current_mark(1);
720
    }
721
 
11 efrain 722
    public function test_interactive_no_right_clears(): void {
1 efrain 723
 
724
        // Create a drag-and-drop question.
725
        $dd = \test_question_maker::make_question('ddimageortext');
726
        $dd->hints = array(
727
            new question_hint_with_parts(23, 'This is the first hint.', FORMAT_MOODLE, false, true),
728
            new question_hint_with_parts(24, 'This is the second hint.', FORMAT_MOODLE, true, true),
729
        );
730
        $dd->shufflechoices = false;
731
        $this->start_attempt_at_question($dd, 'interactive', 3);
732
 
733
        // Check the initial state.
734
        $this->check_current_state(question_state::$todo);
735
        $this->check_current_mark(null);
736
 
737
        $this->check_current_output(
738
            $this->get_contains_marked_out_of_summary(),
739
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
740
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
741
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
742
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
743
            $this->get_contains_hidden_expectation(
744
                $this->quba->get_field_prefix($this->slot) . 'p1'),
745
            $this->get_contains_hidden_expectation(
746
                $this->quba->get_field_prefix($this->slot) . 'p2'),
747
            $this->get_contains_hidden_expectation(
748
                $this->quba->get_field_prefix($this->slot) . 'p3'),
749
            $this->get_contains_hidden_expectation(
750
                $this->quba->get_field_prefix($this->slot) . 'p4'),
751
            $this->get_contains_submit_button_expectation(true),
752
            $this->get_does_not_contain_feedback_expectation(),
753
            $this->get_tries_remaining_expectation(3),
754
            $this->get_no_hint_visible_expectation());
755
 
756
        // Save the a completely wrong answer.
757
        $this->process_submission(
758
            array('p1' => '2', 'p2' => '1', 'p3' => '2', 'p4' => '1', '-submit' => 1));
759
 
760
        // Verify.
761
        $this->check_current_state(question_state::$todo);
762
        $this->check_current_mark(null);
763
        $this->check_current_output(
764
            $this->get_contains_marked_out_of_summary(),
765
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
766
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
767
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
768
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
769
            $this->get_does_not_contain_submit_button_expectation(),
770
            $this->get_contains_hint_expectation('This is the first hint'));
771
 
772
        // Do try again.
773
        $this->process_submission(
774
            array('p1' => '', 'p2' => '', 'p3' => '', 'p4' => '', '-tryagain' => 1));
775
 
776
        // Check that all the wrong answers have been cleared.
777
        $this->check_current_state(question_state::$todo);
778
        $this->check_current_mark(null);
779
        $this->check_current_output(
780
            $this->get_contains_marked_out_of_summary(),
781
            $this->get_contains_drag_image_home_expectation(1, 1, 1),
782
            $this->get_contains_drag_image_home_expectation(2, 2, 1),
783
            $this->get_contains_drag_image_home_expectation(3, 1, 2),
784
            $this->get_contains_drag_image_home_expectation(4, 2, 2),
785
            $this->get_contains_hidden_expectation(
786
                $this->quba->get_field_prefix($this->slot) . 'p1', 0),
787
            $this->get_contains_hidden_expectation(
788
                $this->quba->get_field_prefix($this->slot) . 'p2', 0),
789
            $this->get_contains_hidden_expectation(
790
                $this->quba->get_field_prefix($this->slot) . 'p3', 0),
791
            $this->get_contains_hidden_expectation(
792
                $this->quba->get_field_prefix($this->slot) . 'p4', 0),
793
            $this->get_contains_submit_button_expectation(true),
794
            $this->get_does_not_contain_feedback_expectation(),
795
            $this->get_tries_remaining_expectation(2),
796
            $this->get_no_hint_visible_expectation());
797
    }
798
 
11 efrain 799
    public function test_display_of_right_answer_when_shuffled(): void {
1 efrain 800
 
801
        // Create a drag-and-drop question.
802
        $dd = \test_question_maker::make_question('ddimageortext');
803
        $this->start_attempt_at_question($dd, 'deferredfeedback', 3);
804
 
805
        // Check the initial state.
806
        $this->check_current_state(question_state::$todo);
807
        $this->check_current_mark(null);
808
 
809
        $this->check_current_output(
810
            $this->get_contains_hidden_expectation(
811
                $this->quba->get_field_prefix($this->slot) . 'p1'),
812
            $this->get_contains_hidden_expectation(
813
                $this->quba->get_field_prefix($this->slot) . 'p2'),
814
            $this->get_contains_hidden_expectation(
815
                $this->quba->get_field_prefix($this->slot) . 'p3'),
816
            $this->get_contains_hidden_expectation(
817
                $this->quba->get_field_prefix($this->slot) . 'p4'),
818
            $this->get_does_not_contain_feedback_expectation());
819
 
820
        // Save a partial answer.
821
        $this->process_submission($dd->get_correct_response());
822
 
823
        // Verify.
824
        $this->check_current_state(question_state::$complete);
825
        $this->check_current_mark(null);
826
        $this->check_current_output(
827
            $this->get_contains_hidden_expectation(
828
                $this->quba->get_field_prefix($this->slot) . 'p1',
829
                $dd->get_right_choice_for(1)),
830
            $this->get_contains_hidden_expectation(
831
                $this->quba->get_field_prefix($this->slot) . 'p2',
832
                $dd->get_right_choice_for(2)),
833
            $this->get_contains_hidden_expectation(
834
                $this->quba->get_field_prefix($this->slot) . 'p3',
835
                $dd->get_right_choice_for(3)),
836
            $this->get_contains_hidden_expectation(
837
                $this->quba->get_field_prefix($this->slot) . 'p4',
838
                $dd->get_right_choice_for(4)),
839
            $this->get_does_not_contain_correctness_expectation(),
840
            $this->get_does_not_contain_feedback_expectation());
841
 
842
        // Finish the attempt.
843
        $this->quba->finish_all_questions();
844
 
845
        // Verify.
846
        $this->displayoptions->rightanswer = question_display_options::VISIBLE;
847
        $this->assertEquals('Drop zone 1 -> {1. quick} '.
848
                'Drop zone 2 -> {2. fox} '.
849
                'Drop zone 3 -> {3. lazy} '.
850
                'Drop zone 4 -> {4. dog}',
851
            $dd->get_right_answer_summary());
852
        $this->check_current_state(question_state::$gradedright);
853
        $this->check_current_mark(3);
854
    }
855
 
11 efrain 856
    public function test_mixed_lang_rendering(): void {
1 efrain 857
 
858
        // Create a mixe drag-and-drop question.
859
        $dd = \test_question_maker::make_question('ddimageortext', 'mixedlang');
860
        $dd->shufflechoices = false;
861
        $this->start_attempt_at_question($dd, 'interactive', 1);
862
 
863
        // Check the initial state.
864
        $this->check_current_state(question_state::$todo);
865
        $this->check_current_mark(null);
866
        $this->check_current_output(
867
            new \question_pattern_expectation(
868
                '~<div class="group1 draghome user-select-none choice1"><span lang="fr">la</span></div>~'),
869
            new \question_pattern_expectation(
870
                '~<div class="group1 draghome user-select-none choice2"><span lang="fr">ma</span></div>~')
871
        );
872
    }
873
}