Remove product dimensions from single product pages in Woocommerce - wordpress

Anyone knows how to hide the product dimensions from the additional tabs on Single Product page but still show the Weight value?
I search and see this filter but it hides both weight and dimensions.
add_filter( 'woocommerce_product_get_dimensions', '__return_false' );

To hide only dimensions (but not weight), there is 2 ways to make it work.
1) using hooks (here composite filter hooks):
Looking at the template that displays dimension in single products, you can see this line:
<?php if ( $display_dimensions && $product->has_dimensions() ) : ?>
Then if you look at WC_Product has_dimensions() method, you will see this line (where $this is the WC_Product Object instance):
return ( $this->get_length() || $this->get_height() || $this->get_width() ) && ! $this->get_virtual();
So when the length, the height and the with are empty (or false), the method returns false…
The following code that use composite hooks, will hide dimensions from "Additional information" tab in single product pages only:
add_filter( 'woocommerce_product_get_width', 'hide_single_product_dimentions', 25, 2 );
add_filter( 'woocommerce_product_get_height', 'hide_single_product_dimentions', 25, 2 );
add_filter( 'woocommerce_product_get_length', 'hide_single_product_dimentions', 25, 2 );
function hide_single_product_dimentions( $value, $product ){
// Only on single product pages
if( is_product() )
$value = '';
return $value;
}
Code goes in function.php file of your active child theme (or active theme). Tested and works.
To hide weight (just for info) use this composite hook code:
add_filter( 'woocommerce_product_get_weight', 'hide_single_product_weight', 25, 2 );
function hide_single_product_weight( $value, $product ){
// Only on single product pages
if( is_product() )
$value = '';
return $value;
}
2) Overriding Woocommerce templates via your active theme:
First read: Overriding Woocommerce template via the theme.
It explain how to copy the template to your theme before editing it.
Here the related template is single-product/product-attributes.php.
You will have to remove this block from the template code (from line 33 to line 38):
<?php if ( $display_dimensions && $product->has_dimensions() ) : ?>
<tr>
<th><?php _e( 'Dimensions', 'woocommerce' ) ?></th>
<td class="product_dimensions"><?php echo esc_html( wc_format_dimensions( $product->get_dimensions( false ) ) ); ?></td>
</tr>
<?php endif; ?>

You can also use the css property display:none if everything else fails.

Related

Hide add to cart button in WooCommerce but show stock status

