I need configure Product price range like
For the product name: $140 - 310 i use below code
if(Mage::getSingleton('customer/session')->isLoggedIn())
{
// Get group Id
$groupId = Mage::getSingleton('customer/session')->getCustomerGroupId();
}
else
{
$groupId = 0;
}
$db = Mage::getSingleton('core/resource')->getConnection('core_write');
$result = $db->query('SELECT price ,final_price, min_price, max_price, tier_price, group_price FROM catalog_product_index_price WHERE entity_id='.$_product->getId().' AND customer_group_id ='.$groupId.' ORDER BY customer_group_id ASC LIMIT 1');
$rows = $result->fetch();
i also need a regular price range for the configure product. i also think that my range after product name my be wrong because in Your Price have a price $135 so how can i get minimum value and maximum special price and also in regular price?
How can i get that?
Thanks and Regards
This answer to a similar question on the Magento StackExchange is a good basis to work from. Using that, here's a solution to this problem that takes into account the potential for configurable products having more than one price-changing attribute.
I've written it as function that takes a configurable product id, and returns a string of min to max price. It should be pretty clear how to work it into the context that you need.
function getPriceRange($productId) {
$max = '';
$min = '';
$pricesByAttributeValues = array();
$product = Mage::getModel('catalog/product')->load($productId);
$attributes = $product->getTypeInstance(true)->getConfigurableAttributes($product);
$basePrice = $product->getFinalPrice();
foreach ($attributes as $attribute){
$prices = $attribute->getPrices();
foreach ($prices as $price){
if ($price['is_percent']){ //if the price is specified in percents
$pricesByAttributeValues[$price['value_index']] = (float)$price['pricing_value'] * $basePrice / 100;
}
else { //if the price is absolute value
$pricesByAttributeValues[$price['value_index']] = (float)$price['pricing_value'];
}
}
}
$simple = $product->getTypeInstance()->getUsedProducts();
foreach ($simple as $sProduct){
$totalPrice = $basePrice;
foreach ($attributes as $attribute){
$value = $sProduct->getData($attribute->getProductAttribute()->getAttributeCode());
if (isset($pricesByAttributeValues[$value])){
$totalPrice += $pricesByAttributeValues[$value];
}
}
if(!$max || $totalPrice > $max)
$max = $totalPrice;
if(!$min || $totalPrice < $min)
$min = $totalPrice;
}
return "$min - $max";
}
can u try to get all the child products of that configurable product first, then get the price of each child product, and compare them, find the highest and the lowest.
//load configurable product
$product = Mage::getModel('catalog/product')->load(some_id);
//load all children
$childProducts = Mage::getModel('catalog/product_type_configurable')
->getUsedProducts(null,$product);
foreach($childProducts as $child){
$_child = Mage::getModel('catalog/product')->load($child->getId());
$childPrice = $_child->getPrice();
//compare the $childPrice
}
You can use something like this
$prices = array();
$associated = $_product->getTypeInstance(true)->getAssociatedProductCollection($_product)
->addAttributeToSelect('special_price');
foreach ($associated as $assoc) {
$prices[] = $assoc->getSpecialPrice();
}
// calculate min max price here
if (count($prices)) {
$min_price = min($prices);
$max_price = max($prices);
} else {
$min_price = 0;
$max_price = 0;
}
Maybe not perfect solution, but it works
Try using the $product->getMinPrice() and $product->getMaxPrice()
Take a look at app/code/core/Mage/Catalog/Model/Resource/Product/Collection.php
Related
Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 3 years ago.
Improve this question
Im not sure how to
Modify/Add the code with the foreach loop below to only show the books within
the price range selected. I want the under $20 books to only show under the $20 section. The same for under $50 and under $100.
<?php
$books = array ();
$books[0] = array();
$books[0]['ISBN'] = "1234567890";
$books[0]['Title'] = "PHP for Dummies";
$books[0]['Price'] = "35.99";
$books[1] = array();
$books[1]['ISBN'] = "2345678901";
$books[1]['Title'] = "SQL for Dummies";
$books[1]['Price'] = "78.49";
$books[2] = array();
$books[2]['ISBN'] = "3456789012";
$books[2]['Title'] = "Economics for Dummies";
$books[2]['Price'] = "44.99";
$books[3] = array();
$books[3]['ISBN'] = "4567890123";
$books[3]['Title'] = "History of Dummies";
$books[3]['Price'] = "62.49";
$books[4] = array();
$books[4]['ISBN'] = "5678901234";
$books[4]['Title'] = "Marketing for Dummies";
$books[4]['Price'] = "52.49";
$books[5] = array();
$books[5]['ISBN'] = "6789012345";
$books[5]['Title'] = "Gardening for Dummies";
$books[5]['Price'] = "19.99";
// function to generate the book list
function listBook($maximum){
global $books; // make $books array available inside the function
echo "<table>\n
<caption>Under $maximum</caption>
<tr><th>Title</th><th>ISBN</th><th>Price</th></tr>\n
";
//###############################
// Try the script in its current form. You will find that no matter what price range is chosen, all books are presented all the time. It's not what we want.
// Modify/Add to the code with the foreach loop below to only show the books within the price range selected.
//###############################
foreach ($books as $book) {
$title = $book['Title'];
$ISBN = $book['ISBN'];
$price = $book['Price'];
echo "<tr><td>$title</td> <td>$ISBN</td> <td>$price</td></tr>\n";
}
echo "</table>";
}
With a simple if:
function listBook($maximum) {
global $books; // make $books array available inside the function
echo "<table>\n
<caption>Under $maximum</caption>
<tr><th>Title</th><th>ISBN</th><th>Price</th></tr>\n
";
//###############################
// Try the script in its current form. You will find that no matter what price range is chosen, all books are presented all the time. It's not what we want.
// Modify/Add to the code with the foreach loop below to only show the books within the price range selected.
//###############################
foreach ($books as $book) {
$title = $book['Title'];
$ISBN = $book['ISBN'];
$price = $book['Price'];
if ($price <= $maximum) {
echo "<tr><td>$title</td> <td>$ISBN</td> <td>$price</td></tr>\n";
}
}
echo "</table>";
}
The simplest way to do this to wrap the echo statement that outputs the HTML in an IF statement. Say you have a variable that holds the selected price, then you would do this:
$selectedPrice = 20;
if($price <= $selectedPrice) {
echo "<tr><td>$title</td> <td>$ISBN</td> <td>$price</td></tr>\n";
}
or, for a range between a high and low price
$highPrice = 100;
$lowPrice = 50
if($lowPrice <= $price && $price <= $selectedPrice) {
echo "<tr><td>$title</td> <td>$ISBN</td> <td>$price</td></tr>\n";
}
Your example doesn't include how the price is collected however, although a likely mechanism would be either a select drop down or a couple of input boxes.
Hope that helps.
Your foreach loop:
foreach ($books as $book) {
$title = $book['Title'];
$ISBN = $book['ISBN'];
$price = $book['Price'];
if ((int) $price > round($maximum, 2))
continue;
echo "<tr><td>$title</td> <td>$ISBN</td> <td>$price</td></tr>\n";
}
echo "</table>";
}
Im not pro in programming
i have a foreach loop that gets the values from a form calculating the total and subtotal
public function salecal()
{
if ($this->input->post())
{
$i = 0;
$data = array();
$subtotal = 0;
foreach($this->input->post('pname') as $d){
$data[] = array(
'pid' => $this->input->post('pid[]')[$i],
'pname' => $this->input->post('pname[]')[$i],
'quantity' => $this->input->post('qty[]')[$i],
);
foreach ($data as $entry) {
$qty = $entry['quantity'];
$pid = $entry['pid'];
$proname = $entry ['pname'];
}
$value = $this->insert_model->get_price($pid); ///pasing the product id to get the the price from database
foreach ($value->result() as $row)
{
$price = $row->price;
}
$total = $price * $qty; ////Total calculation
$subtotal = $subtotal + $total;/////Sub Total Calculation
$i++;
}
$result = compact("proname", "price", "qty", "total","i", "subtotal");
$this->load->view("bill", $result);
}
}
when i run this code im getting only the finally entered products details but the subtotal is correct
but the data inserting form is dynamic
what i want as result is
user will insert several or one item with quantity
data should be calculated and pass the calculated values to view
but currently im getting it only for the last inserted data please help me how to catch all the datas that user insert to form and how to pass them to view
Because your overwriting the variables consequently so it's passing last overwrite value only . you should make array for each one
This how you need to send all data to view using array
<?php
public function salecal()
{
if ($this->input->post())
{
$i = 0;
$data = array();
$subtotal = 0;
$final_array_collection =array();
foreach($this->input->post('pname') as $d){
$total =0; //reset the total to zero for each product
$pid = $this->input->post('pid[]')[$i];
$pname = $this->input->post('pname[]')[$i];
$quantity = $this->input->post('qty[]')[$i];
$value = $this->insert_model->get_price($pid); ///pasing the product id to get the the price from database
foreach ($value->result() as $row)
{
$price = $row->price;
}
$total = $price * $quantity; ////Total calculation
$subtotal = $subtotal + $total;/////Sub Total Calculation
$final_array_collection[] =array("proname"=>$pname, "price"=>$price, "qty"=>$quantity, "total"=>$total,"i"=>$i, "subtotal"=> $subtotal);
$i++;
}
$result = compact("final_array_collection");
$this->load->view("bill", $result);
}
}
?>
I have a data array that totals all the items in the cart for all the products as one number.
I've been trying to figure out a way to get a data array count() all the different totals of all the different items in the cart and have them presented in my data layer comma separated. I hope that makes sense.
if ($order->getId()) {
$items = $order->getAllVisibleItems();
$itemIds = array();
$itemNames = array();
$itemPrices = array();
$itemMargins = array();
$itemTypes = array();
$itemGenders = array();
$itemSports = array();
$itemCategoryIds = array();
$itemCategoryNames = array();
/** #var Mage_Sales_Model_Quote_Item $item */
foreach ($items as $item) {
// Get the parent item - it is NOT included in the quote due to
// customizations made by the OrganicInternet module for simple
// product pricing. So I had to come up with another way to get it.
$options = $item->getProductOptions();
$parent = $item->getProduct();
if (array_key_exists('info_buyRequest', $options)) {
if (array_key_exists('cpid', $options['info_buyRequest'])) {
$parentId = $options['info_buyRequest']['cpid'];
$parent = Mage::getModel('catalog/product')->getCollection()
->addAttributeToSelect('name')
->addAttributeToSelect('season')
->addAttributeToSelect('gender')
->addAttributeToSelect('sport')
->addAttributeToFilter('entity_id', $parentId)
->getFirstItem();
}
}
$itemIds[] = $item->getSku();
$itemNames[] = $parent->getName();
$itemPrices[] = $item->getBasePrice() ?: 0;
$itemMargins[] = $this->_calculateMargin($parent, null, $item);
$itemTypes[] = $parent->getAttributeText('season');
$itemGenders[] = $parent->getAttributeText('gender');
$itemSports[] = $parent->getAttributeText('sport') ?: 'Other';
$categories = $this->_getAllCategoryIdsAndNames($item->getProduct());
$itemCategoryIds[] = $categories['id'];
$itemCategoryNames[] = $categories['name'];
}
// # Products
$data['u1'] = count($items);
The above will return:
dataLayer = [{"visitorLoginState":"Logged out","visitorType":"NOT LOGGED IN","visitorLifetimeValue":0,"visitorExistingCustomer":"No","u1":2,"u2":["889623392590","889623135517"]
It shows a total of 2 products for the U1 variable and the two sku's for the u2 variable in the data array.
If i have multiple products for the first sku i want it to seperate the quantities. ie.. "u1":1,1,3
Would i use array_sumor some type of multi-dimensional array to acquire my needs?
If i have multiple products for the first sku i want it to seperate
the quantities. ie.. "u1":1,1,3
It is not exactly clear to me is the relationship between sku and product and which variables in your array refer to which. I make the following presumptions:
1) A product is equivalent to one $items element
2) A sku is a unique $itemIds[] value
I use the array key as a simple way to keep track for each unique sku and the value to keep track of the product count for the sku.
if ($order->getId()) {
$items = $order->getAllVisibleItems();
$itemIds = array();
$itemNames = array();
$itemPrices = array();
$itemMargins = array();
$itemTypes = array();
$itemGenders = array();
$itemSports = array();
$itemCategoryIds = array();
$itemCategoryNames = array();
// My addition (UPDATE: fixed to the correct variable name)
$uniqueItemIds = array();
/** #var Mage_Sales_Model_Quote_Item $item */
foreach ($items as $item) {
// Get the parent item - it is NOT included in the quote due to
// customizations made by the OrganicInternet module for simple
// product pricing. So I had to come up with another way to get it.
$options = $item->getProductOptions();
$parent = $item->getProduct();
if (array_key_exists('info_buyRequest', $options)) {
if (array_key_exists('cpid', $options['info_buyRequest'])) {
$parentId = $options['info_buyRequest']['cpid'];
$parent = Mage::getModel('catalog/product')->getCollection()
->addAttributeToSelect('name')
->addAttributeToSelect('season')
->addAttributeToSelect('gender')
->addAttributeToSelect('sport')
->addAttributeToFilter('entity_id', $parentId)
->getFirstItem();
}
}
// *******************************
// My addition / changes
$sku = $item->getSku();
$itemIds[] = $sku; // I don't use this but keep $itemIds for compatibility
// use the array key to track counts for each sku
if (!isset($uniqueItemIds[$sku])){
$uniqueItemIds[$sku] = 1; // UPDATE: fixed to start at 1 not 0
} else {
$uniqueItemIds[$sku]++;
}
// *******************************
$itemNames[] = $parent->getName();
$itemPrices[] = $item->getBasePrice() ?: 0;
$itemMargins[] = $this->_calculateMargin($parent, null, $item);
$itemTypes[] = $parent->getAttributeText('season');
$itemGenders[] = $parent->getAttributeText('gender');
$itemSports[] = $parent->getAttributeText('sport') ?: 'Other';
$categories = $this->_getAllCategoryIdsAndNames($item->getProduct());
$itemCategoryIds[] = $categories['id'];
$itemCategoryNames[] = $categories['name'];
}
// show # Products
// "u1":1,1,3 NOTE: this should be a string => "u1":"1,1,3"
$data['u1'] = "";
foreach ($uniqueItemIds as $key => $val)
// show unique skus in u2
$data['u2'][] = $key;
// show counts for each sku in u1
if (strlen($data['u1'] == 0)){
$data['u1'] = (string)$value;
} else {
$data['u1'] .= ("," . $value);
}
}
How about something like...
if ($order->getId()) {
.....
.....
.....
/** #var Mage_Sales_Model_Quote_Item $item */
$sku_based_array = array();
foreach ($items as $item) {
......
......
......
$categories = $this->_getAllCategoryIdsAndNames($item->getProduct());
$itemCategoryIds[] = $categories['id'];
$itemCategoryNames[] = $categories['name'];
if (isset($sku_based_array[$item->getSku()])) {
$sku_based_array[$item->getSku()] = $sku_based_array[$item->getSku()]++;
} else {
$sku_based_array[$item->getSku()] = 1;
}
}
// # Products
$data['u1'] = array_values($sku_based_array);
Looking at the code it looks like it will only every return one product as the $parent variable is overwritten to get a first item. I have added a new variable named $itemProductCounts this will be returned to the output $data array as itemProductCounts I suspect this will always equal one.
<?php
if ($order->getId()) {
$items = $order->getAllVisibleItems();
$itemIds = array();
$itemNames = array();
$itemPrices = array();
$itemMargins = array();
$itemTypes = array();
$itemGenders = array();
$itemSports = array();
$itemCategoryIds = array();
$itemCategoryNames = array();
$itemProductCounts = array();
/** #var Mage_Sales_Model_Quote_Item $item */
foreach ($items as $item) {
// Get the parent item - it is NOT included in the quote due to
// customizations made by the OrganicInternet module for simple
// product pricing. So I had to come up with another way to get it.
$options = $item->getProductOptions();
$parent = $item->getProduct();
if (array_key_exists('info_buyRequest', $options)) {
if (array_key_exists('cpid', $options['info_buyRequest'])) {
$parentId = $options['info_buyRequest']['cpid'];
$parent = Mage::getModel('catalog/product')->getCollection()
->addAttributeToSelect('name')
->addAttributeToSelect('season')
->addAttributeToSelect('gender')
->addAttributeToSelect('sport')
->addAttributeToFilter('entity_id', $parentId)
->getFirstItem();
}
}
$itemIds[] = $item->getSku();
$itemNames[] = $parent->getName();
$itemPrices[] = $item->getBasePrice() ?: 0;
$itemMargins[] = $this->_calculateMargin($parent, null, $item);
$itemTypes[] = $parent->getAttributeText('season');
$itemGenders[] = $parent->getAttributeText('gender');
$itemSports[] = $parent->getAttributeText('sport') ?: 'Other';
$categories = $this->_getAllCategoryIdsAndNames($item->getProduct());
$itemCategoryIds[] = $categories['id'];
$itemCategoryNames[] = $categories['name'];
$itemProductCounts[$item->getSku()] = count($parent);
}
// # Products
$data['u1'] = count($items);
$data['itemProductCounts'] = $itemProductCounts;
With that all being said, the code above should get you close to what you need, you should replace the line $itemProductCounts[$item->getSku()] = count($parent); with the correct array with the product counts for that SKU.
Part of the issue with your data here is that everything in an $item is hidden behind an accessor. Rather than creating multitudes of arrays, I would suggest either creating a new object to house the information, or just modifying the $item directly.
Messing with the object directly has the risk of you accidentally using a variable name that exists in a protected or private scope though, so probably best to use your own, like so.
if ($order->getId()) {
$items = $order->getAllVisibleItems();
// only need one array, no need for all data points to have their own
$myItems = [];
/** #var Mage_Sales_Model_Quote_Item $item */
foreach ($items as $item) {
// basic shell
$myItem = [];
// get $options and $parent
// ...
// build your own data object
$myItem['sku'] = $item->getSku();
$myItem['name'] = $parent->getName();
$myItem['price'] = $item->getBasePrice() ?: 0;
$myItem['margin'] = $this->_calculateMargin($parent, null, $item);
$myItem['type'] = $parent->getAttributeText('season');
$myItem['gender'] = $parent->getAttributeText('gender');
$myItem['sport'] = $parent->getAttributeText('sport') ?: 'Other';
$categories = $this->_getAllCategoryIdsAndNames($item->getProduct());
$myItem['categoryId'] = $categories['id'];
$myItem['categoryName'] = $categories['name'];
$myItems[] = $myItem;
}
// At this point, $myItems is manipulable by all the array_* functions
// number of items e.g. 3
$data['u1'] = count($myItems);
// array of skus e.g. ["889623392590","889623392590","889623135517"]
// note: can use objects for $myItem if on PHP 7
// if you like -> notation better (in the loop)
$skus = array_column($myItems, 'sku');
// array of skus with counts e.g. ["889623392590" => 2, "889623135517" => 1]
$skus_with_counts = array_count_values($skus);
// just the counts (assuming indexes on other arrays must match) e.g. [2, 1]
// note: might be useful if you want to keep the counts as an array in dataLayer
$sku_counts = array_values($skus_with_counts);
// if you want this as a comma-separated list for u1, e.g. "2,1"
// note: will also work if you implode $skus_with_counts
$data['u1'] = implode(',', $sku_counts);
// get a list of unique SKUs (both will work), e.g. ["889623392590","889623135517"]
$data['u2'] = array_unique($skus);
$data['u2'] = array_keys($skus_with_counts);
}
Most of these kinds of PHP functions will work on your other data types as well if you want to do counting and clustering, and as you point out, you can run sum operations over them as well if you wish.
PHP array manipulation references: array_column, array_count_values, array_values, implode, array_unique, array_keys.
As a sidebar, Mage_Sales_Model_Quote_Item does have a getParentItemId() method available and a getQtyOptions method, which returns both the quantity and the product model.
I think you are mixing things.
In a simple sistem you should have:
Order has an array of OrderedItems
Each OrderedItem stores ProductObject and OrderedQuantity
And the ProductObject contains all product data.
So in your example instead of counting SKUs you must have $item->quantity field and you should work with that when you add/delete/edit order contents.
I need to calculate a sub total of the items in a shopping cart. It stores the items added to the cart as an array of the product IDs in a session variable.
So to start with I need to use the ID in the cart array to pull the product information from the database (name, price etc.) and then add the prices of all the items in the cart, of which there could be more than one of the same product.
My test cart should have a total price of 96,049.98 but my code is returning a total price of 18. I don't know where it's getting that from.
Here is the code:
function subTotal() {
global $db;
global $table_prefix;
$table = $table_prefix . "products";
foreach($_SESSION['cart'] as $item) {
$sql = $db->prepare("SELECT * FROM $table WHERE id = :id");
$sql->bindParam(":id", $item[0]);
$sql->execute();
$amount = 0;
$product = $sql->fetch(PDO::FETCH_ASSOC);
foreach($product as $price) {
$amount += $price['price'];
}
}
return $amount;
}
You are restarting the value $amount to 0 per iteration.
Try initializating it at the top:
function subTotal() {
global $db;
global $table_prefix;
$table = $table_prefix . "products";
$amount = 0; //MOVED HERE at the top
foreach($_SESSION['cart'] as $item) {
$sql = $db->prepare("SELECT * FROM $table WHERE id = :id");
$sql->bindParam(":id", $item[0]);
$sql->execute();
$product = $sql->fetch(PDO::FETCH_ASSOC);
foreach($product as $price) {
$amount += $price['price'];
}
}
return $amount;
}
Just take out $amount = 0 out of the loop. As it's getting reset on each product loop.
$amount = 0;
foreach($_SESSION['cart'] as $item) {
$sql = $db->prepare("SELECT * FROM $table WHERE id = :id");
$sql->bindParam(":id", $item[0]);
$sql->execute();
$product = $sql->fetch(PDO::FETCH_ASSOC);
foreach($product as $price) {
$amount += $price['price'];
}
}
As I mentioned in my comment: In case you are able to change the way your shopping cart stores items, you could refactor your code to something like this:
function subTotal() {
$db = $GLOBALS['db'];
$table_prefix = $GLOBALS['table_prefix'];
$table = $table_prefix . "products";
$totalPrice = 0;
// assuming that you actually store ($id => $amount) pairs
$ids = join(',', array_map('intval', array_keys($_SESSION['cart'])));
$stmt = $db->prepare("SELECT id, price FROM $table WHERE id IN ($ids)");
while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
$amount = $_SESSION['cart'][$row['id']];
$totalPrice += $amount * $row['price'];
}
return $totalPrice;
}
If would assume, that your shopping cart variable would contain something like this:
array(
4 => 1, // 1 item with ID 4
22 => 8 // 8 items with ID 22
)
i am building a shopping cart and cant figure out how to store something like this into a session.
[product_id1] = quantity;
[product_id1] = size
[product_id1] = color;
[product_id2] = quantity;
[product_id2] = size;
[product_id2] = color;
...
etc
so when a user select the quantity of a product then selects its color then selects to add to a cart i want the items selected to be added into a session and each item added to the cart , its attributes selected to be added into a session. how would i do this?
many many thanks.
$_SESSION['productid1']['quantity'] = 15;
$_SESSION['productid1']['size'] = 30;
$_SESSION['productid1']['color'] = 'red';
$_SESSION['productid2']['quantity'] = 35;
$_SESSION['productid2']['size'] = 2;
$_SESSION['productid2']['color'] = 'blue';
Don't forget to put session_start() at the beginning of every page to carry the sessions through the pages.
$item[$catalog_number]['quantity'] = 1;
$item[$catalog_number]['size'] = 'XL';
$item[$catalog_number]['color'] = 'yellow';
$_SESSION['cart'][] = $item;
unset($item);
Repeat for each item you are adding. Alternatively you could do:
$item['catalog_number'] = 'ABC-123';
$item['quantity'] = 1;
$item['size'] = 'XL';
$item['color'] = 'yellow';
$_SESSION['cart'][] = $item;
unset($item);
Both will work, just make sure you are consistent. Use only one or the other.
You should create an array in session array for your products:
$_SESSION['products'] = Array();
then you can put products there like this:
$product = Array();
$product['quantity'] = 6;
$product['size'] = 'XXL';
$product['color'] = 'blue';
$_SESSION['products'][] = $product;
$product = Array();
$product['quantity'] = 2;
$product['size'] = 'XL';
$product['color'] = 'blue';
$_SESSION['products'][] = $product;
this will give you numbered array, if you want an associative array, you will just put identifier into []:
$_SESSION['products']['productID'] = $product;