tutor
/
templates
/
shared
/
components
/
quiz
/
attempt-details
/
questions
/
review-answer-dnd.php
fill-in-the-blank.php
2 weeks ago
multiple-choice.php
2 weeks ago
open-ended.php
1 month ago
review-answer-dnd.php
2 weeks ago
true-false.php
2 weeks ago
review-answer-dnd.php
136 lines
| 1 | <?php |
| 2 | /** |
| 3 | * Shared read-only review template for DnD-like question types. |
| 4 | * |
| 5 | * Supports: image_answering, ordering, matching, image_matching. |
| 6 | * |
| 7 | * @package Tutor\Templates |
| 8 | * @subpackage LearningArea\Quiz\AttemptDetails |
| 9 | * @since 4.0.0 |
| 10 | */ |
| 11 | |
| 12 | defined( 'ABSPATH' ) || exit; |
| 13 | |
| 14 | use TUTOR\Quiz; |
| 15 | use Tutor\Models\QuizModel; |
| 16 | |
| 17 | if ( ! isset( $question ) || ! is_object( $question ) ) { |
| 18 | return; |
| 19 | } |
| 20 | |
| 21 | $question_settings = maybe_unserialize( $question->question_settings ); |
| 22 | $question_settings = is_array( $question_settings ) ? $question_settings : array(); |
| 23 | $question_type = (string) ( $question->question_type ?? '' ); |
| 24 | $is_image_matching = 'image_matching' === $question_type || '1' === (string) ( $question_settings['is_image_matching'] ?? '0' ); |
| 25 | |
| 26 | if ( $is_image_matching ) { |
| 27 | $question_type = 'matching'; |
| 28 | } |
| 29 | |
| 30 | $question_settings['show_question_mark'] = $question_settings['show_question_mark'] ?? '1'; |
| 31 | $question_settings['is_image_matching'] = $is_image_matching ? '1' : ( $question_settings['is_image_matching'] ?? '0' ); |
| 32 | $question_answers = QuizModel::get_answers_by_quiz_question( (int) $question->question_id ); |
| 33 | $question_answers = is_array( $question_answers ) ? array_values( $question_answers ) : array(); |
| 34 | $given_raw = $question->given_answer ?? null; |
| 35 | $given_answer = maybe_unserialize( $given_raw ); |
| 36 | |
| 37 | $normalize = static function ( $value ) { |
| 38 | return strtolower( trim( wp_strip_all_tags( (string) $value ) ) ); |
| 39 | }; |
| 40 | |
| 41 | $get_answer_by_id = static function ( $answer_id ) { |
| 42 | $results = QuizModel::get_answer_by_id( (int) $answer_id ); |
| 43 | return is_array( $results ) && ! empty( $results ) ? $results[0] : null; |
| 44 | }; |
| 45 | |
| 46 | $get_image_url = static function ( $answer ) { |
| 47 | if ( ! empty( $answer->image_id ) ) { |
| 48 | return wp_get_attachment_image_url( $answer->image_id, 'thumbnail' ); |
| 49 | } |
| 50 | return ''; |
| 51 | }; |
| 52 | |
| 53 | $rows = array(); |
| 54 | |
| 55 | if ( 'ordering' === $question_type ) { |
| 56 | $given_ids = is_array( $given_answer ) ? array_values( $given_answer ) : array(); |
| 57 | foreach ( $question_answers as $idx => $correct_item ) { |
| 58 | $selected_item = isset( $given_ids[ $idx ] ) ? $get_answer_by_id( $given_ids[ $idx ] ) : null; |
| 59 | $is_row_ok = $selected_item && (int) $selected_item->answer_id === (int) $correct_item->answer_id; |
| 60 | |
| 61 | $rows[] = array( |
| 62 | 'given_text' => $selected_item->answer_title ?? '', |
| 63 | 'given_image' => $selected_item ? $get_image_url( $selected_item ) : '', |
| 64 | 'correct_text' => $correct_item->answer_title ?? '', |
| 65 | 'correct_image' => $get_image_url( $correct_item ), |
| 66 | 'given_status' => $is_row_ok ? 'correct' : 'incorrect', |
| 67 | ); |
| 68 | } |
| 69 | } elseif ( 'matching' === $question_type ) { |
| 70 | $given_ids = is_array( $given_answer ) ? array_values( $given_answer ) : array(); |
| 71 | foreach ( $question_answers as $idx => $correct_item ) { |
| 72 | $selected_item = isset( $given_ids[ $idx ] ) ? $get_answer_by_id( $given_ids[ $idx ] ) : null; |
| 73 | $given_text = $is_image_matching ? ( $selected_item->answer_title ?? '' ) : ( $selected_item->answer_two_gap_match ?? '' ); |
| 74 | $correct_text = $is_image_matching ? ( $correct_item->answer_title ?? '' ) : ( $correct_item->answer_two_gap_match ?? '' ); |
| 75 | $is_row_ok = $normalize( $given_text ) === $normalize( $correct_text ); |
| 76 | |
| 77 | $rows[] = array( |
| 78 | 'given_text' => $given_text, |
| 79 | 'given_image' => $is_image_matching && $selected_item ? $get_image_url( $selected_item ) : '', |
| 80 | 'correct_text' => $correct_text, |
| 81 | 'correct_image' => $is_image_matching ? $get_image_url( $correct_item ) : '', |
| 82 | 'given_status' => $is_row_ok ? 'correct' : 'incorrect', |
| 83 | ); |
| 84 | } |
| 85 | } elseif ( 'image_answering' === $question_type ) { |
| 86 | $given_map = is_array( $given_answer ) ? $given_answer : array(); |
| 87 | $answer_status = QuizModel::get_attempt_answer_status( $question ); |
| 88 | $row_item_state = 'correct' === $answer_status ? 'correct' : ( 'pending' === $answer_status ? 'pending' : 'incorrect' ); |
| 89 | |
| 90 | foreach ( $question_answers as $correct_item ) { |
| 91 | $answer_id = (int) ( $correct_item->answer_id ?? 0 ); |
| 92 | $given_text = (string) ( $given_map[ $answer_id ] ?? '' ); |
| 93 | $correct_text = (string) ( $correct_item->answer_title ?? '' ); |
| 94 | |
| 95 | $rows[] = array( |
| 96 | 'given_text' => $given_text, |
| 97 | 'given_image' => $get_image_url( $correct_item ), |
| 98 | 'correct_text' => $correct_text, |
| 99 | 'correct_image' => $get_image_url( $correct_item ), |
| 100 | 'given_status' => $row_item_state, |
| 101 | ); |
| 102 | } |
| 103 | } |
| 104 | ?> |
| 105 | |
| 106 | <div class="tutor-quiz-review-dnd-grid"> |
| 107 | <div class="tutor-quiz-review-dnd-head"> |
| 108 | <div class="tutor-quiz-review-col-title tutor-quiz-review-given"><?php esc_html_e( 'Given Answer', 'tutor' ); ?></div> |
| 109 | <div class="tutor-quiz-review-col-title tutor-quiz-review-correct"><?php esc_html_e( 'Correct Answer', 'tutor' ); ?></div> |
| 110 | </div> |
| 111 | |
| 112 | <div class="tutor-quiz-review-dnd-rows"> |
| 113 | <?php |
| 114 | foreach ( $rows as $row ) : |
| 115 | $given_text = isset( $row['given_text'] ) ? Quiz::sanitize_quiz_content( $row['given_text'] ) : ''; |
| 116 | $correct_text = isset( $row['correct_text'] ) ? Quiz::sanitize_quiz_content( $row['correct_text'] ) : ''; |
| 117 | $given_status = isset( $row['given_status'] ) ? $row['given_status'] : 'neutral'; |
| 118 | ?> |
| 119 | <div class="tutor-quiz-review-dnd-row"> |
| 120 | <div class="tutor-quiz-review-item tutor-quiz-review-given" data-option="<?php echo esc_attr( $given_status ); ?>"> |
| 121 | <?php if ( ! empty( $row['given_image'] ) ) : ?> |
| 122 | <img src="<?php echo esc_url( $row['given_image'] ); ?>" alt="<?php echo esc_attr( $given_text ); ?>"> |
| 123 | <?php endif; ?> |
| 124 | <span><?php echo esc_html( $given_text ); ?></span> |
| 125 | </div> |
| 126 | <div class="tutor-quiz-review-item tutor-quiz-review-correct" data-option="neutral"> |
| 127 | <?php if ( ! empty( $row['correct_image'] ) ) : ?> |
| 128 | <img src="<?php echo esc_url( $row['correct_image'] ); ?>" alt="<?php echo esc_attr( $correct_text ); ?>"> |
| 129 | <?php endif; ?> |
| 130 | <span><?php echo esc_html( $correct_text ); ?></span> |
| 131 | </div> |
| 132 | </div> |
| 133 | <?php endforeach; ?> |
| 134 | </div> |
| 135 | </div> |
| 136 |