Use Magento opConfig.reloadPrice() with jQuery and Custom options - php

I am trying to use the Magento reloadPrice() with jQuery to refresh the price. I have a configurable product with custom options. Without jQuery, the SELECT code for the option is :
<select id="select_281" class=" required-entry product-custom-option" title="" name="options[281]" onchange="opConfig.reloadPrice()">
<option value="0"></option>
<option rel="1" price="0" value="275"></option>
<option rel="2" price="0" value="276"></option>
</select>
With jQuery I remove the Prototype onchange code and try to calculate the price for my option (say $50) :
jQuery('#select_281').removeAttr('onchange').change(function(){
//Price of the option to add to a basic price of the conf product
price = 50;
optionsPrice.changePrice('opConfig', price);
optionsPrice.reload();
});
Price of the configurable product: $150.
Add an option (SELECT): we add $50.
The new price $200 is displayed in the product page, But not in the cart page : the cart page displays just $150 which is not correct.
Someone can help?
Best regards,
COM.

The reloadPrice() cant change any price serverside.
So we solved this issue by using 2 observers : checkout_cart_product_add_after observer to change the price the first time the product is added to the cart, and checkout_cart_update_items_after observer to change the price for each item in the cart (when user click the "Modify cart" button on cart page).
The code here tested for configurable products with 2 custom options numberOfColors and engravingType. For each couple numberOfColors/engravingType we have tierprices stored in special MySQL table, we may change price with a custom price. Each simple product has its tierPrices.
<code>//checkout_cart_product_add_after observer
public function modifyPrice(Varien_Event_Observer $observer)
{
$item = $observer->getQuoteItem();
$item = ( $item->getParentItem() ? $item->getParentItem() : $item );
$productType = $product->getTypeID();
$price = 100;//Unit price of product without engraving, 100 for example
//Unit price with engraving, depending of 2 custom options of configurable product
if($productType == 'configurable'){
//get custom options of config here
.
.
$engravingPrice = 1.2;//Get unit price with engraving from a special MySQL table
$finalUnitPrice = $price + $engravingPrice;//Final custom price
//Modify the price
$item->setCustomPrice($finalUnitPrice);
$item->setOriginalCustomPrice($finalUnitPrice);
$item->getProduct()->setIsSuperMode(true);
}
}
//checkout_cart_update_items_after observer
public function modifyCartItems(Varien_Event_Observer $observer)
{
foreach ($observer->getCart()->getQuote()->getAllVisibleItems() as $item ) {
if ($item->getParentItem()) {$item = $item->getParentItem();}
$productType = $product->getTypeID();
$productType = $product->getTypeID();
$price = 100;//Unit price of product without engraving
//Unit price with engraving, depending of 2 custom options of configurable product
if($productType == 'configurable'){
.
.
$engravingPrice = 1.2;//Get unit price with engraving from a special MySQL table
$finalUnitPrice = $price + $engravingPrice;//Final custom price
//Modify the price for the item
$item->setCustomPrice($finalUnitPrice);
$item->setOriginalCustomPrice($finalUnitPrice);
$item->getProduct()->setIsSuperMode(true);
}
}
}</code>
But.....one problem remains : on the cart page, when user clicks the link "Edit" to edit the product in product page so he can change quantity, ...and click the "Update cart" button, this update button does not read the checkout_cart_product_add_after to refresh price.
Dont't know how to force this "Update cart" action to process the code in checkout_cart_product_add_after observer? Is this code executed just the first time the product is added to the cart?
Thanks.
COM

Related

Load a custom attribute in the cart Magento

