Woocommerce Checkout - Display custom inline error messages (including custom validation messages)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
/** | |
* adds custom js file to handle inline error messages | |
*/ | |
add_action( 'woocommerce_after_checkout_form', 'add_custom_validation_script', 20 ); | |
function add_custom_validation_script() { | |
wp_enqueue_script( | |
'inline_validation_script', | |
get_stylesheet_directory_uri() . '/js/inline-validation.js', | |
['jquery'] | |
); | |
} | |
/** | |
* adds error message field element to get inline error messages working | |
* | |
* @param array $fields | |
* @param object $errors | |
*/ | |
add_filter( 'woocommerce_form_field', 'add_inline_error_messages_element', 10, 4 ); | |
function add_inline_error_messages_element( $field, $key, $args, $value ) { | |
if ( strpos( $field, '</span>' ) !== false ) { | |
$error = '<span class="js-custom-error-message" style="display:none"></span>'; | |
$field = substr_replace( $field, $error, strpos( $field, '</span>' ), 0); | |
} | |
return $field; | |
} | |
/** | |
* process custom checkout validations | |
* | |
* @param array $fields | |
* @param object $errors | |
*/ | |
add_action('woocommerce_after_checkout_validation', 'custom_checkout_validations', 10, 2); | |
function custom_checkout_validations($data, $errors) | |
{ | |
$your_custom_checkout_field = filter_input(INPUT_POST, 'your_custom_input_field'); | |
// your custom validations goes here | |
// this is an example to check for the length of the string | |
if ( !empty($your_custom_checkout_field) && strlen($your_custom_checkout_field) > 50 ) { | |
$errors->add('your_custom_input_field', __('This field needs to be max 50 chars', 'YourThemeName')); | |
} | |
// this loop adds a data array to all error messages which will be applied as a "data-error-for" HTML attribute | |
// to read out the corresponding field ids with javascript and display the error messages inline | |
foreach( $errors->errors as $original_key => $error ) { | |
$field_key = $original_key; | |
// filter and rewrite the field id for native woocommerce error messages with a key containing _required | |
if(strpos($original_key, '_required') !== false) { | |
$field_key = str_replace('_required','', $original_key); | |
$error[0] = __('This is a required field', 'YourThemeName'); | |
} | |
// switch out the old error messages with the ones including a spiced up data array | |
// to display with javascript | |
$errors->remove($original_key); | |
$errors->add($original_key, trim($error[0]), ['error-for' => $field_key . '_field']); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
jQuery(function ($) { | |
'use strict'; | |
addInlineMessages(); | |
// Implementation | |
// Listen to js event | |
$(document.body).on('updated_checkout', function() { | |
addInlineMessages(); | |
}); | |
function addInlineMessages() { | |
var woocommerceErrorsEl = $('.woocommerce-error'); | |
var woocommerceInlineErrorsEl = $('li[data-error-for]', woocommerceErrorsEl); | |
var inlineErrorMessagesEl = $('.js-custom-error-message'); | |
// as we use ajax submitting hide old validation messages | |
if(inlineErrorMessagesEl.length) { | |
inlineErrorMessagesEl.hide(); | |
} | |
if(woocommerceInlineErrorsEl.length) { | |
woocommerceInlineErrorsEl.each(function () { | |
var errorEl = $(this); | |
var errorText = $.trim(errorEl.text()); | |
var targetFieldId = errorEl.data('error-for'); | |
if(errorText && targetFieldId) { | |
var targetFieldEl = $('#' + targetFieldId); | |
var errorMessageField = $('.js-custom-error-message', targetFieldEl); | |
if(targetFieldEl.length && errorMessageField.length) { | |
targetFieldEl.removeClass('woocommerce-validated'); | |
targetFieldEl.addClass('woocommerce-invalid'); | |
errorMessageField.text(errorText); | |
errorMessageField.show(); | |
errorEl.hide(); | |
} | |
} | |
}); | |
if(woocommerceInlineErrorsEl.filter(':visible').length === 0) { | |
woocommerceErrorsEl.hide(); | |
if(inlineErrorMessagesEl.filter(':visible').length > 0) { | |
scrollToElement(inlineErrorMessagesEl.filter(':visible').first()); | |
} | |
} else { | |
$('li:not([data-error-for])', woocommerceErrorsEl).hide(); | |
scrollToElement(woocommerceErrorsEl); | |
} | |
} | |
} | |
function scrollToElement(el) { | |
if(el.length) { | |
$([document.documentElement, document.body]).animate({ | |
scrollTop: el.offset().top - 100 | |
}, 2000); | |
} | |
} | |
// event listeners | |
$(document.body).on('checkout_error', function (event) { | |
jQuery('html, body').stop(); | |
addInlineMessages(); | |
}); | |
}); |
@lucasjahn thank you so much for your help and quick response. I finally validated my checkbox field! The code works perfectly!
All the best to you!
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
@Z1pas this is totally possible. This is done in my code in the
custom_checkout_validations
function.Basically you can add any validation you want and it will add it to the corresponding fields if it is created with the
woocommerce_form_field
method.Anyway, I think I have to have a little overhaul of the code above as some people have some problems with it (probably due to other themes/plugins) enabled etc. but the basic I idea stays.
Cheers.