PageSourceSearch

https://www.rjsinnovativebuilding.com/wp-content/plugins/trx_addons/components/api/woocommerce/woocommerce.js

js rjsinnovativebuilding.com collected 2026-10-06 20:33:14 UTC 67,159 bytes, 1,519 lines download raw bytes

1/* global jQuery */
2
3(function() {
4	"use strict";
5
6	var $window   = jQuery( window ),
7		$document = jQuery( document ),
8		$body     = jQuery( 'body' );
9
10	$document.on('action.before_init_trx_addons', function() {
11		// Remove theme-animations inside sliders with WooCommerce products
12		jQuery( '.slides.products .slider-slide' ).each( function() {
13			var $self = jQuery( this );
14			$self.find( '>[data-animation]' ).removeAttr( 'data-animation' );
15			$self.find( '>[data-post-animation]' ).removeAttr( 'data-post-animation' );
16		} );
17	} );
18
19	$document.on('action.ready_trx_addons', function() {
20
21		// WooCommerce categories on homepages
22		//----------------------------------------------------------
23
24		// Add arrows to the WooCommerce categories on homepages
25		if ( ! $body.hasClass( 'woocommerce' ) ) {
26			$body.find( '.widget_area:not(' + TRX_ADDONS_STORAGE['footer_wrap_class'] + ') .widget_product_categories:not(.inited)' ).each( function() {
27				var widget = jQuery(this).addClass('inited');
28				widget.find('ul.product-categories .has_children > a').append('<span class="open_child_menu"></span>');
29				widget.on('click', 'ul.product-categories.plain li a .open_child_menu', function(e) {
30					var $a = jQuery(this).parent();
31					if ($a.siblings('ul:visible').length > 0)
32						$a.siblings('ul').slideUp().parent().removeClass('opened');
33					else {
34						jQuery(this).parents('li').siblings('li').find('ul:visible').slideUp().parent().removeClass('opened');
35						$a.siblings('ul').slideDown().parent().addClass('opened');
36					}
37					e.preventDefault();
38					return false;
39				} );
40
41				// Resize handlers
42				jQuery(document).on('action.resize_trx_addons', function() {
43					trx_addons_woocommerce_resize_actions();
44				});
45				trx_addons_woocommerce_resize_actions();
46			
47				// Switch popup menu / hierarchical list on product categories list placed in sidebar
48				function trx_addons_woocommerce_resize_actions() {
49					var cat_menu = widget.find('ul.product-categories');
50					var sb = cat_menu.parents('.widget_area');
51					if ( sb.length > 0 && cat_menu.length > 0 ) {
52						if ( sb.width() == sb.parents('.content_wrap').width() ) {
53							if ( cat_menu.hasClass('inited') ) {
54								cat_menu.removeClass('inited').addClass('plain').superfish('destroy');
55								cat_menu.find('ul.animated').removeClass('animated').addClass('no_animated');
56							}
57						} else {
58							if ( ! cat_menu.hasClass('inited') ) {
59								cat_menu.removeClass('plain').addClass('inited');
60								cat_menu.find('ul.no_animated').removeClass('no_animated').addClass('animated');
61								trx_addons_init_sfmenu('body:not(.woocommerce) .widget_area:not(' + TRX_ADDONS_STORAGE['footer_wrap_class'] + ') .widget_product_categories ul.product-categories');
62							}
63						}
64					}
65				}
66			});
67		}
68
69		
70		// Extended attributes in single product
71		//----------------------------------------------------------
72
73		// Change a behaviour to AJAX for the button 'Add to Cart' placed inside the popup 'Quick View'
74		function trx_addons_woocommerce_add_to_cart_ajax( $popup, type ) {
75			if ( $popup.length ) {
76				var $bt = $popup.find( '.single_add_to_cart_button' );
77				if ( $bt.length ) {
78					var $form = $bt.parents( 'form.cart' );
79					var is_variable = $form.hasClass( 'variations_form' );
80					var is_grouped = $form.hasClass( 'grouped_form' );
81					var product_id = $bt.attr( 'value' );
82					if ( ! product_id ) {
83						product_id = $bt.siblings( 'input[name="product_id"],input[name="add-to-cart"]' ).eq(0).val();
84					}
85					$bt.addClass( 'add_to_cart_button ajax_add_to_cart' )
86						.attr( 'data-product_id', product_id );
87					if ( is_variable ) {
88						$bt.siblings( 'input[name="variation_id"]' )
89							.on( 'change', function() {
90								$bt.attr( 'data-product_id', jQuery( this ).val() );	// Variation ID must be in the 'data-product_id'
91							} );
92						$popup.find( '[data-attribute_name]' )
93							.on( 'change', function() {
94								var $fld = jQuery( this ),
95									attribute_name = $fld.data( 'attribute_name' );
96								$bt.attr( 'data-' + attribute_name, $fld.val() );
97							} );
98					}
99					$popup.find( '.input-text.qty' )
100						.on( 'change', function() {
101							$bt.attr( 'data-quantity', jQuery( this ).val() );
102						} );
103					if ( is_grouped ) {
104						// Prevent a WooCommerce event handler
105						$bt.addClass( 'wc-interactive' );
106						// Send ajax add_to_cart for each product in the grouped product
107						var add_grouped_to_cart = function( $products, idx ) {
108							if ( idx <= $products.length - 1 ) {
109								$bt.removeClass( 'added' );
110								$bt.addClass( 'loading' );
111							}
112							var qty = $products.eq( idx ).val();
113							if ( qty > 0 ) {
114								var pid = $products.eq( idx ).attr( 'name' ).replace( 'quantity[', '' ).replace( ']', '' );
115								jQuery( document.body ).trigger( 'adding_to_cart', [ $bt ] );
116								jQuery.post( wc_add_to_cart_params.wc_ajax_url.toString().replace( '%%endpoint%%', 'add_to_cart' ), {
117									product_id: pid,
118									quantity: qty
119								}, function( response ) {
120									var rez = trx_addons_parse_ajax_response( response );
121									if ( rez.error || ! rez.cart_hash ) {
122										$bt.removeClass( 'loading' );
123										alert( rez.error );
124										return false;
125									} else {
126										jQuery( document.body ).trigger( 'added_to_cart', [rez.fragments, rez.cart_hash, $bt] );
127										if ( idx < $products.length - 1 ) {
128											add_grouped_to_cart( $products, idx + 1 );
129										}
130									}
131								} );
132							} else if ( idx < $products.length - 1 ) {
133								add_grouped_to_cart( $products, idx + 1 );
134							} else {
135								$bt.removeClass( 'loading' );
136								$bt.addClass( 'added' );
137							}
138						};
139						$bt.on( 'click', function(e) {
140							var $products = $form.find( 'input[name^="quantity["]' );
141							if ( $products.length ) {
142								e.preventDefault();
143								e.stopImmediatePropagation();
144								add_grouped_to_cart( $products, 0 );
145								return false;
146							}
147						} );
148					}
149				}
150			}
151		}
152		if ( trx_addons_apply_filters( 'trx_addons_filter_ajax_add_to_cart_in_quick_view', true ) ) {
153			jQuery( document.body ).on( 'woosq_loaded', function( e ) {
154				trx_addons_woocommerce_add_to_cart_ajax( $body.find( '>.mfp-wrap' ), e.type );
155			} );
156			$document.on( 'qv_loader_stop', function( e ) {
157				trx_addons_woocommerce_add_to_cart_ajax( $body.find( '>#yith-quick-view-modal' ), e.type );
158			} );
159			$document.on( 'trx_qv_loaded', function( e ) {
160				trx_addons_woocommerce_add_to_cart_ajax( $body.find( '.trx-addons-woo-products-quick-view-modal' ), e.type );
161			} );
162			// Prevent the plugin 'Tutor' from adding extra classes to the button 'Add to Cart' before adding a product to the cart
163			$document.on( 'adding_to_cart', function( t, e ) {
164				setTimeout( function() {
165					e.removeClass("is-loading");
166				}, 0 );
167			} );
168			// Prevent the plugin 'Tutor' from adding extra classes to the button 'View Cart' after adding a product to the cart
169			$document.on( 'added_to_cart', function( t, e, r, o ) {
170				setTimeout( function() {
171					o.removeClass("is-loading")
172						.siblings("a.added_to_cart")
173							.removeClass( "tutor-btn tutor-btn-outline-primary tutor-btn-md tutor-btn-block" )
174							.find( '>span.tutor-icon-cart-line' ).remove();
175				}, 0 );
176			} );
177		}
178
179		// Init product attributes with variations
180		jQuery( document.body ).on( 'woosq_loaded', function( e ) {
181			trx_addons_woocommerce_init_variations( $body, 'popup_wpc' );
182		} );
183		$body.on( 'wcpt_product_modal_ready', function( e ) {
184			$document.trigger( 'action.init_hidden_elements', [$body] );
185		} );
186
187		$document.on( 'action.init_hidden_elements qv_loader_stop trx_qv_loaded', function( e, cont ) {
188			if ( ! cont ) cont = $body;
189			trx_addons_woocommerce_init_variations( cont, e.type );
190		} );
191
192		// Check available product variations
193		function trx_addons_woocommerce_init_variations( cont, type ) {
194			cont.find( '.variations_form.cart:not(.inited)' ).each( function() {
195				var form = jQuery(this).addClass('inited');
196				var trx_addons_attribs = form.find('.trx_addons_attrib_item');
197				if ( trx_addons_attribs.length === 0 ) return;
198
199				// First check after variation form inited
200				form.on( 'wc_variation_form', function( variation_form ) {
201					form.on( 'check_variations', function() {
202						trx_addons_woocommerce_check_variations( form );
203					} );
204					trx_addons_woocommerce_check_variations( form );
205				} );
206
207				// Click on our variations attribs
208				trx_addons_attribs.on( 'click', function(e) {
209					var $attrib = jQuery(this);
210					e.preventDefault();
211					if ( ! $attrib.hasClass('trx_addons_attrib_disabled') ) {
212						$attrib.toggleClass('trx_addons_attrib_selected').siblings().removeClass('trx_addons_attrib_selected');
213						var term = $attrib.hasClass('trx_addons_attrib_selected') ? $attrib.data('value') : '';
214						if ( term === '' ) {
215							$attrib.siblings('.trx_addons_attrib_item[data-value=""]').addClass('trx_addons_attrib_selected');
216						}
217						// Old way: not compatible with non-latin attribute names
218						// var attrib_name = $attrib.parents('.trx_addons_attrib_extended').data('attrib');
219						// $attrib.parents('.trx_addons_attrib_extended').parent().find('#'+attrib_name).val(term).trigger('change');
220						
221						// Way #2: still not compatible with non-latin attribute names, because the 'data-attrib' (urlencode)
222						// and the select's id (sanitize_title) encode non-ASCII chars in a different hex case (%D1 vs %d1),
223						// so the select is not found, its 'change' is not fired and the variations are not rechecked.
224						// $attrib.parents('.trx_addons_attrib_extended').parent().find('[id="'+attrib_name+'"]').val(term).trigger('change');
225						
226						// New way: find the select by the DOM relation (it is a neighbour of our extended block in the same cell),
227						// so it does not depend on the attribute name encoding at all.
228						$attrib.parents('.trx_addons_attrib_extended').parent().find('select').val(term).trigger('change');
229					}
230					return false;
231				} );
232			} );
233		}
234		
235		function trx_addons_woocommerce_check_variations( form ) {
236			// Refresh attributes on selects are changed
237			form.find( '.variations select' ).each( function() {
238				var select_box = jQuery(this),
239					select_val = select_box.val(),
240					attrib_box = select_box.siblings('.trx_addons_attrib_extended').length == 1 
241									? select_box.siblings('.trx_addons_attrib_extended')
242									: select_box.parent().siblings('.trx_addons_attrib_extended');
243				attrib_box.find('.trx_addons_attrib_item').removeClass('trx_addons_attrib_selected').addClass('trx_addons_attrib_disabled');
244				select_box.find('option').each( function() {
245					var opt = jQuery( this );
246					attrib_box.find( '.trx_addons_attrib_item[data-value="' + opt.val() + '"]' )
247								.removeClass( 'trx_addons_attrib_disabled' )
248								.toggleClass( 'trx_addons_attrib_selected', opt.val() == select_val );//opt.get(0).selected
249				} );
250			} );
251		}
252
253		
254		// Extended attributes in the products list (shop page or category/tag list)
255		//----------------------------------------------------------
256		if ( true || $body.hasClass( 'woocommerce' ) && $body.hasClass( 'archive' ) ) {
257			$document.on( 'action.init_hidden_elements', function( e, cont ) {
258				// If products with attributes are not present on this page - exit
259				if ( ! jQuery( '.trx_addons_product_attributes' ).length ) return;
260				// Click on the attribute - add filter
261				cont
262					.find( '.trx_addons_product_attribute_item_action_filter:not(.attribute_action_filter_inited)' )
263					.addClass( 'attribute_action_filter_inited' )
264					.on( 'click', function( e ) {
265						var flt    = jQuery( this ),
266							item   = flt.parent(),
267							type   = item.data( 'type' ),
268							attr   = item.data( 'attribute' ),
269							value  = item.data( 'value' ),
270							widget = jQuery( '.trx_addons_woocommerce_search_type_filter' ).eq(0);
271						if ( widget.length ) {
272							var widget_fld = widget.find( '.sc_form_field_' + attr );
273							if ( widget_fld.length ) {
274								var widget_item = widget_fld.find( '.sc_form_field_item[data-value="' + value + '"]' ).eq( 0 );
275								if ( widget_item.length && ! widget_item.hasClass( 'sc_form_field_item_checked' ) ) {
276									widget_item.trigger( 'click' );
277									var apply = widget_fld.find( '.trx_addons_search_apply' );
278									if ( apply.length ) {
279										apply.trigger( 'click' );
280									}
281								}
282							}
283						}
284						e.preventDefault();
285						return false;
286					} );
287				// Click on the attribute - swap image
288				var $swap_atts = cont
289									.find( '.trx_addons_product_attribute_item_action_swap:not(.attribute_action_swap_inited)' )
290									.addClass( 'attribute_action_swap_inited' );
291				if ( $swap_atts.length ) {
292					$swap_atts.on( 'click', function( e ) {
293						var $link = jQuery( this ),
294							$item = $link.parent(),
295							active = $item.hasClass( 'trx_addons_product_attribute_item_active' ),
296							disabled = $item.hasClass( 'trx_addons_product_attribute_item_disabled' );
297						if ( ! disabled ) {
298							$item.parents( '.trx_addons_product_attribute' )
299								.find( '.trx_addons_product_attribute_item_active' )
300								.removeClass( 'trx_addons_product_attribute_item_active' );
301							swap_product_image( $item.toggleClass( 'trx_addons_product_attribute_item_active', ! active ) );
302							check_available_variations( $item.parents( '.trx_addons_product_attributes' ) );
303						}
304						e.preventDefault();
305						return false;
306					} );
307					// Swap image and display corresponding price on first run or after new products are loaded
308					swap_product_image( $swap_atts.eq(0) );
309					// Check variations on first run or after new products are loaded
310					$swap_atts.parents( '.trx_addons_product_attributes' ).each( function() {
311						check_available_variations( jQuery( this ) );
312					} );
313				}
314				// Hover on the attribute - change the product image
315				cont
316					.find( '.trx_addons_product_attributes[data-product-variations] .trx_addons_product_attribute_item:not(.attribute_action_swap_inited)' )
317					.addClass( 'attribute_action_swap_inited' )
318					.on( 'focus mouseover', function( e ) {
319						var $self = jQuery( this );
320						if ( ! $self.find( '>.trx_addons_product_attribute_item_action_swap' ).length ) {
321							swap_product_image( $self );
322						}
323					} );
324
325				// Check available variations for product in the archive
326				function check_available_variations( $wrap ) {
327					var variations = $wrap.data( 'product-variations' ),
328						variation_sel = {},
329						$active_items = $wrap.find( '.trx_addons_product_attribute_item_active' );
330					// Collect active items to the current variation
331					$active_items.each( function( idx ) {
332						variation_sel[ $active_items.eq( idx ).data( 'attribute' ) ] = $active_items.eq( idx ).data( 'value' );
333					} );
334					$wrap.find( '.trx_addons_product_attribute_item' ).each( function() {
335						var $attr = jQuery( this ),
336							attr_name = $attr.data( 'attribute' ),
337							attr_value = $attr.data( 'value' ),
338							attr_variation = trx_addons_object_clone( variation_sel );
339						attr_variation[ attr_name ] = attr_value;
340						$attr.toggleClass( 'trx_addons_product_attribute_item_disabled', get_closest_variation( variations, attr_variation ) === false );
341					} );
342				}
343
344				// Get a closest variation
345				function get_closest_variation( variations, variation_sel ) {
346					var variation = false,
347						variation_max = 0,
348						variation_cur = 0;
349					for ( var i = 0; i < variations.length; i++ ) {
350						if ( ! variations[i].variation_is_active || ! variations[i].variation_is_visible ) {
351							continue;
352						}
353						variation_cur = 0;
354						for ( var attr in variation_sel ) {
355							if ( ! variations[i].attributes['attribute_'+attr] ) {
356								variation_cur += 1;
357							} else if ( variations[i].attributes['attribute_' + attr] == variation_sel[attr] ) {
358								variation_cur += 10;
359							} else {
360								variation_cur = 0;
361								break;
362							}
363						}
364						if ( variation_max < variation_cur ) {
365							variation_max = variation_cur;
366							variation = variations[i];
367						}
368					}
369					return variation;
370				}
371
372				// Return true if all attributes from variation are selected
373				function is_full_variation_present( variations, variation_sel_count ) {
374					var variation_total = 0;
375					for ( var i = 0; i < variations.length; i++ ) {
376						if ( ! variations[i].variation_is_active || ! variations[i].variation_is_visible ) {
377							continue;
378						}
379						for ( var p in variations[i].attributes ) {
380							if ( variations[i].attributes.hasOwnProperty( p ) ) {
381								variation_total++;
382							}
383						}
384						break;
385					}
386					return variation_total == variation_sel_count;
387				}
388
389				// Swap a product image on an attribute hover or click
390				function swap_product_image( $flt ) {
391					var $wrap = $flt.parents( '.trx_addons_product_attributes' ),
392						$product = $flt.parents( '.product' ),
393						variations = $wrap.data( 'product-variations' ),
394						variation = false,
395						variation_sel = {},
396						variation_sel_count = 0;
397					if ( variations ) {
398						// Collect active items to the current variation
399						var $active_items = $wrap.find( '.trx_addons_product_attribute_item_action_swap' ).length
400												? $wrap.find( '.trx_addons_product_attribute_item_active' )
401												: $flt;
402						$active_items.each( function( idx ) {
403							variation_sel[ $active_items.eq( idx ).data( 'attribute' ) ] = $active_items.eq( idx ).data( 'value' );
404							variation_sel_count++;
405						} );
406						// Get a closest variation
407						if ( variation_sel_count ) {
408							variation = get_closest_variation( variations, variation_sel );
409						}
410						// Swap image if a variation found
411						// or change back the original image if a variation with selected atributes is not found
412						var $img = $product.find( 'img[class*="attachment-woocommerce"],img[class*="woocommerce-placeholder"]' );
413						if ( $img.length ) {
414							if ( ! $img.data( 'src-old' ) ) {
415								$img.data( {
416									'src-old': $img.attr( 'src' ),
417									'srcset-old': $img.attr( 'srcset' ),
418									'sizes-old': $img.attr( 'sizes' )
419								} );
420							}
421							if ( variation ) {
422								$img.attr( {
423									'src': variation.image.src,
424									'srcset': variation.image.srcset ? variation.image.srcset : '',
425									'sizes': variation.image.sizes ? variation.image.sizes : ''
426								} );
427							} else {
428								$img.attr( {
429									'src': $img.data( 'src-old' ),
430									'srcset': $img.data( 'srcset-old' ),
431									'sizes': $img.data( 'sizes-old' )
432								} );
433							}
434						}
435						// Swap price if a full variation found (all attributes present in the item and selected)
436						// or change back the original price if a variation with selected atributes is not found
437						if ( trx_addons_apply_filters( 'trx_addons_filter_swap_price_for_variable_products', is_full_variation_present( variations, variation_sel_count ) ) ) {
438							var $price = $product.find( '.price_wrap' );
439							if ( ! $price.length ) {
440								$price = $product.find( '.price' );
441							}
442							if ( $price.length ) {
443								if ( ! $price.data( 'price-old' ) ) {
444									$price.data( {
445										'price-old': $price.html()
446									} );
447								}
448								if ( variation ) {
449									// A 'price_html' can be empty if all variations have an equal price.
450									// In this case leave a price unchanged.
451									if ( variation.price_html != '' ) {
452										$price.html( $price.hasClass( 'price_wrap' ) ? variation.price_html : jQuery( variation.price_html ).html() );
453									}
454								} else {
455									$price.html( $price.data( 'price-old' ) );
456								}
457							}
458						}
459					}
460				}
461			} );
462		}
463
464
465		// WooCommerce Search Widget
466		//----------------------------------------------------------
467		
468		var reopen_after_reload = trx_addons_apply_filters( 'trx_addons_filter_reopen_filter_after_reload_products', false ),
469			reopened = false,
470			reload_is_busy = false,
471			reload_is_allowed = true,
472			last_clicked_item = '',
473			last_opened_filter = '',
474			inline_css_selector = trx_addons_apply_filters( 'trx_addons_filter_reload_inline_css_selector', '#trx_addons-inline-styles-inline-css' ),
475			inline_css_wrap = jQuery( inline_css_selector ),
476			inline_css_start = trx_addons_apply_filters( 'trx_addons_filter_reload_inline_css_start', '#woocommerce_output_start{}' ),
477			inline_css_end = trx_addons_apply_filters( 'trx_addons_filter_reload_inline_css_end', '#woocommerce_output_end{}' ),
478			list_products_selector = trx_addons_apply_filters( 'trx_addons_filter_reload_products_selector', '.list_products' ),
479			list_products_wrap = jQuery( list_products_selector ),
480			list_products_loading = 0,
481			list_products_loading_class = '.trx_addons_loading',
482			list_products_loading_selector  = trx_addons_apply_filters( 'trx_addons_filter_reload_products_loading_wrap_selector',
483																		'.list_products .products,.list_products .woocommerce-info,.woocommerce-no-products-found'
484																		),
485			list_products_loading_html  = trx_addons_apply_filters( 'trx_addons_filter_reload_products_loading_html', TRX_ADDONS_STORAGE['loading_layout'] ),
486			single_product_selector = trx_addons_apply_filters( 'trx_addons_filter_single_product_selector', '.post_item_single.post_type_product' ),
487			mask_fields_wrap_on_loading = true;
488
489		$document.on( 'action.init_hidden_elements', function() {
490
491			// Reinit search form after page reloaded
492			var search_forms = jQuery('.trx_addons_woocommerce_search_form:not(.inited)');
493			if ( search_forms.length ) {
494				search_forms.each( function() {
495					var form   = jQuery(this).addClass('inited'),
496						widget = form.parents('.trx_addons_woocommerce_search'),
497						type   = widget.hasClass( 'trx_addons_woocommerce_search_type_filter')
498									? 'filter'
499									: ( widget.hasClass( 'trx_addons_woocommerce_search_type_form')
500										? 'form'
501										: 'inline'
502										),
503						apply  = widget.hasClass( 'trx_addons_woocommerce_search_apply' ),
504						ajax   = widget.hasClass( 'trx_addons_woocommerce_search_ajax' ),
505						number = widget.data('number') || 1,
506						expanded = widget.data('expanded') || 0;
507
508					// Reload products after timeout ('filter' style)
509					var trx_addons_woocommerce_search_form_reload_products_after_timeout = trx_addons_throttle(
510							trx_addons_woocommerce_search_form_reload_products,
511							trx_addons_apply_filters( 'trx_addons_filter_reload_products_timeout', ajax ? 500 : 0 ),
512							true
513						);
514
515					// Update available products counter ('filter' style)
516					var trx_addons_woocommerce_search_form_update_available_products_counter = trx_addons_throttle(
517						function( form ) {
518							// Get all filters to the params array
519							var params = trx_addons_woocommerce_search_form_get_params( form, '.sc_form_field_param' );
520							// If any filter selected
521							if ( params !== false ) {
522								var shop_url = trx_addons_add_to_url(form.attr('action'), params),
523									counter  = form.find('.trx_addons_woocommerce_search_button_show_total');
524								if ( counter.length ) {
525									jQuery.get( shop_url ).done( function( response ) {
526										var value = jQuery( response ).find('.trx_addons_woocommerce_search_button_show_total').html();
527										if ( value !== '') {
528											counter.html( value );
529										}
530									} );
531								}
532							}
533						},
534						trx_addons_apply_filters( 'trx_addons_filter_update_products_counter_timeout', 500 ),
535						true
536					);
537
538					form
539						// Submit form ('inline' or 'form' styles)
540						.on('submit', function(e) {
541							var shop_url = form.attr('action');
542							var params = trx_addons_woocommerce_search_form_get_params(form);
543							if (params !== false) {
544								window.location.href = trx_addons_add_to_url(shop_url, params);
545							} else {
546								e.preventDefault();
547							}
548							return false;
549						})
550						// Enable/Disable submit button ('inline' or 'form' styles)
551						.on('change', 'select,input', function(e) {
552							var button = form.find('.trx_addons_woocommerce_search_button');
553							if ( button.length ) {
554								var params = trx_addons_woocommerce_search_form_get_params(form);
555								if (params === false) {
556									button.attr('disable', 'disable');
557								} else {
558									button.removeAttr('disable');
559								}
560							}
561						})
562						// Open/Close dropdown with items ('inline' style)
563						.on('click', '.trx_addons_woocommerce_search_form_field_label', function(e) {
564							jQuery(this)
565								.parent('.trx_addons_woocommerce_search_form_field')
566								.siblings('.trx_addons_woocommerce_search_form_field')
567								.find('.trx_addons_woocommerce_search_form_field_list').slideUp();
568							jQuery(this).siblings('.trx_addons_woocommerce_search_form_field_list').slideToggle();
569							e.preventDefault();
570							return false;
571						})
572						// Select item in the 'inline' form
573						.on('click', '.trx_addons_woocommerce_search_form_field_list li', function(e) {
574							var list = jQuery(this).parent();
575							list.siblings('.trx_addons_woocommerce_search_form_field_label').html(jQuery(this).html());
576							list.siblings('input[type="hidden"]').val(jQuery(this).data('value'));
577							list.slideUp();
578							e.preventDefault();
579							return false;
580						})
581						// Keypress on the field's title
582						.on('keyup', '.sc_form_field_title', function(e) {
583							if ( type == 'filter' ) {
584								if ( e.keyCode == 13 ) {
585									jQuery(this).trigger('click');
586								}
587							}
588						})
589						// Open/Close dropdown with items ('filter' style)
590						.on('click', '.sc_form_field_title', function(e) {
591							if ( type == 'filter' ) {
592								var $self  = jQuery(this),
593									field  = $self.parent(),
594									opened = field.hasClass('sc_form_field_opened');
595								// Close all opened fields
596								if ( $self.parents('.trx_addons_woocommerce_tools').length !== 0
597									&& $self.parents('.trx_addons_woocommerce_search_form_fields_wrap_opened').length === 0
598								) {
599									$self
600										.parents('.trx_addons_woocommerce_search_form_fields_wrap')
601										.find('.sc_form_field_opened').each( function() {
602											var cur_field = jQuery( this ),
603												cur_param = cur_field.find( '.sc_form_field_param' ),
604												cur_apply = cur_field.find( '.trx_addons_search_apply' ),
605												need_apply = apply && cur_apply.length && ! cur_apply.attr('disabled') && cur_param.data('changed');
606											if ( need_apply ) {
607												cur_apply.trigger( 'click' );
608											} else {
609												trx_addons_woocommerce_search_form_close_field( cur_field );	// , apply
610											}
611										} );
612								} else if ( opened ) {
613									var cur_apply = field.find( '.trx_addons_search_apply' ),
614										cur_param = field.find( '.sc_form_field_param' ),
615										need_apply = apply && cur_apply.length && ! cur_apply.attr('disabled') && cur_param.data('changed');
616									if ( false && need_apply ) {	// Don't apply on click a title in sidebar or mobile
617										cur_apply.trigger( 'click' );
618									} else {
619										trx_addons_woocommerce_search_form_close_field( field );	// , apply
620									}
621								}
622								// Open clicked field
623								if ( ! opened ) {
624									trx_addons_woocommerce_search_form_open_field( field );
625								}
626								e.preventDefault();
627								return false;
628							}
629						})
630						// Keypress on the field's title
631						.on('keyup', '.sc_form_field_item', function(e) {
632							if ( type == 'filter' ) {
633								if ( e.keyCode == 13 ) {
634									jQuery(this).trigger('click');
635								} else if ( e.keyCode == 27 ) {
636									jQuery(this).parents('.sc_form_field').find('.sc_form_field_title').focus().trigger('click');
637								}
638							}
639						})
640						// Check item in the select ('filter' style)
641						.on('click', '.sc_form_field .sc_form_field_item', function(e) {
642							if ( type == 'filter' ) {
643								var $self = jQuery(this),
644									wrap  = $self.parents('.sc_form_field_wrap'),
645									multi = $self.parents('.sc_form_field').data('multiple') == '1';
646								last_clicked_item = $self.data('value');
647								if ( ! multi ) {
648									wrap.find('.sc_form_field_item_checked').removeClass('sc_form_field_item_checked');
649								}
650								$self.toggleClass('sc_form_field_item_checked');
651								var value = trx_addons_woocommerce_search_form_get_multiple_field_value( wrap );
652								wrap.find( '.sc_form_field_param' ).val( value ).trigger( 'change' );
653								e.preventDefault();
654								return false;
655							}
656						})
657						// All fields: Keypress on the 'Clear all' button
658						.on('keyup', '.trx_addons_woocommerce_search_clear_all', function(e) {
659							if ( type == 'filter' ) {
660								if ( e.keyCode == 27 ) {
661									jQuery(this).siblings('.trx_addons_woocommerce_search_close').trigger('click');
662								}
663							}
664						})
665						// All fields: Clear all selected items in the multiselect fields
666						.on('click', '.trx_addons_woocommerce_search_clear_all', function(e) {
667							e.preventDefault();
668							if ( type == 'filter' ) {
669								var need_reload = false;
670								reload_is_allowed = false;
671								form.find('.sc_form_field').each( function() {
672									var $self = jQuery(this),
673										param = $self.find( '.sc_form_field_param' );
674									if ( param.attr('name') != 'product_cat' && param.val() !== '' ) {
675										var field = param.parents('.sc_form_field'),
676											value = '';
677										if ( field.hasClass( 'sc_form_field_slider' ) ) {
678											value = param.next().data('min');
679										} else if ( field.hasClass( 'sc_form_field_range' ) ) {
680											value = param.next().data('min') + ',' + param.next().data('max');
681										}
682										need_reload = true;
683										param.val( value ).trigger( 'change' );
684										trx_addons_woocommerce_search_form_restore_field_view( $self );
685									}
686								} );
687								reload_is_allowed = true;
688								if ( need_reload ) {
689									trx_addons_woocommerce_search_form_reload_products( form );
690								}
691							}
692							return false;
693						})
694						// Keypress on the 'Clear all' button
695						.on('keyup', '.sc_form_field_items_selected_clear', function(e) {
696							if ( type == 'filter' ) {
697								if ( e.keyCode == 27 ) {
698									jQuery(this).parents('.sc_form_field').find('.sc_form_field_title').focus().trigger('click');
699								}
700							}
701						})
702						// Clear all selected items in the multiselect fields
703						.on('click', '.sc_form_field_items_selected_clear', function(e) {
704							e.preventDefault();
705							if ( type == 'filter' ) {
706								var $self = jQuery(this),
707									wrap  = $self.parents('.sc_form_field_wrap');
708								wrap.find( '.sc_form_field_param' ).val( '' ).trigger( 'change' );
709								trx_addons_woocommerce_search_form_restore_field_view( wrap.parents( '.sc_form_field' ) );
710							}
711							return false;
712						})
713						// Keypress on the 'Select all' button
714						.on('keyup', '.sc_form_field_items_selected_select_all', function(e) {
715							if ( type == 'filter' ) {
716								if ( e.keyCode == 27 ) {
717									jQuery(this).parents('.sc_form_field').find('.sc_form_field_title').focus().trigger('click');
718								}
719							}
720						})
721						// Select all items in the multiselect fields
722						.on('click', '.sc_form_field_items_selected_select_all', function(e) {
723							e.preventDefault();
724							if ( type == 'filter' ) {
725								var $self = jQuery(this),
726									wrap  = $self.parents('.sc_form_field_wrap');
727								wrap.find('.sc_form_field_item').toggleClass('sc_form_field_item_checked', true);
728								var value = trx_addons_woocommerce_search_form_get_multiple_field_value( wrap );
729								wrap.find( '.sc_form_field_param' ).val( value ).trigger( 'change' );
730							}
731							return false;
732						})
733						// Update 'param' field on change text ('filter' style)
734						.on('change', '.sc_form_field_text .sc_form_field_input', function(e) {
735							if ( type == 'filter' ) {
736								var $self = jQuery(this),
737									wrap  = $self.parents('.sc_form_field_wrap');
738								wrap.find( '.sc_form_field_param' ).val( $self.val() ).trigger( 'change' );
739							}
740						})
741						// Prevent submit form on Enter in the text field
742						.on('keydown', '.sc_form_field_text .sc_form_field_input', function(e) {
743							if ( type == 'filter' ) {
744								var $buttons = jQuery(this).parents('.sc_form_field_wrap').find('.sc_form_field_buttons');
745								if ( $buttons.length ) {
746									if ( e.keyCode == 13 ) {
747										var $apply = $buttons.find('.trx_addons_search_apply');
748										if ( $apply.length ) {
749											e.preventDefault();
750											jQuery(this).trigger('change');
751											$apply.trigger('click');
752										}
753									} else if ( e.keyCode == 27 ) {
754										var $cancel = $buttons.find('.trx_addons_search_cancel');
755										if ( $cancel.length ) {
756											e.preventDefault();
757											$cancel.trigger('click');
758										}
759									}
760								}
761							}
762						})
763						// Show/hide items with specified keywords ('filter' style)
764						.on('keyup', '.sc_form_field_items_filter_text', function(e) {
765							if ( type == 'filter' ) {
766								var $self = jQuery(this),
767									value = $self.val().toLowerCase(),
768									wrap  = $self.parents('.sc_form_field_wrap');
769								wrap.find('.sc_form_field_item').each( function() {
770									var $item = jQuery(this);
771									$item.toggleClass('trx_addons_hidden_important', value !== '' && ('' + $item.data('value')).toLowerCase().indexOf(value) === -1);
772								} );
773							}
774						})
775						// Update result in the price range ('filter' style)
776						.on('change', '.sc_form_field_price .sc_form_field_param', function(e) {
777							if ( type == 'filter' ) {
778								var $self  = jQuery(this),
779									value  = $self.val().split(','),
780									slider = $self.next('.trx_addons_range_slider '),
781									result = slider.next('.trx_addons_range_result');
782								if ( result.length ) {
783									result.find('.trx_addons_range_result_value').html( value[0] + ( value.length > 1 ? ' - ' + value[1] : '' ) );
784								}
785							}
786						})
787						// Mark title as filled and update selected total value on param changed ('filter' style)
788						.on('change', '.sc_form_field_param', function(e) {
789							if ( type == 'filter' ) {
790								var $self = jQuery(this).data('changed', 1);
791								$self.parents('.trx_addons_woocommerce_search_form_fields_wrap').toggleClass('trx_addons_woocommerce_search_form_fields_changed', true);
792								trx_addons_woocommerce_search_form_param_changed( $self );
793							}
794						} )
795						// Remove attr 'disabled' from buttons 'Apply' and 'Cancel' on param changed ('filter' style)
796						.on('change', '.sc_form_field_param', function(e) {
797							if ( type == 'filter' ) {
798								var field_wrap = jQuery(this).parents('.sc_form_field_wrap');
799								field_wrap.find('.trx_addons_search_apply').removeAttr('disabled');
800								field_wrap.find('.trx_addons_search_cancel').removeAttr('disabled');
801							}
802						} )
803						// Update available (filtered) products counter on param changed ('filter' style)
804						.on('change', '.sc_form_field_param', function(e) {
805							var $self = jQuery(this),
806								fields_wrap = $self.parents('.trx_addons_woocommerce_search_form_fields_wrap').data('param-changed', 1);
807							if ( type == 'filter'
808									&& $self.attr('name') != 'product_cat'
809									&& ( fields_wrap.hasClass('trx_addons_woocommerce_search_form_fields_wrap_opened')
810										||
811										( fields_wrap.parents(TRX_ADDONS_STORAGE['sidebar_wrap_class']).length && ( apply || ajax ) )
812										)
813							) {
814								trx_addons_woocommerce_search_form_update_available_products_counter( form );
815							}
816						} )
817						// Reload page on any param are changed, except 's' and 'price' ('filter' style)
818						.on('change', '.sc_form_field_param', function(e) {
819							var $self = jQuery(this);
820							if ( type == 'filter' && reload_is_allowed ) {
821								if ( $self.attr('name') == 'product_cat' ) {
822									var $fld = $self.parents('.sc_form_field_opened'),
823										fld_idx = $fld.index();
824									if ( fld_idx > expanded ) {
825										trx_addons_woocommerce_search_form_close_field( $fld );
826									}
827									trx_addons_woocommerce_search_form_reload_products( form, $self, '.sc_form_field_param[name="product_cat"]', true );
828								} else if ( ! apply
829											&& ! $self.parents('.trx_addons_woocommerce_search_form_fields_wrap').hasClass('trx_addons_woocommerce_search_form_fields_wrap_opened')
830											&& ( ['price', 's'].indexOf($self.attr('name')) == -1 || $self.parents(TRX_ADDONS_STORAGE['sidebar_wrap_class']).length )
831								) {
832									trx_addons_woocommerce_search_form_reload_products_after_timeout( form, $self );
833								}
834							}
835						})
836						// Reload page on click button 'Apply' ('filter' style)
837						.on('click', '.trx_addons_search_apply', function(e) {
838							if ( type == 'filter' ) {
839								var $self = jQuery(this);
840								if ( ! $self.attr('disabled') ) {
841									if ( ! $self.parents('.trx_addons_woocommerce_search_form_fields_wrap').hasClass('trx_addons_woocommerce_search_form_fields_wrap_opened')
842										&& $self.parents(TRX_ADDONS_STORAGE['sidebar_wrap_class']).length === 0
843									) {
844										trx_addons_woocommerce_search_form_close_field( $self.parents('.sc_form_field_opened') );
845									}
846									trx_addons_woocommerce_search_form_reload_products( form, $self.parents('.sc_form_field').find('.sc_form_field_param') );
847								}
848								e.preventDefault();
849								return false;
850							}
851						})
852						// Restore values on click button 'Cancel' ('filter' style)
853						.on('click', '.trx_addons_search_cancel', function(e) {
854							if ( type == 'filter' ) {
855								var $self = jQuery(this);
856								if ( ! $self.attr('disabled') ) {
857									trx_addons_woocommerce_search_form_close_field( $self.parents('.sc_form_field_opened'), true );
858								}
859								e.preventDefault();
860								return false;
861							}
862						})
863						// Open/Close panel with filters
864						.on('click', '.trx_addons_woocommerce_search_button_filters,'
865									+'.trx_addons_woocommerce_search_button_show,'
866									+'.trx_addons_woocommerce_search_close',
867							function(e) {
868								var $self = jQuery(this),
869									applied = false,
870									wrap = form.find('.trx_addons_woocommerce_search_form_fields_wrap');
871								if ( $self.hasClass('trx_addons_woocommerce_search_button_filters') && ! wrap.hasClass('trx_addons_woocommerce_search_form_fields_wrap_opened') ) {
872									wrap.addClass('trx_addons_woocommerce_search_form_fields_wrap_opened');
873								} else {
874									if ( wrap.hasClass('trx_addons_woocommerce_search_form_fields_wrap_opened')
875										||
876										( $self.parents(TRX_ADDONS_STORAGE['sidebar_wrap_class']).length
877											&&
878											$self.parents('.trx_addons_woocommerce_search').hasClass('trx_addons_woocommerce_search_apply')
879											)
880									) {
881										if ( wrap.data('param-changed') > 0 ) {
882											var last_apply = last_opened_filter
883																? form.find('input[name="'+last_opened_filter+'"]')
884																	.parents('.sc_form_field')
885																	.find('.trx_addons_search_apply:not([disabled])')
886																: false;
887											if ( ! last_apply || ! last_apply.length || last_apply.attr('disabled') == 'disabled' ) {
888												last_apply = form.find('.trx_addons_search_apply:not([disabled])').eq(0);
889											}
890											applied = true;
891											if ( last_apply && last_apply.length && last_apply.attr('disabled') != 'disabled' ) {
892												last_apply.trigger( 'click' );
893											} else {
894												trx_addons_woocommerce_search_form_reload_products( form );
895											}
896										}
897									}
898									if ( true || ! applied ) {	// Always hide fields wrap on mobile
899										wrap.removeClass('trx_addons_woocommerce_search_form_fields_wrap_opened');
900									}
901								}
902								e.preventDefault();
903								return false;
904							}
905						);
906				
907					// Open initially toggled fields
908					if ( form.parents(TRX_ADDONS_STORAGE['sidebar_wrap_class']).length > 0 ) {
909						form.find('.sc_form_field_expanded').each( function() {
910							trx_addons_woocommerce_search_form_open_field( jQuery(this).removeClass('sc_form_field_expanded'), 'show', false );
911						} );
912					}
913
914					// Show/hide 'Clear all' on fields changed (exclude the field "Product category")
915					form.find('.trx_addons_woocommerce_search_form_fields_wrap')
916						.toggleClass( 'trx_addons_woocommerce_search_form_fields_filled', 
917										form.find('.sc_form_field:not(.sc_form_field_product_cat) .sc_form_field_title_filled').length > 0
918									);
919
920					// Reopen filter after reload products page ('filter' style)
921					if ( type == 'filter' && ! reopened ) {
922						reopened = true;
923						last_opened_filter = trx_addons_get_value_gp( 'last_filter' );
924						if ( last_opened_filter ) {
925							var last_stop = trx_addons_get_value_gp( 'last_stop' );
926							if ( last_stop > 0 ) {
927								trx_addons_document_animate_to( last_stop );
928							} else if ( trx_addons_window_scroll_top() > 0 ) {
929								trx_addons_document_animate_to( 0 );
930							}
931							if ( reopen_after_reload && ! apply ) {
932								// Reopen fields wrap on mobile
933								/*
934								var fields_wrap = form.find('.trx_addons_woocommerce_search_form_fields_wrap');
935								if ( fields_wrap.length && ! fields_wrap.hasClass('trx_addons_woocommerce_search_form_fields_wrap_opened') && fields_wrap.css('position') == 'fixed' ) {
936									fields_wrap.addClass('trx_addons_woocommerce_search_form_fields_wrap_opened trx_addons_woocommerce_search_form_fields_wrap_show');
937									setTimeout( function() {
938										fields_wrap.removeClass('trx_addons_woocommerce_search_form_fields_wrap_show');
939									}, 500 );
940								}
941								*/
942								// Reopen last active field
943								var field = form.find('input[name="'+last_opened_filter+'"]').parents('.sc_form_field');
944								trx_addons_woocommerce_search_form_open_field( field );
945								last_clicked_item = trx_addons_get_value_gp( 'last_item' );
946								if ( last_clicked_item ) {
947									field.find('.sc_form_field_item[data-value="'+last_clicked_item+'"]').focus();
948								}
949							}
950						}
951					}
952
953					// Reload products ('filter' style)
954					function trx_addons_woocommerce_search_form_reload_products( form, filter, selector, force_reload_page ) {
955						// Get all filters to the params array
956						if ( selector === undefined ) {
957							selector = '.sc_form_field_param';
958						}
959						var params = trx_addons_woocommerce_search_form_get_params( form, selector );
960						// If any filter selected
961						if ( params !== false ) {
962							// Close last filter field
963							if ( filter
964								&& ( ! ajax || apply || force_reload_page )
965								&& filter.parents('.trx_addons_woocommerce_tools').length !== 0
966								&& filter.parents('.trx_addons_woocommerce_search_form_fields_wrap_opened').length === 0
967							) {
968								trx_addons_woocommerce_search_form_close_field( filter.parents('.sc_form_field_opened') );
969							}
970							// Add filter's name and window scroll position to the parameters
971							if ( last_opened_filter ) {
972								params['last_filter'] = last_opened_filter;
973							}
974							if ( last_clicked_item ) {
975								params['last_item'] = last_clicked_item;
976							}
977							// Add scroll top position to the query (commented to prevent scroll to blank window area if sidebar with filters too long)
978							// params['last_stop'] = jQuery(window).scrollTop();
979							// Make query url
980							var shop_url = trx_addons_add_to_url(form.attr('action'), params),
981								fields_wrap = form.find('.trx_addons_woocommerce_search_form_fields_wrap').data('param-changed', 0);
982							// Reload products by AJAX
983							if ( ajax && ! force_reload_page ) {
984								trx_addons_woocommerce_search_form_get_products_from_url( shop_url, fields_wrap );
985							// Redirect page
986							} else {
987								jQuery( list_products_loading_selector )
988									.addClass( 'trx_addons_woocommerce_search_loading' )
989									.append( list_products_loading_html );
990								window.location.href = shop_url;
991							}
992						}
993					}
994
995				});
996			}
997
998			// WooCommerce NavFilters: AJAX reload products on filter removed (if woocommerce_search_filter is present near this widget)
999			jQuery( '.widget_layered_nav_filters:not(.trx_addons_woocommerce_search_compatibility_inited)' ).each( function() {
1000				var $self = jQuery(this).addClass('trx_addons_woocommerce_search_compatibility_inited'),
1001					widget_search = $self.siblings('.widget_woocommerce_search');
1002				// Allow AJAX reload on filter removed only if widget 'Product Filter' is present on same sidebar
1003				// and ajax search is turned on for the widget
1004				// and field 'rating' is not present in the fields set (because WooCommerce don't mark this field in the widget Active filters)
1005				if ( widget_search.length
1006					&& widget_search.find('.trx_addons_woocommerce_search_ajax').length
1007					&& widget_search.find('.sc_form_field_rating').length === 0 
1008				) {
1009					$self.find('a').on('click', function(e) {
1010						var $link = jQuery(this),
1011							list = $link.parents('ul').eq(0),
1012							url = location.href;	//$link.attr('href');
1013						e.preventDefault();
1014						// Remove current filter from active filters
1015						$link.parents('li').eq(0).fadeOut( 200, function() {
1016							jQuery(this).remove();
1017							// Prepare url - remove not exists filters
1018							var parts = url.split('?'),
1019								query = trx_addons_parse_query_string(url),
1020								query_new = {},
1021								query_val = [],
1022								query_val_new = [];
1023							for (var i in query) {
1024								if ( i == 'min_price' || i == 'max_price' ) {
1025									list.find('.chosen .amount').each( function() {
1026										if ( jQuery(this).text().replace(/[\$\.\,]/g, '') == query[i].replace(/[\$\.\,]/g, '') ) {
1027											query_new[i] = query[i];
1028										}
1029									} );
1030								} else if ( i.substring(0, 7) == 'filter_' ) {
1031									query_val = query[i].split(',');
1032									query_val_new = [];
1033									for (var j = 0; j < query_val.length; j++ ) {
1034										if ( list.find('.chosen-' + i.substring(7) + '-' +query_val[j] ).length ) {
1035											query_val_new.push( query_val[j] );
1036										}
1037									}
1038									if ( query_val_new.length > 0 ) {
1039										query_new[i] = query_val_new.join(',');
1040									}
1041								} else {
1042									query_new[i] = query[i];
1043								}
1044							}
1045							trx_addons_woocommerce_search_form_get_products_from_url( trx_addons_add_to_url( parts[0], trx_addons_woocommerce_search_form_add_orderby_to_query_params( query_new ) ) );
1046						} );
1047						return false;
1048					} );
1049				}
1050			} );
1051
1052			// WooCommerce Ordering: Reload products on 'orderby' is changed
1053			jQuery('.woocommerce-ordering:not(.trx_addons_woocommerce_search_compatibility_inited)').each( function() {
1054				var form = jQuery( this ).addClass( 'trx_addons_woocommerce_search_compatibility_inited' ),
1055					select = form.find( '.orderby' ),
1056					widget_search = list_products_wrap.find( '.widget_woocommerce_search' ),
1057					url = location.href.split( '?' );
1058				if ( widget_search.length === 0 ) {
1059					widget_search = jQuery( '.trx_addons_woocommerce_search_type_filter' ).eq(0).parents( '.widget_woocommerce_search' );
1060				}
1061				if ( widget_search.length ) {
1062					select.on( 'change', function(e) {
1063						var params = trx_addons_woocommerce_search_form_get_params( widget_search, '.sc_form_field_param' );
1064						/*
1065						var page = form.find('input[name="paged"]').val() || 1;
1066						if ( page > 1 ) {
1067							params['page'] = page;
1068						}
1069						*/
1070						// Prevent to execute other scripts
1071						e.preventDefault();
1072						e.stopImmediatePropagation();
1073						// If a widget with filters present and its mode is AJAX - get products via AJAX
1074						if ( widget_search.find('.trx_addons_woocommerce_search_ajax').length ) {
1075							trx_addons_woocommerce_search_form_get_products_from_url( trx_addons_add_to_url( url[0], params ) );
1076						// Else - reload a current page with new params
1077						} else {
1078							jQuery( list_products_loading_selector )
1079								.addClass( 'trx_addons_woocommerce_search_loading' )
1080								.append( list_products_loading_html );
1081							window.location.href = trx_addons_add_to_url( url[0], params );
1082						}
1083						return false;
1084					} );
1085				}
1086			} );
1087
1088			// Open field ('filter' style)
1089			function trx_addons_woocommerce_search_form_open_field( field, open_style, need_focus ) {
1090				if ( open_style === undefined ) {
1091					open_style = 'slideDown';
1092				}
1093				if ( need_focus === undefined ) {
1094					need_focus = true;
1095				}
1096				var open_time = open_style == 'show'
1097									? 0
1098									: trx_addons_apply_filters( 'trx_addons_filter_woocommerce_filter_show_time', field.parents('.trx_addons_woocommerce_tools').length === 0 || field.parents('.trx_addons_woocommerce_search_form_fields_wrap_opened').length > 0 ? 300 : 0 );
1099				// Save current value
1100				var param = field.find( '.sc_form_field_param' );
1101				param.data( 'old-value', param.val() );
1102				// Mark field unchanged
1103				param.data( 'changed', 0 );
1104				// Save last opened filter
1105				last_opened_filter = param.attr('name');
1106				// Set buttons 'Apply' and 'Cancel' to disabled
1107				if ( false && field.parents('.trx_addons_woocommerce_search').hasClass('trx_addons_woocommerce_search_apply') ) {
1108					field.find('.trx_addons_search_apply').attr('disabled', 'disabled');
1109					field.find('.trx_addons_search_cancel').attr('disabled', 'disabled');
1110				}
1111				// Open field wrap
1112				var wrap = field.addClass('sc_form_field_opened').find('.sc_form_field_wrap');
1113				if ( open_style == 'slideDown' && open_time > 0 ) {
1114					wrap.slideDown( open_time, function() {
1115						if ( need_focus && field.hasClass('sc_form_field_text') ) {
1116							field.find( 'input[type="text"]').focus();
1117						}
1118					} );
1119				} else {
1120					wrap.show();
1121					if ( need_focus && field.hasClass('sc_form_field_text') ) {
1122						field.find( 'input[type="text"]').focus();
1123					}
1124				}
1125			}
1126
1127			// Close field ('filter' style)
1128			function trx_addons_woocommerce_search_form_close_field( field, restore_value, close_style ) {
1129				// Restore last value
1130				if ( restore_value ) {
1131					trx_addons_woocommerce_search_form_restore_field_value( field );
1132				}
1133				last_opened_filter = '';
1134				// Close field wrap
1135				field.removeClass('sc_form_field_opened');
1136				if ( close_style === undefined ) {
1137					close_style = 'slideUp';
1138				}
1139				var close_time = close_style == 'hide'
1140									? 0
1141									: trx_addons_apply_filters( 'trx_addons_filter_woocommerce_filter_show_time', field.parents('.trx_addons_woocommerce_tools').length === 0 || field.parents('.trx_addons_woocommerce_search_form_fields_wrap_opened').length > 0 ? 300 : 0 );
1142				if ( close_style == 'slideUp' && close_time > 0 ) {
1143					field.find('.sc_form_field_wrap').slideUp( close_time );
1144				} else {
1145					field.find('.sc_form_field_wrap').hide();
1146				}
1147			}
1148
1149			// Restore field's value ('filter' style)
1150			function trx_addons_woocommerce_search_form_restore_field_value( field ) {
1151				var param = field.find('.sc_form_field_param'),
1152					value = param.data('old-value');
1153				// Restore old value in the param
1154				param.val( value );
1155				// Mark title as filled and update selected items and restore field's view (mark items as checked, restore search string, etc.)
1156				trx_addons_woocommerce_search_form_restore_field_view( field );
1157			}
1158
1159			// Restore field's view ('filter' style)
1160			function trx_addons_woocommerce_search_form_restore_field_view( field ) {
1161				var param = field.find('.sc_form_field_param'),
1162					value = param.val();
1163				// Mark title as filled and update selected items
1164				trx_addons_woocommerce_search_form_param_changed( param );
1165				// Restore field's view (mark items as checked, restore search string, etc.)
1166				if ( field.hasClass('sc_form_field_select')
1167					|| field.hasClass('sc_form_field_image')
1168					|| field.hasClass('sc_form_field_color')
1169					|| field.hasClass('sc_form_field_button')
1170				) {
1171					field.find('.sc_form_field_item_checked').removeClass('sc_form_field_item_checked');
1172					var parts = ( '' + value ).split( ',' );
1173					for (var i = 0; i < parts.length; i++ ) {
1174						field.find('[data-value="'+parts[i]+'"]').addClass('sc_form_field_item_checked');
1175					}
1176				} else if ( field.hasClass('sc_form_field_text') ) {
1177					field.find('.sc_form_field_input').val( value );
1178				} else if ( field.hasClass('sc_form_field_slider') ) {
1179					field.find('.ui-slider').slider( "value", value );
1180				} else if ( field.hasClass('sc_form_field_range') ) {
1181					field.find('.ui-slider').slider( "values", ( '' + value ).split( ',' ) );
1182				}
1183			}
1184
1185			// Mark title as filled and update selected total value on param changed ('filter' style)
1186			function trx_addons_woocommerce_search_form_param_changed(param) {
1187				var value    = param.val(),
1188					empty    = value === '',
1189					title_filled = !empty,
1190					wrap     = param.parents('.sc_form_field_wrap'),
1191					title    = wrap.siblings('.sc_form_field_title'),
1192					selected = title.find('.sc_form_field_selected_items'), //wrap.siblings('.sc_form_field_selected_items'),
1193					slider   = param.next('.trx_addons_range_slider '),
1194					fields_wrap = param.parents('.trx_addons_woocommerce_search_form_fields_wrap');
1195				// Mark title as 'filled'
1196				if ( slider.length == 1 ) {
1197					var min = slider.data('min'),
1198						max = slider.data('max'),
1199						val = value.split(',');
1200					title_filled = Number( val[0] ) !== Number( min ) || ( val.length > 1 && Number( val[1] ) !== Number( max ) );
1201					title.toggleClass( 'sc_form_field_title_filled', title_filled );
1202				} else {
1203					title.toggleClass( 'sc_form_field_title_filled', !empty );
1204				}
1205				// Update selected items counter
1206				wrap.find('.sc_form_field_items_selected_value').html( value ? value.split(',').length : 0 );
1207				// Update info with selected items
1208				if ( selected.length
1209					&& ( 
1210						wrap.parents('.trx_addons_woocommerce_tools').length === 0
1211						||
1212						fields_wrap.hasClass( 'trx_addons_woocommerce_search_form_fields_wrap_opened' )
1213						)
1214				) {
1215					// Get value to display below title
1216					//var value_to_show = decodeURIComponent(''+value).split(',').map(trx_addons_proper).join(', ');
1217					var value_to_show = '',
1218						parts = (''+value).split(','),
1219						$item = null;
1220					for ( var i=0; i<parts.length; i++ ) {
1221						// Try find a text label (name) of the selected item
1222						$item = wrap.find('.sc_form_field_item[data-value="'+parts[i]+'"] .sc_form_field_item_text');
1223						value_to_show += ( value_to_show ? ', ' : '' )
1224										+ ( $item.length && $item.text() == $item.html()
1225											? $item.text()											// Use text label (name)
1226											: trx_addons_proper( decodeURIComponent( parts[i] ) )	// Use selected slug (value)
1227											);
1228					}
1229					// Display selected items below title
1230					if ( selected.html() === '' && title_filled ) {
1231						selected.hide().html( value_to_show ).slideDown();
1232					} else if ( selected.html() !== '' && ! title_filled ) {
1233						selected.slideUp( function() {
1234							selected.html( '' ).show();
1235						} );
1236					} else {
1237						selected.html( title_filled ? value_to_show : '' );
1238					}
1239				}
1240				// Update filters total counters
1241				var filters_total = 0;
1242				fields_wrap.find('.sc_form_field_title_filled + .sc_form_field_wrap .sc_form_field_param').each( function() {
1243					var $self = jQuery( this ),
1244						field = $self.parents('.sc_form_field');
1245					// Exclude the field "Category" from totals and prevent 'Clear all' to be displayed on category selected
1246					if ( ! field.hasClass('sc_form_field_product_cat') ) {
1247						filters_total += field.hasClass('sc_form_field_text') || field.hasClass('sc_form_field_range') ? 1 : $self.val().split(',').length;
1248					}
1249				});
1250				fields_wrap.parents('form').find( '.trx_addons_woocommerce_search_button_filters_total' )
1251					.html( filters_total )
1252					.toggleClass( 'trx_addons_woocommerce_search_button_filters_total_empty', filters_total === 0 );
1253				// Show/hide 'Clear all'
1254				fields_wrap.toggleClass( 'trx_addons_woocommerce_search_form_fields_filled', filters_total > 0 );
1255			}
1256
1257			// Return comma-separated values from the field with multiple select allowed ('filter' style)
1258			function trx_addons_woocommerce_search_form_get_multiple_field_value( $wrap ) {
1259				var value = '';
1260				$wrap.find('.sc_form_field_item_checked').each( function() {
1261					value += ( value !== '' ? ',' : '' ) + jQuery(this).data('value');
1262				} );
1263				return value;
1264			}
1265
1266			// Get products page from specified url and replace products on the page
1267			function trx_addons_woocommerce_search_form_get_products_from_url( shop_url, fields_wrap ) {
1268				reload_is_busy = true;
1269				var need_open_fields_wrap = false,
1270					widget_number = 0;
1271				if ( fields_wrap && fields_wrap.length ) {
1272					if ( mask_fields_wrap_on_loading ) {
1273						if ( ! list_products_loading ) {
1274							fields_wrap.append( list_products_loading_html );
1275						}
1276						need_open_fields_wrap = false;	//fields_wrap.hasClass('trx_addons_woocommerce_search_form_fields_wrap_opened')
1277														//	&& ! fields_wrap.parents('.trx_addons_woocommerce_search').hasClass('trx_addons_woocommerce_search_apply');
1278						widget_number = fields_wrap.parents('.trx_addons_woocommerce_search_type_filter').data('number') || 1;
1279					}
1280					fields_wrap.removeClass('trx_addons_woocommerce_search_form_fields_changed');
1281				}
1282				// Reset a current page number
1283				jQuery( 'input[name="paged"]' ).val( 1 );
1284				jQuery( '.woocommerce-load-more' ).data( 'page', 1 ).parent().show();
1285				// Mark products wrapper with 'loading'
1286				if ( ! list_products_loading ) {
1287					jQuery( list_products_loading_selector )
1288						.addClass( 'trx_addons_woocommerce_search_loading' )
1289						.append( list_products_loading_html )
1290						.find('>' + list_products_loading_class)
1291							.addClass('trx_addons_hidden')
1292							.fadeIn(200);
1293				}
1294				list_products_loading++;
1295				// Make GET query to the shop
1296				jQuery.get( shop_url ).done( function( response ) {
1297					list_products_loading--;
1298					if ( list_products_loading ) {
1299						list_products_replace();
1300					} else {
1301						jQuery( list_products_loading_selector )
1302							.find('>' + list_products_loading_class)
1303							.fadeOut( 200, function() {
1304								list_products_replace( true );
1305							} );
1306					}
1307					function list_products_replace( remove_loading ) {
1308						var $response = jQuery( response ),
1309							new_products = $response.find( list_products_selector ).html(),
1310							new_inline_css = $response.find( inline_css_selector ).html(),
1311							new_total = $response.find('.trx_addons_woocommerce_search_button_show_total').eq(0).text() || 0;
1312						// If products found
1313						if ( new_products ) {
1314							// Replace document url in the browser's address bar
1315							trx_addons_document_set_location( shop_url );
1316							// Replace products with new items
1317							list_products_wrap.html( new_products );
1318							// Replace inline css with new styles
1319							if ( inline_css_wrap.length ) {
1320								// If inline css is not found via jQuery - try search with regular expression
1321								if ( ! new_inline_css ) {
1322									var mask = '<style[^>]*id="' + inline_css_selector.substr(1).replace( /\-/g, '\\-' ) + '"[^>]*>([^<]+)</style>';
1323									var re = new RegExp( mask );
1324									var matches = response.match( re );
1325									if ( matches && matches[1] ) {
1326										new_inline_css = matches[1];
1327									}
1328								}
1329								// If found inline css for list products - replace it
1330								if ( new_inline_css ) {
1331									var new_inline_block_start = new_inline_css.indexOf( inline_css_start ),
1332										new_inline_block_end = new_inline_css.indexOf( inline_css_end ),
1333										new_inline_block = new_inline_block_start >= 0
1334																? new_inline_css.substring( new_inline_block_start, new_inline_block_end + inline_css_end.length )
1335																: '';
1336									if ( new_inline_block ) {
1337										var old_inline_css = inline_css_wrap.html(),	
1338											old_inline_block_start = old_inline_css.indexOf( inline_css_start ),
1339											old_inline_block_end = old_inline_css.indexOf( inline_css_end );
1340										if ( old_inline_block_start >= 0 ) {
1341											old_inline_css = old_inline_css.substring( 0, old_inline_block_start )
1342															+ new_inline_block
1343															+ old_inline_css.substring( old_inline_block_end + inline_css_end.length );
1344											inline_css_wrap.html( old_inline_css );
1345										}
1346									}
1347								}
1348							}
1349							// Place back a 'loading' icon
1350							if ( ! remove_loading ) {
1351								jQuery( list_products_loading_selector )
1352									.toggleClass('trx_addons_woocommerce_search_loading', true)
1353									.append( list_products_loading_html );
1354							}
1355							// Replace total products counters
1356							jQuery('.trx_addons_woocommerce_search_button_show_total').text(new_total);
1357							// Got new elements
1358							jQuery( document ).trigger( 'action.got_ajax_response', {
1359								action: 'woocommerce_ajax_get_posts',
1360								result: response,
1361								products: list_products_wrap.hasClass('products')
1362												? list_products_wrap
1363												: list_products_wrap.find('ul.products')
1364							});
1365							// Init new elements
1366							$document.trigger( 'action.init_hidden_elements', [list_products_wrap] );
1367						} else {
1368							// If a result is a redirect to the single product - commit it
1369							if ( $response.find( single_product_selector ).length ) {
1370								var url = $response.filter( 'link[rel="canonical"]' ).attr( 'href' );
1371								if ( url ) {
1372									window.location = url;
1373									return;
1374								}
1375							}
1376							alert( TRX_ADDONS_STORAGE['msg_no_products_found'] );
1377						}
1378						// Remove 'loading' from products container
1379						if ( remove_loading ) {
1380							jQuery( list_products_loading_selector )
1381								.removeClass('trx_addons_woocommerce_search_loading')
1382								.find('>' + list_products_loading_class).remove();
1383						}
1384						// If fields_wrap not empty
1385						if ( widget_number ) {
1386							// Get new object for fields_wrap after products replaced (old fields wrap may be removed)
1387							var widget = jQuery('.trx_addons_woocommerce_search_type_filter[data-number="' + widget_number + '"]').eq(0),
1388								fields_wrap = widget.find('.trx_addons_woocommerce_search_form_fields_wrap').eq(0);
1389							if ( fields_wrap.length ) {
1390								// Remove 'loading'
1391								if ( remove_loading && mask_fields_wrap_on_loading ) {
1392									fields_wrap.find('>' + list_products_loading_class).remove();
1393								}
1394								// Reopen fields wrap
1395								if ( need_open_fields_wrap ) {
1396									widget.find('.trx_addons_woocommerce_search_form_fields_wrap').addClass('trx_addons_woocommerce_search_form_fields_wrap_opened trx_addons_woocommerce_search_form_fields_wrap_show');
1397									setTimeout( function() {
1398										widget.find('.trx_addons_woocommerce_search_form_fields_wrap_show').removeClass('trx_addons_woocommerce_search_form_fields_wrap_show');
1399									}, 500 );
1400								}
1401								// Reopen last active field
1402								if ( last_opened_filter ) {// && ! fields_wrap.parents('.trx_addons_woocommerce_search ').hasClass('trx_addons_woocommerce_search_apply') ) {
1403									var field = widget.find('input[name="'+last_opened_filter+'"]').parents('.sc_form_field');
1404									trx_addons_woocommerce_search_form_open_field( field, 'show' );
1405									if ( last_clicked_item ) {
1406										field.find('.sc_form_field_item[data-value="'+last_clicked_item+'"]').get(0).focus();
1407									}
1408								}
1409								// Clear 'param-changed' data parameter
1410								fields_wrap.data('param-changed', 0);
1411							}
1412						}
1413						// Scroll to top
1414						if ( trx_addons_window_scroll_top() > 0 ) {
1415							trx_addons_document_animate_to( list_products_wrap );
1416						}
1417						reload_is_busy = false;
1418					}
1419				} );
1420			}
1421
1422		} );
1423
1424		// Close opened field on click outside the field wrap
1425		var trx_addons_woocommerce_search_form_click_outside = trx_addons_throttle(
1426								function() {
1427									var opened = jQuery('.trx_addons_woocommerce_search_form .sc_form_field_opened').eq(0);
1428									if ( opened.length ) {
1429										var fields_wrap = opened.parents('.trx_addons_woocommerce_search_form_fields_wrap');
1430										if ( fields_wrap.parents('.trx_addons_woocommerce_tools').length
1431											&& ! fields_wrap.hasClass('trx_addons_woocommerce_search_form_fields_wrap_opened')
1432										) {
1433											opened.find('.sc_form_field_title').trigger('click');
1434										} else {
1435											fields_wrap.find('.trx_addons_woocommerce_search_button_show').trigger('click');
1436										}
1437									}
1438								},
1439								trx_addons_apply_filters( 'trx_addons_filter_woocommerce_search_click_outside_timeout', 10 ),
1440								true
1441							);
1442
1443		$document.on( 'click', function(e) {
1444			var $self = jQuery( e.target );
1445			if ( ! $self.hasClass('sc_form_field_wrap')
1446					&& $self.parents('.sc_form_field_wrap').length === 0
1447					&& $self.parents('.trx_addons_woocommerce_search_form_fields_wrap').length === 0
1448					&& ! $self.hasClass(list_products_loading_class)
1449			) {
1450				trx_addons_woocommerce_search_form_click_outside();
1451			}
1452			// Close opened fields wrap
1453			/*
1454			if ( ! $self.hasClass('trx_addons_woocommerce_search_form_fields_wrap_opened')
1455					&& $self.parents('.trx_addons_woocommerce_search_form_fields_wrap_opened').length === 0
1456			) {
1457				jQuery('.trx_addons_woocommerce_search_form_fields_wrap_opened').removeClass('trx_addons_woocommerce_search_form_fields_wrap_opened');
1458			}
1459			*/
1460		} );
1461		
1462		// Collect all form params to array (any style)
1463		function trx_addons_woocommerce_search_form_get_params( form, selector ) {
1464			var params = {}, not_empty = false;
1465			// Collect all filters
1466			form.find( selector ? selector : 'select,input' ).each( function() {
1467				var $self = jQuery(this),
1468					val   = $self.val(),
1469					name  = $self.attr('name'),
1470					type  = '';
1471				if ( name && ( ( val !== '' && ( '' + val ) !== '0' ) || name == 'product_cat' ) ) {
1472					if ( name == 'price' ) {
1473						var values  = val.split(','),
1474							$slider = $self.next('.trx_addons_range_slider '),
1475							min     = $slider.data('min'),
1476							max     = $slider.data('max');
1477						if ( values.length == 2 && $slider.length == 1 ) {
1478							if ( Number( values[0] ) > min ) {
1479								params['min_price'] = values[0];
1480							}
1481							if ( Number( values[1] ) < max ) {
1482								params['max_price'] = values[1];
1483							}
1484						}
1485						name = '';
1486					} else if ( name.substring(0, 3) == 'pa_' ) {
1487						type = 'query_type_' + name.substring(3);
1488						name = 'filter_' + name.substring(3);
1489					} else if ( name == 'rating' ) {
1490						name = name + '_filter';
1491					}
1492					if ( name !== '' ) {
1493						params[name] = val;
1494					}
1495					if ( type !== '' && val.indexOf(',') > 0 ) {
1496						params[type] = 'or';
1497					}
1498					not_empty = true;
1499				}
1500			} );
1501			// Add sort order
1502			if ( not_empty || selector ) {
1503				params = trx_addons_woocommerce_search_form_add_orderby_to_query_params( params );
1504			}
1505			return not_empty || typeof params['orderby'] != 'undefined' ? params : false;
1506		}
1507
1508		// Add sort order to the query params
1509		function trx_addons_woocommerce_search_form_add_orderby_to_query_params( params ) {
1510			var orderby = jQuery('.woocommerce-ordering .orderby').val();
1511			if ( orderby && orderby != 'menu_order' ) {
1512				params['orderby'] = orderby;
1513			}
1514			return params;
1515		}
1516
1517	});
1518
1519})();

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.