Hi for a Magento website i need to load a custom attribute in the shopping cart.
i use getmodel function to load the items. but i have no clue how i load the attribute. maybe i haven't configure the attribute right. i have enabled yes for enable on product listing. de attribute code is 'staffel_percentage'. it is just a regular string
also when i change the price per product it doesn't change the subtotal maybe this is because we already change the price for the product on the rest of the website?
maybe it is in the event? i use this event: controller_action_layout_render_before.
this is the code in observer i use for it
$cart = Mage::getModel('checkout/cart')->getQuote(); // Gets the collection of checkout
foreach ($cart->getAllItems() as $item) { // adds all items to $item and does the following code for each item
if ($item->getParentItem()) { // If items is part of a parent
$item = $item->getParentItem(); // Get parentItem;
}
//echo 'ID: '.$item->getProductId().'<br />';
$percentage = 80;// init first percentage
$quantity = $item->getQty(); //quantity
//$staffelstring = loadattribute//loads attribute
//gives the right percentage per quantity
//$staffelarray = explode(';', ^);
//foreach($staffelarray as $staffels){
//$stafel = explode(':', $staffels);
//if($quantity >= $stafel[0]){
//$percentage = $Stafel[1];
//}
//}
$currency = Mage::app()->getStore()->getCurrentCurrencyRate(); // Currencyrate that is used currently
$specialPrice = (($this->CalculatePrice($item) * $currency)* $percentage) / 100; //New prices we want to give the products
if ($specialPrice > 0) { // Check if price isnt lower then 0
$item->setCustomPrice($specialPrice); //Custom Price will have our new price
$item->setOriginalCustomPrice($specialPrice); //Original Custom price will have our new price, if there was a custom price before
$item->getProduct()->setIsSuperMode(true); //set custom prices against the quote item
}
}
You need to load the product right after your first if statement
$product = Mage::getModel('catalog/product')->load($item->getId()); // may be $item->getProductId() instead here
Then on the next line after that you can add some logging statements that will appear in var/log/system.log
Mage::log($product->getData()); // this will output all of the product data and attributes. You will see your custom attribute value here if it is set on this product.
If there is a value set for your product for your custom attribute then you can get it like this
$value = $product->getData('staffel_percentage');
As for the prices changing, not sure how you have the prices set up. You need to set a positive or negative number to add or subtract from the price in the fields found in the parent product configuration page in Catalog > Products > Your product > Associated Products.
See this image for what the section looks like.

Magento product attribute not showing in checkout, shows in cart

There are a few threads on here explaining how to get a product attribute in the cart or checkout. However, I just can't get it to work.
In the cart I can see the product attribute, but not in the checkout.
From what I've read, the checkout doesnt know about the product, so I need to load it. This would explain why Im not seeing it.
I've tried a lot of things, but I either don't get my shipping step to load in the cart, or it just doesn't display.
Any help would be great! Here is my code in a custom shipping module.
$cart = Mage::getSingleton('checkout/session');
//Order value by category
$gold = 0;
foreach ($cart->getQuote()->getAllItems() as $item) {
$itemPrice = $item->getPrice();
$qty = $item->getQty();
$metalType = Mage::getModel('catalog/product')->load($item->getProduct()->getId())->getAttributeText('metal');
if ($metalType == "Gold") {
//Apply some business logic
$gold = $itemPrice * $qty;
}
}
Magento get cart single item price incl. tax
Magento Product Attribute Get Value
In the afterLoad of the Mage_Sales_Model_Resource_Quote_Item_Collection object, a method is called to _assignProducts to each quote item. This method loads a product collection using the following code:
$productCollection = Mage::getModel('catalog/product')->getCollection()
->setStoreId($this->getStoreId())
->addIdFilter($this->_productIds)
->addAttributeToSelect(Mage::getSingleton('sales/quote_config')->getProductAttributes())
->addOptionsToResult()
->addStoreFilter()
->addUrlRewrite()
->addTierPriceData();
If you add the product attribute to the config.xml of your new module in the following way, it should be added as an attribute to be selected in the product collection.
<sales>
<quote>
<item>
<product_attributes>
<metal/>
</product_attributes>
</item>
</quote>
</sales>

Add products to sales quote in magento admin programmatically

