diff --git a/css/common.css b/css/common.css index 78469a2da..3dead6e27 100644 --- a/css/common.css +++ b/css/common.css @@ -256,7 +256,7 @@ footer.qsm-popup__footer button.qsm-popup-secondary-button:hover { align-content: center; } .qsm-quiz-container .qsm-contact-type-checkbox input { - margin: 0 5px 0 3px; + margin: 0 5px 9px 3px; } .mlw_qmn_question_number { font-weight: bold; diff --git a/css/qsm-admin.css b/css/qsm-admin.css index a0da07f7b..2d6a3dc7d 100644 --- a/css/qsm-admin.css +++ b/css/qsm-admin.css @@ -2683,7 +2683,7 @@ input#duplicate_questions { flex-wrap: wrap; justify-content: flex-start; align-content: flex-start; - margin-bottom: 150px; + margin-bottom: 250px; } .contact-form-builder-wrap a { display: inline-block; diff --git a/js/qsm-admin.js b/js/qsm-admin.js index 3298265c5..d24fc6d06 100644 --- a/js/qsm-admin.js +++ b/js/qsm-admin.js @@ -3209,7 +3209,11 @@ var import_button; var questionType = $('#question_type').val(); var answer_length = $('#answers').find('.answers-single').length; var answerType = $('#change-answer-editor').val(); - if (answer_length > 1 && $('#question_type').val() == 13) { + let isMultiPolar = { + isActive: false, + } + jQuery(document).trigger('qsm_new_answer_button_before', [isMultiPolar, question_id]); + if (answer_length > 1 && $('#question_type').val() == 13 && !isMultiPolar.isActive) { alert(qsm_admin_messages.polar_options_validation); return; } @@ -4111,4 +4115,28 @@ var import_button; }); } ); +}(jQuery)); + +(function ($) { + $(document).ready(function() { + let $settingsFields = $('.settings-field'); + let $popups = $('.qsm-contact-form-field-settings'); + + // Function to hide all popups + function qsmHideAllPopups() { + $popups.hide(); + } + + // Close popup on document click if popup is open and clicking outside + $(document).on('click', function(event) { + if (!$settingsFields.is(event.target) && $settingsFields.has(event.target).length === 0) { + qsmHideAllPopups(); + } + }); + + // Prevent the click event from propagating to the document when clicking inside the popup + $popups.on('click', function(event) { + event.stopPropagation(); + }); + }); }(jQuery)); \ No newline at end of file diff --git a/mlw_quizmaster2.php b/mlw_quizmaster2.php index 242550b1d..2b6a65ad5 100644 --- a/mlw_quizmaster2.php +++ b/mlw_quizmaster2.php @@ -2,7 +2,7 @@ /** * Plugin Name: Quiz And Survey Master * Description: Easily and quickly add quizzes and surveys to your website. - * Version: 9.0.4 + * Version: 9.0.5 * Author: ExpressTech * Author URI: https://quizandsurveymaster.com/ * Plugin URI: https://expresstech.io/ @@ -43,7 +43,7 @@ class MLWQuizMasterNext { * @var string * @since 4.0.0 */ - public $version = '9.0.4'; + public $version = '9.0.5'; /** * QSM Alert Manager Object @@ -473,7 +473,8 @@ public function qsm_admin_scripts_style( $hook ) { } } // load admin JS after all dependencies are loaded - wp_enqueue_script( 'qsm_admin_js', plugins_url( 'js/qsm-admin.js', __FILE__ ), array( 'jquery', 'backbone', 'underscore', 'wp-util', 'jquery-ui-sortable', 'jquery-touch-punch', 'qsm-jquery-multiselect-js' ), $this->version, true ); + /** Fixed wpApiSettings is not defined js error by using 'wp-api-request' core script to allow the use of localized version of wpApiSettings. **/ + wp_enqueue_script( 'qsm_admin_js', plugins_url( 'js/qsm-admin.js', __FILE__ ), array( 'jquery', 'backbone', 'underscore', 'wp-util', 'jquery-ui-sortable', 'jquery-touch-punch', 'qsm-jquery-multiselect-js', 'wp-api-request' ), $this->version, true ); wp_enqueue_style( 'jquer-multiselect-css', QSM_PLUGIN_CSS_URL . '/jquery.multiselect.min.css', array(), $this->version ); wp_enqueue_script( 'qsm-jquery-multiselect-js', QSM_PLUGIN_JS_URL . '/jquery.multiselect.min.js', array( 'jquery' ), $this->version, true ); wp_enqueue_script( 'micromodal_script', plugins_url( 'js/micromodal.min.js', __FILE__ ), array( 'jquery', 'qsm_admin_js' ), $this->version, true ); diff --git a/php/classes/class-qmn-plugin-helper.php b/php/classes/class-qmn-plugin-helper.php index 88ece3223..d6c6ffaee 100644 --- a/php/classes/class-qmn-plugin-helper.php +++ b/php/classes/class-qmn-plugin-helper.php @@ -1097,7 +1097,7 @@ public function convert_contacts_to_preferred_date_format( $qsm_qna_array ) { $qsm_contact_array = $qsm_qna_array['contact']; foreach ( $qsm_contact_array as $qsm_contact_id => $qsm_contact ) { - if ( 'date' === $qsm_contact['type'] && null !== $GLOBALS['qsm_date_format'] ) { + if ( 'date' === $qsm_contact['type'] && '' !== $qsm_contact['value'] && null !== $GLOBALS['qsm_date_format'] ) { $qsm_qna_array['contact'][ $qsm_contact_id ]['value'] = date_i18n( $GLOBALS['qsm_date_format'], strtotime( ( $qsm_contact['value'] ) ) ); } } diff --git a/php/classes/class-qsm-contact-manager.php b/php/classes/class-qsm-contact-manager.php index 35cd74e38..758e9b5fa 100644 --- a/php/classes/class-qsm-contact-manager.php +++ b/php/classes/class-qsm-contact-manager.php @@ -353,6 +353,25 @@ public static function save_fields( $quiz_id, $fields ) { $fields[ $i ]['label'] = $label; $mlwQuizMasterNext->pluginHelper->qsm_register_language_support( $label, "quiz_contact_field_text-{$i}-{$quiz_id}" ); $mlwQuizMasterNext->pluginHelper->qsm_register_language_support( $placeholder, "quiz_contact_field_placeholder-{$i}-{$quiz_id}" ); + + // Validate allowed domains + if ( ! empty( $fields[ $i ]['allowdomains'] ) ) { + $allowdomains = explode( ',', $fields[ $i ]['allowdomains'] ); + // Trim domains + $allowdomains = array_map( 'trim', $allowdomains ); + // filter domain + $allowdomains = array_filter( $allowdomains, function( $allowdomain ) { + /** + * full domain name may not exceed a total length of 253 ASCII characters + * The domain name consists of valid labels (1-63 characters of letters, digits, + * or hyphens) followed by a dot. The domain ends with a valid TLD + * (2-63 characters of letters). + */ + return preg_match( '/^([a-zA-Z0-9-]{1,63}\.)+[a-zA-Z]{2,63}$/', $allowdomain ) && ( strlen( $allowdomain ) <= 253 ); + } ); + + $fields[ $i ]['allowdomains'] = implode( ',', $allowdomains ); + } if ( ! empty( $fields[ $i ]['options'] ) ) { $options = sanitize_text_field( wp_unslash( $fields[ $i ]['options'] ) ); $fields[ $i ]['options'] = $options; @@ -394,6 +413,8 @@ public static function generate_contact_field( $field, $index, $quiz_options, $d $class .= ' mlwRequiredRadio '; }elseif ( 'select' === $field["type"] ) { $class .= 'qsmRequiredSelect'; + }elseif ( 'number' === $field["type"] ) { + $class .= 'mlwRequiredNumber'; }else { $class .= 'mlwRequiredText qsm_required_text'; if ( 'checkbox' === $field["type"] ) { @@ -533,7 +554,7 @@ public static function generate_contact_field( $field, $index, $quiz_options, $d ?> - maxlength='' oninput='maxLengthCheck(this)' /> + maxlength='' oninput='maxLengthCheck(this)' />
@@ -570,8 +591,8 @@ class="qmn_quiz_radio"
'; + } break; case 'select': // Filer Value @@ -582,7 +603,7 @@ class="qmn_quiz_radio" $fieldAttr .= " autocomplete='off' "; } // If REQUIRED is set then assigning the required class - if ( isset( $field['options'] ) ) { + if ( isset( $field['options'] ) && ! empty( trim( $field['options'] ) ) ) { ?> - $email ) { $email_subject = $mlwQuizMasterNext->pluginHelper->qsm_language_support( $email['subject'], "quiz-email-subject-{$index}-{$response_data['quiz_id']}" ); + + // kses converts ampersands to & core.trac.wordpress.org/ticket/11311. + $email_subject = str_replace( '&', '&', $email_subject ); + $email_content = $mlwQuizMasterNext->pluginHelper->qsm_language_support( $email['content'], "quiz-email-content-{$index}-{$response_data['quiz_id']}" ); // Checks if any conditions are present. Else, send it always. if ( ! empty( $email['conditions'] ) ) { diff --git a/php/classes/class-qsm-install.php b/php/classes/class-qsm-install.php index 322ad7bef..7ee73ac20 100644 --- a/php/classes/class-qsm-install.php +++ b/php/classes/class-qsm-install.php @@ -2029,7 +2029,9 @@ public function update() { if ( ! get_option( 'fixed_duplicate_questions' ) ) { QSM_Migrate::fix_duplicate_questions(); } - QSM_Migrate::fix_deleted_quiz_posts(); + if ( ! get_option( 'fix_deleted_quiz_posts' ) ) { + QSM_Migrate::fix_deleted_quiz_posts(); + } update_option( 'mlw_quiz_master_version', $data ); } diff --git a/php/classes/class-qsm-migrate.php b/php/classes/class-qsm-migrate.php index 98db81c63..ca763c4db 100644 --- a/php/classes/class-qsm-migrate.php +++ b/php/classes/class-qsm-migrate.php @@ -123,7 +123,7 @@ public static function fix_duplicate_questions() { if ( ! empty( $all_quizzes ) ) { foreach ( $all_quizzes as $quiz ) { $quiz_id = $quiz->quiz_id; - $settings = maybe_unserialize( $quiz->quiz_settings ); + $settings = ! empty( $quiz->quiz_settings ) ? maybe_unserialize( $quiz->quiz_settings ) : array(); $pages = isset( $settings['pages'] ) ? maybe_unserialize( $settings['pages'] ) : array(); $qpages = isset( $settings['qpages'] ) ? maybe_unserialize( $settings['qpages'] ) : array(); if ( ! empty( $pages ) ) { @@ -179,6 +179,7 @@ public static function fix_deleted_quiz_posts() { } } } + update_option( 'fix_deleted_quiz_posts', 1 ); } } diff --git a/php/question-types/qsm-question-type-polar.php b/php/question-types/qsm-question-type-polar.php index 6464eff20..d471991dc 100644 --- a/php/question-types/qsm-question-type-polar.php +++ b/php/question-types/qsm-question-type-polar.php @@ -41,7 +41,10 @@ function qmn_polar_display( $id, $question, $answers ) { } $new_question_title = $mlwQuizMasterNext->pluginHelper->get_question_setting( $id, 'question_title' ); qsm_question_title_func( $question, '', $new_question_title, $id ); - + $show = true; + $show = apply_filters( 'qsm_check_advance_polar_show_status', $show, $id ); + echo apply_filters( 'qmn_polar_display_front_before', '', $id, $question, $answers ); + if ( $show ) { ?>
pluginHelper->get_quiz_setting( 'contact_form' ); + $return = ''; if ( isset( $results['contact'] ) && ( is_array( $results['contact'] ) || is_object( $results['contact'] ) ) ) { - for ( $i = 0; $i < count( $results['contact'] ); $i++ ) { - $return .= $results['contact'][ $i ]['label'] . ': ' . $results['contact'][ $i ]['value'] . '
'; + foreach ( $results['contact'] as $results_contact ) { + $options = qsm_get_options_of_contact_fields($contact_form, $results_contact['label'], $results_contact['type'] ); + $isRadioOrSelect = in_array($results_contact['type'], ['radio', 'select']); + $hasOptions = !empty(trim($options)); + + if (($isRadioOrSelect && $hasOptions) || !$isRadioOrSelect) { + $return .= $results_contact['label'] . ': ' . $results_contact['value'] . '
'; + } } } $content = str_replace( '%CONTACT_ALL%', $return, $content ); return $content; } - +function qsm_get_options_of_contact_fields($data, $label, $type) { + foreach ($data as $item) { + if ($item['label'] === $label && $item['type'] === $type) { + return $item['options']; + } + } + return null; // Option not found +} /** * Converts the %QUESTIONS_ANSWERS% into the template * @@ -1557,7 +1573,8 @@ function qmn_polar_display_on_resultspage( $id, $question, $answers, $answer ) { $input_text .= ""; $question = $input_text; $question_display .= "" . do_shortcode( htmlspecialchars_decode( $question, ENT_QUOTES ) ) . ''; - return apply_filters( 'qmn_polar_display_front', $question_display, $id, $question, $answers ); + $question_display = apply_filters( 'qmn_polar_display_front', $question_display, $id, $question, $answers ); + return apply_filters( 'qmn_polar_display_result_page', $question_display, $id, $question, $answers, $answer ); } /** diff --git a/readme.txt b/readme.txt index d78e51d99..e8aaf4971 100644 --- a/readme.txt +++ b/readme.txt @@ -4,7 +4,7 @@ Tags: quiz, survey, test, exam, online assessment Requires at least: 4.9 Tested up to: 6.5 Requires PHP: 5.4 -Stable tag: 9.0.4 +Stable tag: 9.0.5 License: GPLv2 License URI: http://www.gnu.org/licenses/gpl-2.0.html @@ -163,6 +163,13 @@ This is usually a theme conflict. You can [checkout out our common conflict solu 18. Database == Changelog == += 9.0.5 ( June 19, 2024 ) = +* Bug: Resolved a security vulnerability +* Bug: Fixed the wpApiSettings JavaScript error +* Bug: Fixed an issue with & character in email templates +* Bug: Fixed the date contact field issue +* Enhancement: Improved contact field UI + = 9.0.4 ( June 10, 2024 ) = * Enhancement: Improved HTML code management on the result page