@surdeddd/bottom-sheet 0.9.1 → 0.11.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (50) hide show
  1. package/README.md +126 -83
  2. package/dist/{BottomSheetEngine-CBRcBwV-.d.ts → BottomSheetEngine-DRjCU73e.d.ts} +6 -5
  3. package/dist/{BottomSheetEngine-BcyruNP1.d.cts → BottomSheetEngine-DzsIwD28.d.cts} +6 -5
  4. package/dist/element.cjs +388 -222
  5. package/dist/element.d.cts +1 -1
  6. package/dist/element.d.ts +1 -1
  7. package/dist/element.iife.global.js +2 -2
  8. package/dist/element.js +388 -222
  9. package/dist/index.cjs +389 -266
  10. package/dist/index.d.cts +2 -2
  11. package/dist/index.d.ts +2 -2
  12. package/dist/index.js +389 -266
  13. package/dist/integrations/formik.d.cts +1 -1
  14. package/dist/integrations/formik.d.ts +1 -1
  15. package/dist/integrations/react-hook-form.d.cts +1 -1
  16. package/dist/integrations/react-hook-form.d.ts +1 -1
  17. package/dist/overlay.cjs +191 -58
  18. package/dist/overlay.d.cts +4 -3
  19. package/dist/overlay.d.ts +4 -3
  20. package/dist/overlay.js +191 -58
  21. package/dist/preact.d.cts +2 -1
  22. package/dist/preact.d.ts +2 -1
  23. package/dist/qwik.cjs +396 -211
  24. package/dist/qwik.d.cts +11 -2
  25. package/dist/qwik.d.ts +11 -2
  26. package/dist/qwik.js +396 -211
  27. package/dist/react.cjs +500 -332
  28. package/dist/react.d.cts +26 -4
  29. package/dist/react.d.ts +26 -4
  30. package/dist/react.js +500 -332
  31. package/dist/solid.cjs +362 -210
  32. package/dist/solid.d.cts +14 -4
  33. package/dist/solid.d.ts +14 -4
  34. package/dist/solid.js +362 -210
  35. package/dist/solid.source.jsx +362 -210
  36. package/dist/styles.css +17 -1
  37. package/dist/svelte-core.cjs +345 -208
  38. package/dist/svelte-core.js +345 -208
  39. package/dist/svelte-src/BottomSheet.svelte +6 -0
  40. package/dist/svelte.cjs +359 -220
  41. package/dist/svelte.d.cts +2 -0
  42. package/dist/svelte.d.ts +2 -0
  43. package/dist/svelte.js +359 -220
  44. package/dist/teleport-7uYNiEAT.d.cts +3 -0
  45. package/dist/teleport-7uYNiEAT.d.ts +3 -0
  46. package/dist/vue.cjs +353 -209
  47. package/dist/vue.d.cts +3 -1
  48. package/dist/vue.d.ts +3 -1
  49. package/dist/vue.js +353 -209
  50. package/package.json +11 -9
@@ -1,4 +1,4 @@
1
- import { e as SheetEventMap } from '../BottomSheetEngine-BcyruNP1.cjs';
1
+ import { d as SheetEventMap } from '../BottomSheetEngine-DzsIwD28.cjs';
2
2
  import '../transform-jVfAikE9.cjs';
3
3
 