I have customized search product grid as per client need(created new grid and disabled search grid) under sales order create page.
I have created new grid successfully after "Items Ordered" block.
When i click "Add product(s) To Item" button of my custom grid, I got product id and quantity of that selected product in my custom controller file.
I have tried to add those products to quote, Nothing has been changed. I dunno, how to add these selected products from my custom grid under "Items Ordered" block.
I have tried following code to add products to quote.
$customer_id = 26; // set this to the ID of the customer.
$customerObj = Mage::getModel('customer/customer')->load($customer_id);
$quoteObj=Mage::getModel('sales/quote')->assignCustomer($customerObj);
$quoteObj = $quoteObj->setStoreId(Mage::app()->getStore()->getId());
$productModel=Mage::getModel('catalog/product');
$productObj = $productModel->load($_id);
$quoteItem = Mage::getModel('sales/quote_item')->setProduct($productObj);
$quoteItem->setQty($qty);
$quoteObj->addItem($quoteItem);
$quoteObj->collectTotals();
$quoteObj->save();
I'm not sure, That block containing quote products or else
Have any idea, How to add selected products to "Items Ordered" block in sales order create page.
Eagerly awaiting for your response!
I have found the solution after long hunt.
Just passed products array to productGridAddSelected() method like below
order.productGridAddSelected(products);
products array must be like
products[product_id]= quantity;

How to override existing quantity already in cart?

Problem I am having here is that people go to a Product page, set a quantity on how much they want of that product and add to cart (which than takes them to the cart page). Client wants the ability to go back to the shop/product page if they want to make further changes to that product (honestly this is strange, since they can do this on the cart page, but whatever). But when people go to update the quantity on the product page, instead of updating the quantity, it adds to the existing quantity for that product.
How to get it to update the existing quantity when the quantity has been submitted more than once on the product page? Is there a woocommerce loop that I can take advantage of here?
Thanks guys, I have dug through the plugin and coded the solution below:
add_action('woocommerce_add_to_cart_handler', 'update_product_in_cart', 11, 2);
function update_product_in_cart($p, $q) {
global $woocommerce;
$cartItem = $woocommerce->cart->cart_contents;
$currentProductId = $q->id;
$wCart = $woocommerce->cart->get_cart();
// If cart already exists, and product exists, than remove product, and add the new product to it.
if ($wCart)
{
$cart_item_keys = array_keys($wCart);
foreach($cart_item_keys as $key)
{
foreach($cartItem as $item)
{
$productItemId = $item['product_id'];
if ($productItemId == $currentProductId)
{
// If you want to empty the entire cart...
// $woocommerce->cart->empty_cart();
// If you want to remove just the product from the cart...
$woocommerce->cart->set_quantity($key, 0);
}
}
}
}
// This adds the product to the cart...
return $q;
}
This gets added to functions.php, and basically, if the product id exists in the cart, it removes the product and the return of $q adds in the new product info.
Works a charm!

Programmatically add product to cart with price change

