Created
December 28, 2014 19:38
-
-
Save UltimateWoo/ef753b04dca4fd626afd to your computer and use it in GitHub Desktop.
WooCommerce Conditional Upsells
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
/* | |
Plugin Name: WooCommerce Conditional Upsells | |
Plugin URI: http://www.ultimatewoo.com/woocommerce-conditional-upsells | |
Description: This is a fork of another Gist that we have put into plugin format. Define a list of Upsell products and a list of Required products. Upsells will be shown as an option to add to cart when all required products are currently in cart. They'll also be removed when a required product is removed. | |
Version: 1.0 | |
Author: UltimateWoo | |
Author URI: http://www.ultimatewoo.com/ | |
Source: https://gist.github.com/EngageWP/9a3e30d9dc164ebce458 | |
*/ | |
/* | |
* Replace the following ID lists with your own | |
* Keep the IDs comma separated and within the single quotes | |
* | |
* REQUIRED_PRODUCT_IDS takes IDs of the products required to be in the cart | |
* before the Upsells can be added | |
* | |
* UPSELL_PRODUCT_IDS takes IDs of the products considered to be Upsells | |
*/ | |
define( 'REQUIRED_PRODUCT_IDS', '70, 37, 53, 19' ); | |
define( 'UPSELL_PRODUCT_IDS', '73, 50' ); | |
class WC_Conditional_Upsells { | |
private $required; | |
private $required_items_count; | |
private $upsells; | |
private $upsells_count; | |
private $cart; | |
private $message; | |
public function __construct() { | |
$this->cart = array(); // Cart contents | |
$this->required = explode( ',', trim( REQUIRED_PRODUCT_IDS ) ); // Products required to purchase upsell(s) | |
$this->upsells = explode( ',', trim( UPSELL_PRODUCT_IDS ) ); // Upsell(s) that can be purchased when all required products are in cart | |
$this->required_items_count = count( $this->required ); // Number of required products | |
$this->upsells_count = count( $this->upsells ); // Number of upsell products | |
add_action( 'init', array( $this, 'list_cart_items' ) ); | |
add_action( 'template_redirect', array( $this, 'empty_cart' ) ); | |
add_action( 'woocommerce_before_cart', array( $this, 'show_upsell' ) ); | |
} | |
/* | |
* Stores the cart items | |
*/ | |
public function list_cart_items() { | |
global $woocommerce; | |
$in_cart = $woocommerce->cart->get_cart(); | |
foreach ( $in_cart as $cart_item ) { | |
$cart_items[] = array( | |
'id' => $cart_item['product_id'], | |
'qty' => $cart_item['quantity'] | |
); | |
} | |
if ( !empty( $cart_items ) ) | |
$this->cart = $cart_items; | |
} | |
/* | |
* Show add-to-cart links for each Upsell NOT in the cart | |
* Displays upsells only when all requierd items are in cart | |
*/ | |
public function show_upsell() { | |
global $woocommerce; | |
$upsells = $this->upsells; | |
$cart_items = $this->cart; | |
$add_to_cart_url = trailingslashit( $woocommerce->cart->get_cart_url() ) . '?add-to-cart='; | |
$running_count = 0; | |
$required = $this->required; | |
//* Assemble cart product IDs into a simple array | |
foreach ( $cart_items as $key => $value ) { | |
$current_ids[] = $value['id']; | |
} | |
foreach ( $required as $id ) { | |
if ( in_array( $id, $current_ids ) ) { | |
$running_count++; | |
} | |
} | |
//* If all the required items are in the cart and there are upsells | |
if ( $running_count == $this->required_items_count && !empty( $upsells ) ) { | |
echo '<div class="upsell">'; | |
echo '<ul>'; | |
foreach ( $upsells as $upsell ) { | |
if ( !in_array( $upsell, $current_ids ) ) { | |
echo '<li><a href="' . $add_to_cart_url . $upsell . '">Add ' . get_the_title( $upsell ) . ' to cart</a></li>'; | |
} | |
} | |
echo '</ul>'; | |
echo '</div>'; | |
} | |
} | |
/* | |
* If all the required items are NOT in the cart and there are upsells in the cart | |
* then empty the cart and re-add the items minus the required item that was removed and the upsell(s) | |
*/ | |
public function empty_cart() { | |
global $woocommerce; | |
$upsells = $this->upsells; | |
$cart_items = $this->cart; | |
$required = $this->required; | |
//* Count to see if required products are in cart | |
$required_items_in_cart = 0; | |
//* Count to see if upsells are in cart | |
$upsells_in_cart = 0; | |
//* Assemble cart product IDs into a simple array | |
foreach ( $cart_items as $key => $value ) { | |
$current_ids[] = $value['id']; | |
} | |
foreach ( $required as $id ) { | |
if ( !empty( $current_ids ) && in_array( $id, $current_ids ) ) { | |
$required_items_in_cart++; | |
} | |
} | |
foreach ( $upsells as $upsell ) { | |
if ( !empty( $current_ids ) && in_array( $upsell, $current_ids ) ) { | |
$upsells_in_cart++; | |
} | |
} | |
if ( ( $required_items_in_cart < $this->required_items_count ) && $upsells_in_cart > 0 ) { | |
//* Get a fresh copy of the cart | |
$in_cart = $woocommerce->cart->get_cart(); | |
foreach ( $in_cart as $cart_item ) { | |
$current_ids_refreshed[] = array( | |
'id' => $cart_item['product_id'], | |
'qty' => $cart_item['quantity'] | |
); | |
} | |
//* Reset $cart_items to store the fresh cart array | |
$cart_items = $current_ids_refreshed; | |
//* Empty the cart | |
$woocommerce->cart->empty_cart(); | |
//* Loop through the new $cart_items | |
foreach ( $cart_items as $cart_item ) { | |
$id = $cart_item['id']; // ID of each item in cart | |
$qty = $cart_item['qty']; // Quantity of each item in cart | |
// re-add items the items that are not upsells | |
if ( !in_array( $id, $upsells ) ) { | |
$woocommerce->cart->add_to_cart( $id, $qty ); | |
} else { | |
$not_readded[] = $id; | |
} | |
} | |
$list_items = ''; | |
foreach ( $not_readded as $key => $value ) { | |
$list_items .= '<li><a href="' . get_permalink( $value ) . '">' . get_the_title( $value ) . '</a></li>'; | |
} | |
$message = '<p>The following items were removed from your cart because they are not available based on your cart\'s contents:</p>'; | |
$message .= '<ul>' . $list_items . '</ul>'; | |
$this->message = $message; | |
if ( !empty( $not_readded ) ) { | |
add_action( 'woocommerce_before_cart', array( $this, 'rv_wc_print_notices' ) ); | |
} | |
} | |
} | |
public function rv_wc_print_notices() { | |
wc_print_notice( $this->message, 'notice' ); | |
} | |
} | |
if ( !is_admin() ) | |
new WC_Conditional_Upsells; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment