I am quite new to woocommerce, here are my questions. I successfully expanded the default template for a cart now it does look like this:
Customized file path: my-theme/woocommerce/cart/cart.php
Majority of the changes did happen in the cart.php file: Here is the structure of the contents in the table with the last thing being the "product-remove" button.
Table content structure (for first three cells of the table):
<td class="">
<input type="checkbox" name="demoCheckBox" value="1" onClick="onClickCheckbox()">
<script>
function onClickCheckbox() {
return "<?php echo 'Hello World';?>"
}
</script>
</td>
<td class="product-thumbnail">
<?php
$thumbnail = apply_filters( 'woocommerce_cart_item_thumbnail', $_product->get_image(), $cart_item, $cart_item_key );
if ( ! $product_permalink ) {
ho $thumbnail; // PHPCS: XSS ok.
} else {
printf( '<a href="%s">%s</a>', esc_url( $product_permalink ), $thumbnail ); // PHPCS: XSS ok.
}
?>
</td>
</td>
<td class="product-name" data-title="<?php esc_attr_e( 'Product', 'woocommerce' ); ?>">
<?php
if ( ! $product_permalink ) {
echo wp_kses_post( $product_name . ' ' );
} else {
/**
* This filter is documented above.
*
* @since 2.1.0
*/
echo wp_kses_post( apply_filters( 'woocommerce_cart_item_name', sprintf( '<a href="%s">%s</a>', esc_url( $product_permalink ), $_product->get_name() ), $cart_item, $cart_item_key ) );
}
do_action( 'woocommerce_after_cart_item_name', $cart_item, $cart_item_key );
// Meta data.
echo wc_get_formatted_cart_item_data( $cart_item ); // PHPCS: XSS ok.
// Backorder notification.
if ( $_product->backorders_require_notification() && $_product->is_on_backorder( $cart_item['quantity'] ) ) {
echo wp_kses_post( apply_filters( 'woocommerce_cart_item_backorder_notification', '<p class="backorder_notification">' . esc_html__( 'Available on backorder', 'woocommerce' ) . '</p>', $product_id ) );
}
?>
</td>
Question: When someone selects the checkbox, I need to know the id of the item selected. How via selecting a checkbox trigger a checkbox onChange function, that is going to execute php code, that should add the product ID, to global array.
How should one modify the following code in order to reach that:
<td class="">
<input type="checkbox" name="demoCheckBox" value="1" onClick="onClickCheckbox()">
<script>
function onClickCheckbox () {
return "<?php
echo 'Hello World';
?>"
}
You can use WooCommerce Session variables, as Cart and Checkout already uses them.
Each time a checkbox is checked, the cart item key and the product ID pairs will be stored in a session variable (array). If the checkbox is unchecked, then the related data will be removed from the array (same thing, when a cart item is removed). When the order will be placed, the session variable will be removed.
First in cart.php
template use instead:
<td class="item-checkbox">
<?php $cart_item_cbs = (array) WC()->session->get('cart_items_cbs'); // Get session variable
printf('<input type="checkbox" name="item_cb" value="1" data-id="%s" data-key="%s"%s />',
$_product->get_id(), $cart_item_key, isset($cart_item_cbs[$cart_item_key]) ? ' checked' : '');
?>
</td>
Then you will add the following in functions.php file of your child theme:
// Javascript code for cart page only
add_action( 'woocommerce_after_cart', 'cart_item_checkbox_js' );
function cart_item_checkbox_js() {
?>
<script>
jQuery(function($) {
if (typeof wc_cart_params === 'undefined')
return false;
const cartForm = '.woocommerce-cart-form',
blockWhite = {message: null, overlayCSS: {background: '#fff', opacity: 0.6}};
$(cartForm).on('change', 'input[name=item_cb]', function(){
const checked = $(this).prop('checked') ? 'yes' : 'no';
$(cartForm).block(blockWhite);
$.ajax({
type: 'POST',
url: wc_cart_params.ajax_url,
data: {
'action' : 'cart_item_cb',
'product_id': $(this).data('id'),
'item_key' : $(this).data('key'),
'checked' : checked
},
success: function (response) {
$(cartForm).unblock();
console.log(response);
},
error: function (error) {
console.log(error);
}
});
})
});
</script>
<?php
}
// The PHP AJAX Receiver
add_action( 'wp_ajax_cart_item_cb', 'get_cart_item_cb_values' );
add_action('wp_ajax_nopriv_cart_item_cb', 'get_cart_item_cb_values');
function get_cart_item_cb_values() {
if ( isset($_POST['product_id']) && isset($_POST['item_key']) && isset($_POST['checked']) ) {
// Get session variable
$cart_item_cbs = (array) WC()->session->get('cart_items_cbs');
$product_id = intval($_POST['product_id']);
$item_key = esc_attr($_POST['item_key']);
if ( $_POST['checked'] == 'yes' ) {
$cart_item_cbs[$item_key] = $product_id; // Add to the array
$message = 'Product ID:' . $product_id . 'added to the array.';
} else {
if ( isset($cart_item_cbs[$item_key]) ) {
unset($cart_item_cbs[$item_key]); // Remove from the array
$message = 'Product ID:' . $product_id . 'removed from the array.';
}
}
if ( isset($message) ) {
WC()->session->set('cart_items_cbs', $cart_item_cbs); // save data
wp_die($message);
}
}
wp_die('Something went wrong.');
}
// When an item is removed from cart, remove it also from our session variable array
add_action( 'woocommerce_cart_item_removed', 'action_remove_cart_item' );
function action_remove_cart_item( $cart_item_key ) {
// Get session variable
$cart_item_cbs = (array) WC()->session->get('cart_items_cbs');
if ( isset($cart_item_cbs[$cart_item_key]) ) {
unset($cart_item_cbs[$cart_item_key]); // Remove from the array
WC()->session->set('cart_items_cbs', $cart_item_cbs); // Save data
}
}
// When order has been created remove the session variable
add_action( 'woocommerce_checkout_order_created', 'remove_custom_session_variable' );
function remove_custom_session_variable( $order) {
if( WC()->session->__isset('cart_items_cbs') ) {
WC()->session->__unset('cart_items_cbs');
}
}
To get the stored data array in PHP, you will use:
$cart_item_cbs = (array) WC()->session->get('cart_items_cbs');
Tested and works.
If you want to use this data after the order is placed, you will have to save it as custom metadata in the order.