@destyler/popover 0.0.1-beta.2 → 0.0.1-beta.20

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.
@@ -0,0 +1,489 @@
1
+ import { defineComponent, h, mergeProps, toRef, ref, withDirectives, onMounted } from 'vue';
2
+ import { DestylerPopperArrow, DestylerPopperRoot, DestylerPopperContent, DestylerPopperAnchor } from '@destyler/popper';
3
+ import { DestylerPrimitive } from '@destyler/primitive';
4
+ import { createContext } from '@destyler/shared';
5
+ import { useVModel, useId, useForwardProps, useFocusGuards, useForwardPropsEmits, useForwardExpose, useHideOthers } from '@destyler/composition';
6
+ import { DestylerPresence } from '@destyler/presence';
7
+ import { DestylerDismissableLayer } from '@destyler/dismissable-layer';
8
+ import { DestylerFocusScope } from '@destyler/focus-scope';
9
+ import { BindOnceDirective } from '@destyler/directives';
10
+ import { DestylerTeleport } from '@destyler/teleport';
11
+
12
+ const destylerPopoverArrowProps = {
13
+ asChild: {
14
+ type: Boolean,
15
+ required: false,
16
+ default: false
17
+ },
18
+ width: {
19
+ type: Number,
20
+ required: false,
21
+ default: 5
22
+ },
23
+ height: {
24
+ type: Number,
25
+ required: false,
26
+ default: 10
27
+ },
28
+ as: {
29
+ type: [String, Object],
30
+ required: false,
31
+ default: "svg"
32
+ }
33
+ };
34
+ const DestylerPopoverArrow = defineComponent({
35
+ name: "DestylerPopoverArrow",
36
+ props: destylerPopoverArrowProps,
37
+ render() {
38
+ return h(DestylerPopperArrow, mergeProps(this.$props, {}), {
39
+ default: () => this.$slots.default?.()
40
+ });
41
+ }
42
+ });
43
+
44
+ const [injectPopoverRootContext, providePopoverRootContext] = createContext("DestylerPopoverRoot");
45
+ const destylerPopoverRootProps = {
46
+ defaultOpen: {
47
+ type: Boolean,
48
+ required: false,
49
+ default: false
50
+ },
51
+ open: {
52
+ type: Boolean,
53
+ required: false,
54
+ default: void 0
55
+ },
56
+ modal: {
57
+ type: Boolean,
58
+ required: false,
59
+ default: false
60
+ }
61
+ };
62
+ const DestylerPopoverRoot = defineComponent({
63
+ name: "DestylerPopoverRoot",
64
+ props: destylerPopoverRootProps,
65
+ emits: ["update:open"],
66
+ setup(props, { emit }) {
67
+ const modalRef = toRef(props.modal);
68
+ const openRef = useVModel(props, "open", emit, {
69
+ defaultValue: props.defaultOpen,
70
+ passive: props.open === void 0
71
+ });
72
+ const triggerElement = ref();
73
+ const hasCustomAnchor = ref(false);
74
+ function handleUpdateOpen(value) {
75
+ openRef.value = value;
76
+ }
77
+ providePopoverRootContext({
78
+ contentId: useId(),
79
+ modal: modalRef,
80
+ open: openRef,
81
+ onOpenChange: (value) => {
82
+ handleUpdateOpen(value);
83
+ },
84
+ onOpenToggle: () => {
85
+ handleUpdateOpen(!openRef.value);
86
+ },
87
+ triggerElement,
88
+ hasCustomAnchor
89
+ });
90
+ return {
91
+ openRef,
92
+ modalRef,
93
+ triggerElement,
94
+ hasCustomAnchor
95
+ };
96
+ },
97
+ render() {
98
+ return h(DestylerPopperRoot, null, {
99
+ default: () => this.$slots.default?.()
100
+ });
101
+ }
102
+ });
103
+
104
+ const destylerPopoverCloseProps = {
105
+ asChild: {
106
+ type: Boolean,
107
+ required: false,
108
+ default: false
109
+ },
110
+ as: {
111
+ type: [String, Object],
112
+ required: false,
113
+ default: "button"
114
+ }
115
+ };
116
+ const DestylerPopoverClose = defineComponent({
117
+ name: "DestylerPopoverClose",
118
+ props: destylerPopoverCloseProps,
119
+ setup() {
120
+ const rootContext = injectPopoverRootContext();
121
+ return {
122
+ rootContext
123
+ };
124
+ },
125
+ render() {
126
+ return h(DestylerPrimitive, {
127
+ as: this.$props.as,
128
+ asChild: this.$props.asChild,
129
+ type: this.$props.as === "button" ? "button" : void 0,
130
+ onClick: () => {
131
+ this.rootContext.onOpenChange(false);
132
+ }
133
+ }, {
134
+ default: () => this.$slots.default?.()
135
+ });
136
+ }
137
+ });
138
+
139
+ const destylerPopoverContentImplProps = {
140
+ side: {
141
+ type: String,
142
+ required: false,
143
+ default: "bottom"
144
+ },
145
+ sideOffset: {
146
+ type: Number,
147
+ required: false,
148
+ default: 0
149
+ },
150
+ align: {
151
+ type: String,
152
+ required: false,
153
+ default: "center"
154
+ },
155
+ alignOffset: {
156
+ type: Number,
157
+ required: false,
158
+ default: 0
159
+ },
160
+ avoidCollisions: {
161
+ type: Boolean,
162
+ required: false,
163
+ default: true
164
+ },
165
+ collisionBoundary: {
166
+ type: [Object, Array, null],
167
+ required: false,
168
+ default: () => []
169
+ },
170
+ collisionPadding: {
171
+ type: [Number, Object],
172
+ required: false,
173
+ default: 0
174
+ },
175
+ arrowPadding: {
176
+ type: Number,
177
+ required: false,
178
+ default: 0
179
+ },
180
+ sticky: {
181
+ type: String,
182
+ required: false,
183
+ default: "partial"
184
+ },
185
+ hideWhenDetached: {
186
+ type: Boolean,
187
+ required: false,
188
+ default: false
189
+ },
190
+ updatePositionStrategy: {
191
+ type: String,
192
+ required: false,
193
+ default: "optimized"
194
+ },
195
+ onPlaced: {
196
+ type: Function,
197
+ required: false
198
+ },
199
+ prioritizePosition: {
200
+ type: Boolean,
201
+ required: false,
202
+ default: false
203
+ },
204
+ as: {
205
+ type: [String, Object],
206
+ required: false,
207
+ default: "div"
208
+ },
209
+ asChild: {
210
+ type: Boolean,
211
+ required: false,
212
+ default: false
213
+ },
214
+ disableOutsidePointerEvents: {
215
+ type: Boolean,
216
+ required: false,
217
+ default: false
218
+ },
219
+ trapFocus: {
220
+ type: Boolean,
221
+ required: false,
222
+ default: false
223
+ }
224
+ };
225
+ const destylerPopoverContentImplEmits = ["escapeKeyDown", "pointerDownOutside", "focusOutside", "interactOutside", "dismiss", "openAutoFocus", "closeAutoFocus"];
226
+ const DestylerPopoverContentImpl = defineComponent({
227
+ name: "DestylerPopoverContentImpl",
228
+ props: destylerPopoverContentImplProps,
229
+ emits: destylerPopoverContentImplEmits,
230
+ setup(props) {
231
+ const forwarded = useForwardProps(props);
232
+ const rootContext = injectPopoverRootContext();
233
+ useFocusGuards();
234
+ return {
235
+ rootContext,
236
+ forwarded
237
+ };
238
+ },
239
+ render() {
240
+ return h(DestylerFocusScope, {
241
+ asChild: true,
242
+ loop: true,
243
+ trapped: this.$props.trapFocus,
244
+ onMountAutoFocus: (event) => {
245
+ this.$emit("openAutoFocus", event);
246
+ },
247
+ onUnmountAutoFocus: (event) => {
248
+ this.$emit("closeAutoFocus", event);
249
+ }
250
+ }, h(DestylerDismissableLayer, {
251
+ asChild: true,
252
+ disableOutsidePointerEvents: this.$props.disableOutsidePointerEvents,
253
+ onPointerDownOutside: (event) => {
254
+ this.$emit("pointerDownOutside", event);
255
+ },
256
+ onInteractOutside: (event) => {
257
+ this.$emit("interactOutside", event);
258
+ },
259
+ onEscapeKeyDown: (event) => {
260
+ this.$emit("escapeKeyDown", event);
261
+ },
262
+ onFocusOutside: (event) => {
263
+ this.$emit("focusOutside", event);
264
+ },
265
+ onDismiss: () => {
266
+ this.rootContext.onOpenChange(false);
267
+ }
268
+ }, withDirectives(h(DestylerPopperContent, mergeProps(this.forwarded, {
269
+ "data-state": this.rootContext.open.value ? "open" : "closed",
270
+ "role": "dialog",
271
+ "style": {
272
+ "--destyler_popover_content_transform_origin": "var(--destyler_popper_transform_origin)",
273
+ "--destyler_popover_content_available_width": "var(--destyler_popper_available_width)",
274
+ "--destyler_popover_content_available_height": "var(--destyler_popper_available_height)",
275
+ "--destyler_popover_trigger_width": "var(--destyler_popper_anchor_width)",
276
+ "--destyler_popover_trigger_height": "var(--destyler_popper_anchor_height)"
277
+ }
278
+ }), {
279
+ default: () => this.$slots.default?.()
280
+ }), [
281
+ [BindOnceDirective, { id: this.rootContext.contentId }]
282
+ ])));
283
+ }
284
+ });
285
+
286
+ const DestylerPopoverContentModal = defineComponent({
287
+ name: "DestylerPopoverContentModal",
288
+ props: destylerPopoverContentImplProps,
289
+ emits: destylerPopoverContentImplEmits,
290
+ setup(props, { emit }) {
291
+ const rootContext = injectPopoverRootContext();
292
+ const isRightClickOutsideRef = ref(false);
293
+ const forwarded = useForwardPropsEmits(props, emit);
294
+ const { forwardRef, currentElement } = useForwardExpose();
295
+ useHideOthers(currentElement);
296
+ return {
297
+ rootContext,
298
+ forwarded,
299
+ isRightClickOutsideRef,
300
+ forwardRef
301
+ };
302
+ },
303
+ render() {
304
+ return h(DestylerPopoverContentImpl, {
305
+ ref: (el) => this.forwardRef(el),
306
+ ...mergeProps(this.forwarded),
307
+ trapFocus: this.rootContext.open.value,
308
+ disableOutsidePointerEvents: true,
309
+ onCloseAutoFocusPrevent: (event) => {
310
+ this.$emit("closeAutoFocus", event);
311
+ if (!this.isRightClickOutsideRef)
312
+ this.rootContext.triggerElement.value?.focus();
313
+ },
314
+ onPointerDownOutside: (event) => {
315
+ this.$emit("pointerDownOutside", event);
316
+ const originalEvent = event.detail.originalEvent;
317
+ const ctrlLeftClick = originalEvent.button === 0 && originalEvent.ctrlKey === true;
318
+ const isRightClick = originalEvent.button === 2 || ctrlLeftClick;
319
+ this.isRightClickOutsideRef = isRightClick;
320
+ }
321
+ }, {
322
+ default: () => this.$slots.default?.()
323
+ });
324
+ }
325
+ });
326
+
327
+ const DestylerPopoverContentNonModal = defineComponent({
328
+ name: "DestylerPopoverContentNonModal",
329
+ props: destylerPopoverContentImplProps,
330
+ emits: destylerPopoverContentImplEmits,
331
+ setup(props, { emit }) {
332
+ const rootContext = injectPopoverRootContext();
333
+ const hasInteractedOutsideRef = ref(false);
334
+ const hasPointerDownOutsideRef = ref(false);
335
+ const forwarded = useForwardPropsEmits(props, emit);
336
+ return {
337
+ forwarded,
338
+ rootContext,
339
+ hasInteractedOutsideRef,
340
+ hasPointerDownOutsideRef
341
+ };
342
+ },
343
+ render() {
344
+ return h(DestylerPopoverContentImpl, {
345
+ ...this.forwarded,
346
+ trapFocus: false,
347
+ disableOutsidePointerEvents: false,
348
+ onCloseAutoFocus: (event) => {
349
+ this.$emit("closeAutoFocus", event);
350
+ if (!event.defaultPrevented) {
351
+ if (!this.hasInteractedOutsideRef)
352
+ this.rootContext.triggerElement.value?.focus();
353
+ event.preventDefault();
354
+ }
355
+ this.hasInteractedOutsideRef = false;
356
+ this.hasPointerDownOutsideRef = false;
357
+ },
358
+ onInteractOutside: async (event) => {
359
+ this.$emit("interactOutside", event);
360
+ if (!event.defaultPrevented) {
361
+ this.hasInteractedOutsideRef = true;
362
+ if (event.detail.originalEvent.type === "pointerdown")
363
+ this.hasPointerDownOutsideRef = true;
364
+ }
365
+ const target = event.target;
366
+ const targetIsTrigger = this.rootContext.triggerElement.value?.contains(target);
367
+ if (targetIsTrigger)
368
+ event.preventDefault();
369
+ if (event.detail.originalEvent.type === "focusin" && this.hasPointerDownOutsideRef)
370
+ event.preventDefault();
371
+ }
372
+ }, {
373
+ default: () => this.$slots.default?.()
374
+ });
375
+ }
376
+ });
377
+
378
+ const destylerPopoverContentProps = {
379
+ ...destylerPopoverContentImplProps,
380
+ forceMount: {
381
+ type: Boolean,
382
+ required: false,
383
+ default: false
384
+ }
385
+ };
386
+ const destylerPopoverContentEmits = [...destylerPopoverContentImplEmits];
387
+ const DestylerPopoverContent = defineComponent({
388
+ name: "DestylerPopoverContent",
389
+ props: destylerPopoverContentProps,
390
+ emits: destylerPopoverContentEmits,
391
+ setup(props, { emit }) {
392
+ const rootContext = injectPopoverRootContext();
393
+ const forwarded = useForwardPropsEmits(props, emit);
394
+ return {
395
+ rootContext,
396
+ forwarded
397
+ };
398
+ },
399
+ render() {
400
+ const useVShow = this.rootContext.modal.value;
401
+ return h(DestylerPresence, {
402
+ present: this.forceMount || this.rootContext.open.value
403
+ }, useVShow ? h(DestylerPopoverContentModal, {
404
+ ...this.forwarded
405
+ }, {
406
+ default: () => this.$slots.default?.()
407
+ }) : h(DestylerPopoverContentNonModal, {
408
+ ...this.forwarded
409
+ }, {
410
+ default: () => this.$slots.default?.()
411
+ }));
412
+ }
413
+ });
414
+
415
+ const destylerPopoverPortalProps = {
416
+ to: {
417
+ type: [String, Object],
418
+ required: false,
419
+ default: "body"
420
+ },
421
+ disabled: {
422
+ type: Boolean,
423
+ required: false,
424
+ default: false
425
+ },
426
+ forceMount: {
427
+ type: Boolean,
428
+ required: false,
429
+ default: false
430
+ }
431
+ };
432
+ const DestylerPopoverPortal = defineComponent({
433
+ name: "DestylerPopoverPortal",
434
+ props: destylerPopoverPortalProps,
435
+ render() {
436
+ return h(DestylerTeleport, mergeProps(this.$props), {
437
+ default: () => this.$slots.default?.()
438
+ });
439
+ }
440
+ });
441
+
442
+ const destylerPopoverTriggerProps = {
443
+ asChild: {
444
+ type: Boolean,
445
+ required: false,
446
+ default: false
447
+ },
448
+ as: {
449
+ type: [String, Object],
450
+ required: false,
451
+ default: "button"
452
+ }
453
+ };
454
+ const DestylerPopoverTrigger = defineComponent({
455
+ name: "DestylerPopoverTrigger",
456
+ props: destylerPopoverTriggerProps,
457
+ setup() {
458
+ const rootContext = injectPopoverRootContext();
459
+ const { forwardRef, currentElement: triggerElement } = useForwardExpose();
460
+ onMounted(() => {
461
+ rootContext.triggerElement.value = triggerElement.value;
462
+ });
463
+ return {
464
+ rootContext,
465
+ forwardRef
466
+ };
467
+ },
468
+ render() {
469
+ return h(this.rootContext.hasCustomAnchor.value ? DestylerPrimitive : DestylerPopperAnchor, {
470
+ asChild: true
471
+ }, h(DestylerPrimitive, {
472
+ "ref": (el) => this.forwardRef(el),
473
+ "type": this.$props.as === "button" ? "button" : void 0,
474
+ "as": this.$props.as,
475
+ "aria-haspopup": "dialog",
476
+ "asChild": this.$props.asChild,
477
+ "aria-expanded": this.rootContext.open.value,
478
+ "aria-controls": this.rootContext.contentId,
479
+ "data-state": this.rootContext.open.value ? "open" : "closed",
480
+ "onClick": () => {
481
+ this.rootContext.onOpenToggle();
482
+ }
483
+ }, {
484
+ default: () => this.$slots.default?.()
485
+ }));
486
+ }
487
+ });
488
+
489
+ export { DestylerPopoverArrow as D, DestylerPopoverClose as a, DestylerPopoverContent as b, DestylerPopoverContentImpl as c, DestylerPopoverContentModal as d, DestylerPopoverContentNonModal as e, DestylerPopoverPortal as f, DestylerPopoverRoot as g, DestylerPopoverTrigger as h, injectPopoverRootContext as i };