PageRenderTime 26ms CodeModel.GetById 17ms RepoModel.GetById 0ms app.codeStats 0ms

/wp-content/plugins/learnpress-fill-in-blank/inc/class-lp-question-fill-in-blank.php

https://gitlab.com/gregtyka/lfmawordpress
PHP | 252 lines | 144 code | 31 blank | 77 comment | 23 complexity | 1bf5edbb5e249a2c18b37c3fc820ba36 MD5 | raw file
  1. <?php
  2. if ( class_exists( 'LP_Abstract_Question' ) ) {
  3. /**
  4. * Class LP_Question_Sorting_Choice
  5. *
  6. * @extend LP_Question_Abstract
  7. */
  8. class LP_Question_Fill_In_Blank extends LP_Abstract_Question {
  9. /**
  10. * @var string
  11. */
  12. protected $_shortcode_pattern = '!\[fib(.*)fill=["|\'](.*)["|\']!iSU';
  13. /**
  14. * LP_Question_Fill_In_Blank constructor.
  15. *
  16. * @param null $the_question
  17. * @param null $args
  18. */
  19. function __construct( $the_question, $args ) {
  20. add_action( 'wp_enqueue_scripts', array( $this, 'load_assets' ) );
  21. add_shortcode( 'fib', array( $this, 'shortcode' ) );
  22. parent::__construct( $the_question, $args );
  23. $this->checked = $this->get_answers();
  24. add_action( 'learn_press_save_user_question_answer', array( $this, '_get_checked' ), 5, 5 );
  25. add_filter( 'learn_press_check_question_answers', array( $this, '_check_answer' ), 5, 4 );
  26. learn_press_add_question_type_support( $this->type, array( 'check-answer', 'hint' ) );
  27. }
  28. /**
  29. * @param $question_answer
  30. * @param $save_id
  31. * @param $quiz_id
  32. * @param $user_id
  33. * @param $a
  34. */
  35. function _get_checked( $question_answer, $save_id, $quiz_id, $user_id, $a ) {
  36. $this->user_answered = $question_answer;
  37. }
  38. /**
  39. * @param $checked
  40. * @param $question_id
  41. * @param $quiz_id
  42. * @param $user_id
  43. *
  44. * @return string
  45. */
  46. function _check_answer( $checked, $question_id, $quiz_id, $user_id ) {
  47. //
  48. if( $question_id == $this->id) {
  49. settype( $checked, 'array' );
  50. $content = reset( $checked );
  51. $content = stripcslashes( current( $content ) );
  52. $pattern = $this->_shortcode_pattern;
  53. $content = preg_replace_callback( $pattern, array( $this, '_replace_callback' ), $content );
  54. $checked = '<div class="question-passage">' . do_shortcode( $content ) . '</div>';
  55. }
  56. return $checked;
  57. }
  58. /**
  59. * @param $a
  60. *
  61. * @return string
  62. */
  63. function _replace_callback( $a ) {
  64. $user_fill = '';
  65. if ( !empty( $this->user_answered ) ) {
  66. settype( $this->user_answered, 'array' );
  67. $input_name = $this->get_input_name( $a[2] );
  68. if ( !empty( $this->user_answered[$input_name] ) ) {
  69. settype( $this->user_answered[$input_name], 'array' );
  70. $user_fill = array_shift( $this->user_answered[$input_name] );
  71. }
  72. }
  73. return $a[0] . ' correct_fill="' . $a[2] . '" user_fill="' . $user_fill . '"';
  74. }
  75. /**
  76. * @param $fill
  77. *
  78. * @return string
  79. */
  80. function get_input_name( $fill ) {
  81. return '_' . md5( wp_create_nonce( $fill ) );
  82. }
  83. /**
  84. * @param null $atts
  85. *
  86. * @return string
  87. */
  88. function shortcode( $atts = null ) {
  89. $atts = shortcode_atts(
  90. array(
  91. 'fill' => '',
  92. 'user_fill' => '',
  93. 'correct_fill' => ''
  94. ), $atts
  95. );
  96. $input_name = $this->get_input_name( $atts['fill'] );
  97. return sprintf(
  98. '<input type="text" name="%s" data-fill="%s" value="%s" %s />%s',
  99. 'learn-press-question-' . $this->id . '[' . $input_name . '][]',
  100. esc_attr( $input_name ),
  101. $atts['user_fill'],
  102. $atts['correct_fill'] ? ' disabled="disabled"' : '',
  103. $atts['correct_fill'] ? sprintf( '<span class="check-label %s">%s</span>', $atts['user_fill'] == $atts['correct_fill'] ? 'correct' : 'wrong', $atts['correct_fill'] ) : ''
  104. );
  105. }
  106. /**
  107. * Assets
  108. */
  109. function load_assets() {
  110. wp_enqueue_style( 'fill-in-blank', plugins_url( 'assets/style.css', LP_QUESTION_FILL_IN_BLANK_FILE ) );
  111. }
  112. /**
  113. * Magic __get helper
  114. *
  115. * @param $key
  116. *
  117. * @return mixed|null|string
  118. */
  119. function __get( $key ) {
  120. if ( $key == 'passage' || $key == 'passage_checked' ) {
  121. $answers = (array) $this->get_answers();
  122. $passage = reset( $answers );
  123. $passage = !empty( $passage[0] ) ? stripcslashes( $passage[0] ) : null;
  124. if ( $key == 'passage_checked' ) {
  125. if ( $passage ) {
  126. $pattern = $this->_shortcode_pattern;
  127. $passage = preg_replace_callback( $pattern, array( $this, '_replace_callback' ), $passage );
  128. }
  129. }
  130. return $passage;
  131. }
  132. return parent::__get( $key );
  133. }
  134. /**
  135. * Admin interface
  136. *
  137. * @param array $args
  138. *
  139. * @return string
  140. */
  141. function admin_interface( $args = array() ) {
  142. ob_start();
  143. $view = learn_press_get_admin_view( 'admin-fill-in-blank-options', LP_QUESTION_FILL_IN_BLANK_FILE );
  144. include $view;
  145. $output = ob_get_clean();
  146. if ( !isset( $args['echo'] ) || ( isset( $args['echo'] ) && $args['echo'] === true ) ) {
  147. echo $output;
  148. }
  149. return $output;
  150. }
  151. /**
  152. * Question content
  153. *
  154. * @param null $args
  155. */
  156. function render( $args = null ) {
  157. settype( $args, 'array' );
  158. $answered = !empty( $args['answered'] ) ? $args['answered'] : array();
  159. $view = LP_Addon_Question_Fill_In_Blank::locate_template( 'fill-in-blank.php' );
  160. include $view;
  161. }
  162. /**
  163. * Check result of question
  164. *
  165. * @param null $args
  166. *
  167. * @return mixed
  168. */
  169. function check( $args = null ) {
  170. $key = wp_create_nonce( maybe_serialize( $args ) );
  171. $check_results = $this->check_results;
  172. if ( empty( $check_results ) ) {
  173. $check_results = array();
  174. }
  175. if ( empty( $check_results[$key] ) ) {
  176. $return = array(
  177. 'correct' => true
  178. );
  179. $passage = $this->passage;
  180. if ( preg_match_all( $this->_shortcode_pattern, $passage, $matches ) ) {
  181. settype( $args, 'array' );
  182. $input_pos = array();
  183. foreach ( $matches[0] as $k => $v ) {
  184. $input_name = $this->get_input_name( $matches[2][$k] );
  185. $user_fill = '';
  186. if ( !empty( $args[$input_name] ) ) {
  187. $pos = !empty( $input_pos[$input_name] ) ? $input_pos[$input_name] : 1;
  188. if ( !empty( $args[$input_name][$pos - 1] ) ) {
  189. $user_fill = $args[$input_name][$pos - 1];
  190. }
  191. $input_pos[$input_name] = $pos + 1;
  192. }
  193. if ( $user_fill != $matches[2][$k] ) {
  194. $return['correct'] = false;
  195. }
  196. }
  197. $return['mark'] = $return['correct'] ? $this->mark : 0;
  198. }
  199. $check_results[$key] = $return;
  200. $this->check_results = $check_results;
  201. }
  202. return $check_results[$key];
  203. }
  204. /**
  205. * @param null $post_data
  206. */
  207. function save( $post_data = null ) {
  208. global $wpdb;
  209. $wpdb->delete( $wpdb->prefix . 'learnpress_question_answers', array( 'question_id' => $this->id ), array( '%d' ) );
  210. $wpdb->insert(
  211. $wpdb->prefix . 'learnpress_question_answers',
  212. array(
  213. 'question_id' => $this->id,
  214. 'answer_data' => maybe_serialize( $post_data ),
  215. 'answer_order' => 1
  216. ),
  217. array( '%d', '%s', '%d' )
  218. );
  219. }
  220. }
  221. }