PluginProbe
ShopBuilder – WooCommerce Builder For Elementor / 3.4.0
ShopBuilder – WooCommerce Builder For Elementor v3.4.0
3.4.2 3.4.1 3.4.0 2.0.1 2.0.2 2.0.3 2.1.0 2.1.1 2.1.10 2.1.11 2.1.12 2.1.13 2.1.14 2.1.15 2.1.2 2.1.3 2.1.4 2.1.5 2.1.6 2.1.7 2.1.8 2.1.9 2.2.0 2.2.1 2.2.2 All 63 releases
shopbuilder / app / Elementor / Widgets / Single / ProductAddToCart.php

ProductAddToCart.php in ShopBuilder – WooCommerce Builder For Elementor 3.4.0, at app/Elementor/Widgets/Single/ProductAddToCart.php

327 lines 10.0 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * Main ProductDescription class.
4 *
5 * @package RadiusTheme\SB
6 */
7
8 namespace RadiusTheme\SB\Elementor\Widgets\Single;
9
10 use RadiusTheme\SB\Helpers\Fns;
11 use RadiusTheme\SB\Abstracts\ElementorWidgetBase;
12 use RadiusTheme\SB\Elementor\Widgets\Controls\AddToCartSettings;
13 use RadiusTheme\SBPRO\Elementor\Widgets\Controls\CatalogButtonSettings;
14 use RadiusTheme\SBPRO\Modules\CatalogMode\CatalogModeFns;
15 use RadiusTheme\SBPRO\Modules\CatalogMode\CatalogModeFrontEnd;
16 use RadiusTheme\SBPRO\Modules\BackInStockNotifier\BackInStockNotifierFrontEnd;
17
18 // Do not allow directly accessing this file.
19 if ( ! defined( 'ABSPATH' ) ) {
20 exit( 'This script cannot be accessed directly.' );
21 }
22
23 /**
24 * Product Description class
25 */
26 class ProductAddToCart extends ElementorWidgetBase {
27 /**
28 * Construct function
29 *
30 * @param array $data default array.
31 * @param mixed $args default arg.
32 */
33 public function __construct( $data = [], $args = null ) {
34 $this->rtsb_name = esc_html__( 'Product add to cart', 'shopbuilder' );
35 $this->rtsb_base = 'rtsb-product-add-to-cart';
36 parent::__construct( $data, $args );
37 }
38 /**
39 * Widget Field
40 *
41 * @return array
42 */
43 public function widget_fields() {
44 if ( Fns::is_catalog_mode() ) {
45 return CatalogButtonSettings::settings( $this );
46 } else {
47 return AddToCartSettings::widget_fields( $this );
48 }
49 }
50 /**
51 * Set Widget Keyword.
52 *
53 * @return array
54 */
55 public function get_keywords() {
56 return [ 'Cart' ] + parent::get_keywords();
57 }
58 /**
59 * Widget Field.
60 *
61 * @return void
62 */
63 public function the_hooks() {
64 $controllers = $this->get_settings_for_display();
65 add_filter( 'rtsb/module/flash_sale_countdown/show_counter', '__return_false', 99 );
66 $product = Fns::get_product();
67 $is_visible_qty = Fns::is_visible_qty_input( $product );
68
69 if ( ! empty( $controllers['quantity_style'] ) && $is_visible_qty ) {
70 if ( in_array( $controllers['quantity_style'], [ 'style-1', 'style-2' ], true ) ) {
71 add_action( 'woocommerce_before_quantity_input_field', [ $this, 'quantity_wrapper_start' ] );
72 add_action( 'woocommerce_after_quantity_input_field', [ $this, 'quantity_wrapper_end' ] );
73 }
74
75 if ( in_array( $controllers['quantity_style'], [ 'style-3', 'style-4' ], true ) && $is_visible_qty ) {
76 add_action( 'woocommerce_before_quantity_input_field', [ $this, 'quantity_wrapper_with_inner_border' ] );
77 add_action( 'woocommerce_after_quantity_input_field', [ $this, 'close_quantity_wrapper' ] );
78 }
79 }
80
81 if ( $this->is_edit_mode() ) {
82 if ( class_exists( Rtwpvs\Controllers\Hooks::class ) ) {
83 remove_filter( 'woocommerce_ajax_variationX_threshold', [ Rtwpvs\Controllers\Hooks::class, 'ajax_variation_threshold' ], 99 );
84 }
85
86 add_filter( 'woocommerce_ajax_variation_threshold', [ $this, 'override_ajax_variation_threshold' ], 99 );
87 }
88 }
89 /**
90 * Start quantity wrapper.
91 *
92 * @return void
93 */
94 public function reset_hooks() {
95 $controllers = $this->get_settings_for_display();
96 $product = Fns::get_product();
97 $is_visible_qty = Fns::is_visible_qty_input( $product );
98 if ( ! empty( $controllers['quantity_style'] ) && $is_visible_qty ) {
99 if ( in_array( $controllers['quantity_style'], [ 'style-1', 'style-2' ], true ) ) {
100 remove_action( 'woocommerce_before_quantity_input_field', [ $this, 'quantity_wrapper_start' ] );
101 remove_action( 'woocommerce_after_quantity_input_field', [ $this, 'quantity_wrapper_end' ] );
102 }
103
104 if ( in_array( $controllers['quantity_style'], [ 'style-3', 'style-4' ], true ) && $is_visible_qty ) {
105 remove_action( 'woocommerce_before_quantity_input_field', [ $this, 'quantity_wrapper_with_inner_border' ] );
106 remove_action( 'woocommerce_after_quantity_input_field', [ $this, 'close_quantity_wrapper' ] );
107 }
108 }
109 }
110 /**
111 * Start quantity wrapper.
112 *
113 * @return void
114 */
115 public function quantity_wrapper_start() {
116 $controllers = $this->get_settings_for_display();
117 ?>
118 <!-- Quantity Wrapper Start -->
119 <div class="rtsb-quantity-box-group rtsb-quantity-box-group-<?php echo esc_attr( $controllers['quantity_style'] ); ?>"">
120 <button type="button" class="rtsb-quantity-btn rtsb-quantity-minus">
121 <?php Fns::print_html( Fns::icons_manager( $controllers['decrement_icon'] ), true ); ?>
122 </button>
123 <?php
124 }
125
126 /**
127 * End quantity wrapper.
128 *
129 * @return void
130 */
131 public function quantity_wrapper_end() {
132 $controllers = $this->get_settings_for_display();
133 ?>
134 <button type="button" class="rtsb-quantity-btn rtsb-quantity-plus">
135 <?php Fns::print_html( Fns::icons_manager( $controllers['increment_icon'] ), true ); ?>
136 </button>
137 </div>
138 <!-- Quantity Wrapper End -->
139 <?php
140 }
141
142 /**
143 * Start quantity wrapper with inner border.
144 *
145 * @return void
146 */
147 public function quantity_wrapper_with_inner_border() {
148 $controllers = $this->get_settings_for_display();
149 $inner_border = ! empty( $controllers['show_inner_border'] ) ? 'show-inner-border' : '';
150 ?>
151 <!-- Quantity Wrapper Start -->
152 <div class="rtsb-quantity-box-group rtsb-quantity-box-group-<?php echo esc_attr( $controllers['quantity_style'] . ' ' . $inner_border ); ?>">
153 <div class="rtsb-qty-btns-group">
154 <button type="button" class="rtsb-quantity-btn rtsb-quantity-plus">
155 <?php Fns::print_html( Fns::icons_manager( $controllers['increment_icon'] ), true ); ?>
156 </button>
157 <button type="button" class="rtsb-quantity-btn rtsb-quantity-minus">
158 <?php Fns::print_html( Fns::icons_manager( $controllers['decrement_icon'] ), true ); ?>
159 </button>
160 </div>
161 <?php
162 }
163
164 /**
165 * Close quantity wrapper.
166 *
167 * @return void
168 */
169 public function close_quantity_wrapper() {
170 ?>
171 </div>
172 <!-- Quantity Wrapper End -->
173 <?php
174 }
175 /**
176 * Render catalog mode contact buttons
177 *
178 * @param int $product_id Product ID.
179 * @return void
180 */
181 public function catalog_mode_buttons( $product_id ) {
182 $settings = CatalogModeFns::get_options();
183 $contact_buttons = $settings['contact_buttons'] ?? [];
184 if ( empty( $contact_buttons ) || ! is_array( $contact_buttons ) ) {
185 return;
186 }
187
188 echo '<div class="rtsb-product-add-to-cart">';
189 echo '<div class="rtsb-catalog-mode-product-page-buttons">';
190
191 foreach ( $contact_buttons as $button_type ) {
192 $this->render_contact_button( $button_type, $product_id, $settings );
193 }
194 echo '</div>';
195 echo '</div>';
196 }
197 /**
198 * Render specific contact button
199 *
200 * @param string $button_type Button type.
201 * @param int $product_id Product ID.
202 * @param array $settings Plugin settings.
203 * @return void
204 */
205 public function render_contact_button( $button_type, $product_id, $settings ) {
206 switch ( $button_type ) {
207 case 'custom':
208 CatalogModeFrontEnd::render_custom_button( $product_id, $settings );
209 break;
210 case 'whatsapp':
211 CatalogModeFrontEnd::render_whatsapp_button( $product_id, $settings );
212 break;
213 case 'call':
214 CatalogModeFrontEnd::render_call_button( $settings );
215 break;
216 case 'email':
217 CatalogModeFrontEnd::render_email_button( $settings );
218 break;
219 case 'inquiry':
220 CatalogModeFrontEnd::render_inquiry_button( $product_id, $settings );
221 break;
222 }
223 }
224
225 /**
226 * Show an editor-only notice when the add to cart button is hidden
227 * because the product is out of stock.
228 *
229 * @param \WC_Product|null $product Current product.
230 * @return void
231 */
232 public function out_of_stock_editor_notice( $product ) {
233 if ( ! $product instanceof \WC_Product || $product->is_in_stock() ) {
234 return;
235 }
236 $this->editor_notice(
237 esc_html__( 'The add to cart button and quantity are hidden because this product is out of stock.', 'shopbuilder' ),
238 'rtsb-add-to-cart-editor-notice'
239 );
240 }
241
242 /**
243 * Override WooCommerce AJAX variation threshold.
244 *
245 * @return int
246 */
247 public function override_ajax_variation_threshold() {
248 return 1;
249 }
250
251 /**
252 * Elementor Edit mode need some extra js for isotop reinitialize
253 *
254 * @return void
255 */
256 public function editor_script() {
257 if ( $this->is_edit_mode() ) {
258 ?>
259 <script type="text/javascript">
260 function addToCartAction() {
261 var singleAddToCart = jQuery('.rtsb-product-add-to-cart');
262
263 if (singleAddToCart.length > 0) {
264 singleAddToCart
265 .find(
266 '.stock.available-on-pre-order, .stock.available-on-backorder'
267 )
268 .remove();
269 }
270 }
271 if (typeof elementorFrontend !== 'undefined') {
272 elementorFrontend.hooks.addAction(
273 'frontend/element_ready/rtsb-product-add-to-cart.default',
274 () => {
275 addToCartAction();
276 }
277 );
278 }
279 </script>
280 <?php
281 }
282 }
283
284 /**
285 * Render Function
286 *
287 * @return void
288 */
289 protected function render() {
290 global $product;
291 $_product = $product;
292 $product = Fns::get_product();
293 $controllers = $this->get_settings_for_display();
294 $controllers['cart_icon_html'] = ! empty( $controllers['cart_icon'] ) ? Fns::icons_manager( $controllers['cart_icon'] ) : '';
295 $add_to_cart_visibility = rtsb()->has_pro() && Fns::is_guest_feature_disabled( 'hide_add_to_cart', '' );
296 $controllers['visibility'] = $add_to_cart_visibility ? ' rtsb-not-visible' : ' rtsb-is-visible';
297
298 $this->the_hooks();
299 $this->theme_support();
300
301 if ( rtsb()->has_pro() && ! empty( $controllers['enable_single_ajax_add_to_cart'] ) ) {
302 wp_enqueue_script( 'wc-add-to-cart' );
303 }
304 if ( Fns::is_back_in_stock_notifier_enable() ) {
305 remove_filter( 'woocommerce_get_stock_html', [ BackInStockNotifierFrontEnd::instance(),'add_waitlist_to_stock_html' ], 20, 2 );
306 }
307 $data = [
308 'template' => 'elementor/single-product/add-to-cart',
309 'controllers' => $controllers,
310 'product_type' => $product ? $product->get_type() : '',
311 ];
312 if ( $this->is_builder_mode() && Fns::is_catalog_mode() ) {
313 $this->catalog_mode_buttons( $product->get_id() );
314 } else {
315 Fns::load_template( $data['template'], $data );
316 $this->out_of_stock_editor_notice( $product );
317 }
318
319 $this->editor_cart_icon_script();
320 add_filter( 'rtsb/module/flash_sale_countdown/show_counter', '__return_true', 99 );
321 $this->reset_hooks();
322 $this->theme_support( 'render_reset' );
323 $this->editor_script();
324 $product = $_product; // phpcs:ignore WordPress.WP.GlobalVariablesOverride.Prohibited
325 }
326 }
327