I want to add a product to cart programmatically. Also, I want to change the product price when added to cart.
Suppose, my product's price is $100. I wanted to change it to $90 when added to cart.
I added product to cart. However, I am unable to change the product price.
Is it possible?
Here is the code to add product to cart:-
$cart = Mage::getSingleton('checkout/cart');
try {
$cart->addProduct($product, array('qty' => 1));
$cart->save();
}
catch (Exception $ex) {
echo $ex->getMessage();
}
After digging a bit into Magento's core code, I found that you need to use $item->getProduct()->setIsSuperMode(true) in order to make $item->setCustomPrice() and $item->setOriginalPrice() work.
Here is some sample code you can use within an Observer that listens for the checkout_cart_product_add_after or checkout_cart_update_items_after events. The code is logically the same except checkout_cart_product_add_after is called for only one item and checkout_cart_update_items_after is called for all items in the cart. This code is separated/duplicated into 2 methods only as an example.
Event: checkout_cart_product_add_after
/**
* #param Varien_Event_Observer $observer
*/
public function applyDiscount(Varien_Event_Observer $observer)
{
/* #var $item Mage_Sales_Model_Quote_Item */
$item = $observer->getQuoteItem();
if ($item->getParentItem()) {
$item = $item->getParentItem();
}
// Discounted 25% off
$percentDiscount = 0.25;
// This makes sure the discount isn't applied over and over when refreshing
$specialPrice = $item->getOriginalPrice() - ($item->getOriginalPrice() * $percentDiscount);
// Make sure we don't have a negative
if ($specialPrice > 0) {
$item->setCustomPrice($specialPrice);
$item->setOriginalCustomPrice($specialPrice);
$item->getProduct()->setIsSuperMode(true);
}
}
Event: checkout_cart_update_items_after
/**
* #param Varien_Event_Observer $observer
*/
public function applyDiscounts(Varien_Event_Observer $observer)
{
foreach ($observer->getCart()->getQuote()->getAllVisibleItems() as $item /* #var $item Mage_Sales_Model_Quote_Item */) {
if ($item->getParentItem()) {
$item = $item->getParentItem();
}
// Discounted 25% off
$percentDiscount = 0.25;
// This makes sure the discount isn't applied over and over when refreshing
$specialPrice = $item->getOriginalPrice() - ($item->getOriginalPrice() * $percentDiscount);
// Make sure we don't have a negative
if ($specialPrice > 0) {
$item->setCustomPrice($specialPrice);
$item->setOriginalCustomPrice($specialPrice);
$item->getProduct()->setIsSuperMode(true);
}
}
}
Magento have changed the way the prices are calculated in the cart which makes it very difficult to do this in v1.4 onwards. If you do set the price using an Observer or other device, it will almost certainly be overwritten back to the catalog price.
Effectively, you need to use Shopping Cart rules to implement this.
It is possible to set a customer specific price of a quote item. Hence, something like this should do it:
$quoteItem = $quote->addProduct($product, $qty);
$quoteItem->setCustomPrice($price);
// we need this since Magento 1.4
$quoteItem->setOriginalCustomPrice($price);
$quote->save();
Hope this helps...
Jonathan's answer is likely the best for most situations. But some customers might not like how shopping cart discounts are displayed in the cart. I recently did a project (with Magento 1.3.3) where the customer didn't like how the each line item still showed the full price as well as the subtotal, with a Discount line below the subtotal - he wanted to see the price of each item discounted, and the subtotal show the discounted price as well. He really didn't like having the Discount line after the Subtotal line.
Anyway, if you find yourself in the same boat, one approach is to override the getCalculationPrice() and getBaseCalculationPrice() methods in Mage_Sales_Model_Quote_Address_Item and Mage_Sales_Model_Quote_Item. I know that it isn't always pretty to override, much better to use events, but in this case I couldn't get events to work seamlessly on both the frontend and backend. Not sure if this approach will work in Magento 1.4+.
If I have to share my solution that I made on the base of Simon then I have managed to rewrite model class save function of quote.
public function save()
{
$this->getQuote()->getBillingAddress();
$this->getQuote()->getShippingAddress()->setCollectShippingRates(true);
$this->getQuote()->collectTotals();
//$this->getQuote()->save();
foreach($this->getQuote()->getAllItems() as $item) {
$productId = $item->getProductId();
$product = Mage::getModel('catalog/product')->load($productId);
if($product->getAttributeText('is_dummy') == 'Yes') {
$price = 2;
$item->setCustomPrice($price);
// we need this since Magento 1.4
$item->setOriginalCustomPrice($price);
}
}
$this->getQuote()->save();
$this->getCheckoutSession()->setQuoteId($this->getQuote()->getId());
/**
* Cart save usually called after chenges with cart items.
*/
Mage::dispatchEvent('checkout_cart_save_after', array('cart'=>$this));
return $this;
}
I had the same issue and i am not a developer. What i did was added a new price attribute in magento backend called "site price". On the product page this showed the higher price $100. the actual price of the item was $90. so when the shopper adds it to cart they will see the actual price of the item, but on the product page they see the custom attribute price of $100
if all your prices on the product page are a set % higher then the real price just multiply your product price by the 1+percent. So if you want to add 10% to all your prices do price*1.1
This will display your price as 10% higher but when the shopper adds to cart they will see the real price.

Categories