PageSourceSearch

https://www.teamtailor.com/js/webflow-initialize-carousel-entry.global.js

js teamtailor.com collected 2026-10-01 08:55:34 UTC 19,243 bytes, 503 lines download raw bytes

vendor: 28 bytes, lines 1-3
1"use strict";
2(() => {
3  // 
3../web-design-system/src/components/composition/slider/custom/webflow-initialize-carousel.ts
4  function initializeCarousel(sliderId, prevButtonId, nextButtonId, options) {
5    const debug = options?.debug ?? false;
6    if (!sliderId || !prevButtonId || !nextButtonId) {
7      if (debug) {
8        console.error("[initializeCarousel] Missing required parameters:", { sliderId, prevButtonId, nextButtonId });
9      }
10      return null;
11    }
12    const sliderContainer = document.getElementById(sliderId);
13    if (!sliderContainer) {
14      if (debug) {
15        console.error("[initializeCarousel] Slider container not found:", sliderId);
16        console.log(
17          "[initializeCarousel] Available elements with IDs:",
18          Array.from(document.querySelectorAll("[id]")).map((el) => el.id).filter(Boolean)
19        );
20      }
21      return null;
22    }
23    if (debug) {
24      console.log("[initializeCarousel] Slider container found:", sliderContainer);
25    }
26    let track = sliderContainer.querySelector(".c-carousel_track, .c-slider_track");
27    if (!track) {
28      if (sliderContainer.classList.contains("c-carousel_track") || sliderContainer.classList.contains("c-slider_track")) {
29        track = sliderContainer;
30      }
31    }
32    if (!track) {
33      return null;
34    }
35    const slides = Array.from(track.querySelectorAll(".c-carousel_item, .c-slider_item"));
36    if (slides.length === 0) {
37      return null;
38    }
39    let prevButton = document.getElementById(prevButtonId);
40    let nextButton = document.getElementById(nextButtonId);
41    if (!prevButton && sliderContainer) {
42      prevButton = sliderContainer.querySelector(`#${prevButtonId}`);
43    }
44    if (!nextButton && sliderContainer) {
45      nextButton = sliderContainer.querySelector(`#${nextButtonId}`);
46    }
47    if (!prevButton || !nextButton) {
48      if (debug) {
49        console.error("[initializeCarousel] Navigation buttons not found:", {
50          prevButtonId,
51          nextButtonId,
52          prevButtonFound: !!prevButton,
53          nextButtonFound: !!nextButton,
54          sliderContainerId: sliderId
55        });
56        console.log(
57          "[initializeCarousel] Available elements with IDs:",
58          Array.from(document.querySelectorAll("[id]")).map((el) => el.id).filter(Boolean)
59        );
60      }
61      return null;
62    }
63    if (debug) {
64      console.log("[initializeCarousel] Navigation buttons found:", {
65        prevButton,
66        nextButton,
67        prevButtonParent: prevButton.parentElement?.tagName,
68        nextButtonParent: nextButton.parentElement?.tagName
69      });
70    }
71    const centerSlides = options?.centerSlides ?? false;
72    const initialSlide = options?.initialSlide;
73    const onIndexChange = options?.onIndexChange;
74    const paginationContainerId = options?.paginationContainerId;
75    let currentIndex = 0;
76    const disabledClassName = "u-disabled";
77    const updateIndex = (newIndex) => {
78      if (newIndex !== currentIndex) {
79        currentIndex = newIndex;
80        if (onIndexChange) {
81          onIndexChange(currentIndex);
82        }
83        updatePaginationActive();
84      }
85    };
86    let paginationContainer = null;
87    let paginationDots = [];
88    const paginationCleanupFunctions = [];
89    const updatePaginationActive = () => {
90      paginationDots.forEach((dot, index) => {
91        if (index === currentIndex) {
92          dot.classList.add("active");
93        } else {
94          dot.classList.remove("active");
95        }
96      });
97    };
98    const updateButtonStates = () => {
99      const isFirstSlide = currentIndex === 0;
100      const isLastSlide = currentIndex === slides.length - 1;
101      if (isFirstSlide) {
102        prevButton.classList.add(disabledClassName);
103      } else {
104        prevButton.classList.remove(disabledClassName);
105      }
106      if (isLastSlide) {
107        nextButton.classList.add(disabledClassName);
108      } else {
109        nextButton.classList.remove(disabledClassName);
110      }
111      if (debug) {
112        console.log("[initializeCarousel] Button states updated:", {
113          currentIndex,
114          totalSlides: slides.length,
115          isFirstSlide,
116          isLastSlide,
117          prevButtonDisabled: prevButton.classList.contains(disabledClassName),
118          nextButtonDisabled: nextButton.classList.contains(disabledClassName),
119          prevButtonElement: prevButton,
120          nextButtonElement: nextButton
121        });
122      }
123    };
124    const scrollToSlide = (index, instant) => {
125      if (debug) {
126        console.log("[initializeCarousel] scrollToSlide called:", {
127          requestedIndex: index,
128          currentIndex,
129          totalSlides: slides.length,
130          indexValid: index >= 0 && index < slides.length
131        });
132      }
133      if (index < 0 || index >= slides.length) {
134        if (debug) {
135          console.warn("[initializeCarousel] Invalid slide index:", {
136            index,
137            minIndex: 0,
138            maxIndex: slides.length - 1,
139            totalSlides: slides.length
140          });
141        }
142        return;
143      }
144      const targetSlide = slides[index];
145      if (targetSlide) {
146        const scrollContainer2 = track.scrollWidth > track.clientWidth ? track : track.parentElement;
147        if (scrollContainer2) {
148          const containerRect = scrollContainer2.getBoundingClientRect();
149          const slideRect = targetSlide.getBoundingClientRect();
150          const currentScrollLeft = scrollContainer2.scrollLeft;
151          const slideLeftRelativeToViewport = slideRect.left;
152          const containerLeftRelativeToViewport = containerRect.left;
153          const slideLeftRelativeToContainer = slideLeftRelativeToViewport - containerLeftRelativeToViewport + currentScrollLeft;
154          const slideLeftRelativeToTrack = targetSlide.offsetLeft;
155          const useOffsetLeft = scrollContainer2 === track;
156          let targetScrollLeft;
157          if (centerSlides) {
158            if (useOffsetLeft) {
159              targetScrollLeft = slideLeftRelativeToTrack - scrollContainer2.clientWidth / 2 + slideRect.width / 2;
160            } else {
161              targetScrollLeft = slideLeftRelativeToContainer - scrollContainer2.clientWidth / 2 + slideRect.width / 2;
162            }
163          } else {
164            if (useOffsetLeft) {
165              targetScrollLeft = slideLeftRelativeToTrack;
166            } else {
167              const trackRect = track.getBoundingClientRect();
168              const trackLeftRelativeToContainer = trackRect.left - containerLeftRelativeToViewport + currentScrollLeft;
169              targetScrollLeft = trackLeftRelativeToContainer + slideLeftRelativeToTrack;
170            }
171          }
172          if (debug) {
173            const trackRect = track.getBoundingClientRect();
174            const trackLeftRelativeToContainer = !useOffsetLeft && !centerSlides ? trackRect.left - containerLeftRelativeToViewport + currentScrollLeft : "N/A";
175            console.log("[initializeCarousel] Scroll calculation:", {
176              targetIndex: index,
177              slideLeftRelativeToTrack: useOffsetLeft ? slideLeftRelativeToTrack : slideLeftRelativeToTrack,
178              slideLeftRelativeToContainer: useOffsetLeft ? "N/A (using offsetLeft)" : slideLeftRelativeToContainer,
179              trackLeftRelativeToContainer,
180              currentScrollLeft,
181              targetScrollLeft,
182              useOffsetLeft,
183              scrollContainerWidth: scrollContainer2.clientWidth,
184              scrollContainerScrollWidth: scrollContainer2.scrollWidth,
185              canScroll: scrollContainer2.scrollWidth > scrollContainer2.clientWidth,
186              centerSlides,
187              scrollContainer: scrollContainer2.tagName,
188              scrollContainerId: scrollContainer2.id || "no-id",
189              trackClasses: track.className
190            });
191          }
192          if (scrollContainer2.scrollWidth > scrollContainer2.clientWidth) {
193            isProgrammaticScroll = true;
194            if (programmaticScrollTimeout) {
195              clearTimeout(programmaticScrollTimeout);
196            }
197            scrollContainer2.scrollTo({
198              left: Math.max(0, targetScrollLeft),
199              // Load-time positioning (initialSlide) must be instant: a smooth
200              // scroll animates on the compositor, and Chrome permanently stops
201              // LCP tracking on compositor scrolls (PSI NO_LCP).
202              behavior: instant ? "auto" : "smooth"
203            });
204            programmaticScrollTimeout = setTimeout(() => {
205              isProgrammaticScroll = false;
206              if (debug) {
207                console.log("[initializeCarousel] Programmatic scroll completed, scroll snap detection re-enabled");
208              }
209            }, 600);
210            updateIndex(index);
211            if (debug) {
212              console.log("[initializeCarousel] Scroll initiated:", {
213                targetIndex: index,
214                scrollLeft: Math.max(0, targetScrollLeft),
215                behavior: "smooth",
216                isProgrammaticScroll: true
217              });
218            }
219          } else {
220            if (debug) {
221              console.warn("[initializeCarousel] Cannot scroll - container does not support horizontal scrolling:", {
222                scrollWidth: scrollContainer2.scrollWidth,
223                clientWidth: scrollContainer2.clientWidth
224              });
225            }
226          }
227        } else {
228          if (debug) {
229            console.warn("[initializeCarousel] No scroll container found");
230          }
231        }
232        updateIndex(index);
233        if (debug) {
234          console.log("[initializeCarousel] Current index updated to:", currentIndex);
235        }
236        updateButtonStates();
237      } else {
238        if (debug) {
239          console.warn("[initializeCarousel] Target slide not found:", {
240            index,
241            slidesLength: slides.length,
242            targetSlide
243          });
244        }
245      }
246    };
247    const handlePrevClick = (e) => {
248      if (debug) {
249        console.log("[initializeCarousel] Previous button clicked:", {
250          currentIndex,
251          totalSlides: slides.length,
252          canGoBack: currentIndex > 0,
253          targetIndex: currentIndex > 0 ? currentIndex - 1 : null,
254          event: e,
255          button: prevButton,
256          buttonDisabled: prevButton.classList.contains(disabledClassName),
257          timestamp: (/* @__PURE__ */ new Date()).toISOString()
258        });
259      }
260      if (currentIndex > 0) {
261        scrollToSlide(currentIndex - 1);
262      } else {
263        if (debug) {
264          console.warn("[initializeCarousel] Cannot go to previous slide - already at first slide:", {
265            currentIndex,
266            totalSlides: slides.length
267          });
268        }
269      }
270    };
271    const handleNextClick = (e) => {
272      if (debug) {
273        console.log("[initializeCarousel] Next button clicked:", {
274          currentIndex,
275          totalSlides: slides.length,
276          canGoForward: currentIndex < slides.length - 1,
277          targetIndex: currentIndex < slides.length - 1 ? currentIndex + 1 : null,
278          event: e,
279          button: nextButton,
280          buttonDisabled: nextButton.classList.contains(disabledClassName),
281          timestamp: (/* @__PURE__ */ new Date()).toISOString()
282        });
283      }
284      if (currentIndex < slides.length - 1) {
285        scrollToSlide(currentIndex + 1);
286      } else {
287        if (debug) {
288          console.warn("[initializeCarousel] Cannot go to next slide - already at last slide:", {
289            currentIndex,
290            totalSlides: slides.length
291          });
292        }
293      }
294    };
295    if (paginationContainerId) {
296      paginationContainer = paginationContainerId.startsWith("#") ? document.querySelector(paginationContainerId) : document.getElementById(paginationContainerId);
297    } else {
298      paginationContainer = document.querySelector(".c-pag_dots");
299    }
300    if (paginationContainer) {
301      if (debug) {
302        console.log("[initializeCarousel] Pagination container found:", paginationContainer);
303      }
304      const existingDots = Array.from(paginationContainer.querySelectorAll(".c-pag_dot"));
305      if (existingDots.length > 0) {
306        const templateDot = existingDots[0];
307        existingDots.forEach((dot) => dot.remove());
308        for (let i = 0; i < slides.length; i++) {
309          const dot = templateDot.cloneNode(true);
310          dot.classList.remove("active");
311          if (i === 0) {
312            dot.classList.add("active");
313          }
314          const handleDotClick = () => {
315            if (debug) {
316              console.log("[initializeCarousel] Pagination dot clicked:", {
317                dotIndex: i,
318                currentIndex,
319                targetIndex: i
320              });
321            }
322            scrollToSlide(i);
323          };
324          dot.addEventListener("click", handleDotClick);
325          dot.setAttribute("role", "button");
326          dot.setAttribute("tabindex", "0");
327          dot.setAttribute("aria-label", `Go to slide ${i + 1}`);
328          const handleDotKeyDown = (e) => {
329            if (e.key === "Enter" || e.key === " ") {
330              e.preventDefault();
331              handleDotClick();
332            }
333          };
334          dot.addEventListener("keydown", handleDotKeyDown);
335          paginationContainer.appendChild(dot);
336          paginationDots.push(dot);
337          paginationCleanupFunctions.push(() => {
338            dot.removeEventListener("click", handleDotClick);
339            dot.removeEventListener("keydown", handleDotKeyDown);
340          });
341        }
342        if (debug) {
343          console.log("[initializeCarousel] Created pagination dots:", {
344            count: paginationDots.length,
345            slidesCount: slides.length
346          });
347        }
348      } else {
349        if (debug) {
350          console.warn("[initializeCarousel] No template dot found in pagination container");
351        }
352      }
353    } else if (paginationContainerId) {
354      if (debug) {
355        console.warn("[initializeCarousel] Pagination container not found:", paginationContainerId);
356      }
357    }
358    updateButtonStates();
359    updatePaginationActive();
360    if (onIndexChange) {
361      onIndexChange(currentIndex);
362    }
363    if (debug) {
364      console.log("[initializeCarousel] Initial state:", {
365        currentIndex,
366        totalSlides: slides.length,
367        centerSlides,
368        initialSlide,
369        track,
370        trackClasses: track.className,
371        slidesFound: slides.length
372      });
373    }
374    if (initialSlide !== void 0 && initialSlide >= 0 && initialSlide < slides.length) {
375      if (debug) {
376        console.log("[initializeCarousel] Navigating to initial slide:", {
377          initialSlide,
378          totalSlides: slides.length,
379          willNavigate: true
380        });
381      }
382      setTimeout(() => {
383        scrollToSlide(initialSlide, true);
384      }, 50);
385    } else if (initialSlide !== void 0) {
386      if (debug) {
387        console.warn("[initializeCarousel] Invalid initial slide index:", {
388          initialSlide,
389          totalSlides: slides.length,
390          validRange: `0-${slides.length - 1}`
391        });
392      }
393    }
394    if (debug) {
395      console.log("[initializeCarousel] Adding event listeners:", {
396        prevButton,
397        nextButton,
398        prevButtonId,
399        nextButtonId
400      });
401    }
402    prevButton.addEventListener("click", handlePrevClick);
403    nextButton.addEventListener("click", handleNextClick);
404    if (debug) {
405      console.log("[initializeCarousel] Event listeners attached successfully");
406    }
407    const scrollContainer = track.scrollWidth > track.clientWidth ? track : track.parentElement;
408    let scrollTimeout = null;
409    let isProgrammaticScroll = false;
410    let programmaticScrollTimeout = null;
411    const calculateCurrentSlideIndex = () => {
412      if (!scrollContainer || slides.length === 0) {
413        return currentIndex;
414      }
415      const scrollLeft = scrollContainer.scrollLeft;
416      const containerCenter = scrollLeft + scrollContainer.clientWidth / 2;
417      let closestIndex = 0;
418      let minDistance = Infinity;
419      slides.forEach((slide, index) => {
420        const slideLeft = slide.offsetLeft;
421        const slideWidth = slide.offsetWidth;
422        const slideCenter = slideLeft + slideWidth / 2;
423        const distance = Math.abs(containerCenter - slideCenter);
424        if (distance < minDistance) {
425          minDistance = distance;
426          closestIndex = index;
427        }
428      });
429      return closestIndex;
430    };
431    const handleScroll = () => {
432      if (!scrollContainer) return;
433      if (isProgrammaticScroll) {
434        if (debug) {
435          console.log("[initializeCarousel] Scroll event during programmatic scroll, skipping snap detection");
436        }
437        return;
438      }
439      const snappedIndex = calculateCurrentSlideIndex();
440      if (snappedIndex !== currentIndex) {
441        const previousIndex = currentIndex;
442        updateIndex(snappedIndex);
443        if (debug) {
444          console.log("[initializeCarousel] Slide index updated from scroll:", {
445            previousIndex,
446            newIndex: currentIndex,
447            scrollLeft: scrollContainer.scrollLeft,
448            timestamp: (/* @__PURE__ */ new Date()).toISOString()
449          });
450        }
451        updateButtonStates();
452      }
453      if (debug) {
454        console.log("[initializeCarousel] Scroll event fired:", {
455          currentIndex,
456          snappedIndex,
457          scrollLeft: scrollContainer.scrollLeft,
458          scrollWidth: scrollContainer.scrollWidth,
459          clientWidth: scrollContainer.clientWidth,
460          timestamp: (/* @__PURE__ */ new Date()).toISOString()
461        });
462      }
463      if (scrollTimeout) {
464        clearTimeout(scrollTimeout);
465      }
466      scrollTimeout = setTimeout(() => {
467        if (debug) {
468          console.log("[initializeCarousel] Scroll completed:", {
469            currentIndex,
470            timestamp: (/* @__PURE__ */ new Date()).toISOString()
471          });
472        }
473      }, 150);
474    };
475    if (scrollContainer) {
476      scrollContainer.addEventListener("scroll", handleScroll, { passive: true });
477      if (debug) {
478        console.log("[initializeCarousel] Scroll listener attached to:", scrollContainer);
479      }
480    }
481    return () => {
482      prevButton.removeEventListener("click", handlePrevClick);
483      nextButton.removeEventListener("click", handleNextClick);
484      if (scrollContainer) {
485        scrollContainer.removeEventListener("scroll", handleScroll);
486      }
487      if (scrollTimeout) {
488        clearTimeout(scrollTimeout);
489      }
490      if (programmaticScrollTimeout) {
491        clearTimeout(programmaticScrollTimeout);
492      }
493      paginationCleanupFunctions.forEach((cleanup) => cleanup());
494    };
495  }
496
497  
497// ../web-design-system/src/components/composition/slider/custom/webflow-initialize-carousel-entry.ts
498  if (typeof window !== "undefined") {
499    window.initializeCarousel = initializeCarousel;
500  }
501})();
502!function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="e6a8b68e-1d7f-55c6-aa69-88e2d1f5bdcf")}catch(e){}}();
503//# debugId=e6a8b68e-1d7f-55c6-aa69-88e2d1f5bdcf

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.