i have a product with 6 variations of Membership (MEMBER, SPECIALMEMBER, NOMEMBER...)
it is possible to enable or disable purchase of this whole product (all variations), if the logged in user is in member group "specialmembers".
if ( user_can( $current_user, "specialmember" )) {
return true;
}
else {
return true;
}
How is it possible to disable just one single variation (MEMBER) für this user group?
Thank you very much for helping a beginner!
By using any one of these hook tags you can disable particular variations.
woocommerce_available_variation
woocommerce_variation_is_active
Solution 1
add_filter(
'woocommerce_available_variation',
function ( $data, $product, $variation ) {
if ( 'green' === strtolower( $variation->get_attribute( 'pa_color' ) ) ) {
$data['variation_is_active'] = false;
}
return $data;
},
10,
3
);
Solution 2
add_filter(
'woocommerce_variation_is_active',
function( $data, $variation ) {
if ( 'green' === strtolower( $variation->get_attribute( 'pa_color' ) ) ) {
return false;
}
return $data;
},
10,
2
);
In both solution we checking if the variation attribute pa_color is green if so then disable that option by assigning false for the variation active property.
As a result that variation will be disabled as represented in the given below image.
Filter Hook Source Code
woocommerce_available_variation
woocommerce_variation_is_active
Related
Need some help on this...Please :)
I have this site that is using the Woocommerce's shipping option for "Starken por pagar", that works globally for all cities
And right after that is "Envío Gratis" that is send it for my actual shipping plugin, that calculate free shipping "Envío Gratis" when one particular city is selected.
My idea is that I need to remove "Starken por pagar" when the user select one particular city (one only - the same that is used by my shipping plugin) and left only the "Envío Gratis" for that city.
Because now I dont need the users need to pay for some service that is free. And as you may know, some people barely read the things in front of ther eyes :P
I tried with this (Im not an expert, sorry)
function filter_woocommerce_package_rates( $rates, $package ) {
// Loop trough
foreach ( $rates as $rate_id => $rate ) {
// Checks if a value exists in an array, multiple can be added, separated by a comma
if ( in_array( $rate->method_id, array( 'local_pickup', 'free_shipping' ) ) ) {
unset( $rates['flat_rate:28'] );
}
}
return $rates;
}
add_filter( 'woocommerce_package_rates', 'filter_woocommerce_package_rates', 10, 2 );
Or
// Hide shipping in cart page.
add_filter( 'woocommerce_product_needs_shipping', 'disable_shipping_in_cart_page', 10, 2 );
function disable_shipping_in_cart_page( $needs_shipping, $product ){
if ( is_cart() )
$needs_shipping = false;
return $needs_shipping;
}
// Conditionally remove Flat Rate which qualifies for free shipping
add_filter( 'woocommerce_package_rates', 'hide_flat_rate_when_free_is_available', 10, 3 );
function hide_flat_rate_when_free_is_available( $rates, $package ) {
$free = array();
$free_available = false;
foreach ( $rates as $rate_key => $rate ) {
if ( 'free_shipping' === $rate->method_id ){
$free_available = true;
break;
}
}
foreach ( $rates as $rate_key => $rate ) {
if ( $free_available && 'flat_rate' === $rate->method_id )
unset($rates[$rate_key]);
}
return $rates;
}
Thank you :)
I hope you can help me out.
I need to check the SKU before saving a new product
And I also want to avoid errors due to duplicated SKU value. The SKU should just be change so it is unique.
I have tried a lot of combinations and different hooks – and nothing happens, the product just saves whether or not the SKU is set.
// Disable default duplicte sku check
add_filter( 'wc_product_has_unique_sku', '__return_false' );
//Check SKU
add_action( 'woocommerce_before_product_object_save', 'set_sku', 50, 2 );
function set_sku( $product_id, $product ) {
function generateRandomString($length = 10) {
return substr(str_shuffle(str_repeat($x='0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ', ceil($length/strlen($x)) )),1,$length);
}
$currentSku = $product->get_sku();
if( empty( $currentSku ) ) { //If SKU field is empty then use slug for SKU
$product->set_sku($product->get_slug());
}else if( !wc_product_has_unique_sku($product_id, $currentSku ) ) {
$product->set_sku($currentSku.'-'.$generateRandomString()); //SKU duplicated - add random string to end
}
}
Why don't you just use the 'pre_post_update' hook?
The hook 'woocommerce_before_product_object_save' doesn't work, it was probably removed.
add_action( 'pre_post_update', 'set_sku', 50, 2 );
function set_sku( $product_id, $product_data ) {
// Only run this code for products
if ($product_data['post_type'] !== 'product') {
return;
}
$product = wc_get_product($product_id);
//... your sku related code ...
pls how can I disable local pickup depending on a cart total weight? I want to disable possibility for local pickup when the cart total weight == 0. I used this snippet found elsewhere and modified, but it is not working and the local pickup is still offered
add_filter( 'woocommerce_package_rates', 'bbloomer_woocommerce_tiered_shipping', 9999, 2 );
function bbloomer_woocommerce_tiered_shipping( $rates, $package ) {
if ( WC()->cart->get_cart_contents_weight() == 0 ) {
unset( $rates['local_pickup'] );
unset( $rates['local_delivery'] );
}
return $rates;
}
What am I doing wrong please?
Actually my code mentioned above is working. I did not realized two things:
ID of my local_pickup was wrong, I did not explore the page to find out, that the correct variable name is 'local_pickup:13' (code updated)
To see changes on the web I always have to open the site in anonymous window. Even Ctrl+F5, Ctrl+Shift+R in Chrome does not help.
You can count total weight by WC()->cart->cart_contents loop.
try this code
add_filter( 'woocommerce_package_rates', 'hide_shipping_based_on_weight', 10, 2 );
function hide_shipping_based_on_weight( $rates, $package ) {
$cart_total_weight = 0;
$shipping_id = 'local_pickup'; // your shipping id
// Calculate cart weight total.
foreach( WC()->cart->cart_contents as $key => $value ){
$cart_total_weight += $value['data']->weight * $value['quantity'];
}
// check cart total
if( $cart_total_weight <= 0 ){
unset( $rates[ $shipping_id ] );
}
return $rates;
}
I have an event based WordPress website on that I sell tickets using WooCommerce. Is there any way to hide the "add to cart" button for the product having cost zero?
Thanks.
You write this code in your theme function.php
function remove_add_to_cart_on_0 ( $purchasable, $product ){
if( $product->get_price() == 0 )
$purchasable = false;
return $purchasable;
}
add_filter( 'woocommerce_is_purchasable', 'remove_add_to_cart_on_0', 10, 2 );
This code work like charm in function.php using this two filter.
add_filter('remove_add_to_cart', 'my_woocommerce_is_purchasable', 10, 2);
function remove_add_to_cart($is_purchasable, $product) {
if( $product->get_price() == 0 )
$is_purchasable = false;
return $purchasable;
}
function remove_add_to_cart_on_0 ( $purchasable, $product ){
if( $product->get_price() == 0 )
$purchasable = false;
return $purchasable;
}
add_filter( 'woocommerce_is_purchasable', 'remove_add_to_cart_on_0', 10, 2 );
This may be a suitable solution according to the documentation
woocommerce_is_purchasable – filter
Function name: WC_Product::is_purchasable
is_purchasable() — Returns false if the product cannot be bought.
https://woocommerce.wp-a2z.org/oik_api/wc_productis_purchasable/
function remove_add_to_cart_on_0 ( $is_purchasable, $product ){
if( $product->get_price() == 0 ) {
return false; }
else {
return $is_purchasable; }
}
add_filter( 'woocommerce_is_purchasable', 'remove_add_to_cart_on_0', 10, 2 );
Hi I am trying to limit the options certain users have when viewing the products list within woocommerce for wordpress admin pages.
if( current_user_can('vendor') ) {
function my_columns_filter( $columns ) {
unset($columns['tags']);
unset($columns['featured']);
unset($columns['type']);
return $columns;
}
}
add_filter( 'manage_edit-product_columns', 'my_columns_filter', 10, 1 );
Any help or guidance would be much appreciated.
You're doing it wrong.
Place if/else inside the function instead of wrapping the function.
function my_columns_filter( $columns ) {
if( current_user_can('vendor') ) {
unset($columns['tags']);
unset($columns['featured']);
unset($columns['type']);
return $columns;
}
}
add_filter( 'manage_edit-product_columns', 'my_columns_filter', 10, 1 );
You are not using the correct column names, or perhaps WC has changed them since you posted your question. It also better to check if a column still exists before removing it in case WC does change their column names.
Here is a future proof solution you can past into your theme's functions.php:
function my_product_columns_filter( $columns ) {
if ( current_user_can( 'vendor' ) ) {
foreach ( array( 'product_tag', 'featured', 'product_type' ) as $name ) {
if ( isset( $columns[ $name ] ) ) {
unset( $columns[ $name ] );
}
}
}
return $columns;
}
add_filter( 'manage_edit-product_columns', 'my_product_columns_filter' );
no coding solution
If you're just looking for a quick solution without the need for coding, you could use the free admin columns plugin from wordpress.org, which allows you to add and remove columns with a few clicks.