I was wondering how to get all the items in my cart as an array.
I need this because I have to use array_intersect, this way I can compare them.
I haven't found anything about this on the internet.
You can access the cart contents through the WC()->cart object, like so:
<?php
$cart_contents = WC()->cart->cart_contents;
$cart_item_names = array();
foreach($cart_contents as $item) {
array_push($cart_item_names, $item['data']->post->post_title);
}
Related
I've been getting great help here during the year, regarding a woocommerce issue where I needed an automatic fee added based on total cart height in this thread and then later updated with width in this thread.
Now my only issue is that I need to exclude some shipping classes from the function, as they are shipped differently and don't need a Bulky fee added.
I've been playing around with the answer to "Add a fee based on cart items dimensions in Woocommerce", trying to add a class variable to it:
// Initializing variables
$total_height = 0;
$class = 1390,1392,1389;
$apply_fee = false;
But it instantly breaks the website. I've been searching on stackoverflow.com and Google for a way to do this but no luck, and I'm still not qualified enough for that type of advanced editing of code.
Appreciate any help I can get.
You can't have a list of ids like that with just commas between them. To fix this put the ids in an array. Within the foreach loop, check the shipping class id of the product, and if it's in the array exclude it.
$exclClasses = array(1390,1392,1389);
// Checking item with
if ( $cart_item['data']->get_width() > $width_threshold ) {
$apply_fee = true;
}
// make sure product isn't in excluded shipping classes
if (in_array( $cart_item['data']->get_shipping_class_id(), $exclClasses))
{
$apply_fee = false;
}
or to use 1 statement instead of 2
if ( $cart_item['data']->get_width() > $width_threshold && !in_array( $cart_item['data']->get_shipping_class_id(), $exclClasses)) {
$apply_fee = true;
}
I'm more or less a total newbie to php. My goal is to get the names of items from the logged in user's cart and dynamically populate a GravityForms template with the information. I've successfully managed to do that with the code below, but there are three things that I'm failing to do. 1: I only want to populate the form with all items of a certain variation. 2: the echo function will list all of the item names, but not inside the relevant field, and the return function will populate the field, but only with the first item name. 3: I'd like to have the output items listed with some form of separator in between each item name. Here's what I have so far:
<?php
add_filter( 'gform_field_value_beat_names', 'beat_names_function' );
function beat_names_function( $value ) {
global $woocommerce;
$items = $woocommerce->cart->get_cart();
foreach ($items as $item) {
$product_variation_id = $item['variation_id'];
$license_id = new WC_Product($product_variation_id);
$license_string = $license_id->get_formatted_name();
$beat_id = $item['data']->post;
$beat_name = $beat_id->post_title;
if (strpos($license_string, 'basic') !== false) {
echo $beat_name;
}
}
}?>
As you can see, I'm attempting to use strpos to isolate the particular item variation I want to target, using a certain word found in the name of the variation option, being "basic". I'm sure there's a more secure way of doing that, but it works for now. The problem lies with the return function I set up inside the conditional strpos statement, being that it will still just return the entire list of cart items, as opposed to only the items that I'm trying to isolate with the strpos conditional.
The ultimate goal is to create a license agreement that is dynamically populated with the relevant information, including the names of the items being licensed. The item variations are different license options that I have available for the products in my store. The purpose of the above code is to filter cart items by license type so that the wrong item names don't get listed on the wrong license agreement at checkout.
Any tips would be appreciated
Figured it out after some more tinkering. I broke it down step by step to help anyone as clueless as I am
add_filter( 'gform_field_value_basic_beat_names', 'basic_beat_names_function' );
function basic_beat_names_function( $value ) {
global $woocommerce;
$items = $woocommerce->cart->get_cart();
// the item names you want will be stored in this array
$license_check = array();
// Loop through cart items
foreach ($items as $item) {
// get the id number of each product variation in the cart. this won't work for "simple" products
$product_variation_id = $item['variation_id'];
// translate that id number into a string containing the name of the product, and the options applied to the product
$license_id = new WC_Product($product_variation_id);
$license_string = $license_id->get_formatted_name();
// check to see if the word "basic" is found anywhere in that string. "basic" is contained in the name of the product option being targeted
if (strpos($license_string, 'basic') !== false) {
// if the above condition is met, fetch the name of any products in the cart that have that option applied. The product name will be fetched from the title of the product's page
$beat_id = $item['data']->post;
$beat_name = $beat_id->post_title;
// store the retrieved product names in the $license_check array
$license_check [] = $beat_name;
}
}
// pull the stored product names from the $license_check array, and format them using implode and concatenation, then return the final result to the form field
return "\"" . implode("\", \"", $license_check) . "\"";
}
As a warning, the strpos method is a little hacky. It'll only work properly if your string is specific enough to target ONLY the option you're looking for.
As an example, here's the format for the product variation string being fed into the strpos function:
item-name-option-one-name-option-two-name – variation #xxx of item page title
So, if you want to filter items ONLY by option one, your safest bet would be to write the strpos function like so:
if (strpos($license_string, 'option-one-name') !== false) {
//do something
}
When all is said and done, the final result should look like: "item1", "item2", "item3", etc.
Then, to do the same with any other option, and output the result in a different field, or separate form altogether, I'll just duplicate this code, and replace any mention of the word "basic" with some different unique string contained in the other option. Don't forget to configure the gravity forms field as necessary too.
I'm trying to select the chosen_shipping_method price in woocommerce using this code:
$packages = WC()->shipping->get_packages();
foreach ($packages as $i => $package) {
$chosen_method = isset(WC()->session->chosen_shipping_methods[$i]) ? WC()->session->chosen_shipping_methods[$i] : '';
}
echo $chosen_method;
the code works, but it prints the ID, and i cannot figure out how to make it print out the price.
Here's package structure:
What i get with my code is table_rate_shipping_shipping_self_install, but what i need is the cost for the selected element, and not the id.
i tried to change the code like this:
foreach ($packages as $i => $package['rates']) {
$chosen_method = isset(WC()->session->chosen_shipping_methods[$i]) ? WC()->session->chosen_shipping_methods[$i] : '';
}
But it printed out the id, same as before.
Any ideas? sorry i'm a bit new to php.
Thanks in advance
Did you try this inside your foreach loop?
$rate = $package['rates'][$chosen_method]->cost;
If yo need to get price of shipping method that was chosen by user and stored in session, you should try this:
$chosen_shipping_method_price = WC()->session->get('cart_totals')['shipping_total'];
Hi I'm trying to get a product attribute admin value or id (since it's multilanguage) from the cart items. I've tried many versions of code like this one:
$session = Mage::getSingleton('checkout/session');
foreach ($session->getQuote()->getAllItems() as $item) {
$_product = Mage::getModel('catalog/product')->load($item->getId());
$attribute = $_product->getAttribute('producttype');
}
But I only ever get false or null. Also how can I be sure to not get the store specific language value, but the attributes admin value/id? Maybe there's an even better way to read out the item attributes directly from the quote items without having to load the product first? Thanks in advance!
Solved with:
$session = Mage::getSingleton('checkout/session');
foreach ($session->getQuote()->getAllVisibleItems() as $_item)
{
$_product = Mage::getModel('catalog/product')->load($_item->getProductId());
$attributeId = $_product->getProducttype();
}
and comparing by value ID instead of text.
If you need to get the product's value for a specific shop, while the items in the quote belong to a different store view, you can do the folowing:
$_product = Mage::getModel('catalog/product')
->setStoreId($adminStoreId)
->load($item->getId());
$value = $_product->getData('producttype');
I've set an observer for sales_quote_add_item in order to clear the cart whenever a certain product is going to be added (it's only supposed to be ordered alone).
I'm just not sure on how to get the product ID of the product that is about to get added. With some trial & error I've come up with this:
$tmp = $observer->getEvent()->getQuoteItem()->getData();
echo $tmp['product_id'];
Which seems to be quite an ugly solution. I'm sure there is some shortcut or proper function to call for this, any ideas?
Your solution is good enough
$productId = $observer->getEvent()->getQuoteItem()->getProductId();
You may load product after if is needed
$product = Mage::getModel('catalog/product')->load($productId);
Use the following code to get product id of quote item data
$cart = Mage::getModel('checkout/cart')->getQuote();
foreach ($cart->getAllItems() as $item)
{
$productId = $item->getProduct()->getId();
}
Hope this helps to you.