PluginProbe
FluentCart A New Era of eCommerce – Faster, Lighter, and Simpler / 1.3.26
FluentCart A New Era of eCommerce – Faster, Lighter, and Simpler v1.3.26
1.6.6 1.6.5 1.6.4 1.6.3 1.6.2 1.6.1 1.6.0 1.5.4 1.5.5 1.5.3 1.5.2 1.5.1 1.5.0 1.4.2 1.4.1 1.4.0 1.3.28 1.3.27 1.3.26 1.3.25 1.3.23 1.3.22 1.3.21 1.3.20 1.3.19 All 49 releases
fluent-cart / app / Services / Renderer / CartItemRenderer.php

CartItemRenderer.php in FluentCart A New Era of eCommerce – Faster, Lighter, and Simpler 1.3.26, at app/Services/Renderer/CartItemRenderer.php

306 lines 12.1 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 namespace FluentCart\App\Services\Renderer;
4
5 use FluentCart\App\Helpers\Helper;
6 use FluentCart\App\Models\Cart;
7 use FluentCart\Framework\Support\Arr;
8
9 class CartItemRenderer
10 {
11 protected $item = [];
12 protected $cart = null;
13
14 protected $product = null;
15
16 protected $variant = null;
17
18 public function __construct($item = [], ?Cart $cart = null)
19 {
20 $this->item = $item;
21 $this->cart = $cart;
22 }
23
24 protected function getEventInfo()
25 {
26 return [
27 'item' => $this->item,
28 'cart' => $this->cart,
29 'product' => $this->product,
30 'variant' => $this->variant,
31 ];
32 }
33
34 public function render()
35 {
36 $wrapperClassAttributes = [
37 'fct_line_item',
38 'fct_product_id_' . Arr::get($this->item, 'post_id', ''),
39 'fct_item_id_' . Arr::get($this->item, 'id', ''),
40 'fct_item_type_' . Arr::get($this->item, 'other_info.payment_type', ''),
41 ];
42
43 if (Arr::get($this->item, 'featured_media')) {
44 $wrapperClassAttributes[] = 'fct_has_image';
45 }
46
47 $promoPriceOriginal = Arr::get($this->item, 'other_info.promo_price_original', 0);
48 if ($promoPriceOriginal && $promoPriceOriginal > $this->item['unit_price']) {
49 $promoPriceOriginal = $promoPriceOriginal * Arr::get($this->item, 'quantity', 1);
50 } else {
51 $promoPriceOriginal = '';
52 }
53 ?>
54 <div class="<?php $this->renderCssAtts($wrapperClassAttributes); ?>" role="listitem">
55 <div class="fct_line_item_info">
56 <?php $this->renderImage(); ?>
57 <div class="fct_item_content">
58 <?php $this->renderTitle(); ?>
59 <?php $this->renderChildVariants(); ?>
60 <?php do_action('fluent_cart/cart/line_item/line_meta', $this->getEventInfo()); ?>
61 </div>
62 </div><!-- .fct_line_item_info -->
63
64 <div class="fct_line_item_price" aria-label="<?php esc_attr_e('Price information', 'fluent-cart'); ?>">
65 <?php do_action('fluent_cart/cart/line_item/before_total', $this->getEventInfo()); ?>
66 <?php if($promoPriceOriginal) : ?>
67 <div style="text-decoration: line-through;" class="fct_line_item_total fct_promo_price" aria-label="<?php esc_attr_e('Original price', 'fluent-cart'); ?>">
68 <?php echo esc_html(Helper::toDecimal($promoPriceOriginal)); ?>
69 </div>
70 <?php endif; ?>
71 <span class="fct_line_item_total" aria-label="<?php esc_attr_e('Total price', 'fluent-cart'); ?>">
72 <?php echo esc_html(Helper::toDecimal(Arr::get($this->item, 'subtotal', 0))); ?>
73 </span>
74 <?php do_action('fluent_cart/cart/line_item/after_total', $this->getEventInfo()); ?>
75 </div><!-- .fct_line_item_price -->
76 </div>
77 <?php
78 }
79
80 public function renderTitle()
81 {
82 $href = Arr::get($this->item, 'view_url', '');
83
84 $mainTitle = (string) Arr::get($this->item, 'post_title', '');
85 $subtitle = (string) Arr::get($this->item, 'title', '');
86
87 $quantity = Arr::get($this->item, 'quantity', 1);
88
89 ?>
90 <div class="fct_item_title">
91 <?php do_action('fluent_cart/cart/line_item/before_main_title', $this->getEventInfo()); ?>
92 <?php if ($quantity > 1): ?>
93 <span class="fct_item_quantity" aria-label="<?php echo esc_attr(sprintf(
94 /* translators: %d: quantity */
95 __('Quantity %d', 'fluent-cart'), $quantity)); ?>">
96 <?php echo esc_attr($quantity); ?> <span aria-hidden="true">x</span>
97 </span>
98 <?php endif; ?>
99 <?php if ($href): ?>
100 <a
101 href="<?php echo esc_url($href); ?>"
102 aria-label="<?php echo esc_attr(sprintf(
103 /* translators: %s: product title */
104 __('View details for %s', 'fluent-cart'), $mainTitle)); ?>"
105 >
106 <?php echo wp_kses_post($mainTitle); ?>
107 </a>
108 <?php else: ?>
109 <?php echo wp_kses_post($mainTitle); ?>
110 <?php endif; ?>
111
112 <?php if ($mainTitle != $subtitle && $subtitle): ?>
113 <div class="fct_item_variant_title" aria-label="<?php esc_attr_e('Variant', 'fluent-cart'); ?>">
114 - <?php echo wp_kses_post($subtitle); ?>
115 </div>
116 <?php endif; ?>
117 <?php $this->maybeRenderPaymentTypeInfo(); ?>
118 <?php $this->maybeRenderPackageInfo(); ?>
119
120 <?php do_action('fluent_cart/cart/line_item/after_main_title', $this->getEventInfo()); ?>
121 </div>
122 <?php
123 }
124
125 public function renderImage()
126 {
127 $image = Arr::get($this->item, 'featured_media');
128 if (!$image) {
129 return;
130 }
131 $href = Arr::get($this->item, 'view_url', '');
132 $altText = sprintf(
133 /* translators: %s: product title */
134 __('Image of %s', 'fluent-cart'), Arr::get($this->item, 'title', __('product', 'fluent-cart')));
135 ?>
136 <div class="fct_item_image">
137 <?php if ($href): ?>
138 <a href="<?php echo esc_url($href); ?>">
139 <img src="<?php echo esc_url($image); ?>"
140 alt="<?php echo esc_attr($altText); ?>"/>
141 </a>
142 <?php else: ?>
143 <img src="<?php echo esc_url($image); ?>"
144 alt="<?php echo esc_attr($altText); ?>"/>
145 <?php endif; ?>
146 </div>
147 <?php
148 }
149
150 protected function renderCssAtts($atts)
151 {
152 echo esc_attr(implode(' ', $atts));
153 }
154
155 protected function maybeRenderPaymentTypeInfo()
156 {
157 $otherInfo = Arr::get($this->item, 'other_info', []);
158 $paymentType = Arr::get($otherInfo, 'payment_type', '');
159 $itemPrice = Arr::get($this->item, 'unit_price', 0);
160
161 if (isset($this->item['recurring_discounts'])) {
162 $otherInfo['recurring_discounts'] = $this->item['recurring_discounts'];
163 }
164
165 if ($paymentType === 'subscription') {
166 $subscriptionInfo = Helper::generateSubscriptionInfo($otherInfo, $itemPrice);
167 $setupFeeInfo = Helper::generateSetupFeeInfo($otherInfo);
168 $trialInfo = Helper::generateTrialInfo($otherInfo);
169 ?>
170 <div class="fct_item_payment_info">
171 <span class="sr-only"><?php esc_html_e('Payment information', 'fluent-cart'); ?></span>
172
173 <span> <?php echo wp_kses($subscriptionInfo, ['del' => true]); ?> </span>
174 <?php if ($trialInfo): ?>
175 <span class="trial-days"> <?php echo esc_html($trialInfo); ?> </span>
176 <?php endif; ?>
177 <?php if (!empty($setupFeeInfo)): ?>
178 <span class="setup-fee"> <?php echo esc_html($setupFeeInfo); ?> </span>
179 <?php endif; ?>
180 </div>
181 <?php
182 return;
183 }
184
185 $quantity = Arr::get($this->item, 'quantity', 1);
186
187 if ($quantity < 2) {
188 return;
189 }
190 ?>
191 <div class="fct_item_payment_info">
192 <?php
193 /* translators: %s is the item price */
194 printf(esc_html__('%s each', 'fluent-cart'), esc_html(Helper::toDecimal($itemPrice)));
195 ?>
196 </div>
197 <?php
198 }
199
200 protected function maybeRenderPackageInfo()
201 {
202 if (Arr::get($this->item, 'fulfillment_type') !== 'physical') {
203 return;
204 }
205
206 $otherInfo = Arr::get($this->item, 'other_info', []);
207 if (!is_array($otherInfo)) {
208 return;
209 }
210
211 $packageSlug = Arr::get($otherInfo, 'package_slug', '');
212 $package = Helper::getPackageBySlug($packageSlug);
213 if (!$package) {
214 return;
215 }
216
217 $name = Arr::get($package, 'name', '');
218 $type = Arr::get($package, 'type', '');
219
220 $parts = [];
221 if ($name) {
222 $parts[] = $name;
223 }
224
225 $storeWeightUnit = Helper::shopConfig('weight_unit') ?: 'kg';
226 $productWeight = floatval(Arr::get($otherInfo, 'weight', 0));
227 $productWeightUnit = Arr::get($otherInfo, 'weight_unit', $storeWeightUnit);
228 $convertedProductWeight = Helper::convertWeight($productWeight, $productWeightUnit, $storeWeightUnit);
229 $packageWeight = floatval(Arr::get($package, 'weight', 0));
230 $packageWeightUnit = Arr::get($package, 'weight_unit', $storeWeightUnit);
231 $convertedPackageWeight = Helper::convertWeight($packageWeight, $packageWeightUnit, $storeWeightUnit);
232 $totalWeight = $convertedProductWeight + $convertedPackageWeight;
233
234 if ($totalWeight) {
235 $formatted = rtrim(rtrim(number_format($totalWeight, 2), '0'), '.');
236 $parts[] = $formatted . ' ' . $storeWeightUnit;
237 }
238
239 if (!$parts) {
240 return;
241 }
242
243 $icon = ShippingMethodsRender::getPackageTypeIcon($type ?: 'box');
244 ?>
245 <div class="fct_item_package_info">
246 <?php echo $icon; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped ?>
247 <span><?php echo esc_html(implode(' · ', $parts)); ?></span>
248 </div>
249 <?php
250 }
251
252 public function renderChildVariants(){
253 $childVariants = Arr::get($this->item, 'child_variants', []);
254
255 if (empty($childVariants)) {
256 return;
257 }
258
259 $total = count($childVariants);
260
261 ?>
262 <div class="fct-bundle-products" data-fluent-cart-collapsibles>
263 <h4 class="fct-bundle-products-title">
264 <?php echo esc_html__('Bundle of', 'fluent-cart') . ':'; ?>
265 </h4>
266 <div class="fct-bundle-products-list">
267 <?php foreach (array_slice($childVariants, 0, 2) as $childVariant): ?>
268 <p>
269 <?php echo esc_html(Arr::get($childVariant, 'post_title')) . ' - ' . esc_html(Arr::get($childVariant, 'variation_title')); ?>
270 </p>
271 <?php endforeach; ?>
272
273 <?php if ($total > 2): ?>
274 <div class="fct-bundle-products-more">
275 <div class="fct-bundle-products-more-list">
276 <?php foreach (array_slice($childVariants, 2) as $childVariant): ?>
277 <p>
278 <?php echo esc_html(Arr::get($childVariant, 'post_title')) . ' - ' . esc_html(Arr::get($childVariant, 'variation_title')); ?>
279 </p>
280 <?php endforeach; ?>
281 </div>
282 </div>
283 <?php endif;?>
284 </div>
285
286 <?php if ($total > 2) : ?>
287 <a href="#" class="fct-see-more-btn" data-fluent-cart-collapsible-toggle>
288 <span class="see-more-text">
289 <?php echo esc_html__('See More', 'fluent-cart'); ?>
290 <svg xmlns="http://www.w3.org/2000/svg" width="12" height="7" viewBox="0 0 12 7" fill="none">
291 <path d="M0.75 0.75L5.04289 5.04289C5.37623 5.37623 5.54289 5.54289 5.75 5.54289C5.95711 5.54289 6.12377 5.37623 6.45711 5.04289L10.75 0.75" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/>
292 </svg>
293 </span>
294 <span class="see-less-text">
295 <?php echo esc_html__('See Less', 'fluent-cart'); ?>
296 <svg xmlns="http://www.w3.org/2000/svg" width="12" height="7" viewBox="0 0 14 8" fill="none">
297 <path d="M0.75 6.54297L6.04289 1.25008C6.37623 0.916742 6.54289 0.750076 6.75 0.750076C6.95711 0.750076 7.12377 0.916742 7.45711 1.25008L12.75 6.54297" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/>
298 </svg>
299 </span>
300 </a>
301 <?php endif; ?>
302 </div>
303 <?php }
304
305 }
306