4
4
  type FormikStateLike = {
@@ -1,4 +1,4 @@
1
- import { e as SheetEventMap } from '../BottomSheetEngine-CBRcBwV-.js';
1
+ import { d as SheetEventMap } from '../BottomSheetEngine-DRjCU73e.js';
2
2
  import '../transform-jVfAikE9.js';
3
3
 
4
4
  type FormikStateLike = {
@@ -1,4 +1,4 @@
1
- import { e as SheetEventMap } from '../BottomSheetEngine-BcyruNP1.cjs';
1
+ import { d as SheetEventMap } from '../BottomSheetEngine-DzsIwD28.cjs';
2
2
  import '../transform-jVfAikE9.cjs';
3
3
 
4
4
  type RhfFormStateLike = {
@@ -1,4 +1,4 @@
1
- import { e as SheetEventMap } from '../BottomSheetEngine-CBRcBwV-.js';
1
+ import { d as SheetEventMap } from '../BottomSheetEngine-DRjCU73e.js';
2
2
  import '../transform-jVfAikE9.js';
3
3
 
4
4
  type RhfFormStateLike = {
package/dist/overlay.cjs CHANGED
@@ -120,6 +120,13 @@ var resolveSnap = (point, mode, measureFit) => {
120
120
  }
121
121
  };
122
122
 
123
+ // src/core/primitives/devWarn.ts
124
+ function devWarn(...args) {
125
+ if (typeof process !== "undefined" && process.env && process.env.NODE_ENV !== "production" && typeof console !== "undefined") {
126
+ console.warn(...args);
127
+ }
128
+ }
129
+
123
130
  // src/core/primitives/instance-id.ts
124
131
  var counters = {};
125
132
  function nextInstanceId(prefix) {
@@ -522,7 +529,147 @@ function installOverlaySwipe(deps) {
522
529
  };
523
530
  }
524
531
 
525
- // src/core/overlay.ts
532
+ // src/core/features/history-coordinator.ts
533
+ var entries = [];
534
+ var subscribers = /* @__PURE__ */ new Set();
535
+ var suppress = 0;
536
+ var pendingRebrand = null;
537
+ var listenerInstalled = false;
538
+ var hasWindow = () => typeof window !== "undefined";
539
+ var hasHistory = () => typeof history !== "undefined";
540
+ var runInternal = (fn) => {
541
+ try {
542
+ fn();
543
+ } finally {
544
+ }
545
+ };
546
+ var notifyRouteChange = () => {
547
+ const snapshot = Array.from(subscribers);
548
+ for (const fn of snapshot) fn();
549
+ };
550
+ var ensureListener = () => {
551
+ if (listenerInstalled || !hasWindow()) return;
552
+ window.addEventListener("popstate", onPopState);
553
+ listenerInstalled = true;
554
+ };
555
+ var maybeTeardownListener = () => {
556
+ if (!listenerInstalled) return;
557
+ if (entries.length > 0 || subscribers.size > 0 || suppress > 0) return;
558
+ if (hasWindow()) window.removeEventListener("popstate", onPopState);
559
+ listenerInstalled = false;
560
+ };
561
+ function onPopState() {
562
+ if (suppress > 0) {
563
+ suppress -= 1;
564
+ const rebrand = pendingRebrand;
565
+ pendingRebrand = null;
566
+ if (rebrand) rebrand();
567
+ maybeTeardownListener();
568
+ return;
569
+ }
570
+ if (entries.length === 0) {
571
+ notifyRouteChange();
572
+ maybeTeardownListener();
573
+ return;
574
+ }
575
+ let target = null;
576
+ let targetIdx = -1;
577
+ for (let i = entries.length - 1; i >= 0; i -= 1) {
578
+ const entry = entries[i];
579
+ if (!entry.surface.isOpen()) continue;
580
+ if (!target) {
581
+ target = entry;
582
+ targetIdx = i;
583
+ }
584
+ if (entry.surface.isTop()) {
585
+ target = entry;
586
+ targetIdx = i;
587
+ break;
588
+ }
589
+ }
590
+ if (!target) {
591
+ const removed = entries.pop();
592
+ if (removed) removed.live = false;
593
+ maybeTeardownListener();
594
+ return;
595
+ }
596
+ target.live = false;
597
+ entries.splice(targetIdx, 1);
598
+ const settled = target;
599
+ void Promise.resolve(settled.surface.close()).then(() => {
600
+ if (settled.surface.isOpen()) restore(settled);
601
+ });
602
+ maybeTeardownListener();
603
+ }
604
+ function restore(entry) {
605
+ if (!hasWindow() || !hasHistory()) return;
606
+ entry.live = true;
607
+ runInternal(() => {
608
+ try {
609
+ history.pushState(entry.surface.markerState(), "", entry.surface.url);
610
+ } catch {
611
+ entry.live = false;
612
+ }
613
+ });
614
+ if (entry.live) {
615
+ entries.push(entry);
616
+ ensureListener();
617
+ }
618
+ }
619
+ function pushBackMarker(surface) {
620
+ const entry = { surface, priorUrl: void 0, live: false };
621
+ if (!hasWindow() || !hasHistory()) {
622
+ return entry;
623
+ }
624
+ entry.priorUrl = surface.url !== void 0 ? location.href : void 0;
625
+ runInternal(() => {
626
+ try {
627
+ history.pushState(surface.markerState(), "", surface.url);
628
+ entry.live = true;
629
+ } catch {
630
+ entry.live = false;
631
+ }
632
+ });
633
+ if (entry.live) {
634
+ entries.push(entry);
635
+ ensureListener();
636
+ }
637
+ return entry;
638
+ }
639
+ function popBackMarker(handle) {
640
+ if (!hasWindow() || !hasHistory()) return;
641
+ const entry = handle;
642
+ const idx = entries.indexOf(entry);
643
+ if (idx === -1 || !entry.live) return;
644
+ const last = entries.length - 1;
645
+ entry.live = false;
646
+ entries.splice(idx, 1);
647
+ if (idx !== last) {
648
+ const rebrandSurface = entries[entries.length - 1].surface;
649
+ const rebrandUrl = entry.priorUrl;
650
+ pendingRebrand = () => {
651
+ runInternal(() => {
652
+ history.replaceState(
653
+ rebrandSurface.markerState(),
654
+ "",
655
+ rebrandUrl !== void 0 ? rebrandUrl : location.href
656
+ );
657
+ });
658
+ };
659
+ }
660
+ suppress += 1;
661
+ runInternal(() => {
662
+ try {
663
+ history.back();
664
+ } catch {
665
+ suppress = Math.max(0, suppress - 1);
666
+ pendingRebrand = null;
667
+ }
668
+ });
669
+ maybeTeardownListener();
670
+ }
671
+
672
+ // src/core/overlay-options.ts
526
673
  var OVERLAY_PRESETS = Object.freeze({
527
674
  sheet: Object.freeze({
528
675
  enterAnimation: "slide",
@@ -553,6 +700,8 @@ var OVERLAY_PRESETS = Object.freeze({
553
700
  swipeToClose: false
554
701
  })
555
702
  });
703
+
704
+ // src/core/overlay.ts
556
705
  var OverlayEngine = class {
557
706
  constructor(opts) {
558
707
  __publicField(this, "id", nextInstanceId("ovl"));
@@ -587,7 +736,7 @@ var OverlayEngine = class {
587
736
  __publicField(this, "detachSwipe", null);
588
737
  __publicField(this, "respectReducedMotionEnabled");
589
738
  __publicField(this, "isTop", true);
590
- __publicField(this, "backPushed", false);
739
+ __publicField(this, "backMarker", null);
591
740
  __publicField(this, "movedToTarget", false);
592
741
  __publicField(this, "onOpenCb");
593
742
  __publicField(this, "onCloseCb");
@@ -599,7 +748,6 @@ var OverlayEngine = class {
599
748
  __publicField(this, "bus", createEventBus());
600
749
  __publicField(this, "detachEscape", null);
601
750
  __publicField(this, "detachBackdrop", null);
602
- __publicField(this, "detachHardwareBack", null);
603
751
  __publicField(this, "releaseStackEntry", null);
604
752
  __publicField(this, "lifecycle");
605
753
  this.element = opts.element;
@@ -629,7 +777,7 @@ var OverlayEngine = class {
629
777
  this.onOpenCb = opts.onOpen;
630
778
  this.onCloseCb = opts.onClose;
631
779
  if (this.peekRaw !== void 0 && this.edge !== "bottom") {
632
- console.warn(
780
+ devWarn(
633
781
  "[OverlayEngine] `peek` is only supported on edge: 'bottom' \u2014 ignoring."
634
782
  );
635
783
  this.peekRaw = void 0;
@@ -696,10 +844,9 @@ var OverlayEngine = class {
696
844
  this.element.style.opacity = "1";
697
845
  if (this.backdrop) {
698
846
  this.backdrop.style.opacity = String(this.backdropOpacity);
699
- this.backdrop.style.pointerEvents = this.backdropOpacity > 0 ? "auto" : "none";
847
+ this.syncBackdropPointerEvents();
700
848
  if (this.backdropFilter) {
701
- this.backdrop.style.backdropFilter = this.backdropFilter;
702
- this.backdrop.style.webkitBackdropFilter = this.backdropFilter;
849
+ this.applyBackdropFilter(this.backdropFilter);
703
850
  }
704
851
  }
705
852
  try {
@@ -719,8 +866,7 @@ var OverlayEngine = class {
719
866
  this.backdrop.style.opacity = "0";
720
867
  this.backdrop.style.pointerEvents = "none";
721
868
  if (this.backdropFilter) {
722
- this.backdrop.style.backdropFilter = "";
723
- this.backdrop.style.webkitBackdropFilter = "";
869
+ this.applyBackdropFilter(void 0);
724
870
  }
725
871
  }
726
872
  this.element.setAttribute("data-state", "closed");
@@ -755,7 +901,10 @@ var OverlayEngine = class {
755
901
  this.isOpen_ = false;
756
902
  this.isAnimating_ = true;
757
903
  sheetStack.update();
758
- this.popBackMarker(reason);
904
+ if (reason !== "back" && this.backMarker) {
905
+ popBackMarker(this.backMarker);
906
+ }
907
+ this.backMarker = null;
759
908
  this.element.setAttribute("data-state", "exiting");
760
909
  const dur = this.effectiveDuration();
761
910
  const transitionStr = `transform ${dur}ms ${this.exitEasing}, opacity ${dur}ms ease-in`;
@@ -778,8 +927,7 @@ var OverlayEngine = class {
778
927
  this.backdrop.style.opacity = "0";
779
928
  this.backdrop.style.pointerEvents = "none";
780
929
  if (this.backdropFilter) {
781
- this.backdrop.style.backdropFilter = "";
782
- this.backdrop.style.webkitBackdropFilter = "";
930
+ this.applyBackdropFilter(void 0);
783
931
  }
784
932
  }
785
933
  this.releaseInteractiveListeners();
@@ -814,6 +962,10 @@ var OverlayEngine = class {
814
962
  this.bus.clear();
815
963
  this.setWillChange(false);
816
964
  this.releaseInteractiveListeners();
965
+ if (this.backMarker) {
966
+ popBackMarker(this.backMarker);
967
+ this.backMarker = null;
968
+ }
817
969
  this.releaseStackEntry?.();
818
970
  this.releaseStackEntry = null;
819
971
  const hadOriginalParent = this.originalParent !== null;
@@ -827,20 +979,14 @@ var OverlayEngine = class {
827
979
  this.backdropOpacity = opacity;
828
980
  if (this.isOpen_ && this.backdrop) {
829
981
  this.backdrop.style.opacity = String(opacity);
982
+ this.syncBackdropPointerEvents();
830
983
  }
831
984
  }
832
985
  setBackdropFilter(filter) {
833
986
  if (this.destroyed) return;
834
987
  this.backdropFilter = filter;
835
988
  if (!this.isOpen_ || !this.backdrop) return;
836
- const style = this.backdrop.style;
837
- if (filter) {
838
- this.backdrop.style.backdropFilter = filter;
839
- style.webkitBackdropFilter = filter;
840
- } else {
841
- this.backdrop.style.backdropFilter = "";
842
- style.webkitBackdropFilter = "";
843
- }
989
+ this.applyBackdropFilter(filter);
844
990
  }
845
991
  setSwipeToClose(config) {
846
992
  if (this.destroyed) return;
@@ -909,16 +1055,10 @@ var OverlayEngine = class {
909
1055
  if (this.isOpen_ && this.backdrop) {
910
1056
  if (merged.backdropOpacity !== void 0) {
911
1057
  this.backdrop.style.opacity = String(this.backdropOpacity);
1058
+ this.syncBackdropPointerEvents();
912
1059
  }
913
1060
  if (merged.backdropFilter !== void 0) {
914
- const style = this.backdrop.style;
915
- if (this.backdropFilter) {
916
- this.backdrop.style.backdropFilter = this.backdropFilter;
917
- style.webkitBackdropFilter = this.backdropFilter;
918
- } else {
919
- this.backdrop.style.backdropFilter = "";
920
- style.webkitBackdropFilter = "";
921
- }
1061
+ this.applyBackdropFilter(this.backdropFilter);
922
1062
  }
923
1063
  }
924
1064
  if (opts.duration !== void 0) this.duration = opts.duration;
@@ -987,19 +1127,6 @@ var OverlayEngine = class {
987
1127
  effectiveDuration() {
988
1128
  return this.respectReducedMotionEnabled && prefersReducedMotion() ? 0 : this.duration;
989
1129
  }
990
- popBackMarker(reason) {
991
- if (!this.backPushed) return;
992
- this.backPushed = false;
993
- if (reason === "back") return;
994
- const state = history.state;
995
- if (state && state.__bsOverlay === this.id) {
996
- try {
997
- history.back();
998
- } catch {
999
- return;
1000
- }
1001
- }
1002
- }
1003
1130
  resolvePeekPx(raw) {
1004
1131
  if (typeof raw === "number") return Math.max(0, raw);
1005
1132
  try {
@@ -1053,6 +1180,21 @@ var OverlayEngine = class {
1053
1180
  this.backdrop.style.pointerEvents = "none";
1054
1181
  }
1055
1182
  }
1183
+ syncBackdropPointerEvents() {
1184
+ if (!this.backdrop) return;
1185
+ this.backdrop.style.pointerEvents = this.backdropOpacity > 0 ? "auto" : "none";
1186
+ }
1187
+ applyBackdropFilter(filter) {
1188
+ if (!this.backdrop) return;
1189
+ const style = this.backdrop.style;
1190
+ if (filter) {
1191
+ this.backdrop.style.backdropFilter = filter;
1192
+ style.webkitBackdropFilter = filter;
1193
+ } else {
1194
+ this.backdrop.style.backdropFilter = "";
1195
+ style.webkitBackdropFilter = "";
1196
+ }
1197
+ }
1056
1198
  setWillChange(on) {
1057
1199
  this.element.style.willChange = on ? "transform, opacity" : "";
1058
1200
  if (this.backdrop) {
@@ -1100,21 +1242,6 @@ var OverlayEngine = class {
1100
1242
  this.backdrop.addEventListener("click", handler);
1101
1243
  this.detachBackdrop = () => this.backdrop?.removeEventListener("click", handler);
1102
1244
  }
1103
- if (this.closeOnBackEnabled && typeof window !== "undefined" && !this.detachHardwareBack) {
1104
- try {
1105
- history.pushState({ __bsOverlay: this.id }, "");
1106
- this.backPushed = true;
1107
- } catch {
1108
- }
1109
- const onPop = () => {
1110
- if (this.isOpen_ && this.isTop) {
1111
- this.backPushed = false;
1112
- void this.close("back");
1113
- }
1114
- };
1115
- window.addEventListener("popstate", onPop);
1116
- this.detachHardwareBack = () => window.removeEventListener("popstate", onPop);
1117
- }
1118
1245
  if (this.closeOnOutsidePointerEnabled && !this.detachOutsidePointer) {
1119
1246
  const handler = (e) => {
1120
1247
  if (!this.isOpen_) return;
@@ -1127,14 +1254,20 @@ var OverlayEngine = class {
1127
1254
  document.addEventListener("pointerdown", handler, true);
1128
1255
  this.detachOutsidePointer = () => document.removeEventListener("pointerdown", handler, true);
1129
1256
  }
1257
+ if (this.closeOnBackEnabled && this.backMarker === null && typeof window !== "undefined") {
1258
+ this.backMarker = pushBackMarker({
1259
+ isOpen: () => this.isOpen_,
1260
+ isTop: () => this.isTop,
1261
+ close: () => this.close("back"),
1262
+ markerState: () => ({ __bsOverlay: this.id })
1263
+ });
1264
+ }
1130
1265
  }
1131
1266
  releaseInteractiveListeners() {
1132
1267
  this.detachEscape?.();
1133
1268
  this.detachEscape = null;
1134
1269
  this.detachBackdrop?.();
1135
1270
  this.detachBackdrop = null;
1136
- this.detachHardwareBack?.();
1137
- this.detachHardwareBack = null;
1138
1271
  this.detachSwipe?.();
1139
1272
  this.detachSwipe = null;
1140
1273
  this.detachOutsidePointer?.();
@@ -75,6 +75,7 @@ type OverlayEventMap = {
75
75
  "before-open": void;
76
76
  "before-close": void;
77
77
  };
78
+
78
79
  type Listener<K extends keyof OverlayEventMap> = (payload: OverlayEventMap[K]) => void;
79
80
  declare class OverlayEngine {
80
81
  private id;
@@ -109,7 +110,7 @@ declare class OverlayEngine {
109
110
  private detachSwipe;
110
111
  private respectReducedMotionEnabled;
111
112
  private isTop;
112
- private backPushed;
113
+ private backMarker;
113
114
  private movedToTarget;
114
115
  private onOpenCb?;
115
116
  private onCloseCb?;
@@ -121,7 +122,6 @@ declare class OverlayEngine {
121
122
  private bus;
122
123
  private detachEscape;
123
124
  private detachBackdrop;
124
- private detachHardwareBack;
125
125
  private releaseStackEntry;
126
126
  private lifecycle;
127
127
  constructor(opts: OverlayOptions);
@@ -143,11 +143,12 @@ declare class OverlayEngine {
143
143
  private assignSwipeFromConfig;
144
144
  private emit;
145
145
  private effectiveDuration;
146
- private popBackMarker;
147
146
  private resolvePeekPx;
148
147
  private maybeMount;
149
148
  private restoreMount;
150
149
  private applyClosedStyles;
150
+ private syncBackdropPointerEvents;
151
+ private applyBackdropFilter;
151
152
  private setWillChange;
152
153
  private awaitTransition;
153
154
  private installInteractiveListeners;
package/dist/overlay.d.ts CHANGED
@@ -75,6 +75,7 @@ type OverlayEventMap = {
75
75
  "before-open": void;
76
76
  "before-close": void;
77
77
  };
78
+
78
79
  type Listener<K extends keyof OverlayEventMap> = (payload: OverlayEventMap[K]) => void;
79
80
  declare class OverlayEngine {
80
81
  private id;
@@ -109,7 +110,7 @@ declare class OverlayEngine {
109
110
  private detachSwipe;
110
111
  private respectReducedMotionEnabled;
111
112
  private isTop;
112
- private backPushed;
113
+ private backMarker;
113
114
  private movedToTarget;
114
115
  private onOpenCb?;
115
116
  private onCloseCb?;
@@ -121,7 +122,6 @@ declare class OverlayEngine {
121
122
  private bus;
122
123
  private detachEscape;
123
124
  private detachBackdrop;
124
- private detachHardwareBack;
125
125
  private releaseStackEntry;
126
126
  private lifecycle;
127
127
  constructor(opts: OverlayOptions);
@@ -143,11 +143,12 @@ declare class OverlayEngine {
143
143
  private assignSwipeFromConfig;
144
144
  private emit;
145
145
  private effectiveDuration;
146
- private popBackMarker;
147
146
  private resolvePeekPx;
148
147
  private maybeMount;
149
148
  private restoreMount;
150
149
  private applyClosedStyles;
150
+ private syncBackdropPointerEvents;
151
+ private applyBackdropFilter;
151
152
  private setWillChange;
152
153
  private awaitTransition;
153
154
  private installInteractiveListeners;