/** * Invoke collector for nominal items * * @param \Magento\Sales\Model\Quote\Address $address * @return $this */ public function collect(\Magento\Sales\Model\Quote\Address $address) { $collector = $this->_collectorFactory->create(array('store' => $address->getQuote()->getStore())); // invoke nominal totals foreach ($collector->getCollectors() as $model) { $model->collect($address); } // aggregate collected amounts into one to have sort of grand total per item foreach ($address->getAllNominalItems() as $item) { $rowTotal = 0; $baseRowTotal = 0; $totalDetails = array(); foreach ($collector->getCollectors() as $model) { $itemRowTotal = $model->getItemRowTotal($item); if ($model->getIsItemRowTotalCompoundable($item)) { $rowTotal += $itemRowTotal; $baseRowTotal += $model->getItemBaseRowTotal($item); $isCompounded = true; } else { $isCompounded = false; } if ((double) $itemRowTotal > 0 && ($label = $model->getLabel())) { $totalDetails[] = new \Magento\Framework\Object(array('label' => $label, 'amount' => $itemRowTotal, 'is_compounded' => $isCompounded)); } } $item->setNominalRowTotal($rowTotal); $item->setBaseNominalRowTotal($baseRowTotal); $item->setNominalTotalDetails($totalDetails); } return $this; }
/** * Fetch discount * * @param \Magento\Sales\Model\Quote\Address $address * @return $this */ public function fetchTotals(\Magento\Sales\Model\Quote\Address $address) { $amount = $address->getDiscountAmount(); if ($amount != 0) { $title = __('Discount'); $couponCode = $address->getQuote()->getCouponCode(); if (strlen($couponCode)) { $title .= sprintf(' (%s)', $couponCode); } $address->addTotal(array('code' => 'discount', 'title' => $title, 'value' => -$amount)); } return $this; }
/** * Remove item * * @param Address $address * @param AddressItem|Item $item * @return $this */ protected function _removeItem($address, $item) { if ($item instanceof Item) { $address->removeItem($item->getId()); if ($address->getQuote()) { $address->getQuote()->removeItem($item->getId()); } } elseif ($item instanceof AddressItem) { $address->removeItem($item->getId()); if ($address->getQuote()) { $address->getQuote()->removeItem($item->getQuoteItemId()); } } return $this; }
/** * Convert address discount description array to string * * @param Address $address * @param string $separator * @return $this */ public function prepareDescription($address, $separator = ', ') { $descriptionArray = $address->getDiscountDescriptionArray(); if (!$descriptionArray && $address->getQuote()->getItemVirtualQty() > 0) { $descriptionArray = $address->getQuote()->getBillingAddress()->getDiscountDescriptionArray(); } $description = $descriptionArray && is_array($descriptionArray) ? implode($separator, array_unique($descriptionArray)) : ''; $address->setDiscountDescription($description); return $this; }
/** * @param Product $product * @param null|false|\Magento\Sales\Model\Quote\Address $shipping * @param null|false|\Magento\Sales\Model\Quote\Address $billing * @param Website $website * @param bool $calculateTax * @param bool $ignoreDiscount * @return \Magento\Framework\Object[] */ public function getProductWeeeAttributes($product, $shipping = null, $billing = null, $website = null, $calculateTax = null, $ignoreDiscount = false) { $result = array(); $allWeee = $this->getWeeeTaxAttributeCodes(); if (!$allWeee) { return $result; } $websiteId = $this->_storeManager->getWebsite($website)->getId(); /** @var \Magento\Store\Model\Store $store */ $store = $this->_storeManager->getWebsite($website)->getDefaultGroup()->getDefaultStore(); /** @var \Magento\Tax\Model\Calculation $calculator */ $calculator = $this->_calculationFactory->create(); if ($shipping) { $customerTaxClass = $shipping->getQuote()->getCustomerTaxClassId(); } else { $customerTaxClass = null; } $rateRequest = $calculator->getRateRequest($shipping, $billing, $customerTaxClass, $store); $defaultRateRequest = $calculator->getDefaultRateRequest($store); $discountPercent = 0; if (!$ignoreDiscount && $this->weeeConfig->isDiscounted($store)) { $discountPercent = $this->_getDiscountPercentForProduct($product); } $productAttributes = $product->getTypeInstance()->getSetAttributes($product); foreach ($productAttributes as $code => $attribute) { if (in_array($code, $allWeee)) { $attributeSelect = $this->getResource()->getReadConnection()->select(); $attributeSelect->from($this->getResource()->getTable('weee_tax'), 'value')->where('attribute_id = ?', (int) $attribute->getId())->where('website_id IN(?)', array($websiteId, 0))->where('country = ?', $rateRequest->getCountryId())->where('state IN(?)', array($rateRequest->getRegionId(), '*'))->where('entity_id = ?', (int) $product->getId())->limit(1); $order = array('state ' . \Magento\Framework\DB\Select::SQL_DESC, 'website_id ' . \Magento\Framework\DB\Select::SQL_DESC); $attributeSelect->order($order); $value = $this->getResource()->getReadConnection()->fetchOne($attributeSelect); if ($value) { if ($discountPercent) { $value = $this->_storeManager->getStore()->roundPrice($value - $value * $discountPercent / 100); } $taxAmount = $amount = 0; $amount = $value; if ($calculateTax && $this->weeeConfig->isTaxable($store)) { /** @var \Magento\Tax\Model\Calculation $calculator */ $defaultPercent = $calculator->getRate($defaultRateRequest->setProductClassId($product->getTaxClassId())); $currentPercent = $calculator->getRate($rateRequest->setProductClassId($product->getTaxClassId())); if ($this->_taxData->priceIncludesTax($store)) { $amountInclTax = $value / (100 + $defaultPercent) * (100 + $currentPercent); //round the "golden price" $amountInclTax = $store->roundPrice($amountInclTax); $taxAmount = $amountInclTax - $amountInclTax / (100 + $currentPercent) * 100; $taxAmount = $store->roundPrice($taxAmount); } else { $appliedRates = $this->_calculationFactory->create()->getAppliedRates($rateRequest); if (count($appliedRates) > 1) { $taxAmount = 0; foreach ($appliedRates as $appliedRate) { $taxRate = $appliedRate['percent']; $taxAmount += $this->_storeManager->getStore()->roundPrice($value * $taxRate / 100); } } else { $taxAmount = $this->_storeManager->getStore()->roundPrice($value * $currentPercent / 100); } $taxAmount = $store->roundPrice($value * $currentPercent / 100); } } $one = new \Magento\Framework\Object(); $one->setName(__($attribute->getFrontend()->getLabel()))->setAmount($amount)->setTaxAmount($taxAmount)->setCode($attribute->getAttributeCode()); $result[] = $one; } } } return $result; }
/** * Add rule discount description label to address object * * @param Address $address * @param \Magento\SalesRule\Model\Rule $rule * @return $this */ public function addDiscountDescription($address, $rule) { $description = $address->getDiscountDescriptionArray(); $ruleLabel = $rule->getStoreLabel($address->getQuote()->getStore()); $label = ''; if ($ruleLabel) { $label = $ruleLabel; } else { if (strlen($address->getCouponCode())) { $label = $address->getCouponCode(); } } if (strlen($label)) { $description[$rule->getId()] = $label; } $address->setDiscountDescriptionArray($description); return $this; }
/** * Update tax related fields for shipping * * @param Address $address * @param \Magento\Tax\Service\V1\Data\TaxDetails\Item $shippingTaxDetails * @param \Magento\Tax\Service\V1\Data\TaxDetails\Item $baseShippingTaxDetails * @return $this */ protected function processShippingTaxInfo(Address $address, $shippingTaxDetails, $baseShippingTaxDetails) { $address->setTotalAmount('shipping', $shippingTaxDetails->getRowTotal()); $address->setBaseTotalAmount('shipping', $baseShippingTaxDetails->getRowTotal()); $address->setTotalAmount('shipping_hidden_tax', $shippingTaxDetails->getDiscountTaxCompensationAmount()); $address->setBaseTotalAmount('shipping_hidden_tax', $baseShippingTaxDetails->getDiscountTaxCompensationAmount()); $address->setShippingInclTax($shippingTaxDetails->getRowTotalInclTax()); $address->setBaseShippingInclTax($baseShippingTaxDetails->getRowTotalInclTax()); $address->setShippingTaxAmount($shippingTaxDetails->getRowTax()); $address->setBaseShippingTaxAmount($baseShippingTaxDetails->getRowTax()); //Add the shipping tax to total tax amount $address->addTotalAmount('tax', $shippingTaxDetails->getRowTax()); $address->addBaseTotalAmount('tax', $baseShippingTaxDetails->getRowTax()); if ($this->_config->discountTax($address->getQuote()->getStore())) { $address->setShippingAmountForDiscount($shippingTaxDetails->getRowTotalInclTax()); $address->setBaseShippingAmountForDiscount($baseShippingTaxDetails->getRowTotalInclTax()); } return $this; }
/** * @param \Magento\Sales\Model\Quote\Address $address * @return $this */ public function collect(\Magento\Sales\Model\Quote\Address $address) { $quote = $address->getQuote(); $eventArgs = array('website_id' => $this->_storeManager->getStore($quote->getStoreId())->getWebsiteId(), 'customer_group_id' => $quote->getCustomerGroupId(), 'coupon_code' => $quote->getCouponCode()); $address->setFreeShipping(0); $totalDiscountAmount = 0; $subtotalWithDiscount = 0; $baseTotalDiscountAmount = 0; $baseSubtotalWithDiscount = 0; $items = $address->getAllItems(); if (!count($items)) { $address->setDiscountAmount($totalDiscountAmount); $address->setSubtotalWithDiscount($subtotalWithDiscount); $address->setBaseDiscountAmount($baseTotalDiscountAmount); $address->setBaseSubtotalWithDiscount($baseSubtotalWithDiscount); return $this; } foreach ($items as $item) { if ($item->getNoDiscount()) { $item->setDiscountAmount(0); $item->setBaseDiscountAmount(0); $item->setRowTotalWithDiscount($item->getRowTotal()); $item->setBaseRowTotalWithDiscount($item->getRowTotal()); $subtotalWithDiscount += $item->getRowTotal(); $baseSubtotalWithDiscount += $item->getBaseRowTotal(); } else { /** * Child item discount we calculate for parent */ if ($item->getParentItemId()) { continue; } /** * Composite item discount calculation */ if ($item->getHasChildren() && $item->isChildrenCalculated()) { foreach ($item->getChildren() as $child) { $eventArgs['item'] = $child; $this->_eventManager->dispatch('sales_quote_address_discount_item', $eventArgs); /** * Parent free shipping we apply to all children */ if ($item->getFreeShipping()) { $child->setFreeShipping($item->getFreeShipping()); } /** * @todo Parent discount we apply for all children without discount */ if (!$child->getDiscountAmount() && $item->getDiscountPercent()) { } $totalDiscountAmount += $child->getDiscountAmount(); //*$item->getQty(); $baseTotalDiscountAmount += $child->getBaseDiscountAmount(); //*$item->getQty(); $child->setRowTotalWithDiscount($child->getRowTotal() - $child->getDiscountAmount()); $child->setBaseRowTotalWithDiscount($child->getBaseRowTotal() - $child->getBaseDiscountAmount()); $subtotalWithDiscount += $child->getRowTotalWithDiscount(); $baseSubtotalWithDiscount += $child->getBaseRowTotalWithDiscount(); } } else { $eventArgs['item'] = $item; $this->_eventManager->dispatch('sales_quote_address_discount_item', $eventArgs); $totalDiscountAmount += $item->getDiscountAmount(); $baseTotalDiscountAmount += $item->getBaseDiscountAmount(); $item->setRowTotalWithDiscount($item->getRowTotal() - $item->getDiscountAmount()); $item->setBaseRowTotalWithDiscount($item->getBaseRowTotal() - $item->getBaseDiscountAmount()); $subtotalWithDiscount += $item->getRowTotalWithDiscount(); $baseSubtotalWithDiscount += $item->getBaseRowTotalWithDiscount(); } } } $address->setDiscountAmount($totalDiscountAmount); $address->setSubtotalWithDiscount($subtotalWithDiscount); $address->setBaseDiscountAmount($baseTotalDiscountAmount); $address->setBaseSubtotalWithDiscount($baseSubtotalWithDiscount); $address->setGrandTotal($address->getGrandTotal() - $address->getDiscountAmount()); $address->setBaseGrandTotal($address->getBaseGrandTotal() - $address->getBaseDiscountAmount()); return $this; }
/** * @param Address $address * @param float $price * @param bool $flag * @return float */ public function getShippingPrice($address, $price, $flag) { return $address->getQuote()->getStore()->convertPrice($this->_taxHelper->getShippingPrice($price, $flag, $address), true); }
/** * @param \Magento\Sales\Model\Quote\Address $address * @return $this */ public function fetch(\Magento\Sales\Model\Quote\Address $address) { $applied = $address->getAppliedTaxes(); $store = $address->getQuote()->getStore(); $amount = $address->getTaxAmount(); if ($amount != 0 || $this->_taxData->displayZeroTax($store)) { $address->addTotal(array('code' => $this->getCode(), 'title' => __('Tax'), 'full_info' => $applied ? $applied : array(), 'value' => $amount)); } return $this; }
/** * Convert quote address model to order * * @param \Magento\Sales\Model\Quote\Address $address * @param null|\Magento\Sales\Model\Order $order * @return \Magento\Sales\Model\Order */ public function addressToOrder(\Magento\Sales\Model\Quote\Address $address, $order = null) { if (!$order instanceof \Magento\Sales\Model\Order) { $order = $this->toOrder($address->getQuote()); } $this->_objectCopyService->copyFieldsetToTarget('sales_convert_quote_address', 'to_order', $address, $order); $this->_eventManager->dispatch('sales_convert_quote_address_to_order', array('address' => $address, 'order' => $order)); return $order; }
/** * Declare address model * * @param \Magento\Sales\Model\Quote\Address $address * @return $this */ public function setAddress(\Magento\Sales\Model\Quote\Address $address) { $this->_address = $address; $this->_quote = $address->getQuote(); return $this; }
/** * Add tax totals information to address object * * @param Address $address * @return $this */ public function fetch(Address $address) { $applied = $address->getAppliedTaxes(); $store = $address->getQuote()->getStore(); $amount = $address->getTaxAmount(); $items = $this->_getAddressItems($address); $discountTaxCompensation = 0; foreach ($items as $item) { $discountTaxCompensation += $item->getDiscountTaxCompensation(); } $taxAmount = $amount + $discountTaxCompensation; $area = null; if ($this->_config->displayCartTaxWithGrandTotal($store) && $address->getGrandTotal()) { $area = 'taxes'; } if ($amount != 0 || $this->_config->displayCartZeroTax($store)) { $address->addTotal(array('code' => $this->getCode(), 'title' => __('Tax'), 'full_info' => $applied ? $applied : array(), 'value' => $amount, 'area' => $area)); } $store = $address->getQuote()->getStore(); /** * Modify subtotal */ if ($this->_config->displayCartSubtotalBoth($store) || $this->_config->displayCartSubtotalInclTax($store)) { if ($address->getSubtotalInclTax() > 0) { $subtotalInclTax = $address->getSubtotalInclTax(); } else { $subtotalInclTax = $address->getSubtotal() + $taxAmount - $address->getShippingTaxAmount(); } $address->addTotal(array('code' => 'subtotal', 'title' => __('Subtotal'), 'value' => $subtotalInclTax, 'value_incl_tax' => $subtotalInclTax, 'value_excl_tax' => $address->getSubtotal())); } return $this; }