11 private $iblockId = 0;
12 private $userDialogParams = array();
21 public function __construct(array $userDialogParams, $iblockId)
24 $this->iblockId = (int)$iblockId;
35 if (!isset($userDialogParams[
'VALUE_CHANGING'])
36 ||((
float)($userDialogParams[
'VALUE_CHANGING'] == 0)
37 ||!isset($userDialogParams[
'PRICE_TYPE'])
38 ||!(
int)($userDialogParams[
'PRICE_TYPE'])))
44 $userDialogParams[
'PRICE_TYPE'] = (int)($userDialogParams[
'PRICE_TYPE']);
47 if (!isset($userDialogParams[
'DIFFERENCE_VALUE'])||!(float)$userDialogParams[
'DIFFERENCE_VALUE'])
49 $userDialogParams[
'DIFFERENCE_VALUE'] = 0;
52 if (!isset($userDialogParams[
'RESULT_MASK'])||!(float)$userDialogParams[
'RESULT_MASK'])
54 $userDialogParams[
'RESULT_MASK'] = 1;
57 if (!isset($userDialogParams[
'UNITS']))
59 $userDialogParams[
'UNITS'] =
null;
63 if ($userDialogParams[
'UNITS'] !=
'percent' && $userDialogParams[
'UNITS'] !=
'multiple')
65 if (
Currency\CurrencyManager::isCurrencyExist($userDialogParams[
'UNITS']))
67 $userDialogParams[
'CURRENCY'] = $userDialogParams[
'UNITS'];
68 $userDialogParams[
'UNITS'] =
'currency';
72 $userDialogParams[
'UNITS'] =
null;
77 $_SESSION[
'CHANGE_PRICE_PARAMS'][
'PRICE_TYPE'] = $userDialogParams[
'PRICE_TYPE'];
78 $_SESSION[
'CHANGE_PRICE_PARAMS'][
'UNITS'] = $userDialogParams[
'UNITS'];
79 $_SESSION[
'CHANGE_PRICE_PARAMS'][
'FORMAT_RESULTS'] = $userDialogParams[
'FORMAT_RESULTS'];
80 $_SESSION[
'CHANGE_PRICE_PARAMS'][
'INITIAL_PRICE_TYPE'] = $userDialogParams[
'INITIAL_PRICE_TYPE'];
82 return $this->userDialogParams = $userDialogParams;
90 private function collectAllSectionsElements(&$productsIdList)
92 $resultAllElementsList = \CIBlockElement::GetList(
95 "SECTION_ID"=>$productsIdList[
'SECTIONS'],
96 "IBLOCK_ID" => $this->iblockId,
97 "WF_PARENT_ELEMENT_ID" => NULL,
98 "INCLUDE_SUBSECTIONS"=>
"Y",
99 "CHECK_PERMISSIONS" =>
"Y",
100 "MIN_PERMISSION" =>
"W"
105 while ($subSectionsResult = $resultAllElementsList->Fetch())
107 $productsIdList[
'ELEMENTS'][] = $subSectionsResult[
'ID'];
109 unset($subSectionsResult, $resultAllElementsList);
110 unset( $productsIdList[
'SECTIONS'] );
119 private function collectPriceSkuElementsId($productsIdList)
121 $sectionElementsIdList = array();
123 $skuIdList = \CCatalogSku::getOffersList($productsIdList[
'ELEMENTS'], $this->iblockId);
124 if(is_array($skuIdList))
126 foreach ($skuIdList as $skuId => $skuListElements)
128 $sectionElementsIdList[] = $skuId;
129 foreach ($skuListElements as $skuElement)
131 $priceElementsIdList[
'SKU_ELEMENTS'][] = $skuElement[
"ID"];
136 if (empty($priceElementsIdList))
138 $priceElementsIdList[
'SIMPLE_ELEMENTS'] = $productsIdList[
'ELEMENTS'];
140 elseif ($elementsWithoutSkuIdList = array_diff($productsIdList[
'ELEMENTS'], $sectionElementsIdList))
142 $priceElementsIdList[
'SIMPLE_ELEMENTS'] = $elementsWithoutSkuIdList;
143 unset ($elementsWithoutSkuIdList);
146 return $priceElementsIdList;
154 private function initFilterParams()
156 $catalogGroups = array();
157 if (isset($this->userDialogParams[
'INITIAL_PRICE_TYPE']))
159 $id = (int)$this->userDialogParams[
'INITIAL_PRICE_TYPE'];
161 $catalogGroups[$id] = $id;
164 if (isset($this->userDialogParams[
'PRICE_TYPE']))
166 $id = (int)$this->userDialogParams[
'PRICE_TYPE'];
168 $catalogGroups[$id] = $id;
172 $filterList = array(
"@CATALOG_GROUP_ID" => $catalogGroups);
183 private function calculateResultPrice($price)
185 $userDialogParams = $this->userDialogParams;
186 $valueChangingPrice = $userDialogParams[
'VALUE_CHANGING'];
188 if ($userDialogParams[
'UNITS'] ===
"percent")
190 $price = ($price * (100 + $valueChangingPrice) / 100);
192 elseif ($userDialogParams[
'UNITS'] ===
"multiple")
194 if ($valueChangingPrice > 0)
196 $price = $price * $valueChangingPrice;
200 $price = $price / $valueChangingPrice * (-1);
205 $price = $price + $valueChangingPrice;
208 switch ($userDialogParams[
'FORMAT_RESULTS'])
211 $price = floor($price * $userDialogParams[
'RESULT_MASK']) / $userDialogParams[
'RESULT_MASK'] - $userDialogParams[
'DIFFERENCE_VALUE'] ;
214 $price = ceil($price * $userDialogParams[
'RESULT_MASK']) / $userDialogParams[
'RESULT_MASK'] - $userDialogParams[
'DIFFERENCE_VALUE'] ;
217 $price = round($price * $userDialogParams[
'RESULT_MASK']) / $userDialogParams[
'RESULT_MASK'] - $userDialogParams[
'DIFFERENCE_VALUE'] ;
221 unset($userDialogParams);
236 if ($this->userDialogParams ==
false)
239 new Main\
Error(
"IBLIST_CHPRICE_ERROR_WRONG_INPUT_VALUE",
null)
244 if($this->userDialogParams[
'UNITS'] ===
null)
247 new Main\
Error(
"IBLIST_CHPRICE_ERROR_WRONG_CURRENCY")
252 if (!empty( $productsIdList[
'SECTIONS']) )
254 $this->collectAllSectionsElements($productsIdList);
257 if (\CCatalogSku::GetInfoByProductIBlock($this->iblockId))
259 $priceElementsListSplitedByType = $this->collectPriceSkuElementsId($productsIdList);
263 $priceElementsListSplitedByType[
'SIMPLE_ELEMENTS'] = $productsIdList[
'ELEMENTS'];
275 'ELEMENT_NAME' =>
'ELEMENT.NAME',
276 'ELEMENT_IBLOCK_ID' =>
'ELEMENT.IBLOCK_ID'
278 "filter" => $this->initFilterParams(),
279 'order' => array(
'PRODUCT_ID' =>
'ASC',
'CATALOG_GROUP_ID' =>
'ASC')
282 $group = Catalog\GroupTable::getList(array(
283 'select' => array(
'ID'),
284 'filter' => array(
'=BASE'=>
'Y')
286 $basePriceId = (!empty($group) ? (int)$group[
'ID'] : 0);
290 if (isset($this->userDialogParams[
'INITIAL_PRICE_TYPE']))
292 $id = (int)$this->userDialogParams[
'INITIAL_PRICE_TYPE'];
299 if (isset($this->userDialogParams[
'PRICE_TYPE']))
301 $id = (int)$this->userDialogParams[
'PRICE_TYPE'];
307 if ($targetType == 0)
310 if ($initialType > 0 && $targetType == $initialType)
313 Catalog\Product\Sku::enableDeferredCalculation();
314 foreach ($priceElementsListSplitedByType as $typeElements => $priceElementsIdList)
316 $priceElementsIdList = array_chunk($priceElementsIdList, 500);
317 foreach ($priceElementsIdList as $productIdList)
319 $parameters[
'filter'][
'@PRODUCT_ID'] = $productIdList;
321 $cpriceResult = Catalog\Model\Price::getList($parameters);
323 $elementsCPriceList = array();
325 while ($row = $cpriceResult->fetch())
327 $row[
'PRODUCT_TYPE_CODE'] = $typeElements;
328 $productId = (int)$row[
'PRODUCT_ID'];
329 if (!isset($elementsCPriceList[$productId]))
330 $elementsCPriceList[$productId] = array(
331 'QUANTITY' => array(),
334 $priceType = (int)$row[
'CATALOG_GROUP_ID'];
335 if ($row[
'QUANTITY_FROM'] !==
null || $row[
'QUANTITY_TO'] !==
null)
337 $hash = ($row[
'QUANTITY_FROM'] ===
null ?
'ZERO' : $row[
'QUANTITY_FROM']).
338 '-'.($row[
'QUANTITY_TO'] ===
null ?
'INF' : $row[
'QUANTITY_TO']);
339 if (!isset($elementsCPriceList[$productId][
'QUANTITY'][$hash]))
340 $elementsCPriceList[$productId][
'QUANTITY'][$hash] = array();
341 $elementsCPriceList[$productId][
'QUANTITY'][$hash][$priceType] = $row;
346 $elementsCPriceList[$productId][
'SIMPLE'][$priceType] = $row;
350 if (!empty($elementsCPriceList))
352 foreach ($elementsCPriceList as $productId => $prices)
354 foreach ($prices as $key => $data)
357 unset($prices[$key]);
361 if (count($prices) !== 1)
364 if (!empty($prices[
'QUANTITY']))
366 foreach ($prices[
'QUANTITY'] as $hash => $rangePrices)
368 if (!empty($rangePrices))
369 $this->updatePriceBlock($productId, $rangePrices, $basePriceId);
371 unset($hash, $rangePrices);
374 if (!empty($prices[
'SIMPLE']))
376 $this->updatePriceBlock($productId, $prices[
'SIMPLE'], $basePriceId);
379 unset($productId, $prices);
381 unset($elementsCPriceList);
384 Catalog\Product\Sku::disableDeferredCalculation();
385 Catalog\Product\Sku::calculate();
386 Catalog\Model\Price::clearCache();
391 private function updatePriceBlock($productId, array $prices, $basePriceId)
396 if (isset($this->userDialogParams[
'INITIAL_PRICE_TYPE']))
398 $id = (int)$this->userDialogParams[
'INITIAL_PRICE_TYPE'];
405 if (isset($this->userDialogParams[
'PRICE_TYPE']))
407 $id = (int)$this->userDialogParams[
'PRICE_TYPE'];
415 $destinationPrice =
null;
416 if ($initialType > 0)
418 if (isset($prices[$initialType]))
420 $sourcePrice = $prices[$initialType];
421 $destinationPrice = $prices[$initialType];
422 unset($destinationPrice[
'ID']);
423 $destinationPrice[
'EXTRA_ID'] =
false;
424 $destinationPrice[
'CATALOG_GROUP_ID'] = $targetType;
425 if (isset($prices[$targetType]))
426 $destinationPrice = $prices[$targetType];
428 $this->userDialogParams[
'UNITS'] !=
'currency'
430 $sourcePrice[
'CURRENCY'] == $this->userDialogParams[
'CURRENCY']
431 && $destinationPrice[
'CURRENCY'] == $this->userDialogParams[
'CURRENCY']
434 $destinationPrice[
'PRICE'] = $this->calculateResultPrice($sourcePrice[
'PRICE']);
436 $destinationPrice =
null;
442 if (isset($prices[$targetType]))
444 $destinationPrice = $prices[$targetType];
446 $this->userDialogParams[
'UNITS'] !=
'currency'
447 || $destinationPrice[
'CURRENCY'] == $this->userDialogParams[
'CURRENCY']
449 $destinationPrice[
'PRICE'] = $this->calculateResultPrice($destinationPrice[
'PRICE']);
451 $destinationPrice =
null;
454 if (!empty($destinationPrice))
456 if ($destinationPrice[
'PRICE'] < 0)
459 new Main\
Error(
"IBLIST_CHPRICE_ERROR_WRONG_VALUE_".$destinationPrice[
'PRODUCT_TYPE_CODE'],
461 '#ID#' => $destinationPrice[
'PRODUCT_ID'],
462 '#NAME#' => $destinationPrice[
'ELEMENT_NAME'],
467 elseif ($destinationPrice[
'EXTRA_ID'] > 0)
470 new Main\
Error(
"IBLIST_CHPRICE_ERROR_PRICE_WITH_EXTRA_".$destinationPrice[
'PRODUCT_TYPE_CODE'],
472 '#ID#' => $destinationPrice[
'PRODUCT_ID'],
473 '#NAME#' => $destinationPrice[
'ELEMENT_NAME'],
480 if (!empty($destinationPrice[
'ID']))
484 'PRICE' => $destinationPrice[
'PRICE'],
485 'CURRENCY' => $destinationPrice[
'CURRENCY']
487 'external_fields' => [
488 'IBLOCK_ID' => $destinationPrice[
'ELEMENT_IBLOCK_ID']
491 if ($basePriceId == $targetType)
493 $data[
'actions'][
'RECOUNT_PRICES'] =
true;
495 $priceResult = Catalog\Model\Price::update($destinationPrice[
'ID'], $data);
500 $priceResult = Catalog\Model\Price::add([
501 'PRODUCT_ID' => $productId,
502 'CATALOG_GROUP_ID' => $targetType,
503 'PRICE' => $destinationPrice[
'PRICE'],
504 'CURRENCY' => $destinationPrice[
'CURRENCY'],
505 'EXTRA_ID' => $destinationPrice[
'EXTRA_ID'],
506 'QUANTITY_FROM' => $destinationPrice[
'QUANTITY_FROM'],
507 'QUANTITY_TO' => $destinationPrice[
'QUANTITY_TO']
511 if ($priceResult->isSuccess())
513 Iblock\PropertyIndex\Manager::updateElementIndex($destinationPrice[
'ELEMENT_IBLOCK_ID'], $destinationPrice[
'PRODUCT_ID']);
514 $ipropValues =
new Iblock\InheritedProperty\ElementValues($destinationPrice[
'ELEMENT_IBLOCK_ID'], $destinationPrice[
'PRODUCT_ID']);
515 $ipropValues->clearValues();
521 unset($destinationPrice);