PageSourceSearch

https://www.apozy.com/styles/airlock-base/main/assets/js/components/_2_image-comparison-slider.js

js apozy.com collected 2026-10-05 06:42:01 UTC 5,799 bytes, 142 lines download raw bytes

1// File#: _2_image-comparison-slider
2// Usage: codyhouse.co/license
3(function() {
4  var ComparisonSlider = function(element) {
5    this.element = element;
6    this.modifiedImg = this.element.getElementsByClassName('js-compare-slider__img--modified')[0];
7    this.handle = this.element.getElementsByClassName('js-compare-slider__handle')[0];
8    this.keyboardHandle = this.element.getElementsByClassName('js-compare-slider__input-handle')[0];
9    this.captions = this.element.getElementsByClassName('js-compare-slider__caption');
10    // drag
11    this.dragStart = false;
12    this.animating = false;
13    this.leftPosition = 50;
14    // store container width
15    this.sliderWidth = getSliderWidth(this);
16    initComparisonSlider(this);
17  };
18
19  function getSliderWidth(slider) {
20    return slider.element.offsetWidth;
21  };
22
23  function initComparisonSlider(slider) {
24    // initial animation
25    if(reducedMotion) { // do not animate slider elements
26      Util.addClass(slider.element, 'compare-slider--reduced-motion compare-slider--in-viewport');
27    } else if(intersectionObserverSupported) { // reveal slider elements when it enters the viewport
28      var observer = new IntersectionObserver(sliderObserve.bind(slider), { threshold: [0, 0.3] });
29      observer.observe(slider.element);
30    } else { // reveal slider elements right away
31      Util.addClass(slider.element, 'compare-slider--in-viewport');
32    }
33    // init drag functionality
34    new SwipeContent(slider.element);
35    slider.element.addEventListener('dragStart', function(event){
36      if(!event.detail.origin.closest('.js-compare-slider__handle')) return;
37      Util.addClass(slider.element, 'compare-slider--is-dragging');
38      if(!slider.dragStart) {
39        slider.dragStart = event.detail.x;
40        detectDragEnd(slider);
41      }
42    });
43    // slider.element.addEventListener('dragging', function(event){
44    slider.element.addEventListener('mousemove', function(event){
45      sliderDragging(slider, event)
46    });
47    slider.element.addEventListener('touchmove', function(event){
48      sliderDragging(slider, event)
49    });
50
51    // detect mouse leave
52    slider.element.addEventListener('mouseleave', function(event){
53      sliderResetDragging(slider, event);
54    });
55    slider.element.addEventListener('touchend', function(event){
56      sliderResetDragging(slider, event);
57    });
58
59    // on resize -> update slider width
60    window.addEventListener('resize', function(){
61      slider.sliderWidth = getSliderWidth(slider);
62    });
63
64    // detect change in keyboardHandle input -> allow keyboard navigation
65    slider.keyboardHandle.addEventListener('change', function(event){
66      slider.leftPosition = Number(slider.keyboardHandle.value);
67      updateCompareSlider(slider, 0);
68    });
69  };
70
71  function sliderDragging(slider, event) {
72    if(!slider.dragStart) return;
73    var pageX = event.pageX || event.touches[0].pageX;
74    if(slider.animating || Math.abs(pageX - slider.dragStart) < 5) return;
75    slider.animating = true;
76    updateCompareSlider(slider, pageX - slider.dragStart);
77    slider.dragStart = pageX;
78  };
79
80  function sliderResetDragging(slider, event) {
81    if(!slider.dragStart) return;
82    if(event.pageX < slider.element.offsetLeft) {
83      slider.leftPosition = 0;
84      updateCompareSlider(slider, 0);
85    }
86    if(event.pageX > slider.element.offsetLeft + slider.element.offsetWidth) {
87      slider.leftPosition = 100;
88      updateCompareSlider(slider, 0);
89    }
90  };
91
92  function sliderObserve(entries, observer) {
93    if(entries[0].intersectionRatio.toFixed(1) > 0) { // reveal slider elements when in viewport
94      Util.addClass(this.element, 'compare-slider--in-viewport');
95      observer.unobserve(this.element);
96    }
97  };
98
99  function detectDragEnd(slider) {
100    document.addEventListener('click', function cb(event){
101      document.removeEventListener('click', cb);
102      Util.removeClass(slider.element, 'compare-slider--is-dragging');
103      updateCompareSlider(slider, event.detail.x - slider.dragStart);
104      slider.dragStart = false;
105    });
106  };
107
108  function updateCompareSlider(slider, delta) {
109    var percentage = (delta*100/slider.sliderWidth);
110    if(isNaN(percentage)) return;
111    slider.leftPosition = Number((slider.leftPosition + percentage).toFixed(2));
112    if(slider.leftPosition < 0) slider.leftPosition = 0;
113    if(slider.leftPosition > 100) slider.leftPosition = 100; 
114    // update slider elements -> modified img width + handle position + input element (keyboard accessibility)
115    slider.keyboardHandle.value = slider.leftPosition;
116    slider.handle.style.left = slider.leftPosition + '%';
117    slider.modifiedImg.style.width = slider.leftPosition + '%'; 
118    updateCompareLabels(slider);
119    slider.animating = false;
120  };
121
122  function updateCompareLabels(slider) { // update captions visibility
123    for(var i = 0; i < slider.captions.length; i++) {
124      var delta = ( i == 0 ) 
125        ? slider.captions[i].offsetLeft - slider.modifiedImg.offsetLeft - slider.modifiedImg.offsetWidth
126        : slider.modifiedImg.offsetLeft + slider.modifiedImg.offsetWidth - slider.captions[i].offsetLeft - slider.captions[i].offsetWidth;
127      Util.toggleClass(slider.captions[i], 'compare-slider__caption--is-hidden', delta < 10);
128    }
129  };
130  
131  //initialize the ComparisonSlider objects
132  var comparisonSliders = document.getElementsByClassName('js-compare-slider'),
133    intersectionObserverSupported = ('IntersectionObserver' in window && 'IntersectionObserverEntry' in window && 'intersectionRatio' in window.IntersectionObserverEntry.prototype),
134    reducedMotion = Util.osHasReducedMotion();
135	if( comparisonSliders.length > 0 ) {
136		for( var i = 0; i < comparisonSliders.length; i++) {
137			(function(i){
138        new ComparisonSlider(comparisonSliders[i]);
139      })(i);
140    }
141	}
142}());

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.