I have conditionally unset the billing address fields on the woocommerce checkout page, but when submitting place order, woocommerce displays error:
Please enter an address to continue.
I then tried adding a filter on woocommerce_default_address_fields to make the fields optional - which only seems to work if the fields aren't unset.
// make address fields optional - this works fine without the next filter
add_filter( 'woocommerce_default_address_fields' , 'filter_default_address_fields', 20, 1 );
function filter_default_address_fields( $address_fields ) {
// Only on checkout page
if( ! is_checkout() ) return $address_fields;
// All field keys in this array
$fields = array('country','company','address_1','address_2','city','state','postcode');
// Loop through each address fields (billing and shipping)
foreach( $fields as $key_field )
$address_fields[$key_field]['required'] = false;
return $address_fields;
}
//conditionally unset fields
add_filter( 'woocommerce_checkout_fields' , 'simplify_checkout' );
function simplify_checkout( $fields ) {
$customField = false;
foreach( WC()->cart->get_cart() as $cart_item_key => $cart_item ) {
// Check if cart item has attribute
if ( ! empty ($cart_item['custom_attribute']) ) $registry = true;
}
if( $customField ) {
unset($fields['billing']['billing_company']);
unset($fields['billing']['billing_address_1']);
unset($fields['billing']['billing_address_2']);
unset($fields['billing']['billing_city']);
unset($fields['billing']['billing_postcode']);
unset($fields['billing']['billing_country']);
unset($fields['billing']['billing_state']);
}
return $fields;
}
I'm hoping to still be able to conditionally hide / unset the fields along with a successful checkout submission.
I had this problem with the validation message two days ago. I only sell to one country, so I created following workaround. Maybe if you have fewer countries to sell this could work for you too:
Uncomment/Remove unset($fields['billing']['billing_country']);
Go to WooCommerce -> Settings -> Sell to specific countries and
enter your countries.
Now the validation message is inactive, as the Country field is
mandatory. You can remove it now with CSS.
#billing_country_field {
display: none;
}
Just change the action name and try it:
add_filter( 'woocommerce_checkout_fields' , 'custom_override_checkout_fields' );
add_action( 'woocommerce_after_shop_loop_item_title', 'filter_default_address_fields' );
Related
I'm trying to do a special logic for my custom plugin. If the user has added a specific product type in their cart, in the checkout page there must be radio inputs that determine whether the user wants the specific product type to be shipped or stored in vault. I've done everything for the frontend part (creating the radio inputs, built the JavaScript logic to remove from the DOM what's not necessary and so on...) but I now need to programatically remove the shipping from the order and remove the "Shipping" row inside the order preview in the checkout page. I tried the following filter
add_filter( 'woocommerce_cart_shipping_method_full_label', 'remove_shipping_labels', 10, 2 );
function remove_shipping_labels( $label, $method ) {
return '';
}
But it's removing just the label text "Free Shipping" but not the entire shipping row inside the order preview in the checkout page. How can I programatically remove the shipping availability from an order through AJAX and update the user interface inside the checkout page?
function hide_shipping_based_on_prod_type( $rates ) {
global $woocommerce;
$items = $woocommerce->cart->get_cart();
foreach ( $items as $item => $values ) {
$product_id = $values['data']->get_id();
$product_type = WC_Product_Factory::get_product_type( $values['data']->get_id() );
if ( 'simple' === $product_type ) { //check product types of woocommerce to add more conditions
unset( $rates['free_shipping:1'] );
}
}
return $rates;
}
add_filter( 'woocommerce_package_rates', 'hide_shipping_based_on_prod_type', 100 );
add_action(
'after_setup_theme',
function() {
WC_Cache_Helper::get_transient_version( 'shipping', true );
}
);
I've got the following code in my functions.php file that is supposed to check if certain products are in the cart and, if they are, remove a field from the billing set of fields at checkout. However, it's not removing the field, or any other field I try. I'm wondering why that is. Other tutorials I'm following are consistent with this code and say it should work, but for me it's not. What did I get wrong?
/**
* Check if a specific product ID is in the cart
*/
function dz_product_is_in_the_cart() {
// Add your special product IDs here
$ids = array( '10771', '10773', '10774', '10943', '10944', '10945', '10946', '10947', '10948', '10949', '10950', '10951', '10952', '10953', '10943', '10943', '10943', '10943');;
// Products currently in the cart
$cart_ids = array();
// Find each product in the cart and add it to the $cart_ids array
foreach( WC()->cart->get_cart() as $cart_item_key => $values ) {
$cart_product = $values['data'];
$cart_ids[] = $cart_product->id;
}
// If one of the special products are in the cart, return true.
if ( ! empty( array_intersect( $ids, $cart_ids ) ) ) {
return true;
} else {
return false;
}
}
/**
* Conditionally remove a checkout field based on products in the cart
*/
function dz_remove_checkout_field( $fields ) {
if ( dz_product_is_in_the_cart() ) {
unset( $fields['billing']['billing_first_name'] );
}
return $fields;
}
add_filter( 'woocommerce_checkout_fields' , 'dz_remove_checkout_field' );
The billing_first_name field is a required field. So do I need to do something to unrequire it before I try to unset it?
The problem was a plugin that was inserting this field was overriding my code that tried to unrequire and remove it. I opted to disable the plugin and add and conditionally control my own field(s) with the code here: https://woocommerce.com/document/tutorial-customising-checkout-fields-using-actions-and-filters/#section-7
I came across with this How to blank all WooCommerce checkout fields by default except country? similar question which has an answer code that meet my needs, but this code will blank all woocommerce shipping and also billing checkout field when customer click checkout button.
if I want the shipping fields only to be blank, how the code will looks like?
To blank all WooCommerce shipping checkout fields, you will use the following:
add_filter('woocommerce_checkout_get_value', 'checkout_get_value_filter', 10, 2 );
function checkout_get_value_filter( $value, $input ) {
if ( strpos($input, "shipping_") === 0 ) {
return '';
}
return $value;
}
Or also this specifying each related shipping field key:
add_filter('woocommerce_checkout_get_value', 'checkout_get_value_filter', 10, 2 );
function checkout_get_value_filter( $value, $input ) {
$key_fields = array(
'shipping_first_name',
'shipping_last_name',
'shipping_company',
'shipping_country',
'shipping_address_1',
'shipping_address_2',
'shipping_city',
'shipping_country',
'shipping_state',
'shipping_postcode',
);
if ( in_array($input, $key_fields) ) {
return '';
}
return $value;
}
Code goes on functions.php file of your active child theme (or active theme). It should works.
I have been working to hide my woocommerce checkout shipping address if a user selects a shipping table rate option that has a Label of "Local Pickup". Most code snippets I have found trigger based on shipping_method. I tried a shipping-method like `table_rate:10:1', to no avail. Any ideas?
Also, I am not completely clear on how to designate the specific row in the table - I inspected the code and found the value above, but am unsure if its correct.
Shipping related plug-ins: Woocommerce Table Rate Shipping
Trying to use the following code as a base:
add_filter( 'woocommerce_checkout_fields', 'xa_remove_billing_checkout_fields' );
function xa_remove_billing_checkout_fields( $fields ) {
global $woocommerce;
// Set the desired shipping method to hide the checkout field(s).
$shipping_method = 'table_rate:10:1';
$chosen_methods = WC()->session->get( 'chosen_shipping_methods' );
$chosen_shipping = $chosen_methods[0];
if ( $chosen_shipping == $shipping_method ) {
// Add/change field name to be hide
unset($fields['billing']['billing_address_1']);
unset($fields['billing']['billing_address_2']);
}
return $fields;
}
website: camp4coffee.com
Is there a way to remove the required asterisk from a billing field on the checkout page in php? I have the following code which isn't working.
add_filter( 'woocommerce_checkout_fields' , 'customize_fields' );
function customize_fields( $fields ) {
$fields['billing']['billing_address_2']['required'] = false;
return $fields;
}
It would probably be easier to do with CSS, and be cleaner and better for screen-readers:
.woocommerce-checkout abbr.required {
display: none;
}
The .woocommerce-checkout is a body class that is only appended to the checkout page so it won't affect any other woo page that might have the .required class in an abbr element.
To make the field not required with a function:
// Hook in
add_filter( 'woocommerce_default_address_fields' , 'custom_override_default_address_fields' );
// Our hooked in function - $address_fields is passed via the filter!
function custom_override_default_address_fields( $address_fields ) {
$address_fields['address_2']['required'] = false;
return $address_fields;
}
There are two filters to manage checkout fields. You can use woocommerce_checkout_fields filter to make field "not-required", but the red asterisk will not be removed.
When dealing with default address fields with woocommerce_checkout_fields filter, some of your changes will not take effect, because woocommerce_default_address_fields filter and its default values may override your changes.
Only partly functional code:
function custom_override_checkout_fields( $fields ) {
$fields['billing']['billing_address_1']['required'] = false ;
return $fields;
}
add_filter( 'woocommerce_checkout_fields' , 'custom_override_checkout_fields' );
Address field (#1) is not required anymore, but still has red asterisk.
Fully functional code:
function custom_override_default_address_fields( $address_fields ) {
$address_fields['address_1'][ 'required' ] = false;
return $address_fields;
}
add_filter( 'woocommerce_default_address_fields' , 'custom_override_default_address_fields' );
Now this field is not required, and red asterisk is gone.
Documentation says that "In some specific cases you will need to use the woocommerce_default_address_fields filter. This filter is applied to all billing and shipping default fields."
You have to add the following code to your functions.php file. The example below is for postal code:
/* Seteaza campul Cod postal ne-obligatoriu */
add_filter( 'woocommerce_billing_fields', 'wc_npr_filter_postcode', 10, 1 );
function wc_npr_filter_postcode( $address_fields ) {
$address_fields['billing_postcode']['required'] = false;
return $address_fields;
}
/* End - Seteaza campul Cod postal ne-obligatoriu */