I want to hide the add to cart button in WooCommerce but still show the stock status message... It's easy in CSS but i am looking for a solution in php.
For now i've been using this code below but it hide all the shop functionnality, I just need to hide the add to cart button and show the out of stock message if the product is out of stock.
// Remove add to cart on single product pages
add_action( 'woocommerce_single_product_summary', 'hide_single_product_prices', 1 );
function hide_single_product_prices(){
global $product;
if ( has_term( array('category1', 'category2', 'category3', 'category4'), 'product_cat', $product->get_id() ) ) :
//Hide add-to-cart button, quantity buttons (and attributes dorpdowns for variable products)
if( ! $product->is_type('variable') ){
remove_action('woocommerce_single_product_summary','woocommerce_template_single_add_to_cart', 30 );
} else {
remove_action( 'woocommerce_single_variation', 'woocommerce_single_variation_add_to_cart_button', 20 );
}
endif;
}```
So the issue is that when you remove the function 'woocommerce_template_single_add_to_cart' from 'woocommerce_single_product_summary' what you're actually doing is telling woocommerce not to load the template at all, located in: templates/single-product/add-to-cart. Which template loads there depends on the product type, but I'll assume simple for now.
If you look at that template, its not ACTUALLY just the add to cart button. It contains the call to wc_get_stock_html() that displays what you're looking for. So there isn't actually a good way just with removing a hook, to hide ONLY the button.
Instead what you'll have to do is one of two things: You can copy the add-to-cart/simple.php template into your theme, and edit it there with your logic. You'll likely want to wrap the button like this:
<?php if( ! your_custom_function( $product ) : ?>
<div class='buttons-container'>
<button type="submit" name="add-to-cart" value="<?php echo esc_attr( $product->get_id() ); ?>" class="single_add_to_cart_button btn btn--pink"><?php echo esc_html( $product->single_add_to_cart_text() ); ?></button>
</div>
<?php endif; ?>
The downside to that is that if you want this to work for all product types, you'd have to copy each template and do something similar.
So alternatively, what you could do is remove the action - as you have in your code above, and then Re-add the stock display wherever you'd like it. I would lean this direction for the reason above. Something like this:
remove_action( 'woocommerce_single_product_summary','woocommerce_template_single_add_to_cart', 30 );
add_action( 'woocommerce_single_product_summary', function(){
global $product;
if( $product->is_purchasable() ){
echo wc_get_stock_html( $product );
}
}, 30 );

Woocommerce Attributes Link

i would to modify the single product page in my shop site.
I have to remove links from attribute list in the Additional Information Tab.
I found this html is called in this page: /woocommerce/templates/single-product/product-attributes.php
In this part of code:
<td class="woocommerce-product-attributes-item__value"><?php echo wp_kses_post( $product_attribute['value'] ); ?></td>
Do you know if exist another argument instead “value” for example “slug” or “name”?
If not, how can modify the call to show only value without link?
Thank’s
Add the follows code snippet in your active theme's functions.php -
function filter_woocommerce_attribute_value( $value ) {
return preg_replace( '#<a.*?>([^>]*)</a>#i', '$1', $value );
}
add_filter( 'woocommerce_attribute', 'filter_woocommerce_attribute_value', 99 );

Woocommerce adding custom product count to products only in specific category and in specific page

I have caught onto some of the logic but battling with how to implement:
display my custom product count only on products in a specific product category
also display product count only on a specific custom WP page (which I used the product_category shortcode)
My code in functions.php is as follows and it does add the $top50_counter value before the product thumbnail but it is doing it site-wide, hence why I need to narrow it down as per my points above.
/* ADD NUMBERING TO TOP 50 LIST PRODUCTS */
add_action( 'woocommerce_before_shop_loop_item_title', 'custom_before_shop_loop_item', 5);
$top50_counter=1;
function custom_before_shop_loop_item() {
global $top50_counter;
echo '<h1>'.$top50_counter.'</h1>';
$top50_counter++;
}
I'm assuming I have to use the $terms = get_the_terms function in there somehow?
You need to use is_page and has_term conditionals. Try re-factoring the code to the following.
/* ADD NUMBERING TO TOP 50 LIST PRODUCTS */
add_action( 'woocommerce_before_shop_loop_item_title', 'custom_before_shop_loop_item', 5);
$top50_counter=1;
function custom_before_shop_loop_item() {
global $top50_counter;
/* Replace 42 with the actual page ID and "your-category" with the actual category slug */
if( ( is_page( 42 ) ) || ( has_term( 'your-category' , 'product_cat') ) ):
echo '<h1>'.$top50_counter.'</h1>';
$top50_counter++;
endif;
}
P.S: untested code.
Try this. Use corresponding category name and custom wp page slug in the following function.
function custom_before_shop_loop_item(){
global $post, $term, $top50_counter;
$id = $post->ID;
$taxonomy = 'product_cat';
$terms = get_the_terms( $id, $taxonomy );
if( ($terms[0]->name == 'Category Name') || ($post->post_name == 'custom-wp-page-slug') ){
echo '<h1>'.$top50_counter.'</h1>';
}
$top50_counter++;
}
Hope this helps.

How to change add-to-cart form?

Is there a way to change the WooCommerce add-to-cart form through functions.php?
The goal is to add a checkbox for an additional product. When the checkbox is checked this product will also be added to the cart after a click on the add to cart button.
I am looking for a solution which doesn't rely on javascript.
A better title would be "WooCommerce up-sells as checkboxes".
A lot of research and several strategies to tackle this problem lead me to a solution which I thought was not even possible in the beginning.
The solution is now exactly what I wanted. A non-JavaScript, no-template-override, but a simple and pure addition to functions.php. It works for simple and variable products (and probably with grouped and external products too).
It misses some nice features still. It won't work yet if an up-sell is a variable product. Quantity selection and limiting up-sells per item or order would be nice additions too. Based on the code below adding those features should not be a big deal anymore.
// create the checkbox form fields and add them before the cart button
add_action( 'woocommerce_before_add_to_cart_button', 'action_woocommerce_before_add_to_cart_form', 10, 0 );
function action_woocommerce_before_add_to_cart_form(){
global $woocommerce, $product;
// get the product up-sells
$upsells = $product->get_upsells();
// store the number of up-sells and pass it on to the add-to-cart hook
?>
<input type="hidden" name="upsells_size" value="<?php echo(sizeof($upsells)); ?>">
<div id="wb-upsell-div">
<?php
// iterate through all upsells and add an input field for each
$i = 1;
foreach( $upsells as $value ){
$product_id = $value;
?>
<input id="wb-upsell-checkboxes" type="checkbox" name="upsell_<?php echo($i) ?>" value="<?php echo($product_id); ?>"><?php echo( '' . get_the_title( $product_id ) . "". " ($" . get_post_meta( $product_id, '_regular_price', true) . ")"); ?><br>
<?php
$i++;
}
?>
</div>
<?php
}
// function to add all up-sells, where the checkbox have been checked, to the cart
add_action('woocommerce_add_to_cart', 'custom_add_to_cart', 10, 3);
function custom_add_to_cart() {
global $woocommerce;
// get the number of up-sells to iterate through
$upsell_size = $_POST['upsells_size'];
// iterate through up-sell fields
for ($i=1; $i<=$upsell_size; $i++){
// get the product id of the up-sell
$product_id = $_POST['upsell_' . $i];
$found = false;
//check if product already in cart
if ( sizeof( WC()->cart->get_cart() ) > 0 ) {
foreach ( WC()->cart->get_cart() as $cart_item_key => $values ) {
$_product = $values['data'];
if ( $_product->id == $product_id )
$found = true;
}
// if product not found, add it
if ( ! $found )
WC()->cart->add_to_cart( $product_id );
} else {
// if no products in cart, add it
WC()->cart->add_to_cart( $product_id );
}
}
}
And here is the CSS for formatting the <div>and the checkboxes. It goes into the style.css file:
#wb-upsell-div {
margin-top: 10px;
margin-bottom: 20px;
}
#wb-upsell-checkboxes{
}
So there's an actual answer to this question, you can add whatever you want inside the add to cart <form> using hooks. For example:
add_action( 'woocommerce_before_add_to_cart_button', 'so_34115452_add_input' );
function so_34115452_add_input(){
echo '<input type="checkbox" name="something"/>' . __( 'Some Checkbox', 'text-domain' );
}

Woocommerce product images replaced with a gallery plugin

First I would like to analyze my problem. Using Wordpress/Woocommerce I need to add videos beside images in the gallery of the product. Woocommerce does not support videos at all.
So, I thought to install an extra gallery plugin that supports both images and videos.
Now, I want to map a specific image/video gallery collection to a specific product. I want also to view this gallery collection in a new region that is not belong to the standard text fields like description or short description. Lets say above of the main product image. The php code that represent the gallery collection id=1 looks like below :
<?php echo do_shortcode('[wonderplugin_gallery id="1"]'); ?>
The problem is that I need the gallery collection id to be variable, something like this :
<?php echo do_shortcode('[wonderplugin_gallery id="X"]'); ?>
where X represnt the specific gallery collection. How the heck can I connect the gallery collection ID XXXX to my Product page XXXXX?
I have programming skills but I am new to the wordpress code logic.
Any other suggestions to my problem like plugins that may replace the default product gallery with better one ?
Regards,
I'd either use the product custom fields as Anand suggested, or create a metabox with the necessary input fields (or dropdowns depending on how you use the gallery plugin).
First I'd create a metabox, and in that metabox I'd pull the info from the plugin (gallery id's and names). Out of that you can create a dropdown. You should be able to select the id from that metabox for each product like you suggested. For instance something like this could work:
<?php
if ( ! function_exists( 'product_add_meta' ) ){
function product_add_meta(){
add_meta_box("gallery_dropdown", "Select Gallery", "product_gallery_meta_box", "product");
}
}
add_action("admin_init", "product_add_meta");
if ( ! function_exists( 'product_gallery_meta_box' ) ){
function product_gallery_meta_box( $post ){
$post_types = array('product'); //limit meta box to certain post types
global $post;
$product = get_product( $post->ID );
$values = get_post_custom( $post->ID );
$gallery = (isset($values['gallery'][0])) ? $values['gallery'][0] : '';
wp_nonce_field( 'my_meta_box_nonce', 'meta_box_nonce' );
?>
<p>
<select name="gallery" id="gallery">
//example of how the option should look
<option value="<?php echo $gallery_id; ?>" <?php selected( $gallery, $gallery_id ); ?>><?php echo $gallery_name; ?></option>
<?php
//pull options from plugin here and create an option dropdown with foreach
?>
</select>
</p>
<?php
}
}
if ( ! function_exists( 'product_gallery_save_meta_box' ) ){
function product_gallery_save_meta_box( $post_id ){
if( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ){
return;
}
if( !isset( $_POST['gallery'] ) || !wp_verify_nonce( $_POST['meta_box_nonce'], 'my_meta_box_nonce' ) ) {
return;
}
if( !current_user_can( 'edit_pages' ) ) {
return;
}
if( isset( $_POST['gallery'] ) ){
update_post_meta( $post_id, 'gallery', wp_kses( $_POST['gallery'] ,'') );
}
}
}
add_action( 'save_post', 'product_gallery_save_meta_box' );
If you put this in the functions.php, it should show a metabox called 'Select Gallery' with an empty dropdown on your woocommerce product page.
I haven't filled the options that you get from the plugin with which you create your galleries, but it shouldn't be too hard.
One way is to bind the product page id and gallery id. If you can change the id of a gallery then change it to match the id of the product page. Now you can create shortcode with any of these two examples.
// outside the loop use global ( uncomment appropriate statement )
// global $product;
// global $post;
do_shortcode( sprintf( '[wonderplugin_gallery id="%d"]', $product->id ) );
do_shortcode( sprintf( '[wonderplugin_gallery id="%d"]', $post->ID ) );
HERE is a link for plugin that reveals most of the IDs on admin pages.
Another is to create Custom Field ( post meta ) in edit product admin page ( named gallery_id for example ), and to save there id of the gallery to use. To create shortcode use get_post_meta() function that retrieves the saved post meta.
do_shortcode( sprintf( '[wonderplugin_gallery id="%d"]', get_post_meta( $post->ID, 'gallery_id', true ) ) );
To get the gallery id meta use $post->ID, $product->id, or get_the_ID() function, the latter only inside the loop.

Resources