]> git.openstreetmap.org Git - rails.git/blob - app/assets/javascripts/numbered_pagination.js
Merge remote-tracking branch 'upstream/pull/6313'
[rails.git] / app / assets / javascripts / numbered_pagination.js
1 (function () {
2   let shadowEffect;
3
4   class ShadowEffect {
5     constructor() {
6       const $scrollableList = $("#versions-navigation-list-middle");
7       const [scrollableFirstItem] = $scrollableList.children().first();
8       const [scrollableLastItem] = $scrollableList.children().last();
9
10       if (scrollableFirstItem) {
11         this.scrollStartObserver = createScrollObserver("#versions-navigation-list-start", "2px 0px");
12         this.scrollStartObserver.observe(scrollableFirstItem);
13       }
14
15       if (scrollableLastItem) {
16         this.scrollEndObserver = createScrollObserver("#versions-navigation-list-end", "-2px 0px");
17         this.scrollEndObserver.observe(scrollableLastItem);
18       }
19
20       function createScrollObserver(shadowTarget, shadowOffset) {
21         const threshold = 0.95;
22         return new IntersectionObserver(([entry]) => {
23           const floating = entry.intersectionRatio < threshold;
24           $(shadowTarget)
25             .css("box-shadow", floating ? `rgba(0, 0, 0, 0.075) ${shadowOffset} 2px` : "")
26             .css("z-index", floating ? "5" : ""); // floating z-index should be larger than z-index of Bootstrap's .page-link:focus, which is 3
27         }, { threshold });
28       }
29     }
30
31     disable() {
32       this.scrollStartObserver?.disconnect();
33       this.scrollEndObserver?.disconnect();
34     }
35   }
36
37   $(document).on("click", "a[href='#versions-navigation-active-page-item']", function (e) {
38     $(document).trigger("numbered_pagination:center");
39     $("#versions-navigation-active-page-item a.page-link").trigger("focus");
40     e.preventDefault();
41   });
42
43   $(document).on("numbered_pagination:enable", function () {
44     shadowEffect = new ShadowEffect();
45     $(document).trigger("numbered_pagination:center");
46   });
47
48   $(document).on("numbered_pagination:disable", function () {
49     shadowEffect?.disable();
50     shadowEffect = null;
51   });
52
53   $(document).on("numbered_pagination:center", function () {
54     const [scrollableList] = $("#versions-navigation-list-middle");
55
56     if (!scrollableList) return;
57
58     const [activeStartItem] = $("#versions-navigation-list-start #versions-navigation-active-page-item");
59     const [activeScrollableItem] = $("#versions-navigation-list-middle #versions-navigation-active-page-item");
60
61     if (activeStartItem) {
62       scrollableList.scrollLeft = 0;
63     } else if (activeScrollableItem) {
64       scrollableList.scrollLeft = Math.round(activeScrollableItem.offsetLeft - (scrollableList.offsetWidth / 2) + (activeScrollableItem.offsetWidth / 2));
65     } else {
66       scrollableList.scrollLeft = scrollableList.scrollWidth - scrollableList.offsetWidth;
67     }
68   });
69 }());