/**
 * Card Carousel: Swiper + lightbox. Magnific Popup requires jQuery; all other logic is plain DOM.
 */
( function () {
	'use strict';

	var cardCarouselSwipers = [];
	var resizeScheduled = false;
	var resizeListenerBound = false;

	function scheduleAllSwipersResize() {
		if ( resizeScheduled ) {
			return;
		}
		resizeScheduled = true;
		requestAnimationFrame( function () {
			resizeScheduled = false;
			for ( var i = 0; i < cardCarouselSwipers.length; i++ ) {
				var s = cardCarouselSwipers[ i ];
				if ( s && typeof s.updateSize === 'function' ) {
					try {
						s.updateSize();
						s.update();
					} catch ( e ) {
						// Swiper may be destroyed.
					}
				}
			}
		} );
	}

	function bindGlobalResizeOnce() {
		if ( resizeListenerBound ) {
			return;
		}
		resizeListenerBound = true;
		window.addEventListener( 'resize', scheduleAllSwipersResize, {
			passive: true,
		} );
	}

	var DSM_CARD_CAROUSEL_LOOP_MINIMUM_CLONE_CLASS =
		'dsm-card-carousel-loop-minimum-clone';

	/**
	 * Swiper 12 loop requires slide count >= slidesPerView + slidesPerGroup (+1 when centered).
	 *
	 * @param {number}  slidesPerView
	 * @param {number}  slidesPerGroup
	 * @param {boolean} centeredSlides
	 * @return {number}
	 */
	function getDsmSwiperLoopMinimumSlideCount(
		slidesPerView,
		slidesPerGroup,
		centeredSlides
	) {
		var spv = Math.max( 1, Number( slidesPerView ) || 1 );
		var spg = Math.max( 1, Number( slidesPerGroup ) || 1 );
		var centeredExtra = centeredSlides ? 1 : 0;

		return spv + spg + centeredExtra;
	}

	/**
	 * @param {Element} wrapper Swiper wrapper element.
	 * @return {HTMLElement[]}
	 */
	function getDsmCarouselRealSlideElements( wrapper ) {
		if ( ! wrapper || typeof wrapper.children === 'undefined' ) {
			return [];
		}

		return Array.prototype.filter.call( wrapper.children, function ( slide ) {
			return (
				slide.nodeType === 1 &&
				! slide.classList.contains( 'swiper-slide-duplicate' ) &&
				! slide.classList.contains(
					DSM_CARD_CAROUSEL_LOOP_MINIMUM_CLONE_CLASS
				)
			);
		} );
	}

	/**
	 * Remove pre-init clones added so Swiper loop can activate when slide count == perView.
	 *
	 * @param {Element|null|undefined} swiperRoot `.swiper` element or wrapper parent.
	 * @return {void}
	 */
	function removeDsmCardCarouselLoopMinimumClones( swiperRoot ) {
		if ( ! swiperRoot || typeof swiperRoot.querySelector !== 'function' ) {
			return;
		}

		var wrapper = swiperRoot.classList.contains( 'swiper-wrapper' )
			? swiperRoot
			: swiperRoot.querySelector( '.swiper-wrapper' );

		if ( ! wrapper ) {
			return;
		}

		wrapper
			.querySelectorAll( '.' + DSM_CARD_CAROUSEL_LOOP_MINIMUM_CLONE_CLASS )
			.forEach( function ( node ) {
				node.parentNode.removeChild( node );
			} );
	}

	/**
	 * Strip Swiper runtime classes/attrs from a pre-init loop pad clone.
	 *
	 * @param {HTMLElement} clone Cloned slide element.
	 * @return {void}
	 */
	function sanitizeDsmCardCarouselLoopMinimumClone( clone ) {
		[
			'swiper-slide-active',
			'swiper-slide-next',
			'swiper-slide-prev',
			'swiper-slide-fully-visible',
			'swiper-slide-visible',
		].forEach( function ( cls ) {
			clone.classList.remove( cls );
		} );

		clone.removeAttribute( 'data-swiper-slide-index' );
		clone.classList.add( DSM_CARD_CAROUSEL_LOOP_MINIMUM_CLONE_CLASS );
		clone.setAttribute( 'aria-hidden', 'true' );
	}

	/**
	 * Clone real slides until Swiper loop minimum is met (cards == columns case).
	 *
	 * Append full cycles of the real slide list (not a partial prefix). Padding
	 * only the first slide yields DOM like `[0,1,2,0]`, which shows two identical
	 * cards side-by-side under loop + multi slidesPerView.
	 *
	 * @param {Element|null|undefined} swiperRoot `.swiper` module root.
	 * @param {{ loop?: boolean, slidesPerView?: number, slidesPerGroup?: number, centeredSlides?: boolean }} options
	 * @return {void}
	 */
	function ensureDsmCardCarouselLoopMinimumSlides( swiperRoot, options ) {
		if ( ! swiperRoot || ! options || ! options.loop ) {
			return;
		}

		var wrapper = swiperRoot.querySelector( '.swiper-wrapper' );
		if ( ! wrapper ) {
			return;
		}

		removeDsmCardCarouselLoopMinimumClones( swiperRoot );

		var minimumSlides = getDsmSwiperLoopMinimumSlideCount(
			options.slidesPerView,
			options.slidesPerGroup,
			!! options.centeredSlides
		);

		var realSlides = getDsmCarouselRealSlideElements( wrapper );
		var slideCount = realSlides.length;

		if ( slideCount === 0 || slideCount >= minimumSlides ) {
			return;
		}

		var totalSlides = slideCount;

		while ( totalSlides < minimumSlides ) {
			for ( var i = 0; i < slideCount; i++ ) {
				var source = realSlides[ i ];
				if ( ! source ) {
					continue;
				}

				var clone = source.cloneNode( true );
				sanitizeDsmCardCarouselLoopMinimumClone( clone );
				wrapper.appendChild( clone );
				totalSlides += 1;
			}
		}
	}

	/**
	 * @param {import('swiper').Swiper} swiperInstance Swiper instance.
	 * @return {{ realCount: number, activeIndex: number }}
	 */
	function getDsmCardCarouselPaginationIndexState( swiperInstance ) {
		if ( ! swiperInstance || ! swiperInstance.el ) {
			return { realCount: 0, activeIndex: 0 };
		}

		var wrapper = swiperInstance.el.querySelector( '.swiper-wrapper' );
		var realSlides = getDsmCarouselRealSlideElements( wrapper );
		var realCount = realSlides.length;
		if ( realCount <= 0 ) {
			return { realCount: 0, activeIndex: 0 };
		}

		var realIndex =
			typeof swiperInstance.realIndex === 'number'
				? swiperInstance.realIndex
				: 0;

		return {
			realCount: realCount,
			activeIndex: ( ( realIndex % realCount ) + realCount ) % realCount,
		};
	}

	/**
	 * Custom pagination: one bullet per real child (excludes loop pad clones).
	 *
	 * @param {import('swiper').Swiper} swiperInstance Swiper instance.
	 * @return {string}
	 */
	function renderDsmCardCarouselPaginationHtml( swiperInstance ) {
		var state = getDsmCardCarouselPaginationIndexState( swiperInstance );
		var realCount = state.realCount;
		var activeIndex = state.activeIndex;
		if ( realCount <= 0 ) {
			return '';
		}

		var bulletClass =
			( swiperInstance.params &&
				swiperInstance.params.pagination &&
				swiperInstance.params.pagination.bulletClass ) ||
			'swiper-pagination-bullet';
		var activeClass =
			( swiperInstance.params &&
				swiperInstance.params.pagination &&
				swiperInstance.params.pagination.bulletActiveClass ) ||
			'swiper-pagination-bullet-active';
		var html = '';
		var i;

		for ( i = 0; i < realCount; i++ ) {
			html +=
				'<span class="' +
				bulletClass +
				( i === activeIndex ? ' ' + activeClass : '' ) +
				'"></span>';
		}

		return html;
	}

	/**
	 * Custom dynamic-style bullets (real children only) when loop pads block
	 * Swiper's native dynamicBullets.
	 *
	 * @param {import('swiper').Swiper} swiperInstance Swiper instance.
	 * @return {string}
	 */
	function renderDsmCardCarouselDynamicPaginationHtml( swiperInstance ) {
		var state = getDsmCardCarouselPaginationIndexState( swiperInstance );
		var realCount = state.realCount;
		var activeIndex = state.activeIndex;
		if ( realCount <= 0 ) {
			return '';
		}

		var bulletClass =
			( swiperInstance.params &&
				swiperInstance.params.pagination &&
				swiperInstance.params.pagination.bulletClass ) ||
			'swiper-pagination-bullet';
		var activeClass =
			( swiperInstance.params &&
				swiperInstance.params.pagination &&
				swiperInstance.params.pagination.bulletActiveClass ) ||
			'swiper-pagination-bullet-active';
		var html = '';
		var i;
		var dist;
		var classes;

		for ( i = 0; i < realCount; i++ ) {
			dist = Math.abs( i - activeIndex );
			classes = bulletClass;
			if ( 0 === dist ) {
				classes += ' ' + activeClass + ' ' + activeClass + '-main';
			} else if ( 1 === dist ) {
				classes +=
					' ' +
					activeClass +
					( i < activeIndex ? '-prev' : '-next' );
			} else if ( 2 === dist ) {
				classes +=
					' ' +
					activeClass +
					( i < activeIndex ? '-prev-prev' : '-next-next' );
			}
			html += '<span class="' + classes + '"></span>';
		}

		return html;
	}

	/**
	 * Custom progressbar sized by real children (excludes loop pad clones).
	 *
	 * @param {import('swiper').Swiper} swiperInstance Swiper instance.
	 * @return {string}
	 */
	function renderDsmCardCarouselProgressbarHtml( swiperInstance ) {
		var state = getDsmCardCarouselPaginationIndexState( swiperInstance );
		var realCount = state.realCount;
		var activeIndex = state.activeIndex;
		var fillClass =
			( swiperInstance.params &&
				swiperInstance.params.pagination &&
				swiperInstance.params.pagination.progressbarFillClass ) ||
			'swiper-pagination-progressbar-fill';
		var progress = realCount > 0 ? ( activeIndex + 1 ) / realCount : 0;
		var isHorizontal =
			! swiperInstance ||
			typeof swiperInstance.isHorizontal !== 'function' ||
			swiperInstance.isHorizontal();
		var scaleX = isHorizontal ? progress : 1;
		var scaleY = isHorizontal ? 1 : progress;
		var speed =
			swiperInstance.params &&
			typeof swiperInstance.params.speed === 'number'
				? swiperInstance.params.speed
				: 300;

		return (
			'<span class="' +
			fillClass +
			'" style="transform: translate3d(0px, 0, 0) scaleX(' +
			scaleX +
			') scaleY(' +
			scaleY +
			'); transition-duration: ' +
			speed +
			'ms;"></span>'
		);
	}

	/**
	 * Build Swiper pagination options for Card Carousel pagi_style.
	 *
	 * @param {HTMLElement} paginationEl Pagination container.
	 * @param {string}      pagiStyle    bullets | dynamic | progressbar.
	 * @param {Element}     wrap         Swiper root.
	 * @return {Record<string, *>}
	 */
	function getDsmCardCarouselPaginationParams(
		paginationEl,
		pagiStyle,
		wrap
	) {
		var style = pagiStyle || 'bullets';
		var hasPadClones = !! (
			wrap &&
			wrap.querySelector(
				'.' + DSM_CARD_CAROUSEL_LOOP_MINIMUM_CLONE_CLASS
			)
		);

		paginationEl.classList.remove(
			'swiper-pagination-bullets',
			'swiper-pagination-bullets-dynamic',
			'swiper-pagination-progressbar',
			'swiper-pagination-clickable',
			'swiper-pagination-custom'
		);
		// Dynamic mode leaves inline width/left/transform on the el.
		paginationEl.removeAttribute( 'style' );
		paginationEl.classList.add( 'swiper-pagination-clickable' );

		if ( 'progressbar' === style ) {
			paginationEl.classList.add( 'swiper-pagination-progressbar' );
			return {
				el: paginationEl,
				type: 'custom',
				clickable: true,
				renderCustom: function ( swiperInstance ) {
					return renderDsmCardCarouselProgressbarHtml(
						swiperInstance
					);
				},
			};
		}

		if ( 'dynamic' === style ) {
			paginationEl.classList.add(
				'swiper-pagination-bullets',
				'swiper-pagination-bullets-dynamic'
			);

			// Native dynamicBullets only when pads are not inflating slide count.
			if ( ! hasPadClones ) {
				return {
					el: paginationEl,
					type: 'bullets',
					clickable: true,
					dynamicBullets: true,
				};
			}

			return {
				el: paginationEl,
				type: 'custom',
				clickable: true,
				renderCustom: function ( swiperInstance ) {
					return renderDsmCardCarouselDynamicPaginationHtml(
						swiperInstance
					);
				},
			};
		}

		paginationEl.classList.add( 'swiper-pagination-bullets' );
		return {
			el: paginationEl,
			type: 'custom',
			clickable: true,
			renderCustom: function ( swiperInstance ) {
				return renderDsmCardCarouselPaginationHtml( swiperInstance );
			},
		};
	}

	/**
	 * Max slidesPerView / slidesPerGroup across breakpoints for conservative loop clones.
	 *
	 * @param {Record<string, *>} params Parsed `data-params` object.
	 * @return {{ slidesPerView: number, slidesPerGroup: number }}
	 */
	function getMaxLoopSlidesConfigFromParams( params ) {
		var isSingle =
			'cube' === params.effect || 'flip' === params.effect;

		var desktopSpv = isSingle
			? 1
			: parseInt( params.slide_to_show, 10 ) || 1;
		var desktopSpg = parseInt( params.slide_to_scroll, 10 ) || 1;

		var tabletSpv =
			'' === params.slide_to_show_tablet
				? desktopSpv
				: parseInt( params.slide_to_show_tablet, 10 ) || desktopSpv;
		var tabletSpg =
			'' === params.slide_to_scroll_tablet
				? 1
				: parseInt( params.slide_to_scroll_tablet, 10 ) || 1;

		var phoneSpv =
			'' === params.slide_to_show_phone
				? 1
				: parseInt( params.slide_to_show_phone, 10 ) || 1;
		var phoneSpg =
			'' === params.slide_to_scroll_phone
				? 1
				: parseInt( params.slide_to_scroll_phone, 10 ) || 1;

		return {
			slidesPerView: isSingle
				? 1
				: Math.max( desktopSpv, tabletSpv, phoneSpv ),
			slidesPerGroup: Math.max( desktopSpg, tabletSpg, phoneSpg ),
		};
	}

	/**
	 * @param {Element} wrap Carousel root (.dsm_card_carousel_wrapper).
	 * @param {string}    selector Sibling selector (e.g. .swiper-button-prev).
	 * @return {Element|null}
	 */
	function getSibling( wrap, selector ) {
		var parent = wrap.parentElement;
		if ( ! parent ) {
			return null;
		}
		var found = parent.querySelectorAll( ':scope > ' + selector );
		return found.length ? found[ 0 ] : null;
	}

	/**
	 * Magnific Popup (jQuery plugin API only).
	 */
	function initMagnificPopup() {
		if ( typeof jQuery === 'undefined' || ! jQuery.fn.magnificPopup ) {
			return;
		}
		var $ = jQuery;
		var nodes = document.querySelectorAll(
			'.dsm_card_carousel .dsm_card_carousel_child_image_wrapper'
		);
		if ( ! nodes.length ) {
			return;
		}

		var videoRe =
			/(youtube\.com|youtu\.be|vimeo\.com|dailymotion\.com)/i;

		nodes.forEach( function ( el ) {
			el.addEventListener( 'click', function () {
				var itemsSrc = el.getAttribute( 'data-mfp-src' );
				if (
					! itemsSrc ||
					itemsSrc === 'undefined' ||
					itemsSrc === ''
				) {
					return;
				}

				var type = videoRe.test( itemsSrc ) ? 'iframe' : 'image';
				var classes = '';

				$.magnificPopup.open( {
					delegate: 'a',
					items: {
						src: itemsSrc,
					},
					type: type,
					iframe: {
						markup:
							'<div class="mfp-iframe-scaler dsm-video-popup">' +
							'<div class="mfp-close"></div>' +
							'<iframe class="mfp-iframe" frameborder="0" allowfullscreen allow="autoplay"></iframe>' +
							'</div>',
						patterns: {
							youtube: {
								index: 'youtube.com/',
								id: 'v=',
								src: '//www.youtube.com/embed/%id%?autoplay=1&rel=0',
							},
							youtu_be: {
								index: 'youtu.be',
								id: '/',
								src: '//www.youtube.com/embed/%id%?autoplay=1&rel=0',
							},
							vimeo: {
								index: 'vimeo.com/',
								id: '/',
								src: '//player.vimeo.com/video/%id%?autoplay=1',
							},
							dailymotion: {
								index: 'dailymotion.com',
								id: function ( url ) {
									var m = url.match(
										/^.+dailymotion.com\/(video|hub)\/([^_]+)[^#]*(#video=([^_&]+))?/
									);
									if ( m !== null ) {
										if ( m[ 4 ] !== undefined ) {
											return m[ 4 ];
										}
										return m[ 2 ];
									}
									return null;
								},
								src: 'https://www.dailymotion.com/embed/video/%id%',
							},
						},
						srcAction: 'iframe_src',
					},
					removalDelay: 500,
					mainClass: classes + 'mfp-fade',
				} );
			} );
		} );
	}

	function startCardAutoplay( swiper ) {
		if (
			swiper &&
			swiper.autoplay &&
			typeof swiper.autoplay.start === 'function'
		) {
			swiper.autoplay.start();
		}
	}

	function destroyCardAutoplayWaypoint( wrap ) {
		if (
			wrap._dsmAutoplayWaypoint &&
			typeof wrap._dsmAutoplayWaypoint.destroy === 'function'
		) {
			wrap._dsmAutoplayWaypoint.destroy();
		}
		wrap._dsmAutoplayWaypoint = null;
	}

	function refreshCardSwiperInstance( wrap ) {
		var instance = wrap && wrap.swiper ? wrap.swiper : null;
		if ( ! instance || typeof instance.updateSize !== 'function' ) {
			return false;
		}

		try {
			instance.updateSize();
			instance.update();
			if ( typeof instance.slideTo === 'function' ) {
				instance.slideTo( instance.realIndex, 0 );
			}
		} catch ( err ) {
			return false;
		}

		return true;
	}

	function initSingleCardCarousel( wrap ) {
		if ( refreshCardSwiperInstance( wrap ) ) {
			return;
		}

		var rawParams = wrap.getAttribute( 'data-params' );
			if (
				! rawParams ||
				typeof rawParams !== 'string' ||
				'' === rawParams.trim()
			) {
				return;
			}

			var parsedParams;
			try {
				parsedParams = JSON.parse( rawParams );
			} catch ( err ) {
				return;
			}
			if (
				! parsedParams ||
				typeof parsedParams !== 'object' ||
				! parsedParams[ 0 ]
			) {
				return;
			}

			var params = parsedParams[ 0 ];

			var prevButton = getSibling( wrap, '.swiper-button-prev' );
			var nextButton = getSibling( wrap, '.swiper-button-next' );
			var paginationEl = getSibling(
				wrap,
				'.swiper-pagination.dsm_card_carousel_pagination'
			);
			if ( ! paginationEl ) {
				paginationEl = getSibling( wrap, '.swiper-pagination' );
			}

			var autoHeight = false !== params.auto_height;
			var checkAutoHeight =
				params.equal_height === true ? false : autoHeight;
			var autoHeightCheckTablet =
				true === params.equal_height_tablet ? false : true;
			var autoHeightCheckPhone =
				true === params.equal_height_phone ? false : true;

			var isLoop = true === params.loop;
			var maxLoopSlides = getMaxLoopSlidesConfigFromParams( params );

			var swiperOptions = {
				resizeObserver: true,
				observer: true,
				observeParents: true,
				observeSlideChildren: true,
				direction: params.direction,
				effect: params.effect,
				coverflowEffect: {
					slideShadows: params.slider_effect_shadows,
					rotate: params.slider_effect_coverflow_rotate,
					depth: params.slider_effect_coverflow_depth,
				},
				flipEffect: {
					rotate: 30,
					slideShadows: params.slider_effect_shadows,
				},
				cubeEffect: {
					slideShadows: params.slider_effect_shadows,
					shadow: params.slider_effect_shadows,
					shadowOffset: 20,
					shadowScale: 0.94,
				},
				centeredSlides: params.centered_slides,
				speed: parseInt( params.speed, 10 ),
				loop: params.loop,
				watchOverflow: ! isLoop,
				preventInteractionOnTransition: false,
				autoplay: {
					enabled: params.autoplay,
					delay:
						params.infinite_smooth_scrolling === true &&
						params.slide_to_show < 6
							? 1
							: parseInt( params.autoplay_speed, 10 ),
					disableOnInteraction: false,
				},
				mousewheel: params.mousewheel,
				grabCursor:
					false === params.touch_move ? false : params.grab,
				preloadImages: false,
				lazy: {
					loadPrevNext: true,
				},
				allowTouchMove: params.touch_move,
				a11y: {
					enabled: false,
					slideRole: 'group',
				},
				breakpoints: {
					981: {
						slidesPerView:
							'cube' === params.effect ||
							'flip' === params.effect
								? 1
								: parseInt( params.slide_to_show, 10 ),
						slidesPerGroup: parseInt(
							params.slide_to_scroll,
							10
						),
						spaceBetween: parseInt(
							params.space_between,
							10
						),
						grid: {
							rows: params.slide_row,
							fill: 'row',
						},
						autoHeight:
							'on' === params.multiple_slide_row
								? false
								: checkAutoHeight,
					},
					768: {
						slidesPerView:
							'cube' === params.effect ||
							'flip' === params.effect
								? 1
								: params.slide_to_show_tablet === ''
								? parseInt( params.slide_to_show, 10 )
								: parseInt(
										params.slide_to_show_tablet,
										10
								  ),
						slidesPerGroup:
							params.slide_to_scroll_tablet === ''
								? 1
								: parseInt(
										params.slide_to_scroll_tablet,
										10
								  ),
						spaceBetween:
							params.space_between_tablet === ''
								? 10
								: parseInt(
										params.space_between_tablet,
										10
								  ),
						grid: {
							rows: params.slide_row_tablet,
							fill: 'row',
						},
						autoHeight:
							'on' === params.multiple_slide_row
								? false
								: autoHeightCheckTablet,
					},
					480: {
						slidesPerView:
							'cube' === params.effect ||
							'flip' === params.effect
								? 1
								: params.slide_to_show_phone === ''
								? 1
								: parseInt(
										params.slide_to_show_phone,
										10
								  ),
						slidesPerGroup:
							params.slide_to_scroll_phone === ''
								? 1
								: parseInt(
										params.slide_to_scroll_phone,
										10
								  ),
						spaceBetween:
							params.space_between_phone === ''
								? 10
								: parseInt(
										params.space_between_phone,
										10
								  ),
						grid: {
							rows: params.slide_row_phone,
							fill: 'row',
						},
						autoHeight:
							'on' === params.multiple_slide_row
								? false
								: autoHeightCheckPhone,
					},
					320: {
						slidesPerView:
							'cube' === params.effect ||
							'flip' === params.effect
								? 1
								: params.slide_to_show_phone === ''
								? 1
								: parseInt(
										params.slide_to_show_phone,
										10
								  ),
						slidesPerGroup:
							params.slide_to_scroll_phone === ''
								? 1
								: parseInt(
										params.slide_to_scroll_phone,
										10
								  ),
						spaceBetween:
							params.space_between_phone === ''
								? 10
								: parseInt(
										params.space_between_phone,
										10
								  ),
						grid: {
							rows: params.slide_row_phone,
							fill: 'row',
						},
						autoHeight:
							'on' === params.multiple_slide_row
								? false
								: autoHeightCheckPhone,
					},
				},
			};

			ensureDsmCardCarouselLoopMinimumSlides( wrap, {
				loop: isLoop,
				slidesPerView: maxLoopSlides.slidesPerView,
				slidesPerGroup: maxLoopSlides.slidesPerGroup,
				centeredSlides: !! params.centered_slides,
			} );

			if ( paginationEl ) {
				swiperOptions.pagination = getDsmCardCarouselPaginationParams(
					paginationEl,
					params.pagi_style || 'bullets',
					wrap
				);
			}

			if ( prevButton && nextButton ) {
				swiperOptions.navigation = {
					nextEl: nextButton,
					prevEl: prevButton,
				};
			}

			var DSM_CardSwiper = new Swiper( wrap, swiperOptions );
			cardCarouselSwipers.push( DSM_CardSwiper );

			if ( params.pause_on_hover === true ) {
				wrap.addEventListener( 'mouseenter', function () {
					if (
						wrap.swiper &&
						wrap.swiper.autoplay &&
						typeof wrap.swiper.autoplay.stop === 'function'
					) {
						wrap.swiper.autoplay.stop();
					}
				} );
				wrap.addEventListener( 'mouseleave', function () {
					startCardAutoplay( wrap.swiper );
				} );
			}

			var tabsRoot = wrap.closest( '.et_pb_tabs' );
			if ( tabsRoot ) {
				tabsRoot.querySelectorAll( 'a' ).forEach( function ( a ) {
					a.addEventListener( 'click', function () {
						DSM_CardSwiper.slideTo(
							DSM_CardSwiper.realIndex,
							0
						);
					} );
				} );
			}

			var advTabs = wrap.closest( '.dsm_advanced_tabs' );
			if ( advTabs ) {
				advTabs.querySelectorAll( '.dsm-tab' ).forEach( function ( tab ) {
					tab.addEventListener( 'click', function () {
						window.requestAnimationFrame( function () {
							window.requestAnimationFrame( function () {
								if ( ! refreshCardSwiperInstance( wrap ) ) {
									initSingleCardCarousel( wrap );
								}
							} );
						} );
					} );
				} );
			}

			if ( params.autoplay === true ) {
				destroyCardAutoplayWaypoint( wrap );

				if ( typeof Waypoint === 'undefined' ) {
					startCardAutoplay( DSM_CardSwiper );
				} else {
					wrap._dsmAutoplayWaypoint = new Waypoint( {
						element: wrap,
						handler: function () {
							startCardAutoplay( wrap.swiper );
							this.destroy();
							wrap._dsmAutoplayWaypoint = null;
						},
						offset: params.autoplay_viewport,
					} );
				}
			}
	}

	function initSwipers( root ) {
		if ( typeof Swiper === 'undefined' ) {
			return;
		}

		var scope = root && root.querySelectorAll ? root : document;
		var wrappers = scope.querySelectorAll(
			'.dsm_card_carousel .dsm_card_carousel_wrapper'
		);
		if ( ! wrappers.length ) {
			return;
		}

		bindGlobalResizeOnce();
		wrappers.forEach( initSingleCardCarousel );
	}

	function refreshOrInitCardCarouselsInRoot( root ) {
		if ( ! root || typeof root.querySelectorAll !== 'function' ) {
			return;
		}

		if ( typeof Swiper === 'undefined' ) {
			return;
		}

		var wrappers = root.querySelectorAll(
			'.dsm_card_carousel .dsm_card_carousel_wrapper'
		);
		if ( ! wrappers.length ) {
			return;
		}

		bindGlobalResizeOnce();
		wrappers.forEach( function ( wrap ) {
			destroyCardAutoplayWaypoint( wrap );
			removeDsmCardCarouselLoopMinimumClones( wrap );

			if ( wrap.swiper && typeof wrap.swiper.destroy === 'function' ) {
				try {
					wrap.swiper.destroy( true, true );
				} catch ( err ) {
					// Stale instance during VB remounts.
				}
			}
			initSingleCardCarousel( wrap );
		} );
	}

	window.dsmReinitCardCarouselsInRoot = refreshOrInitCardCarouselsInRoot;

	[ 'dsm:reinit-library-modules-in-root', 'dsm:reinit-carousels-in-root' ].forEach(
		function ( eventName ) {
			window.addEventListener( eventName, function ( event ) {
				var eventRoot = event && event.detail ? event.detail.root : null;
				if (
					! eventRoot ||
					typeof eventRoot.querySelector !== 'function' ||
					! eventRoot.querySelector( '.dsm_card_carousel' )
				) {
					return;
				}
				refreshOrInitCardCarouselsInRoot( eventRoot );
			} );
		}
	);

	function init() {
		if ( document.querySelector( '.dsm_card_carousel' ) ) {
			initMagnificPopup();
		}
		initSwipers();
	}

	if ( document.readyState === 'loading' ) {
		document.addEventListener( 'DOMContentLoaded', init );
	} else {
		init();
	}
} )();
