src/Manager/PriceManager.php line 380

Open in your IDE?
  1. <?php
  2. namespace App\Manager;
  3. use Doctrine\ORM\EntityManagerInterface;
  4. use App\Entity\Cart;
  5. use App\Service\Mailer;
  6. use App\Manager\CustomerManager;
  7. use App\Manager\CartManager;
  8. use App\Entity\Product;
  9. class PriceManager {
  10. private $em;
  11. private $customerMgr;
  12. private $cartMgr;
  13. private $customer;
  14. private $currentDiscountType = false;
  15. private $currentMarketingRule = false;
  16. // private $rules = [];
  17. public function __construct(EntityManagerInterface $em, CartManager $cartMgr)
  18. {
  19. $this->cartMgr = $cartMgr;
  20. $this->em = $em;
  21. $this->customer = false;
  22. // $this->rules = $this->em->getRepository('App:MarketingRule')->getActiveRules();
  23. }
  24. public function getPrice(Product $product, $qty = 1, $useCart = true, $withEcoTax = true) {
  25. $this->customer = $this->cartMgr->getCustomer();
  26. $discountType = "";
  27. $discountAmount = 0;
  28. $discountPercent = "";
  29. $cart = $this->cartMgr->getCart();
  30. $normalPrice = $product->getPrice(false, $cart->getPriceGroup());
  31. $price = $product->getPrice(false, $cart->getPriceGroup());
  32. $ecoTax = $product->getEcotax();
  33. $this->currentMarketingRule = null;
  34. if($this->customer === false){
  35. return $product->getPrice(true, $cart->getPriceGroup());
  36. }
  37. if($this->cartMgr->isExpert()){
  38. return $product->getPrice(true, $cart->getPriceGroup());
  39. }
  40. // if($useCart){
  41. // }else{
  42. // $cart = false;
  43. // }
  44. // remise standard
  45. $tmp = $this->round($normalPrice) - $this->round($this->getStandardDiscount($product, $qty));
  46. if ($tmp < $price) {
  47. $price = $tmp;
  48. $discountType = "standard";
  49. } else {
  50. $this->hasSpecialPrice = false;
  51. }
  52. // $tmp = $this->round($price) - $this->round($this->getSpecialDiscounts($product, $qty));
  53. // if ($tmp < $price) {
  54. // $price = $tmp;
  55. // $discountType = "specialDiscounts";
  56. // }
  57. // $tmp = $this->round($normalPrice) - $this->round($this->getSpecialDiscounts($product, $qty));
  58. // if ($tmp < $price) {
  59. // $price = $tmp;
  60. // $discountType = "SpecialDiscounts";
  61. // }
  62. if ($this->isLockedPrice($product)) {
  63. return $this->round($price);
  64. }
  65. //remise de bienvenue
  66. $tmp = $this->round($normalPrice) - $this->round($this->getWelcomeDiscount($product));
  67. if ($tmp < $price) {
  68. $price = $tmp;
  69. $discountType = "bienvenue";
  70. }
  71. // remise soleil
  72. $tmp = $this->round($normalPrice) - $this->round($this->getSoleilDiscount($product, $useCart));
  73. if ($tmp < $price) {
  74. $price = $tmp;
  75. $discountType = "soleil";
  76. }
  77. //remises dynamiques
  78. $discounts = $this->getDiscountsByProduct($product);
  79. foreach($discounts as $discount){
  80. if($discount->isTypeOffered() && ($discount->getQtyRequested() < $cart->getItemQuantityByProduct($product))) {
  81. $discountType = $discount->getType();
  82. $this->currentMarketingRule = $discount;
  83. $price = $product->getPrice(true);
  84. }else{
  85. $additonalPercentDiscount = 0;
  86. if($discount->getSkipSoleilDiscount() === false) {
  87. $additonalPercentDiscount = $this->getSoleilPercentDiscount($product);
  88. }
  89. $tmp = $normalPrice - $discount->getProductDiscountByCart($product, $cart);
  90. if($additonalPercentDiscount>0) {
  91. $tmp = $this->getReducedPriceByPercent($tmp, $additonalPercentDiscount);
  92. }
  93. $tmp = $this->round($tmp);
  94. if ($tmp < $price) {
  95. $price = $tmp;
  96. $discountType = $discount->getType();
  97. $this->currentMarketingRule = $discount;
  98. }
  99. }
  100. }
  101. $this->currentDiscountType = $discountType;
  102. return $this->round($price) + ($withEcoTax ? $this->round($ecoTax) : 0);
  103. }
  104. public function getStandardDiscount(Product $product) {
  105. $price = $product->getPrice();
  106. $specialPrice = $this->em->getRepository('App:SpecialPrice')->getDiscount($product);
  107. if (!empty($specialPrice)) {
  108. return $price - $specialPrice->getPrice();
  109. }
  110. return 0;
  111. }
  112. public function getSoleilDiscount(Product $product, $useCart = true) {
  113. if ($this->isLockedPrice($product) || !$this->hasSoleilDiscount())
  114. return 0;
  115. $cart = $this->cartMgr->getCart();
  116. $price = $product->getPrice();
  117. $cartTotal = $this->getCartTotal();
  118. $nonSoleilTotal = $cart->getNonSoleilTotal();
  119. $soleilTotal = $cart->getSoleilTotal();
  120. if(!$useCart){ // on ajoute la prix du produit pour obtenir la remise après ajout au panier
  121. $cartTotal += $price;
  122. $nonSoleilTotal += $price;
  123. $soleilTotal += $price;
  124. }
  125. $discount = 0;
  126. if (($product->getSoleil() == 0) && ($nonSoleilTotal > 100)) {
  127. $discount = $product->getPrice(false) * 0.1;
  128. } else if (($product->getSoleil() == 1) && ($soleilTotal > 100)) {
  129. $coef = 0.25;
  130. $discount = $product->getPrice(false) * $coef;
  131. if ($this->hasTVADiscount()) {
  132. $discount += ($product->getPrice(false) - $discount) * 0.2;
  133. }
  134. } else if ($product->getSoleil() == 1) {
  135. if ($this->hasTVADiscount()) {
  136. $discount += ($product->getPrice(false) - $discount) * 0.2;
  137. }
  138. }
  139. return $discount;
  140. }
  141. public function getSoleilPercentDiscount(Product $product) {
  142. if ($this->isLockedPrice($product) || !$this->hasSoleilDiscount())
  143. return 0;
  144. $cart = $this->cartMgr->getCart();
  145. $price = $product->getPrice();
  146. $cartTotal = $this->getCartTotal();
  147. $nonSoleilTotal = $cart->getNonSoleilTotal();
  148. $soleilTotal = $cart->getSoleilTotal();
  149. $percent = 0;
  150. if (($product->getSoleil() == 0) && ($nonSoleilTotal > 100)) {
  151. $percent = 10;
  152. } else if (($product->getSoleil() == 1) && ($soleilTotal > 100)) {
  153. $percent = 25;
  154. }
  155. return $percent;
  156. }
  157. public function getWelcomeDiscount(Product $product) {
  158. // if ($this->isLockedPrice($product))
  159. // return 0;
  160. // if (!$this->hasCartTotal())
  161. // return 0;
  162. if(!$product->isProduct())
  163. return 0;
  164. $manufacturer = $product->getManufacturer();
  165. if($manufacturer && !$manufacturer->hasWelcomeDiscount()) {
  166. return 0;
  167. }
  168. if (!$product->hasWelcomeDiscount()) {
  169. return 0;
  170. }
  171. if ($this->hasWelcomeDiscount()) {
  172. return $product->getPrice(false) * 0.1;
  173. }
  174. return 0;
  175. }
  176. public function getFidelityDiscount(Product $product) {
  177. if ($this->isLockedPrice($product))
  178. return 0;
  179. $customer = $this->cartMgr->getCustomer();
  180. if($customer) {
  181. if ($customer->hasPlatiniumDiscount()) {
  182. return $product->getPrice() * 0.05;
  183. } else if ($customer->hasEliteDiscount()) {
  184. return $product->getPrice() * 0.1;
  185. }
  186. }
  187. return 0;
  188. }
  189. public function getPalierDiscount(Product $product) {
  190. if ($this->isLockedPrice($product))
  191. return 0;
  192. if ($this->customer && !$this->customer->hasSoleil())
  193. return 0;
  194. if (($product->getSoleil() == 1)) {
  195. if ($this->getCartTotal() >= 2500) {
  196. return $product->getPrice() * 0.30;
  197. } else if ($this->getCartTotal() >= 2000) {
  198. return $product->getPrice() * 0.20;
  199. } else if ($this->getCartTotal() >= 1500) {
  200. return $product->getPrice() * 0.15;
  201. } else if ($this->getCartTotal() >= 1000) {
  202. return $product->getPrice() * 0.10;
  203. } else if ($this->getCartTotal() >= 400) {
  204. return $product->getPrice() * 0.05;
  205. }
  206. // } else {
  207. } else if (($product->getSoleil() == 0)) {
  208. if ($this->getCartTotal() >= 2500) {
  209. return $product->getPrice() * 0.1;
  210. } else if ($this->getCartTotal() >= 2000) {
  211. return $product->getPrice() * 0.05;
  212. }
  213. }
  214. return 0;
  215. }
  216. public function getSpecialDiscounts(Product $product, $qty = 1) {
  217. $from = mktime(0, 0, 0, 11, 1, 2025);
  218. $limit = mktime(23, 59, 59, 12, 15, 2025);
  219. $now = time();
  220. if (($now < $from) || ($now > $limit)) {
  221. return 0;
  222. }
  223. // $refs = ['3006063','3006064','3006067','3006071','3006075','3006345','3006352','3006354','3006411','3006412','3006415','3006419','3006420','3006423','3006427','3006428','3006431','3006435','3006436','3006439','3006443','3006444','3006447','3006451','3006452','3006455','3006731','3006732','3006733','3006734','3006735','3006736','3006737','3006738','3006739','3006740','3006741','3006742','3006743','3006744','3006745','3006746','3006747','3006748','3006749','3006750','3006751','3006752','3006753','3006754','3006360','3006363','3006688','3006689','3006692','3006755','3006756','3006758'];
  224. // if(in_array($product->getModelSAP(), $refs)){
  225. // if($qty>=3){
  226. // return $product->getPrice() * (1-($qty-floor($qty/3))/$qty);
  227. // }
  228. // }
  229. // return 0;
  230. $refs = ['3006063','3006064','3006067','3006071','3006075','3006345','3006352','3006354','3006411','3006412','3006415','3006419','3006420','3006423','3006427','3006428','3006431','3006435','3006436','3006439','3006443','3006444','3006447','3006451','3006452','3006455','3006731','3006732','3006733','3006734','3006735','3006736','3006737','3006738','3006739','3006740','3006741','3006742','3006743','3006744','3006745','3006746','3006747','3006748','3006749','3006750','3006751','3006752','3006753','3006754','3006360','3006363','3006688','3006689','3006692','3006755','3006756','3006758'];
  231. if(in_array($product->getModelSAP(), $refs)){
  232. if($qty>=20){
  233. return $product->getPrice() * 0.3 + $this->getSoleilDiscount($product);
  234. }else if($qty>=15){
  235. return $product->getPrice() * 0.25 + $this->getSoleilDiscount($product);
  236. }else if($qty>=10){
  237. return $product->getPrice() * 0.20 + $this->getSoleilDiscount($product);
  238. }else if($qty>=5){
  239. return $product->getPrice() * 0.15 + $this->getSoleilDiscount($product);
  240. }
  241. }
  242. return 0;
  243. $refs = ['200013', '200014', '200015', '200016', '200017', '200018', '200019', '200020', '200021', '200029', '200033', '200034', '200035', '200040', '200068', '200069', '200070', '200071', '200072', '200073', '200074', '200075', '200076', '200077'];
  244. if(in_array($product->getModel(), $refs)){
  245. return $product->getPrice() * 0.15;
  246. }
  247. $refs = ['22661', '22672', '22668', '22670', '22662', '22663', '22664', '22665', '22666'];
  248. if(in_array($product->getId(), $refs)){
  249. if($qty>=11){
  250. return $product->getPrice() * (1-($qty-1)/$qty);
  251. }
  252. }
  253. $refs = ['22035', '22036', '22037', '22038', '22039', '22635', '22636'];
  254. if(in_array($product->getId(), $refs)){
  255. if($qty>=16){
  256. return $product->getPrice() * (1-($qty-2)/$qty);
  257. }
  258. }
  259. return 0;
  260. }
  261. public function getSpecialDiscountsCart(Product $product, $qty) {
  262. // echo('getSpecialDiscountsCart '. $product->getModel().' '.$qty);
  263. $from = mktime(0, 0, 0, 4, 5, 2023);
  264. $limit = mktime(23, 59, 59, 12, 31, 2023);
  265. $now = time();
  266. if (($now < $from) || ($now > $limit)) {
  267. return 0;
  268. }
  269. $refs = ['13521', '13700.6', '13702.6', '15407R', '15408R', '15409R', '17086', '17091', '17092', '17093', '17094', '17095', '17097', '17126R', '17127R', '17145', '17156V', '17173', '17174', '17175', '17180J', '17181J', '17190B', '17191B', '17195V', '17196V', '18104G', '18105G', '18136', '18413V', '18417B', '18419A', '18420A', '18423A', '18424A', '18426A', '18427A', '18427V', '18428A', '18448.R', '18452.R', '18456.N', '18456.R', '64130', '64131', '75505.1', '75505.4', '75506.1', '75511.8', '75511.9', '75512.1', '75512.9', '75527.1', '75527.5', '75533', '75534', '75535', '75536', '75537', '75539', '75540', '75541', '75542', '75543', '75544', '75549.2', '75550.1', '75550.5', '75550.7', '75551.1', '75551.5', '75552.1', '75554.5', '75555.5', '75562.3', '75562.4', '75597', '75601.3', '75602.3', '75605.3', '75622.6', '75628.2', '75628.3', '75661.2', '75665.1', '75669.1', '75678.2', '75680.2', '75681.1', '75681.2', '75682.1', '75682.2', '75683.1', '75683.2', '75684.1', '75684.2', '75685.1', '75685.2', '75686.1', '75686.2', '75687.1', '75687.2', '75688.1', '75688.2', '75717.1', '75817.2', '75845.1', '75894.1', '75894.2', '75899.1', '75900.1', '75900.2', '75900.3', '75900.4', '75901.1', '75901.2', '75901.3', '75901.4', '75902.2', '75902.4', '75903.2', '75905.1', '75905.2', '75905.3', '75905.4', '75910.1', '75910.2', '75910.3', '75910.4', '75911.3', '75911.4', '75912.1', '75912.2', '75912.3', '75912.4', '75913.1', '75913.2', '75913.3', '75913.4', '75914.1', '75914.3', '75914.4', '75915.2', '75915.3', '75915.4', '75920.1', '75920.3', '75921.1', '75921.3', '75922.1', '75922.3', '75930.1', '75930.2', '75930.3', '75930.4', '75931.2', '75931.3', '75931.4', '75932.1', '75932.2', '75932.3', '75932.4', '75933.1', '75933.2', '75933.3', '75933.4', '75934.1', '75934.2', '75934.3', '75935.1', '75935.2', '75935.3', '75935.4', '76072.2', '76088.1', '76089.1', '76090.1', '76091.1', '76091.2', '76158.1', '76158.2', '76159.1', '76159.2', '76160.2', '76161.1', '76161.2', '77503', '77992.8', '77994.6', '77994.8', '78194', '78443.5', '78444.4', '78444.5', '78445.4', '78445.5', '78445.6', '78445.7', '78445.8', '78448.3', '78458', '78459', '78462', '79144.1', '79640.1', '79645.1', 'D208152', 'D220011', 'D220016', 'D220035', 'D220056', 'D220058', 'D220066', 'D220081', 'D220086', 'D220111', 'D220116', 'D220135', 'D220156', 'D220158', 'D220168', 'D220181', 'D220186', 'D220211', 'D220216', 'D220235', 'D220256', 'D220258', 'D220266', 'D220268', 'D220281', 'D220286', 'D220311', 'D220316', 'D220356', 'D220358', 'D220366', 'D220368', 'D220411', 'D220416', 'D220435', 'D220456', 'D220458', 'D220466', 'D220468', 'D221006', 'D221016', 'D221018', 'D221021', 'D221023', 'D221024', 'D221026', 'D221028', 'D221029', 'D221035', 'D221036', 'D221039', 'D221045', 'D221046', 'D221056', 'D221057', 'D221061', 'D221074', 'D221079', 'D221098', 'D221105', 'D221157', 'D221162', 'D221199', 'D221204', 'D221205', 'D221206', 'D221209', 'D221210', 'MO10357', 'MO10358', 'MO10359', 'MO10365', 'MO10366', 'MO10373', 'MO10380', 'MO10387', 'MO10394', 'MO10395', 'MO10396', 'MO10397', 'MO10398', 'MO10399', 'MO10400', 'MO10401', 'MO10402', 'MO10403', 'MO10404', 'MO10405', 'MO10406', 'MO10407', 'MO10408', 'MO10411', 'MO10412', 'MO10413', 'MO10414', 'MO10419', 'MO10420', 'MO10456', 'MO10464', 'MO10465', 'MO10466', 'MO10467', 'MO10592', 'MO10593', 'MO10685', 'MO10686', 'MO10689', 'MO10692', 'MO10838', 'MO10839', 'MO10841', 'MO10842', 'MO10843', 'MO10844', 'MO10845', 'MO10846', 'MO10847', 'MO10848', 'MO10849', 'MO10850', 'MO10851', 'MO10852', 'MO10853', 'MO10854', 'MO10855', 'MO10856', 'MO10857', 'PP10018', 'PP10028', 'PP10044', 'PP10050', 'PP10056', 'PP10061'];
  270. if(in_array($product->getModel(), $refs)){
  271. return $product->getPrice() * 0.5;
  272. }
  273. $refs = ['76072.2', '76088.1', '76091.1', '76091.2', '76102.2', '76103.2', '76105.2', '76106.2', '76161.1', '76161.2', '76162.1', '76162.2', '76162.3', '76170.1', '76170.2', '76170.3', '76171.1', '76171.2', '76171.3', '76172.2', '76172.3', '76173.3', '76174.2', '76174.3', '76175.2', '76175.3', '76180.1', '76180.2', '76180.3', '76181.1', '76181.2', '76181.3', '76184.1', '76185.1', '76185.2', '76186.1', '76186.2', '76187.1', '76187.2', '76188.1', '76188.2', '76189.1', '76189.2', '76190.1', '76195.1', '76197.2', '76198.1', '76199.2', '76208.1', '76208.2', '76209.1', '76209.2', '76210.2', '76213.2', '76232.1', '76232.2', '76232.3', '76240.1', '76240.2', '76240.3', '76241.1', '76241.2', '76241.3', '76242.1', '76242.2', '76242.3', '76243.1', '76243.2', '76243.3', '76244.2', '76244.3', '76245.3', '76246.3', '76247.1', '76247.2', '76247.3', '76248.1', '76248.2', '76248.3', '76252.2', '76260.1', '76260.2', '76260.3', '76261.1', '76261.2', '76261.3', '76263.2', '76265.2', '76266.2', '76269.2', '76272.2', '76273.1', '76273.2', '76273.3', '76274.1', '76274.2', '76274.3', '76278.2', '76288.1', '76288.2', '76289.1', '76289.2', '76290.1', '76290.2', '76291.1', '76291.2', '76292.1', '76292.2', '76299.1', '76299.2', '76300.1', '76300.2', '76303.1', '76305.1', '76306.1', '76307.1', '76308.1', '76310.1', '76310.2', '76318.1', '76318.2', '76319.1', '76319.2', '76320.1', '76320.2', '76321.1', '76321.2', '76322.1', '76322.2', '76323.1', '76323.2', '76324.1', '76324.2', '76325.1', '76325.2', '76326.1', '76326.2', '76327.1', '76327.2', '76328.1', '76328.2', '76329.1', '76329.2', '78458', '78459', '78462', 'CH10050', 'D208152', 'D400240', 'MO10456', 'MO10464', 'MO10465', 'MO10466', 'MO10467', '15408R', '71045.4', '71045.7', '71045.8', '71045.9', '71046.7', '71200.5', '71201.3', '71201.5', '71203.2', '71203.3', '71208.5', '71209.3', '71209.5', '71210.2', '71211.2', '76066.5', '76066.6', '76066.7', '76067.5', '76067.6', '76067.7', '76068.5', '76068.6', '76068.7', '76069.5', '76069.6', '76069.7', '76070.5', '76070.6', '76070.7', '76071.5', '76071.6', '76071.7'];
  274. if(in_array($product->getModel(), $refs)){
  275. if($qty >= 10){
  276. return $product->getPrice() * 0.5;
  277. }else if($qty >= 5){
  278. return $product->getPrice() * 0.45;
  279. }else if($qty >= 4){
  280. return $product->getPrice() * 0.4;
  281. }else if($qty >= 3){
  282. return $product->getPrice() * 0.35;
  283. }else if($qty >= 2){
  284. return $product->getPrice() * 0.3;
  285. }
  286. }
  287. return 0;
  288. }
  289. public function hasSoleilDiscount() {
  290. if($this->customer) {
  291. return $this->customer->hasSoleil();
  292. }
  293. return true;
  294. }
  295. public function hasWelcomeDiscount() {
  296. $customer = $this->cartMgr->getCustomer();
  297. if(empty($customer) || !$customer->hasBienvenue()) {
  298. return false;
  299. }
  300. $date = date('Y-m-d H:i:s', time() - 365 * 24 * 60 * 60);
  301. $sql = "select count(*) as nb from orders where customers_id = ".$customer->getId()." and date_purchased>'" . $date . "' and (orders_status = 1 OR orders_status = 2 OR orders_status = 3 OR orders_status = 88896)";
  302. $st = $this->em->getConnection()->executeQuery($sql);
  303. $count = $st->fetch();
  304. return $count['nb'] == 0;
  305. }
  306. public function hasTVADiscount() {
  307. //return true;
  308. $start = mktime(10, 0, 0, 9, 27, 2019);
  309. $end = mktime(23, 59, 59, 9, 29, 2019);
  310. $now = time();
  311. return ($now >= $start) && ($now <= $end);
  312. }
  313. public function getCartTotal() {
  314. $cart = $this->cartMgr->getCart();
  315. return $cart->getTotalProducts();
  316. }
  317. protected function round($value) {
  318. return round($value, 2);
  319. }
  320. protected function getReducedPriceByPercent($price, $percent) {
  321. return $price*(1-$percent/100);
  322. }
  323. public function isLockedPrice(Product $product) {
  324. if(!$product->isProduct())
  325. return false;
  326. $manufacturer = $product->getManufacturer();
  327. return $manufacturer && ($manufacturer->getLockedPrice() == 1);
  328. }
  329. public function getPriceInfos(Product $product) {
  330. $price = $this->getPrice($product, 1, true);
  331. $normalPrice = $this->round($product->getPrice(true));
  332. return [
  333. 'normal' => $normalPrice,
  334. 'price' => $price,
  335. 'discountType' => $this->currentDiscountType,
  336. 'percent' => $normalPrice > 0 ? number_format(round((($price-$normalPrice)/$normalPrice)*100), 2, ".", "") : ''
  337. ];
  338. }
  339. public function getPriceGrid(Product $product) {
  340. $max_qty = 1;
  341. $p_tmp = 0;
  342. $priceLines = array();
  343. $from = 0;
  344. $normalPrice = $this->round($product->getPrice(false));
  345. for ($i = 1; $i <= $max_qty; $i++) {
  346. $p = $this->getPrice($product, $i, false, false);
  347. if (count($priceLines) > 0) {
  348. $priceLines[count($priceLines) - 1]['to'] = ($i - 1);
  349. }
  350. if ($p_tmp != $p) {
  351. $p_tmp = $p;
  352. $from = $i;
  353. $priceLines[] = array(
  354. 'price' => $p,
  355. 'normal' => $normalPrice,
  356. 'priceFormat' => number_format($p, 2, ".", ""),
  357. 'normalFormat' => number_format($normalPrice, 2, ".", ""),
  358. 'percent' => number_format(round((($p-$normalPrice)/$normalPrice)*100), 2, ".", ""),
  359. 'from' => $from,
  360. 'to' => "",
  361. 'discountType' => $this->currentDiscountType
  362. );
  363. }
  364. }
  365. return $priceLines;
  366. }
  367. public function updateCartPrice(Cart $cart){
  368. $items = $cart->getItems();
  369. if($this->cartHasOfferedProducts($cart)) {
  370. $this->applyDiscountsToCart($cart);
  371. }
  372. foreach($items as $item){
  373. $price = $this->getPrice($item->getProduct(true, $cart->getPriceGroup()), $item->getQuantity());
  374. $this->setCartItemPrice($item);
  375. }
  376. $this->cartMgr->save($cart);
  377. }
  378. public function setCartItemPrice(\App\Entity\CartItem $item){
  379. if($item->getQuantityOffered() > 0) {
  380. $soleilDiscount = 0;
  381. if($item->getMarketingRule()) {
  382. $soleilDiscount = $item->getMarketingRule()->getSkipSoleilDiscount() === true ? 0 : $this->getSoleilDiscount($item->getProduct(), true);
  383. }
  384. $price = $item->getProduct()->getPrice(true, $item->getCart()->getPriceGroup()) - $this->round($soleilDiscount);
  385. $item->setUnitPrice($price);
  386. $item->setTotalPrice($price * ($item->getQuantity() - $item->getQuantityOffered()));
  387. }else if($this->currentDiscountType != \App\Entity\MarketingRule::TYPE_OFFERED){
  388. $item->setUnitPrice($this->getPrice($item->getProduct(), $item->getQuantity(true), true));
  389. $item->setTotalPrice($this->getPrice($item->getProduct(), $item->getQuantity(), true) * $item->getQuantity());
  390. }else{
  391. $item->setUnitPrice($item->getProduct()->getPrice(true, $item->getCart()->getPriceGroup()));
  392. $item->setTotalPrice($item->getProduct()->getPrice(true, $item->getCart()->getPriceGroup()) * $item->getQuantity());
  393. }/*else{
  394. $item->setUnitPrice($item->getProduct()->getPrice());
  395. $qty = $item->getQuantity();
  396. $qtyOffered = 0;
  397. if($qty >= $this->currentMarketingRule->getQtyRequested()){
  398. $qtyOffered = $this->currentMarketingRule->getQtyOffered() * floor($qty / $this->currentMarketingRule->getQtyRequested());
  399. }
  400. $item->setTotalPrice($item->getProduct()->getPrice() * ($qty - $qtyOffered));
  401. }*/
  402. $item->setMarketingRule($this->currentMarketingRule);
  403. $item->setDiscountType($this->currentDiscountType);
  404. }
  405. protected function getPercent($discount, $normalPrice) {
  406. return round(($discount) / $normalPrice * 100) . "%";
  407. }
  408. public function getDiscountsByProduct(Product $product, $onlyActive = true) {
  409. if($this->cartMgr->isExpert())
  410. return null;
  411. return $this->em->getRepository(\App\Entity\MarketingRule::class)->getByProduct($product, $onlyActive);
  412. }
  413. public function getBestDiscountByProduct(Product $product, $onlyActive = true) {
  414. if($this->cartMgr->isExpert())
  415. return null;
  416. $discounts = $this->em->getRepository(\App\Entity\MarketingRule::class)->getByProduct($product, $onlyActive);
  417. $best = null;
  418. $bestAmount = null;
  419. foreach($discounts as $discount){
  420. $discountAmount = $discount->getProductDiscountByCart($product, null);
  421. if(empty($best) || ($bestAmount<$discountAmount)) {
  422. $best = $discount;
  423. $bestAmount = $discountAmount;
  424. }
  425. }
  426. return empty($best) ? [] : [$best];
  427. }
  428. public function getDiscountsByCart(Cart $cart) {
  429. $products = $cart->getProducts();
  430. return $this->em->getRepository(\App\Entity\MarketingRule::class)->getByProducts($products, true);
  431. }
  432. public function cartHasOfferedProducts(Cart $cart) {
  433. if($this->cartMgr->isExpert())
  434. return false;
  435. $discounts = $this->getDiscountsByCart($cart);
  436. foreach($discounts as $discount) {
  437. if($discount->getType() == \App\Entity\MarketingRule::TYPE_OFFERED) {
  438. return true;
  439. }
  440. }
  441. return false;
  442. }
  443. public function applyDiscountsToCart(Cart $cart) {
  444. $discounts = $this->getDiscountsByCart($cart);
  445. foreach($discounts as $discount) {
  446. if($discount->getType() == \App\Entity\MarketingRule::TYPE_OFFERED) {
  447. $cart->applyDiscount($discount);
  448. }
  449. }
  450. }
  451. public function setPrice(Product $product, $price, \App\Entity\PriceGroup $group) {
  452. $productPrice = $this->em->getRepository(\App\Entity\ProductPrice::class)->findOneBy(
  453. [
  454. 'product' => $product,
  455. 'group' => $group
  456. ]
  457. );
  458. if(empty($productPrice)) {
  459. $productPrice = new \App\Entity\ProductPrice();
  460. $productPrice->setGroup($group);
  461. $productPrice->setProduct($product);
  462. }
  463. $productPrice->setPrice($price);
  464. $this->em->persist($productPrice);
  465. $this->em->flush();
  466. }
  467. public function setPriceByCode(Product $product, $price, string $code) {
  468. $priceGroup = $this->em->getRepository(\App\Entity\PriceGroup::class)->findOneByCode($code);
  469. if($priceGroup) {
  470. return $this->setPrice($product, $price, $priceGroup);
  471. }
  472. return null;
  473. }
  474. public function removePrice(Product $product, \App\Entity\PriceGroup $group) {
  475. $productPrice = $this->em->getRepository(\App\Entity\ProductPrice::class)->findOneBy(
  476. [
  477. 'product' => $product,
  478. 'group' => $group
  479. ]
  480. );
  481. if($productPrice) {
  482. $this->em->remove($productPrice);
  483. $this->em->flush();
  484. }
  485. return true;
  486. }
  487. }