In my WooCommerce shop, when a customers is not logged in I would like to avoid him adding to cart asking him to either login or register an account…
Is it possible?
Updated - You could use this 2 little snippets of code, that will:
Replace add-to-cart button/link in shop pages and archives pages (for non logged in users).
Avoid non logged in customers adding to cart and displaying a custom message.
Here is the code:
// Replacing add-to-cart button in shop pages and archives pages (forn non logged in users)
add_filter( 'woocommerce_loop_add_to_cart_link', 'conditionally_change_loop_add_to_cart_link', 10, 2 );
function conditionally_change_loop_add_to_cart_link( $html, $product ) {
if ( ! is_user_logged_in() ) {
$link = get_permalink($product_id);
$button_text = __( "View product", "woocommerce" );
$html = ''.$button_text.'';
}
return $html;
}
// Avoid add to cart for non logged user (or not registered)
add_filter( 'woocommerce_add_to_cart_validation', 'logged_in_customers_validation', 10, 3 );
function logged_in_customers_validation( $passed, $product_id, $quantity) {
if( ! is_user_logged_in() ) {
$passed = false;
// Displaying a custom message
$message = __("You need to be logged in to be able adding to cart…", "woocommerce");
$button_link = get_permalink( get_option('woocommerce_myaccount_page_id') );
$button_text = __("Login or register", "woocommerce");
$message .= ' '.$button_text.'';
wc_add_notice( $message, 'error' );
}
return $passed;
}
Code goes in function.php file of your active child theme (or theme) or also in any plugin file.
Tested ad works.
Related
Attempting to change the title of the "pay for order" page / "customer payment page"
https://url.com/checkout/order-pay/753/?pay_for_order=true&key=wc_order_xxxxxx
Below is not currently working, it is modified from changing the title on the thank you page.
add_filter( 'the_title', 'woo_title_pay_order', 10, 2 );
function woo_title_pay_order( $title, $id ) {
if ( function_exists( 'is_pay_for_order_page' ) &&
is_pay_for_order_page() && get_the_ID() === $id ) {
$title = "Checkout";
}
return $title;
}
Updated
You can use the following to change "Pay for order" page title:
add_filter( 'the_title', 'change_pay_for_order_title' );
function change_pay_for_order_title( $title ) {
if ( is_wc_endpoint_url( 'order-pay' ) ) {
return __('Checkout', 'woocommerce');
}
return $title;
}
Or also the following code based on 'order-pay' endpoint (but changes the breadcrumb):
add_filter( 'woocommerce_endpoint_order-pay_title', 'change_checkout_order_pay_title' );
function change_checkout_order_pay_title( $title ) {
return __( "Checkout", "woocommerce" );
}
Code goes in functions.php file of the active child theme (or active theme). Tested and works.
Related: Set My Account custom items endpoints titles in WooCommerce
In Woocommerce, I have a function that replace add to cart button by a linked button to the product in shop and archive pages:
function quantity_inputs_for_woocommerce_loop_add_to_cart_link( $html, $product ) {
if ( ! current_user_can('customer') ) {
$link = get_permalink($product_id);
$button_text = __( "View product", "woocommerce" );
$html = ''.$button_text.'';
}
return $html;
}
add_filter( 'woocommerce_loop_add_to_cart_link', 'conditionally_change_loop_add_to_cart_link', 10, 2 );
I would like to remove the add to cart button on all pages if a user is not logged in as a customer.
Can anyone help please?
Instead of your actual code, try the following that will do everything everywhere and will remove add to cart button when user is not logged in:
add_filter('woocommerce_is_purchasable', 'woocommerce_is_purchasable_filter_callback', 10, 2 );
function woocommerce_is_purchasable_filter_callback( $purchasable, $product ) {
if ( ! is_user_logged_in() )
$purchasable = false;
return $purchasable;
}
Code goes in function.php file of your active child theme (or active theme).
I work on site that use External products from Amazon, but want instead pointing users to that external URL, first to add to cart that product. I have this function, that change Default Button text for each product, to Add to cart.
function sv_wc_external_product_button( $button_text, $product ) {
if ( 'external' === $product->get_type() ) {
// enter the default text for external products
return $product->button_text ? $product->button_text : 'Add To Cart';
}
return $button_text;
}
add_filter( 'woocommerce_product_single_add_to_cart_text',
'sv_wc_external_product_button', 10, 2 );
But this function not add product to cart.
How to make this function to Add selected product to cart?
Thanks.
Updated 2020
This is a complete different way with simple products and a custom field external link.
In this answer we will use simple products instead of external products.
We add an "External URL" custom field in product option settings and we save the data.
Add a custom field on general product option settings for simple products only :
add_action( 'woocommerce_product_options_general_product_data', 'simple_product_with_external_url' );
function simple_product_with_external_url() {
global $product_object;
echo '<div class="options_group show_if_simple hidden">';
// External Url
woocommerce_wp_text_input( array(
'id' => '_ext_url_cust',
'label' => 'External Url',
'description' => 'Custom external URL',
'desc_tip' => 'true',
'placeholder' => 'Enter here your custom external URL'
) );
echo '</div>';
}
Save the custom field data if it's a simple product and not empty:
add_action( 'woocommerce_admin_process_product_object', 'save_simple_product_with_external_url' );
function save_simple_product_with_external_url( $product ) {
if( $product->is_type('simple') && isset($_POST['_ext_url_cust']) ) {
$product->update_meta_data( '_ext_url_cust', sanitize_url($_POST['_ext_url_cust']) );
}
}
2) This will not work on shop pages and archives pages, if we don't set in WooCommerce the cart redirection when adding a product to cart.
So we will replace add-to-cart button (just for our simple products with a custom link redirection) on shop pages and archives pages by a linked custom button to single product pages.
Replacing add-to-cart button in shop pages and archives pages (for simple products with custom external url):
add_filter( 'woocommerce_loop_add_to_cart_link', 'quantity_inputs_for_woocommerce_loop_add_to_cart_link', 10, 2 );
function quantity_inputs_for_woocommerce_loop_add_to_cart_link( $html, $product ) {
$external_url = $product->get_meta('_ext_url_cust');
if ( ! empty($external_url) ) {
$html = sprintf( '%s', $product->get_permalink(), __("Read More", "woocommerce") );
}
return $html;
}
3) If the custom field value is not empty, the product is added to cart first and then redirected to the external URL (our custom field value in single product pages)
External URL redirection after adding to cart (when custom field is not empty in simple products):
add_filter( 'woocommerce_add_to_cart_redirect', 'redirect_simple_product_with_external_url' );
function redirect_simple_product_with_external_url( $url ) {
if( isset($_REQUEST['add-to-cart']) && absint( $_REQUEST['add-to-cart'] ) > 0 )
return get_post_meta( absint( $_REQUEST['add-to-cart'] ), '_ext_url_cust', true );
return $url;
}
Code goes in function.php file of your active child theme (or theme) or also in any plugin file.
This code is tested and works on WooCommerce version 3+
Use https://stackoverflow.com/a/44036965/3730754 instead.
You should try to use woocommerce_product_add_to_cart_url filter hook to change the add-to-cart link (here for grouped products), this way:
add_filter( 'woocommerce_product_add_to_cart_url', 'override_external_product_url', 10, 2 );
function override_external_product_url( $url, $product ){
if ( 'external' === $product->get_type() ) {
//Get product ID -- WooCommerce compatibility
if ( method_exists( $product, 'get_id' ) ) {
$product_id = $product->get_id();
} else {
$product_id = $product->id;
}
// custom add to cart url example
$url = home_url( "/product/?add-to-cart=$product_id");
}
return $url;
}
Code goes in function.php file of your active child theme (or theme) or also in any plugin file.
Update: But this will not add to cart this external product before redirecting to an external url even if it works displaying the add-to-cart url (as add-to-cart is ajax driven).
I fixed myself. For External products, to replace default "Buy This Product" with other generic text, add this functions into functions.php file into theme:
add_filter( 'woocommerce_product_add_to_cart_text' ,
'wpf_custom_add_cart_text_archive',11);
function wpf_custom_add_cart_text_archive() {
global $product;
$product_type = $product->product_type;
switch ( $product_type ) {
case 'external':
return __( 'Add to Cart', 'woocommerce' );
break;
case 'grouped':
return __( 'View products', 'woocommerce' );
break;
case 'simple':
return __( 'Add to cart', 'woocommerce' );
break;
case 'variable':
return __( 'Select options', 'woocommerce' );
break;
default:
return __( 'Read more', 'woocommerce' );
}
}
add_filter( 'woocommerce_product_single_add_to_cart_text',
'wpf_custom_add_cart_text',11);
and this one:
function wpf_custom_add_cart_text() {
return __( 'Add to Cart', 'woocommerce' );
}
to replace text everywhere.
In WooCommerce, I'm trying to find a way to disable the woocommerce checkout page for non logged users, OR when they try to checkout they get redirected to the log in page.
So they should log in first to be able to continue their checkout.
Is that possible?
Thanks
Is possible to redirect non logged customers that trying to access to checkout with this code:
add_action( 'template_redirect', 'checkout_redirect_non_logged_to_login_access');
function checkout_redirect_non_logged_to_login_access() {
// Here the conditions (woocommerce checkout page and unlogged user)
if( is_checkout() && !is_user_logged_in()){
// Redirecting to your custom login area
wp_redirect( get_permalink( get_option('woocommerce_myaccount_page_id') ) );
// always use exit after wp_redirect() function.
exit;
}
}
Then you can display a custom notice in cart page with a button linked to login area, to avoid customer frustration. Is better to warn customer before, than after.
// Displaying a message on cart page for non logged users (Optional)
add_action( 'woocommerce_before_cart', 'customer_redirected_displaying_message');
function customer_redirected_displaying_message() {
if( !is_user_logged_in() ){
// HERE Type your displayed message and text button
$message = __('To access checkout, you need first to be logged in', 'woocommerce');
$button_text = __('Login area', 'woocommerce');
$cart_link = get_permalink( get_option('woocommerce_myaccount_page_id') );
wc_add_notice( $message . '' . $button_text . '', 'notice' );
}
}
Code goes in function.php file of your active child theme (or theme) or also in any plugin file.
The code is tested and works.
I would like to bypass cart page and redirect user to checkout page for a few products.
I have created the add to cart link for the product
Product Name
And I have the code below
add_filter( 'woocommerce_add_to_cart_redirect', 'woo_redirect_checkout' );
function woo_redirect_checkout() {
global $woocommerce;
$desire_product = 1461;
//Get product ID
$product_id = (int) apply_filters( 'woocommerce_add_to_cart_product_id', $_POST['add-to-cart'] );
//Check if current product is subscription
if ( $product_id == $desire_product ){
$checkout_url = $woocommerce->cart->get_checkout_url();
return $checkout_url;
exit;
} else {
$cart_url = $woocommerce->cart->get_cart_url();
return $cart_url;
exit;
}
}
from How to skip cart page on woocomerce for certain products only?. But the url redirect me to homepage instead. Just wondering where is the issue,
I have unchecked the add to cart behaviour at woocommerce settings as well.
Thanks in advance.
I chose another approach and a WordPress hook instead of woocommerce. This is based on this answer: WooCommerce - Skip cart page redirecting to checkout page
This is that code:
function skip_cart_page_redirection_to_checkout() {
// desired product id redirection
$product_id = 1461;
$items_ids = array();
// Get all items IDs that are in cart
foreach( WC()->cart->get_cart() as $item ) {
$items_ids[] = $item['product_id'];
}
// If is cart page and the desired peoduct is in cart => redirect to checkout.
if( is_cart() && in_array($product_id, $items_ids) )
// WooCommerce 3.0 compatibility added
if ( version_compare( WC_VERSION, '2.7', '<' ) ) {
wp_redirect( WC()->cart->get_checkout_url() ); // Older than 3.0
} else {
wp_redirect( wc_get_checkout_url() ); // 3.0+ (Thanks to helgatheviking)
}
}
add_action('template_redirect', 'skip_cart_page_redirection_to_checkout');
This code goes in function.php file of your active child theme (or theme) or also in any plugin file.
The code is tested and fully functional.