@zag-js/popover 0.1.8 → 0.1.11
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.
- package/LICENSE +21 -0
- package/dist/index.d.ts +103 -3
- package/dist/index.js +259 -346
- package/dist/index.mjs +255 -351
- package/package.json +19 -15
- package/dist/popover.connect.d.ts +0 -17
- package/dist/popover.dom.d.ts +0 -27
- package/dist/popover.machine.d.ts +0 -2
- package/dist/popover.types.d.ts +0 -100
package/dist/index.mjs
CHANGED
|
@@ -1,35 +1,116 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
var __defProp = Object.defineProperty;
|
|
3
|
-
var __defProps = Object.defineProperties;
|
|
4
|
-
var __getOwnPropDescs = Object.getOwnPropertyDescriptors;
|
|
5
|
-
var __getOwnPropSymbols = Object.getOwnPropertySymbols;
|
|
6
|
-
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
7
|
-
var __propIsEnum = Object.prototype.propertyIsEnumerable;
|
|
8
|
-
var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
|
|
9
|
-
var __spreadValues = (a, b) => {
|
|
10
|
-
for (var prop in b || (b = {}))
|
|
11
|
-
if (__hasOwnProp.call(b, prop))
|
|
12
|
-
__defNormalProp(a, prop, b[prop]);
|
|
13
|
-
if (__getOwnPropSymbols)
|
|
14
|
-
for (var prop of __getOwnPropSymbols(b)) {
|
|
15
|
-
if (__propIsEnum.call(b, prop))
|
|
16
|
-
__defNormalProp(a, prop, b[prop]);
|
|
17
|
-
}
|
|
18
|
-
return a;
|
|
19
|
-
};
|
|
20
|
-
var __spreadProps = (a, b) => __defProps(a, __getOwnPropDescs(b));
|
|
21
|
-
|
|
22
1
|
// ../../utilities/dom/dist/index.mjs
|
|
23
2
|
var dataAttr = (guard) => {
|
|
24
3
|
return guard ? "" : void 0;
|
|
25
4
|
};
|
|
26
|
-
var hasProp = (obj, prop) => Object.prototype.hasOwnProperty.call(obj, prop);
|
|
27
|
-
var isLeftClick = (v) => v.button === 0;
|
|
28
5
|
var runIfFn = (v, ...a) => {
|
|
29
6
|
const res = typeof v === "function" ? v(...a) : v;
|
|
30
|
-
return res
|
|
7
|
+
return res ?? void 0;
|
|
31
8
|
};
|
|
32
|
-
var
|
|
9
|
+
var hasProp = (obj, prop) => Object.prototype.hasOwnProperty.call(obj, prop);
|
|
10
|
+
function isDocument(el) {
|
|
11
|
+
return el.nodeType === Node.DOCUMENT_NODE;
|
|
12
|
+
}
|
|
13
|
+
function isWindow(value) {
|
|
14
|
+
return (value == null ? void 0 : value.toString()) === "[object Window]";
|
|
15
|
+
}
|
|
16
|
+
function isFrame(element) {
|
|
17
|
+
return element.localName === "iframe";
|
|
18
|
+
}
|
|
19
|
+
function getDocument(el) {
|
|
20
|
+
if (isWindow(el))
|
|
21
|
+
return el.document;
|
|
22
|
+
if (isDocument(el))
|
|
23
|
+
return el;
|
|
24
|
+
return (el == null ? void 0 : el.ownerDocument) ?? document;
|
|
25
|
+
}
|
|
26
|
+
function defineDomHelpers(helpers) {
|
|
27
|
+
const dom2 = {
|
|
28
|
+
getRootNode: (ctx) => {
|
|
29
|
+
var _a;
|
|
30
|
+
return ((_a = ctx.getRootNode) == null ? void 0 : _a.call(ctx)) ?? document;
|
|
31
|
+
},
|
|
32
|
+
getDoc: (ctx) => getDocument(dom2.getRootNode(ctx)),
|
|
33
|
+
getWin: (ctx) => dom2.getDoc(ctx).defaultView ?? window,
|
|
34
|
+
getActiveElement: (ctx) => dom2.getDoc(ctx).activeElement,
|
|
35
|
+
getById: (ctx, id) => dom2.getRootNode(ctx).getElementById(id)
|
|
36
|
+
};
|
|
37
|
+
return {
|
|
38
|
+
...dom2,
|
|
39
|
+
...helpers
|
|
40
|
+
};
|
|
41
|
+
}
|
|
42
|
+
function contains(parent, child) {
|
|
43
|
+
if (!parent)
|
|
44
|
+
return false;
|
|
45
|
+
return parent === child || isHTMLElement(parent) && isHTMLElement(child) && parent.contains(child);
|
|
46
|
+
}
|
|
47
|
+
function isHTMLElement(v) {
|
|
48
|
+
return typeof v === "object" && (v == null ? void 0 : v.nodeType) === Node.ELEMENT_NODE && typeof (v == null ? void 0 : v.nodeName) === "string";
|
|
49
|
+
}
|
|
50
|
+
function isVisible(el) {
|
|
51
|
+
if (!isHTMLElement(el))
|
|
52
|
+
return false;
|
|
53
|
+
return el.offsetWidth > 0 || el.offsetHeight > 0 || el.getClientRects().length > 0;
|
|
54
|
+
}
|
|
55
|
+
var isModifiedEvent = (v) => v.ctrlKey || v.altKey || v.metaKey;
|
|
56
|
+
function hasNegativeTabIndex(element) {
|
|
57
|
+
const tabIndex = parseInt(element.getAttribute("tabindex") || "0", 10);
|
|
58
|
+
return tabIndex < 0;
|
|
59
|
+
}
|
|
60
|
+
var focusableSelector = "input:not([type='hidden']):not([disabled]), select:not([disabled]), textarea:not([disabled]), a[href], button:not([disabled]), [tabindex], iframe, object, embed, area[href], audio[controls], video[controls], [contenteditable]:not([contenteditable='false']), details > summary:first-of-type";
|
|
61
|
+
var getFocusables = (container, includeContainer = false) => {
|
|
62
|
+
if (!container)
|
|
63
|
+
return [];
|
|
64
|
+
const elements = Array.from(container.querySelectorAll(focusableSelector));
|
|
65
|
+
const include = includeContainer == true || includeContainer == "if-empty" && elements.length === 0;
|
|
66
|
+
if (include && isHTMLElement(container) && isFocusable(container)) {
|
|
67
|
+
elements.unshift(container);
|
|
68
|
+
}
|
|
69
|
+
const focusableElements = elements.filter(isFocusable);
|
|
70
|
+
focusableElements.forEach((element, i) => {
|
|
71
|
+
if (isFrame(element) && element.contentDocument) {
|
|
72
|
+
const frameBody = element.contentDocument.body;
|
|
73
|
+
focusableElements.splice(i, 1, ...getFocusables(frameBody));
|
|
74
|
+
}
|
|
75
|
+
});
|
|
76
|
+
return focusableElements;
|
|
77
|
+
};
|
|
78
|
+
function isFocusable(element) {
|
|
79
|
+
if (!element)
|
|
80
|
+
return false;
|
|
81
|
+
return element.matches(focusableSelector) && isVisible(element);
|
|
82
|
+
}
|
|
83
|
+
function getTabbables(container, includeContainer) {
|
|
84
|
+
if (!container)
|
|
85
|
+
return [];
|
|
86
|
+
const elements = Array.from(container.querySelectorAll(focusableSelector));
|
|
87
|
+
const tabbableElements = elements.filter(isTabbable);
|
|
88
|
+
if (includeContainer && isTabbable(container)) {
|
|
89
|
+
tabbableElements.unshift(container);
|
|
90
|
+
}
|
|
91
|
+
tabbableElements.forEach((element, i) => {
|
|
92
|
+
if (isFrame(element) && element.contentDocument) {
|
|
93
|
+
const frameBody = element.contentDocument.body;
|
|
94
|
+
const allFrameTabbable = getTabbables(frameBody);
|
|
95
|
+
tabbableElements.splice(i, 1, ...allFrameTabbable);
|
|
96
|
+
}
|
|
97
|
+
});
|
|
98
|
+
if (!tabbableElements.length && includeContainer) {
|
|
99
|
+
return elements;
|
|
100
|
+
}
|
|
101
|
+
return tabbableElements;
|
|
102
|
+
}
|
|
103
|
+
function isTabbable(el) {
|
|
104
|
+
return isFocusable(el) && !hasNegativeTabIndex(el);
|
|
105
|
+
}
|
|
106
|
+
function getFirstTabbable(container, includeContainer) {
|
|
107
|
+
const [first] = getTabbables(container, includeContainer);
|
|
108
|
+
return first || null;
|
|
109
|
+
}
|
|
110
|
+
function getLastTabbable(container, includeContainer) {
|
|
111
|
+
const elements = getTabbables(container, includeContainer);
|
|
112
|
+
return elements[elements.length - 1] || null;
|
|
113
|
+
}
|
|
33
114
|
var isRef = (v) => hasProp(v, "current");
|
|
34
115
|
function addDomEvent(target, eventName, handler, options) {
|
|
35
116
|
const node = isRef(target) ? target.current : runIfFn(target);
|
|
@@ -57,179 +138,11 @@ function raf(fn) {
|
|
|
57
138
|
globalThis.cancelAnimationFrame(id);
|
|
58
139
|
};
|
|
59
140
|
}
|
|
60
|
-
var changeCount = 0;
|
|
61
|
-
var originalBodyPointerEvents;
|
|
62
|
-
function preventBodyPointerEvents(el, opts = {}) {
|
|
63
|
-
const { disabled = false, document: docProp } = opts;
|
|
64
|
-
const doc = docProp || document;
|
|
65
|
-
let isTouchOrPenPressed = false;
|
|
66
|
-
let isLeftClickPressed = false;
|
|
67
|
-
function listen() {
|
|
68
|
-
const onPointerDown = (event) => {
|
|
69
|
-
const isMouse = event.pointerType === "mouse";
|
|
70
|
-
isTouchOrPenPressed = !isMouse;
|
|
71
|
-
isLeftClickPressed = isMouse && isLeftClick(event);
|
|
72
|
-
};
|
|
73
|
-
const onPointerUp = () => {
|
|
74
|
-
isTouchOrPenPressed = false;
|
|
75
|
-
isLeftClickPressed = false;
|
|
76
|
-
};
|
|
77
|
-
return pipe(addDomEvent(doc, "pointerdown", onPointerDown), addDomEvent(doc, "pointerup", onPointerUp));
|
|
78
|
-
}
|
|
79
|
-
function reset() {
|
|
80
|
-
changeCount--;
|
|
81
|
-
if (changeCount === 0) {
|
|
82
|
-
doc.body.style.pointerEvents = originalBodyPointerEvents;
|
|
83
|
-
}
|
|
84
|
-
if (el) {
|
|
85
|
-
el.style.pointerEvents = "";
|
|
86
|
-
}
|
|
87
|
-
}
|
|
88
|
-
function apply() {
|
|
89
|
-
if (disabled)
|
|
90
|
-
return;
|
|
91
|
-
if (changeCount === 0) {
|
|
92
|
-
originalBodyPointerEvents = doc.body.style.pointerEvents;
|
|
93
|
-
}
|
|
94
|
-
doc.body.style.pointerEvents = "none";
|
|
95
|
-
if (el) {
|
|
96
|
-
el.style.pointerEvents = "auto";
|
|
97
|
-
}
|
|
98
|
-
changeCount++;
|
|
99
|
-
return function() {
|
|
100
|
-
if (isTouchOrPenPressed) {
|
|
101
|
-
addDomEvent(doc, "click", reset, { once: true });
|
|
102
|
-
} else if (isLeftClickPressed) {
|
|
103
|
-
addDomEvent(doc, "pointerup", reset, { once: true });
|
|
104
|
-
} else {
|
|
105
|
-
reset();
|
|
106
|
-
}
|
|
107
|
-
};
|
|
108
|
-
}
|
|
109
|
-
const cleanups = [];
|
|
110
|
-
cleanups.push(apply());
|
|
111
|
-
nextTick(() => {
|
|
112
|
-
cleanups.push(listen());
|
|
113
|
-
});
|
|
114
|
-
return function() {
|
|
115
|
-
cleanups.forEach((cleanup) => cleanup == null ? void 0 : cleanup());
|
|
116
|
-
};
|
|
117
|
-
}
|
|
118
|
-
function getStyleCache() {
|
|
119
|
-
;
|
|
120
|
-
globalThis.__styleCache__ = globalThis.__styleCache__ || /* @__PURE__ */ new WeakMap();
|
|
121
|
-
return globalThis.__styleCache__;
|
|
122
|
-
}
|
|
123
|
-
function getComputedStyle(el) {
|
|
124
|
-
var _a;
|
|
125
|
-
if (!el)
|
|
126
|
-
return {};
|
|
127
|
-
const cache = getStyleCache();
|
|
128
|
-
let style = cache.get(el);
|
|
129
|
-
if (!style) {
|
|
130
|
-
const win = (_a = el == null ? void 0 : el.ownerDocument.defaultView) != null ? _a : window;
|
|
131
|
-
style = win.getComputedStyle(el);
|
|
132
|
-
cache.set(el, style);
|
|
133
|
-
}
|
|
134
|
-
return style;
|
|
135
|
-
}
|
|
136
|
-
function contains(parent, child) {
|
|
137
|
-
if (!parent)
|
|
138
|
-
return false;
|
|
139
|
-
return parent === child || isHTMLElement(parent) && isHTMLElement(child) && parent.contains(child);
|
|
140
|
-
}
|
|
141
|
-
function isHTMLElement(v) {
|
|
142
|
-
return typeof v === "object" && (v == null ? void 0 : v.nodeType) === Node.ELEMENT_NODE && typeof (v == null ? void 0 : v.nodeName) === "string";
|
|
143
|
-
}
|
|
144
|
-
var isDisabled = (el) => {
|
|
145
|
-
return (el == null ? void 0 : el.getAttribute("disabled")) != null || !!(el == null ? void 0 : el.getAttribute("aria-disabled")) === true;
|
|
146
|
-
};
|
|
147
|
-
function validateBlur(event, opts) {
|
|
148
|
-
var _a;
|
|
149
|
-
const exclude = Array.isArray(opts.exclude) ? opts.exclude : [opts.exclude];
|
|
150
|
-
const relatedTarget = (_a = event.relatedTarget) != null ? _a : opts.fallback;
|
|
151
|
-
return exclude.every((el) => !(el == null ? void 0 : el.contains(relatedTarget)));
|
|
152
|
-
}
|
|
153
|
-
var focusableSelector = /* @__PURE__ */ [
|
|
154
|
-
"input:not([disabled]):not([type=hidden])",
|
|
155
|
-
"select:not([disabled])",
|
|
156
|
-
"textarea:not([disabled])",
|
|
157
|
-
"button:not([disabled])",
|
|
158
|
-
"embed",
|
|
159
|
-
"iframe",
|
|
160
|
-
"object",
|
|
161
|
-
"a[href]",
|
|
162
|
-
"area[href]",
|
|
163
|
-
"[tabindex]",
|
|
164
|
-
"audio[controls]",
|
|
165
|
-
"video[controls]",
|
|
166
|
-
"*[tabindex]:not([aria-disabled])",
|
|
167
|
-
"[contenteditable]:not([contenteditable=false])",
|
|
168
|
-
"details > summary:first-of-type"
|
|
169
|
-
].join(",");
|
|
170
|
-
function isHidden(el, until) {
|
|
171
|
-
const style = getComputedStyle(el);
|
|
172
|
-
if (!el || style.getPropertyValue("visibility") === "hidden")
|
|
173
|
-
return true;
|
|
174
|
-
while (el) {
|
|
175
|
-
if (until != null && el === until)
|
|
176
|
-
return false;
|
|
177
|
-
if (style.getPropertyValue("display") === "none")
|
|
178
|
-
return true;
|
|
179
|
-
el = el.parentElement;
|
|
180
|
-
}
|
|
181
|
-
return false;
|
|
182
|
-
}
|
|
183
|
-
var getFocusables = (el, includeContainer = false) => {
|
|
184
|
-
if (!el)
|
|
185
|
-
return [];
|
|
186
|
-
let els = Array.from(el.querySelectorAll(focusableSelector));
|
|
187
|
-
const shouldAddContainer = includeContainer == true || includeContainer == "if-empty" && els.length === 0;
|
|
188
|
-
if (shouldAddContainer && isHTMLElement(el)) {
|
|
189
|
-
els.unshift(el);
|
|
190
|
-
}
|
|
191
|
-
return els.filter((el2) => isFocusable(el2) && !isHidden(el2));
|
|
192
|
-
};
|
|
193
|
-
var isFocusable = (el) => {
|
|
194
|
-
if (!isHTMLElement(el) || isHidden(el) || isDisabled(el))
|
|
195
|
-
return false;
|
|
196
|
-
return el == null ? void 0 : el.matches(focusableSelector);
|
|
197
|
-
};
|
|
198
|
-
var getTabbables = (el, includeContainer = false) => {
|
|
199
|
-
if (!el)
|
|
200
|
-
return [];
|
|
201
|
-
return getFocusables(el, includeContainer).filter(isTabbable);
|
|
202
|
-
};
|
|
203
|
-
var isTabbable = (el) => {
|
|
204
|
-
return isFocusable(el) && !isDisabled(el) && !isHidden(el);
|
|
205
|
-
};
|
|
206
|
-
function trackPointerDown(doc, onPointerDown) {
|
|
207
|
-
var _a;
|
|
208
|
-
const win = (_a = doc.defaultView) != null ? _a : window;
|
|
209
|
-
const fn = (event) => {
|
|
210
|
-
if (event.target instanceof win.HTMLElement) {
|
|
211
|
-
onPointerDown(event.target);
|
|
212
|
-
}
|
|
213
|
-
};
|
|
214
|
-
return addDomEvent(doc, "pointerdown", fn);
|
|
215
|
-
}
|
|
216
141
|
|
|
217
142
|
// src/popover.connect.ts
|
|
218
143
|
import { getPlacementStyles } from "@zag-js/popper";
|
|
219
144
|
|
|
220
|
-
// ../../types/dist/index.mjs
|
|
221
|
-
function createNormalizer(fn) {
|
|
222
|
-
return new Proxy({}, {
|
|
223
|
-
get() {
|
|
224
|
-
return fn;
|
|
225
|
-
}
|
|
226
|
-
});
|
|
227
|
-
}
|
|
228
|
-
var normalizeProp = createNormalizer((v) => v);
|
|
229
|
-
|
|
230
145
|
// ../../utilities/core/dist/index.mjs
|
|
231
|
-
var first = (v) => v[0];
|
|
232
|
-
var last = (v) => v[v.length - 1];
|
|
233
146
|
function nextIndex(v, idx, opts = {}) {
|
|
234
147
|
const { step = 1, loop = true } = opts;
|
|
235
148
|
const next2 = idx + step;
|
|
@@ -248,59 +161,50 @@ function next(v, idx, opts = {}) {
|
|
|
248
161
|
}
|
|
249
162
|
var runIfFn2 = (v, ...a) => {
|
|
250
163
|
const res = typeof v === "function" ? v(...a) : v;
|
|
251
|
-
return res
|
|
164
|
+
return res ?? void 0;
|
|
252
165
|
};
|
|
253
|
-
var cast = (v) => v;
|
|
254
166
|
|
|
255
167
|
// src/popover.dom.ts
|
|
256
|
-
var dom = {
|
|
257
|
-
getDoc: (ctx) => {
|
|
258
|
-
var _a;
|
|
259
|
-
return (_a = ctx.doc) != null ? _a : document;
|
|
260
|
-
},
|
|
168
|
+
var dom = defineDomHelpers({
|
|
261
169
|
getActiveEl: (ctx) => dom.getDoc(ctx).activeElement,
|
|
262
|
-
getRootNode: (ctx) => {
|
|
263
|
-
var _a;
|
|
264
|
-
return (_a = ctx.rootNode) != null ? _a : dom.getDoc(ctx);
|
|
265
|
-
},
|
|
266
170
|
getAnchorId: (ctx) => {
|
|
267
|
-
var _a
|
|
268
|
-
return (
|
|
171
|
+
var _a;
|
|
172
|
+
return ((_a = ctx.ids) == null ? void 0 : _a.anchor) ?? `popover:${ctx.id}:anchor`;
|
|
269
173
|
},
|
|
270
174
|
getTriggerId: (ctx) => {
|
|
271
|
-
var _a
|
|
272
|
-
return (
|
|
175
|
+
var _a;
|
|
176
|
+
return ((_a = ctx.ids) == null ? void 0 : _a.trigger) ?? `popover:${ctx.id}:trigger`;
|
|
273
177
|
},
|
|
274
178
|
getContentId: (ctx) => {
|
|
275
|
-
var _a
|
|
276
|
-
return (
|
|
179
|
+
var _a;
|
|
180
|
+
return ((_a = ctx.ids) == null ? void 0 : _a.content) ?? `popover:${ctx.id}:content`;
|
|
277
181
|
},
|
|
278
|
-
getPositionerId: (ctx) => `popover:${ctx.
|
|
279
|
-
getArrowId: (ctx) => `popover:${ctx.
|
|
182
|
+
getPositionerId: (ctx) => `popover:${ctx.id}:popper`,
|
|
183
|
+
getArrowId: (ctx) => `popover:${ctx.id}:arrow`,
|
|
280
184
|
getTitleId: (ctx) => {
|
|
281
|
-
var _a
|
|
282
|
-
return (
|
|
185
|
+
var _a;
|
|
186
|
+
return ((_a = ctx.ids) == null ? void 0 : _a.title) ?? `popover:${ctx.id}:title`;
|
|
283
187
|
},
|
|
284
188
|
getDescriptionId: (ctx) => {
|
|
285
|
-
var _a
|
|
286
|
-
return (
|
|
189
|
+
var _a;
|
|
190
|
+
return ((_a = ctx.ids) == null ? void 0 : _a.description) ?? `popover:${ctx.id}:desc`;
|
|
287
191
|
},
|
|
288
192
|
getCloseButtonId: (ctx) => {
|
|
289
|
-
var _a
|
|
290
|
-
return (
|
|
193
|
+
var _a;
|
|
194
|
+
return ((_a = ctx.ids) == null ? void 0 : _a.closeBtn) ?? `popover:${ctx.id}:close-button`;
|
|
291
195
|
},
|
|
292
|
-
getAnchorEl: (ctx) => dom.
|
|
293
|
-
getTriggerEl: (ctx) => dom.
|
|
294
|
-
getContentEl: (ctx) => dom.
|
|
295
|
-
getPositionerEl: (ctx) => dom.
|
|
296
|
-
getTitleEl: (ctx) => dom.
|
|
297
|
-
getDescriptionEl: (ctx) => dom.
|
|
196
|
+
getAnchorEl: (ctx) => dom.getById(ctx, dom.getAnchorId(ctx)),
|
|
197
|
+
getTriggerEl: (ctx) => dom.getById(ctx, dom.getTriggerId(ctx)),
|
|
198
|
+
getContentEl: (ctx) => dom.getById(ctx, dom.getContentId(ctx)),
|
|
199
|
+
getPositionerEl: (ctx) => dom.getById(ctx, dom.getPositionerId(ctx)),
|
|
200
|
+
getTitleEl: (ctx) => dom.getById(ctx, dom.getTitleId(ctx)),
|
|
201
|
+
getDescriptionEl: (ctx) => dom.getById(ctx, dom.getDescriptionId(ctx)),
|
|
298
202
|
getFocusableEls: (ctx) => getFocusables(dom.getContentEl(ctx)),
|
|
299
203
|
getFirstFocusableEl: (ctx) => dom.getFocusableEls(ctx)[0],
|
|
300
|
-
getDocTabbableEls: (ctx) => getTabbables(
|
|
204
|
+
getDocTabbableEls: (ctx) => getTabbables(dom.getDoc(ctx).body),
|
|
301
205
|
getTabbableEls: (ctx) => getTabbables(dom.getContentEl(ctx), "if-empty"),
|
|
302
|
-
getFirstTabbableEl: (ctx) =>
|
|
303
|
-
getLastTabbableEl: (ctx) =>
|
|
206
|
+
getFirstTabbableEl: (ctx) => getFirstTabbable(dom.getContentEl(ctx), "if-empty"),
|
|
207
|
+
getLastTabbableEl: (ctx) => getLastTabbable(dom.getContentEl(ctx), "if-empty"),
|
|
304
208
|
getInitialFocusEl: (ctx) => {
|
|
305
209
|
let el = runIfFn2(ctx.initialFocusEl);
|
|
306
210
|
if (!el && ctx.autoFocus)
|
|
@@ -309,19 +213,20 @@ var dom = {
|
|
|
309
213
|
el = dom.getContentEl(ctx);
|
|
310
214
|
return el;
|
|
311
215
|
}
|
|
312
|
-
};
|
|
216
|
+
});
|
|
313
217
|
|
|
314
218
|
// src/popover.connect.ts
|
|
315
|
-
function connect(state, send, normalize
|
|
219
|
+
function connect(state, send, normalize) {
|
|
316
220
|
const isOpen = state.matches("open");
|
|
317
|
-
const pointerdownNode = state.context.pointerdownNode;
|
|
318
221
|
const currentPlacement = state.context.currentPlacement;
|
|
222
|
+
const portalled = state.context.currentPortalled;
|
|
223
|
+
const rendered = state.context.renderedElements;
|
|
319
224
|
const popperStyles = getPlacementStyles({
|
|
320
225
|
measured: !!state.context.isPlacementComplete,
|
|
321
226
|
placement: currentPlacement
|
|
322
227
|
});
|
|
323
228
|
return {
|
|
324
|
-
portalled
|
|
229
|
+
portalled,
|
|
325
230
|
isOpen,
|
|
326
231
|
open() {
|
|
327
232
|
send("OPEN");
|
|
@@ -352,12 +257,10 @@ function connect(state, send, normalize = normalizeProp) {
|
|
|
352
257
|
"data-expanded": dataAttr(isOpen),
|
|
353
258
|
"aria-controls": dom.getContentId(state.context),
|
|
354
259
|
onClick() {
|
|
355
|
-
send("
|
|
260
|
+
send("TOGGLE");
|
|
356
261
|
},
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
send("ESCAPE");
|
|
360
|
-
}
|
|
262
|
+
onBlur(event) {
|
|
263
|
+
send({ type: "TRIGGER_BLUR", target: event.relatedTarget });
|
|
361
264
|
}
|
|
362
265
|
}),
|
|
363
266
|
positionerProps: normalize.element({
|
|
@@ -372,34 +275,9 @@ function connect(state, send, normalize = normalizeProp) {
|
|
|
372
275
|
role: "dialog",
|
|
373
276
|
hidden: !isOpen,
|
|
374
277
|
"data-expanded": dataAttr(isOpen),
|
|
375
|
-
"aria-labelledby":
|
|
376
|
-
"aria-describedby":
|
|
377
|
-
"data-placement": currentPlacement
|
|
378
|
-
onKeyDown(event) {
|
|
379
|
-
const keyMap = {
|
|
380
|
-
Escape(event2) {
|
|
381
|
-
send("ESCAPE");
|
|
382
|
-
event2.stopPropagation();
|
|
383
|
-
},
|
|
384
|
-
Tab(event2) {
|
|
385
|
-
const type = event2.shiftKey ? "SHIFT_TAB" : "TAB";
|
|
386
|
-
send({ type, preventDefault: () => event2.preventDefault() });
|
|
387
|
-
}
|
|
388
|
-
};
|
|
389
|
-
const exec = keyMap[event.key];
|
|
390
|
-
exec == null ? void 0 : exec(event);
|
|
391
|
-
},
|
|
392
|
-
onBlur(event) {
|
|
393
|
-
var _a;
|
|
394
|
-
const isValidBlur = validateBlur(event, {
|
|
395
|
-
exclude: [dom.getTriggerEl(state.context), dom.getContentEl(state.context)],
|
|
396
|
-
fallback: pointerdownNode
|
|
397
|
-
});
|
|
398
|
-
if (isValidBlur) {
|
|
399
|
-
const el = (_a = event.relatedTarget) != null ? _a : pointerdownNode;
|
|
400
|
-
send({ type: "INTERACT_OUTSIDE", focusable: isFocusable(el) });
|
|
401
|
-
}
|
|
402
|
-
}
|
|
278
|
+
"aria-labelledby": rendered.title ? dom.getTitleId(state.context) : void 0,
|
|
279
|
+
"aria-describedby": rendered.description ? dom.getDescriptionId(state.context) : void 0,
|
|
280
|
+
"data-placement": currentPlacement
|
|
403
281
|
}),
|
|
404
282
|
titleProps: normalize.element({
|
|
405
283
|
"data-part": "title",
|
|
@@ -415,7 +293,7 @@ function connect(state, send, normalize = normalizeProp) {
|
|
|
415
293
|
type: "button",
|
|
416
294
|
"aria-label": "close",
|
|
417
295
|
onClick() {
|
|
418
|
-
send("
|
|
296
|
+
send("REQUEST_CLOSE");
|
|
419
297
|
}
|
|
420
298
|
})
|
|
421
299
|
};
|
|
@@ -423,32 +301,34 @@ function connect(state, send, normalize = normalizeProp) {
|
|
|
423
301
|
|
|
424
302
|
// src/popover.machine.ts
|
|
425
303
|
import { ariaHidden } from "@zag-js/aria-hidden";
|
|
426
|
-
import { createMachine, guards
|
|
304
|
+
import { createMachine, guards } from "@zag-js/core";
|
|
305
|
+
import { trackDismissableElement } from "@zag-js/dismissable";
|
|
427
306
|
import { getPlacement } from "@zag-js/popper";
|
|
428
307
|
import { preventBodyScroll } from "@zag-js/remove-scroll";
|
|
429
308
|
import { createFocusTrap } from "focus-trap";
|
|
430
|
-
var { and, or } = guards;
|
|
431
|
-
function machine(ctx
|
|
309
|
+
var { and, or, not } = guards;
|
|
310
|
+
function machine(ctx) {
|
|
432
311
|
return createMachine({
|
|
433
312
|
id: "popover",
|
|
434
313
|
initial: "unknown",
|
|
435
|
-
context:
|
|
436
|
-
|
|
437
|
-
closeOnBlur: true,
|
|
314
|
+
context: {
|
|
315
|
+
closeOnInteractOutside: true,
|
|
438
316
|
closeOnEsc: true,
|
|
439
317
|
autoFocus: true,
|
|
440
318
|
modal: false,
|
|
441
|
-
positioning:
|
|
442
|
-
placement: "bottom"
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
319
|
+
positioning: {
|
|
320
|
+
placement: "bottom",
|
|
321
|
+
...ctx.positioning
|
|
322
|
+
},
|
|
323
|
+
currentPlacement: void 0,
|
|
324
|
+
...ctx,
|
|
325
|
+
focusTriggerOnClose: true,
|
|
446
326
|
renderedElements: {
|
|
447
327
|
title: true,
|
|
448
328
|
description: true,
|
|
449
329
|
anchor: false
|
|
450
330
|
}
|
|
451
|
-
}
|
|
331
|
+
},
|
|
452
332
|
computed: {
|
|
453
333
|
currentPortalled: (ctx2) => !!ctx2.modal || !!ctx2.portalled
|
|
454
334
|
},
|
|
@@ -456,63 +336,54 @@ function machine(ctx = {}) {
|
|
|
456
336
|
unknown: {
|
|
457
337
|
on: {
|
|
458
338
|
SETUP: {
|
|
459
|
-
target: ctx.
|
|
460
|
-
actions:
|
|
339
|
+
target: ctx.defaultOpen ? "open" : "closed",
|
|
340
|
+
actions: "checkRenderedElements"
|
|
461
341
|
}
|
|
462
342
|
}
|
|
463
343
|
},
|
|
464
344
|
closed: {
|
|
465
|
-
entry:
|
|
345
|
+
entry: "invokeOnClose",
|
|
466
346
|
on: {
|
|
467
|
-
|
|
347
|
+
TOGGLE: "open",
|
|
468
348
|
OPEN: "open"
|
|
469
349
|
}
|
|
470
350
|
},
|
|
471
351
|
open: {
|
|
472
352
|
activities: [
|
|
473
|
-
"trackPointerDown",
|
|
474
353
|
"trapFocus",
|
|
475
354
|
"preventScroll",
|
|
476
355
|
"hideContentBelow",
|
|
477
|
-
"
|
|
478
|
-
"
|
|
356
|
+
"computePlacement",
|
|
357
|
+
"trackInteractionOutside",
|
|
358
|
+
"trackTabKeyDown"
|
|
479
359
|
],
|
|
480
360
|
entry: ["setInitialFocus", "invokeOnOpen"],
|
|
481
361
|
on: {
|
|
482
|
-
CLOSE:
|
|
362
|
+
CLOSE: "closed",
|
|
363
|
+
REQUEST_CLOSE: {
|
|
483
364
|
target: "closed",
|
|
484
|
-
actions: "
|
|
365
|
+
actions: "focusTriggerIfNeeded"
|
|
485
366
|
},
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
367
|
+
TOGGLE: "closed",
|
|
368
|
+
TRIGGER_BLUR: {
|
|
369
|
+
guard: not("isRelatedTargetWithinContent"),
|
|
370
|
+
target: "closed"
|
|
489
371
|
},
|
|
490
|
-
|
|
491
|
-
guard: "closeOnEsc",
|
|
492
|
-
target: "closed",
|
|
493
|
-
actions: "focusTrigger"
|
|
494
|
-
},
|
|
495
|
-
TAB: {
|
|
496
|
-
guard: and("isLastTabbableElement", "closeOnBlur", "portalled"),
|
|
497
|
-
target: "closed",
|
|
498
|
-
actions: "focusNextTabbableElementAfterTrigger"
|
|
499
|
-
},
|
|
500
|
-
SHIFT_TAB: {
|
|
501
|
-
guard: and(or("isFirstTabbableElement", "isContentFocused"), "closeOnBlur", "portalled"),
|
|
502
|
-
target: "closed",
|
|
503
|
-
actions: "focusTrigger"
|
|
504
|
-
},
|
|
505
|
-
INTERACT_OUTSIDE: [
|
|
372
|
+
TAB: [
|
|
506
373
|
{
|
|
507
|
-
guard: and("
|
|
508
|
-
|
|
374
|
+
guard: and("isTriggerFocused", "portalled"),
|
|
375
|
+
actions: "focusFirstTabbableElement"
|
|
509
376
|
},
|
|
510
377
|
{
|
|
511
|
-
guard: "
|
|
378
|
+
guard: and("isLastTabbableElement", "closeOnInteractOutside", "portalled"),
|
|
512
379
|
target: "closed",
|
|
513
|
-
actions: "
|
|
380
|
+
actions: "focusNextTabbableElementAfterTrigger"
|
|
514
381
|
}
|
|
515
|
-
]
|
|
382
|
+
],
|
|
383
|
+
SHIFT_TAB: {
|
|
384
|
+
guard: and(or("isFirstTabbableElement", "isContentFocused"), "portalled"),
|
|
385
|
+
actions: "focusTriggerIfNeeded"
|
|
386
|
+
}
|
|
516
387
|
}
|
|
517
388
|
}
|
|
518
389
|
}
|
|
@@ -521,7 +392,8 @@ function machine(ctx = {}) {
|
|
|
521
392
|
computePlacement(ctx2) {
|
|
522
393
|
ctx2.currentPlacement = ctx2.positioning.placement;
|
|
523
394
|
const anchorEl = ctx2.renderedElements.anchor ? dom.getAnchorEl(ctx2) : dom.getTriggerEl(ctx2);
|
|
524
|
-
return getPlacement(anchorEl, dom.getPositionerEl(ctx2),
|
|
395
|
+
return getPlacement(anchorEl, dom.getPositionerEl(ctx2), {
|
|
396
|
+
...ctx2.positioning,
|
|
525
397
|
onComplete(data) {
|
|
526
398
|
ctx2.currentPlacement = data.placement;
|
|
527
399
|
ctx2.isPlacementComplete = true;
|
|
@@ -530,34 +402,72 @@ function machine(ctx = {}) {
|
|
|
530
402
|
ctx2.currentPlacement = void 0;
|
|
531
403
|
ctx2.isPlacementComplete = false;
|
|
532
404
|
}
|
|
533
|
-
}));
|
|
534
|
-
},
|
|
535
|
-
trackPointerDown(ctx2) {
|
|
536
|
-
return trackPointerDown(dom.getDoc(ctx2), (el) => {
|
|
537
|
-
ctx2.pointerdownNode = ref(el);
|
|
538
405
|
});
|
|
539
406
|
},
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
|
|
543
|
-
|
|
544
|
-
|
|
407
|
+
trackInteractionOutside(ctx2, _evt, { send }) {
|
|
408
|
+
return trackDismissableElement(dom.getContentEl(ctx2), {
|
|
409
|
+
pointerBlocking: ctx2.modal,
|
|
410
|
+
exclude: dom.getTriggerEl(ctx2),
|
|
411
|
+
onEscapeKeyDown(event) {
|
|
412
|
+
var _a;
|
|
413
|
+
(_a = ctx2.onEscapeKeyDown) == null ? void 0 : _a.call(ctx2, event);
|
|
414
|
+
if (ctx2.closeOnEsc)
|
|
415
|
+
return;
|
|
416
|
+
ctx2.focusTriggerOnClose = true;
|
|
417
|
+
event.preventDefault();
|
|
418
|
+
},
|
|
419
|
+
onInteractOutside(event) {
|
|
420
|
+
var _a;
|
|
421
|
+
(_a = ctx2.onInteractOutside) == null ? void 0 : _a.call(ctx2, event);
|
|
422
|
+
if (event.defaultPrevented)
|
|
423
|
+
return;
|
|
424
|
+
ctx2.focusTriggerOnClose = !(event.detail.focusable || event.detail.contextmenu);
|
|
425
|
+
if (!ctx2.closeOnInteractOutside) {
|
|
426
|
+
event.preventDefault();
|
|
427
|
+
}
|
|
428
|
+
},
|
|
429
|
+
onPointerDownOutside(event) {
|
|
430
|
+
var _a;
|
|
431
|
+
(_a = ctx2.onPointerDownOutside) == null ? void 0 : _a.call(ctx2, event);
|
|
432
|
+
},
|
|
433
|
+
onFocusOutside(event) {
|
|
434
|
+
var _a;
|
|
435
|
+
(_a = ctx2.onFocusOutside) == null ? void 0 : _a.call(ctx2, event);
|
|
436
|
+
if (ctx2.currentPortalled) {
|
|
437
|
+
event.preventDefault();
|
|
438
|
+
}
|
|
439
|
+
},
|
|
440
|
+
onDismiss() {
|
|
441
|
+
send({ type: "REQUEST_CLOSE", src: "#interact-outside" });
|
|
442
|
+
}
|
|
545
443
|
});
|
|
546
444
|
},
|
|
445
|
+
trackTabKeyDown(ctx2, _evt, { send }) {
|
|
446
|
+
if (ctx2.modal)
|
|
447
|
+
return;
|
|
448
|
+
return addDomEvent(dom.getWin(ctx2), "keydown", (event) => {
|
|
449
|
+
const isTabKey = event.key === "Tab" && !isModifiedEvent(event);
|
|
450
|
+
if (!isTabKey)
|
|
451
|
+
return;
|
|
452
|
+
send({
|
|
453
|
+
type: event.shiftKey ? "SHIFT_TAB" : "TAB",
|
|
454
|
+
preventDefault: () => event.preventDefault()
|
|
455
|
+
});
|
|
456
|
+
}, true);
|
|
457
|
+
},
|
|
547
458
|
hideContentBelow(ctx2) {
|
|
548
459
|
if (!ctx2.modal)
|
|
549
460
|
return;
|
|
550
|
-
let
|
|
461
|
+
let cleanup;
|
|
551
462
|
nextTick(() => {
|
|
552
|
-
|
|
463
|
+
cleanup = ariaHidden([dom.getContentEl(ctx2), dom.getTriggerEl(ctx2)]);
|
|
553
464
|
});
|
|
554
|
-
return () =>
|
|
465
|
+
return () => cleanup == null ? void 0 : cleanup();
|
|
555
466
|
},
|
|
556
467
|
preventScroll(ctx2) {
|
|
557
|
-
|
|
558
|
-
|
|
559
|
-
|
|
560
|
-
});
|
|
468
|
+
if (!ctx2.modal)
|
|
469
|
+
return;
|
|
470
|
+
return preventBodyScroll(dom.getDoc(ctx2));
|
|
561
471
|
},
|
|
562
472
|
trapFocus(ctx2) {
|
|
563
473
|
if (!ctx2.modal)
|
|
@@ -577,20 +487,18 @@ function machine(ctx = {}) {
|
|
|
577
487
|
});
|
|
578
488
|
try {
|
|
579
489
|
trap.activate();
|
|
580
|
-
} catch
|
|
490
|
+
} catch {
|
|
581
491
|
}
|
|
582
492
|
});
|
|
583
493
|
return () => trap == null ? void 0 : trap.deactivate();
|
|
584
494
|
}
|
|
585
495
|
},
|
|
586
496
|
guards: {
|
|
587
|
-
|
|
588
|
-
|
|
589
|
-
|
|
590
|
-
portalled: (ctx2) => !!ctx2.portalled,
|
|
591
|
-
isRelatedTargetFocusable: (_ctx, evt) => evt.focusable,
|
|
592
|
-
closeOnBlur: (ctx2) => !!ctx2.closeOnBlur,
|
|
497
|
+
portalled: (ctx2) => ctx2.currentPortalled,
|
|
498
|
+
isRelatedTargetWithinContent: (ctx2, evt) => contains(dom.getContentEl(ctx2), evt.target),
|
|
499
|
+
closeOnInteractOutside: (ctx2) => !!ctx2.closeOnInteractOutside,
|
|
593
500
|
isContentFocused: (ctx2) => dom.getContentEl(ctx2) === dom.getActiveEl(ctx2),
|
|
501
|
+
isTriggerFocused: (ctx2) => dom.getTriggerEl(ctx2) === dom.getActiveEl(ctx2),
|
|
594
502
|
isFirstTabbableElement: (ctx2) => dom.getFirstTabbableEl(ctx2) === dom.getActiveEl(ctx2),
|
|
595
503
|
isLastTabbableElement: (ctx2) => dom.getLastTabbableEl(ctx2) === dom.getActiveEl(ctx2)
|
|
596
504
|
},
|
|
@@ -604,48 +512,44 @@ function machine(ctx = {}) {
|
|
|
604
512
|
});
|
|
605
513
|
});
|
|
606
514
|
},
|
|
607
|
-
setupDocument(ctx2, evt) {
|
|
608
|
-
if (evt.doc)
|
|
609
|
-
ctx2.doc = ref(evt.doc);
|
|
610
|
-
if (evt.root)
|
|
611
|
-
ctx2.rootNode = ref(evt.root);
|
|
612
|
-
ctx2.uid = evt.id;
|
|
613
|
-
},
|
|
614
|
-
clearPointerDown(ctx2) {
|
|
615
|
-
ctx2.pointerdownNode = null;
|
|
616
|
-
},
|
|
617
515
|
setInitialFocus(ctx2) {
|
|
618
516
|
raf(() => {
|
|
619
517
|
var _a;
|
|
620
518
|
(_a = dom.getInitialFocusEl(ctx2)) == null ? void 0 : _a.focus();
|
|
621
519
|
});
|
|
622
520
|
},
|
|
623
|
-
|
|
521
|
+
focusTriggerIfNeeded(ctx2) {
|
|
522
|
+
if (!ctx2.focusTriggerOnClose)
|
|
523
|
+
return;
|
|
624
524
|
raf(() => {
|
|
625
525
|
var _a;
|
|
626
|
-
(_a = dom.getTriggerEl(ctx2)) == null ? void 0 : _a.focus();
|
|
526
|
+
return (_a = dom.getTriggerEl(ctx2)) == null ? void 0 : _a.focus();
|
|
627
527
|
});
|
|
628
528
|
},
|
|
529
|
+
focusFirstTabbableElement(ctx2, evt) {
|
|
530
|
+
var _a;
|
|
531
|
+
evt.preventDefault();
|
|
532
|
+
(_a = dom.getFirstTabbableEl(ctx2)) == null ? void 0 : _a.focus();
|
|
533
|
+
},
|
|
629
534
|
invokeOnOpen(ctx2, evt) {
|
|
630
535
|
var _a;
|
|
631
536
|
if (evt.type !== "SETUP") {
|
|
632
|
-
(_a = ctx2.
|
|
537
|
+
(_a = ctx2.onOpenChange) == null ? void 0 : _a.call(ctx2, true);
|
|
633
538
|
}
|
|
634
539
|
},
|
|
635
540
|
invokeOnClose(ctx2, evt) {
|
|
636
541
|
var _a;
|
|
637
542
|
if (evt.type !== "SETUP") {
|
|
638
|
-
(_a = ctx2.
|
|
543
|
+
(_a = ctx2.onOpenChange) == null ? void 0 : _a.call(ctx2, false);
|
|
639
544
|
}
|
|
640
545
|
},
|
|
641
546
|
focusNextTabbableElementAfterTrigger(ctx2, evt) {
|
|
642
547
|
const content = dom.getContentEl(ctx2);
|
|
643
|
-
const doc = dom.getDoc(ctx2);
|
|
644
548
|
const button = dom.getTriggerEl(ctx2);
|
|
645
549
|
if (!content || !button)
|
|
646
550
|
return;
|
|
647
551
|
const lastTabbable = dom.getLastTabbableEl(ctx2);
|
|
648
|
-
if (lastTabbable !==
|
|
552
|
+
if (lastTabbable !== dom.getActiveEl(ctx2))
|
|
649
553
|
return;
|
|
650
554
|
let tabbables = dom.getDocTabbableEls(ctx2);
|
|
651
555
|
let elementAfterTrigger = next(tabbables, tabbables.indexOf(button), { loop: false });
|