@greypan/web-ui 12.0.0 → 12.1.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.
- package/README.CN.md +2 -0
- package/README.md +2 -0
- package/dist/assets/menu-portal.js +1 -1
- package/dist/assets/menu-portal.js.map +1 -1
- package/dist/assets/toast-containers.js +1 -1
- package/dist/assets/toast-containers.js.map +1 -1
- package/dist/components/autocomplete/index.d.ts +5 -0
- package/dist/components/autocomplete/index.d.ts.map +1 -1
- package/dist/components/autocomplete/index.js +17 -1
- package/dist/components/autocomplete/index.js.map +1 -1
- package/dist/components/autocomplete/style.js +1 -1
- package/dist/components/autocomplete/style.js.map +1 -1
- package/dist/components/back-top/style.js +1 -1
- package/dist/components/back-top/style.js.map +1 -1
- package/dist/components/button-group/style.js +1 -1
- package/dist/components/button-group/style.js.map +1 -1
- package/dist/components/collapse/index.d.ts +2 -2
- package/dist/components/collapse/index.js.map +1 -1
- package/dist/components/collapse/style.js.map +1 -1
- package/dist/components/dialog/index.d.ts +5 -1
- package/dist/components/dialog/index.d.ts.map +1 -1
- package/dist/components/dialog/index.js +16 -4
- package/dist/components/dialog/index.js.map +1 -1
- package/dist/components/dialog/style.js +1 -1
- package/dist/components/dialog/style.js.map +1 -1
- package/dist/components/drawer/index.js.map +1 -1
- package/dist/components/drawer/style.js.map +1 -1
- package/dist/components/dropdown/index.js +1 -1
- package/dist/components/icon/index.d.ts +1 -1
- package/dist/components/icon/index.d.ts.map +1 -1
- package/dist/components/index.d.ts +3 -2
- package/dist/components/index.d.ts.map +1 -1
- package/dist/components/index.js +2 -1
- package/dist/components/layout/index.d.ts +8 -0
- package/dist/components/layout/index.d.ts.map +1 -1
- package/dist/components/layout/index.js +23 -13
- package/dist/components/layout/index.js.map +1 -1
- package/dist/components/layout/style.js +1 -1
- package/dist/components/layout/style.js.map +1 -1
- package/dist/components/popover/index.js +1 -1
- package/dist/components/popover/style.js +1 -1
- package/dist/components/popover/style.js.map +1 -1
- package/dist/components/progress/index.d.ts +30 -0
- package/dist/components/progress/index.d.ts.map +1 -0
- package/dist/components/progress/index.js +103 -0
- package/dist/components/progress/index.js.map +1 -0
- package/dist/components/progress/style.js +5 -0
- package/dist/components/progress/style.js.map +1 -0
- package/dist/components/segmented-trigger/index.d.ts +2 -0
- package/dist/components/segmented-trigger/index.d.ts.map +1 -1
- package/dist/components/segmented-trigger/index.js +7 -0
- package/dist/components/segmented-trigger/index.js.map +1 -1
- package/dist/components/select/index.d.ts +13 -0
- package/dist/components/select/index.d.ts.map +1 -1
- package/dist/components/select/index.js +41 -3
- package/dist/components/select/index.js.map +1 -1
- package/dist/components/select/style.js +1 -1
- package/dist/components/select/style.js.map +1 -1
- package/dist/components/spinner/index.d.ts +0 -3
- package/dist/components/spinner/index.d.ts.map +1 -1
- package/dist/components/spinner/index.js +5 -20
- package/dist/components/spinner/index.js.map +1 -1
- package/dist/components/spinner/style.js +1 -1
- package/dist/components/spinner/style.js.map +1 -1
- package/dist/components/theme/style.js +1 -1
- package/dist/components/theme/style.js.map +1 -1
- package/dist/components/tooltip/index.js +1 -1
- package/dist/components/tooltip/style.js +1 -1
- package/dist/components/tooltip/style.js.map +1 -1
- package/dist/icons/generated/ant-design-sync-outlined.d.ts +7 -0
- package/dist/icons/generated/ant-design-sync-outlined.d.ts.map +1 -0
- package/dist/icons/generated/ant-design-sync-outlined.js +9 -0
- package/dist/icons/generated/ant-design-sync-outlined.js.map +1 -0
- package/dist/icons/generated/ic-baseline-phonelink.d.ts +7 -0
- package/dist/icons/generated/ic-baseline-phonelink.d.ts.map +1 -0
- package/dist/icons/generated/ic-baseline-phonelink.js +9 -0
- package/dist/icons/generated/ic-baseline-phonelink.js.map +1 -0
- package/dist/icons/generated/ic-outline-motion-photos-off.d.ts +7 -0
- package/dist/icons/generated/ic-outline-motion-photos-off.d.ts.map +1 -0
- package/dist/icons/generated/ic-outline-motion-photos-off.js +9 -0
- package/dist/icons/generated/ic-outline-motion-photos-off.js.map +1 -0
- package/dist/icons/generated/ic-outline-motion-photos-on.d.ts +7 -0
- package/dist/icons/generated/ic-outline-motion-photos-on.d.ts.map +1 -0
- package/dist/icons/generated/ic-outline-motion-photos-on.js +9 -0
- package/dist/icons/generated/ic-outline-motion-photos-on.js.map +1 -0
- package/dist/icons/generated/ic-round-menu-open.d.ts +7 -0
- package/dist/icons/generated/ic-round-menu-open.d.ts.map +1 -0
- package/dist/icons/generated/ic-round-menu-open.js +9 -0
- package/dist/icons/generated/ic-round-menu-open.js.map +1 -0
- package/dist/icons/generated/lucide-accessibility.d.ts +7 -0
- package/dist/icons/generated/lucide-accessibility.d.ts.map +1 -0
- package/dist/icons/generated/lucide-accessibility.js +9 -0
- package/dist/icons/generated/lucide-accessibility.js.map +1 -0
- package/dist/icons/generated/lucide-boxes.d.ts +7 -0
- package/dist/icons/generated/lucide-boxes.d.ts.map +1 -0
- package/dist/icons/generated/lucide-boxes.js +9 -0
- package/dist/icons/generated/lucide-boxes.js.map +1 -0
- package/dist/icons/generated/lucide-contrast.d.ts +7 -0
- package/dist/icons/generated/lucide-contrast.d.ts.map +1 -0
- package/dist/icons/generated/lucide-contrast.js +9 -0
- package/dist/icons/generated/lucide-contrast.js.map +1 -0
- package/dist/icons/generated/lucide-keyboard.d.ts +7 -0
- package/dist/icons/generated/lucide-keyboard.d.ts.map +1 -0
- package/dist/icons/generated/lucide-keyboard.js +9 -0
- package/dist/icons/generated/lucide-keyboard.js.map +1 -0
- package/dist/icons/generated/lucide-languages.d.ts +7 -0
- package/dist/icons/generated/lucide-languages.d.ts.map +1 -0
- package/dist/icons/generated/lucide-languages.js +9 -0
- package/dist/icons/generated/lucide-languages.js.map +1 -0
- package/dist/icons/generated/lucide-list.d.ts +7 -0
- package/dist/icons/generated/lucide-list.d.ts.map +1 -0
- package/dist/icons/generated/lucide-list.js +9 -0
- package/dist/icons/generated/lucide-list.js.map +1 -0
- package/dist/icons/generated/lucide-moon.d.ts +7 -0
- package/dist/icons/generated/lucide-moon.d.ts.map +1 -0
- package/dist/icons/generated/lucide-moon.js +9 -0
- package/dist/icons/generated/lucide-moon.js.map +1 -0
- package/dist/icons/generated/lucide-sparkles.d.ts +7 -0
- package/dist/icons/generated/lucide-sparkles.d.ts.map +1 -0
- package/dist/icons/generated/lucide-sparkles.js +9 -0
- package/dist/icons/generated/lucide-sparkles.js.map +1 -0
- package/dist/icons/generated/lucide-sun.d.ts +7 -0
- package/dist/icons/generated/lucide-sun.d.ts.map +1 -0
- package/dist/icons/generated/lucide-sun.js +9 -0
- package/dist/icons/generated/lucide-sun.js.map +1 -0
- package/dist/icons/generated/tabler-brand-typescript.d.ts +7 -0
- package/dist/icons/generated/tabler-brand-typescript.d.ts.map +1 -0
- package/dist/icons/generated/tabler-brand-typescript.js +9 -0
- package/dist/icons/generated/tabler-brand-typescript.js.map +1 -0
- package/dist/icons/index.d.ts +87 -72
- package/dist/icons/index.js +16 -1
- package/dist/shared/group-management/index.js.map +1 -1
- package/dist/shared/locale/builtin-labels.js +2 -1
- package/dist/shared/locale/builtin-labels.js.map +1 -1
- package/dist/shared/open-state/index.js.map +1 -1
- package/dist/shared/overlay/overlay.js.map +1 -1
- package/package.json +4 -2
package/dist/icons/index.d.ts
CHANGED
|
@@ -1,75 +1,90 @@
|
|
|
1
1
|
import _default$2 from "./generated/andrsrxn-inbox.js";
|
|
2
|
-
import _default$
|
|
3
|
-
import _default$
|
|
4
|
-
import _default$
|
|
5
|
-
import _default$
|
|
6
|
-
import _default$
|
|
7
|
-
import _default$
|
|
8
|
-
import _default$
|
|
9
|
-
import _default$
|
|
10
|
-
import _default$
|
|
11
|
-
import _default$
|
|
12
|
-
import _default$
|
|
13
|
-
import _default$68 from "./generated/lucide-
|
|
14
|
-
import _default$
|
|
15
|
-
import _default$
|
|
16
|
-
import _default$
|
|
17
|
-
import _default$
|
|
18
|
-
import _default$
|
|
19
|
-
import _default$
|
|
20
|
-
import _default$
|
|
21
|
-
import _default$
|
|
22
|
-
import _default$
|
|
23
|
-
import _default$
|
|
24
|
-
import _default$
|
|
25
|
-
import _default$
|
|
26
|
-
import _default$
|
|
27
|
-
import _default$
|
|
28
|
-
import _default$
|
|
29
|
-
import _default$
|
|
30
|
-
import _default$
|
|
31
|
-
import _default$
|
|
32
|
-
import _default$
|
|
33
|
-
import _default$
|
|
34
|
-
import _default$
|
|
35
|
-
import _default$
|
|
36
|
-
import _default$
|
|
37
|
-
import _default$
|
|
38
|
-
import _default$
|
|
39
|
-
import _default$
|
|
40
|
-
import _default$
|
|
41
|
-
import _default$
|
|
42
|
-
import _default$
|
|
43
|
-
import _default$
|
|
44
|
-
import _default$
|
|
45
|
-
import _default$
|
|
46
|
-
import _default$
|
|
47
|
-
import _default$
|
|
48
|
-
import _default$
|
|
49
|
-
import _default$
|
|
50
|
-
import _default$
|
|
51
|
-
import _default$
|
|
52
|
-
import _default$61 from "./generated/lucide-
|
|
53
|
-
import _default$
|
|
54
|
-
import _default$
|
|
55
|
-
import _default$
|
|
56
|
-
import _default$
|
|
57
|
-
import _default$
|
|
58
|
-
import _default$
|
|
59
|
-
import _default$
|
|
60
|
-
import _default$
|
|
61
|
-
import _default$
|
|
62
|
-
import _default$
|
|
63
|
-
import _default$
|
|
64
|
-
import _default$
|
|
65
|
-
import _default$
|
|
66
|
-
import _default$
|
|
67
|
-
import _default$
|
|
68
|
-
import _default$
|
|
2
|
+
import _default$45 from "./generated/lucide-inbox.js";
|
|
3
|
+
import _default$54 from "./generated/lucide-loader-circle.js";
|
|
4
|
+
import _default$18 from "./generated/lucide-arrow-up-to-line.js";
|
|
5
|
+
import _default$17 from "./generated/lucide-arrow-down-to-line.js";
|
|
6
|
+
import _default$23 from "./generated/lucide-chevron-left.js";
|
|
7
|
+
import _default$24 from "./generated/lucide-chevron-right.js";
|
|
8
|
+
import _default$25 from "./generated/lucide-chevron-up.js";
|
|
9
|
+
import _default$22 from "./generated/lucide-chevron-down.js";
|
|
10
|
+
import _default$63 from "./generated/lucide-plus.js";
|
|
11
|
+
import _default$56 from "./generated/lucide-minus.js";
|
|
12
|
+
import _default$57 from "./generated/lucide-moon.js";
|
|
13
|
+
import _default$68 from "./generated/lucide-search.js";
|
|
14
|
+
import _default$82 from "./generated/lucide-x.js";
|
|
15
|
+
import _default$36 from "./generated/lucide-file.js";
|
|
16
|
+
import _default$39 from "./generated/lucide-folder.js";
|
|
17
|
+
import _default$31 from "./generated/lucide-copy.js";
|
|
18
|
+
import _default$28 from "./generated/lucide-clipboard-paste.js";
|
|
19
|
+
import _default$76 from "./generated/lucide-trash-2.js";
|
|
20
|
+
import _default$64 from "./generated/lucide-printer.js";
|
|
21
|
+
import _default$69 from "./generated/lucide-settings.js";
|
|
22
|
+
import _default$32 from "./generated/lucide-download.js";
|
|
23
|
+
import _default$79 from "./generated/lucide-upload.js";
|
|
24
|
+
import _default$78 from "./generated/lucide-undo-2.js";
|
|
25
|
+
import _default$65 from "./generated/lucide-redo-2.js";
|
|
26
|
+
import _default$67 from "./generated/lucide-scissors.js";
|
|
27
|
+
import _default$15 from "./generated/jam-close-circle-f.js";
|
|
28
|
+
import _default$21 from "./generated/lucide-check.js";
|
|
29
|
+
import _default$46 from "./generated/lucide-info.js";
|
|
30
|
+
import _default$77 from "./generated/lucide-triangle-alert.js";
|
|
31
|
+
import _default$26 from "./generated/lucide-circle-alert.js";
|
|
32
|
+
import _default$9 from "./generated/heroicons-check-16-solid.js";
|
|
33
|
+
import _default$80 from "./generated/lucide-user.js";
|
|
34
|
+
import _default$10 from "./generated/heroicons-x-mark-16-solid.js";
|
|
35
|
+
import _default$72 from "./generated/lucide-star.js";
|
|
36
|
+
import _default$73 from "./generated/lucide-sun.js";
|
|
37
|
+
import _default$43 from "./generated/lucide-heart.js";
|
|
38
|
+
import _default$19 from "./generated/lucide-bell.js";
|
|
39
|
+
import _default$55 from "./generated/lucide-mail.js";
|
|
40
|
+
import _default$44 from "./generated/lucide-image.js";
|
|
41
|
+
import _default$41 from "./generated/lucide-globe.js";
|
|
42
|
+
import _default$85 from "./generated/radix-icons-panel-left-minimized.js";
|
|
43
|
+
import _default$84 from "./generated/ooui-close.js";
|
|
44
|
+
import _default$34 from "./generated/lucide-external-link.js";
|
|
45
|
+
import _default$37 from "./generated/lucide-file-text.js";
|
|
46
|
+
import _default$38 from "./generated/lucide-film.js";
|
|
47
|
+
import _default$40 from "./generated/lucide-folder-open.js";
|
|
48
|
+
import _default$49 from "./generated/lucide-layout-grid.js";
|
|
49
|
+
import _default$51 from "./generated/lucide-list.js";
|
|
50
|
+
import _default$58 from "./generated/lucide-music.js";
|
|
51
|
+
import _default$59 from "./generated/lucide-package.js";
|
|
52
|
+
import _default$61 from "./generated/lucide-pencil.js";
|
|
53
|
+
import _default$66 from "./generated/lucide-refresh-cw.js";
|
|
54
|
+
import _default$74 from "./generated/lucide-tag.js";
|
|
55
|
+
import _default$75 from "./generated/lucide-tags.js";
|
|
56
|
+
import _default$81 from "./generated/lucide-wrench.js";
|
|
57
|
+
import _default$70 from "./generated/lucide-sliders-horizontal.js";
|
|
58
|
+
import _default$50 from "./generated/lucide-link.js";
|
|
59
|
+
import _default$35 from "./generated/lucide-eye.js";
|
|
60
|
+
import _default$27 from "./generated/lucide-clapperboard.js";
|
|
61
|
+
import _default$42 from "./generated/lucide-headphones.js";
|
|
62
|
+
import _default$60 from "./generated/lucide-pen-line.js";
|
|
63
|
+
import _default$62 from "./generated/lucide-play.js";
|
|
64
|
+
import _default$52 from "./generated/lucide-list-filter.js";
|
|
65
|
+
import _default$88 from "./generated/tabler-sort-ascending-letters.js";
|
|
66
|
+
import _default$29 from "./generated/lucide-code.js";
|
|
67
|
+
import _default$33 from "./generated/lucide-ellipsis-vertical.js";
|
|
68
|
+
import _default$7 from "./generated/heroicons-bars-arrow-down-16-solid.js";
|
|
69
|
+
import _default$8 from "./generated/heroicons-bars-arrow-up-16-solid.js";
|
|
70
|
+
import _default$53 from "./generated/lucide-list-restart.js";
|
|
71
|
+
import _default$86 from "./generated/radix-icons-reset.js";
|
|
69
72
|
import _default from "./generated/akar-icons-check.js";
|
|
70
|
-
import _default$
|
|
71
|
-
import _default$
|
|
73
|
+
import _default$4 from "./generated/bi-check.js";
|
|
74
|
+
import _default$5 from "./generated/bi-check-lg.js";
|
|
72
75
|
import _default$1 from "./generated/akar-icons-circle-check.js";
|
|
73
|
-
import _default$
|
|
74
|
-
import _default$
|
|
75
|
-
|
|
76
|
+
import _default$6 from "./generated/fluent-tag-search-24-regular.js";
|
|
77
|
+
import _default$83 from "./generated/mdi-tag-search-outline.js";
|
|
78
|
+
import _default$16 from "./generated/lucide-accessibility.js";
|
|
79
|
+
import _default$20 from "./generated/lucide-boxes.js";
|
|
80
|
+
import _default$47 from "./generated/lucide-keyboard.js";
|
|
81
|
+
import _default$71 from "./generated/lucide-sparkles.js";
|
|
82
|
+
import _default$87 from "./generated/tabler-brand-typescript.js";
|
|
83
|
+
import _default$13 from "./generated/ic-outline-motion-photos-on.js";
|
|
84
|
+
import _default$12 from "./generated/ic-outline-motion-photos-off.js";
|
|
85
|
+
import _default$30 from "./generated/lucide-contrast.js";
|
|
86
|
+
import _default$48 from "./generated/lucide-languages.js";
|
|
87
|
+
import _default$3 from "./generated/ant-design-sync-outlined.js";
|
|
88
|
+
import _default$11 from "./generated/ic-baseline-phonelink.js";
|
|
89
|
+
import _default$14 from "./generated/ic-round-menu-open.js";
|
|
90
|
+
export { _default as akarIconsCheck, _default$1 as akarIconsCircleCheck, _default$2 as andrsrxnInbox, _default$3 as antDesignSyncOutlined, _default$4 as biCheck, _default$5 as biCheckLg, _default$6 as fluentTagSearch24Regular, _default$7 as heroiconsBarsArrowDown16Solid, _default$8 as heroiconsBarsArrowUp16Solid, _default$9 as heroiconsCheck16Solid, _default$10 as heroiconsXMark16Solid, _default$11 as icBaselinePhonelink, _default$12 as icOutlineMotionPhotosOff, _default$13 as icOutlineMotionPhotosOn, _default$14 as icRoundMenuOpen, _default$15 as jamCloseCircleF, _default$16 as lucideAccessibility, _default$17 as lucideArrowDownToLine, _default$18 as lucideArrowUpToLine, _default$19 as lucideBell, _default$20 as lucideBoxes, _default$21 as lucideCheck, _default$22 as lucideChevronDown, _default$23 as lucideChevronLeft, _default$24 as lucideChevronRight, _default$25 as lucideChevronUp, _default$26 as lucideCircleAlert, _default$27 as lucideClapperboard, _default$28 as lucideClipboardPaste, _default$29 as lucideCode, _default$30 as lucideContrast, _default$31 as lucideCopy, _default$32 as lucideDownload, _default$33 as lucideEllipsisVertical, _default$34 as lucideExternalLink, _default$35 as lucideEye, _default$36 as lucideFile, _default$37 as lucideFileText, _default$38 as lucideFilm, _default$39 as lucideFolder, _default$40 as lucideFolderOpen, _default$41 as lucideGlobe, _default$42 as lucideHeadphones, _default$43 as lucideHeart, _default$44 as lucideImage, _default$45 as lucideInbox, _default$46 as lucideInfo, _default$47 as lucideKeyboard, _default$48 as lucideLanguages, _default$49 as lucideLayoutGrid, _default$50 as lucideLink, _default$51 as lucideList, _default$52 as lucideListFilter, _default$53 as lucideListRestart, _default$54 as lucideLoaderCircle, _default$55 as lucideMail, _default$56 as lucideMinus, _default$57 as lucideMoon, _default$58 as lucideMusic, _default$59 as lucidePackage, _default$60 as lucidePenLine, _default$61 as lucidePencil, _default$62 as lucidePlay, _default$63 as lucidePlus, _default$64 as lucidePrinter, _default$65 as lucideRedo2, _default$66 as lucideRefreshCw, _default$67 as lucideScissors, _default$68 as lucideSearch, _default$69 as lucideSettings, _default$70 as lucideSlidersHorizontal, _default$71 as lucideSparkles, _default$72 as lucideStar, _default$73 as lucideSun, _default$74 as lucideTag, _default$75 as lucideTags, _default$76 as lucideTrash2, _default$77 as lucideTriangleAlert, _default$78 as lucideUndo2, _default$79 as lucideUpload, _default$80 as lucideUser, _default$81 as lucideWrench, _default$82 as lucideX, _default$83 as mdiTagSearchOutline, _default$84 as oouiClose, _default$85 as radixIconsPanelLeftMinimized, _default$86 as radixIconsReset, _default$87 as tablerBrandTypescript, _default$88 as tablerSortAscendingLetters };
|
package/dist/icons/index.js
CHANGED
|
@@ -9,6 +9,7 @@ import lucide_chevron_up_default from "./generated/lucide-chevron-up.js";
|
|
|
9
9
|
import lucide_chevron_down_default from "./generated/lucide-chevron-down.js";
|
|
10
10
|
import lucide_plus_default from "./generated/lucide-plus.js";
|
|
11
11
|
import lucide_minus_default from "./generated/lucide-minus.js";
|
|
12
|
+
import lucide_moon_default from "./generated/lucide-moon.js";
|
|
12
13
|
import lucide_search_default from "./generated/lucide-search.js";
|
|
13
14
|
import lucide_x_default from "./generated/lucide-x.js";
|
|
14
15
|
import lucide_file_default from "./generated/lucide-file.js";
|
|
@@ -32,6 +33,7 @@ import heroicons_check_16_solid_default from "./generated/heroicons-check-16-sol
|
|
|
32
33
|
import lucide_user_default from "./generated/lucide-user.js";
|
|
33
34
|
import heroicons_x_mark_16_solid_default from "./generated/heroicons-x-mark-16-solid.js";
|
|
34
35
|
import lucide_star_default from "./generated/lucide-star.js";
|
|
36
|
+
import lucide_sun_default from "./generated/lucide-sun.js";
|
|
35
37
|
import lucide_heart_default from "./generated/lucide-heart.js";
|
|
36
38
|
import lucide_bell_default from "./generated/lucide-bell.js";
|
|
37
39
|
import lucide_mail_default from "./generated/lucide-mail.js";
|
|
@@ -44,6 +46,7 @@ import lucide_file_text_default from "./generated/lucide-file-text.js";
|
|
|
44
46
|
import lucide_film_default from "./generated/lucide-film.js";
|
|
45
47
|
import lucide_folder_open_default from "./generated/lucide-folder-open.js";
|
|
46
48
|
import lucide_layout_grid_default from "./generated/lucide-layout-grid.js";
|
|
49
|
+
import lucide_list_default from "./generated/lucide-list.js";
|
|
47
50
|
import lucide_music_default from "./generated/lucide-music.js";
|
|
48
51
|
import lucide_package_default from "./generated/lucide-package.js";
|
|
49
52
|
import lucide_pencil_default from "./generated/lucide-pencil.js";
|
|
@@ -72,4 +75,16 @@ import bi_check_lg_default from "./generated/bi-check-lg.js";
|
|
|
72
75
|
import akar_icons_circle_check_default from "./generated/akar-icons-circle-check.js";
|
|
73
76
|
import fluent_tag_search_24_regular_default from "./generated/fluent-tag-search-24-regular.js";
|
|
74
77
|
import mdi_tag_search_outline_default from "./generated/mdi-tag-search-outline.js";
|
|
75
|
-
|
|
78
|
+
import lucide_accessibility_default from "./generated/lucide-accessibility.js";
|
|
79
|
+
import lucide_boxes_default from "./generated/lucide-boxes.js";
|
|
80
|
+
import lucide_keyboard_default from "./generated/lucide-keyboard.js";
|
|
81
|
+
import lucide_sparkles_default from "./generated/lucide-sparkles.js";
|
|
82
|
+
import tabler_brand_typescript_default from "./generated/tabler-brand-typescript.js";
|
|
83
|
+
import ic_outline_motion_photos_on_default from "./generated/ic-outline-motion-photos-on.js";
|
|
84
|
+
import ic_outline_motion_photos_off_default from "./generated/ic-outline-motion-photos-off.js";
|
|
85
|
+
import lucide_contrast_default from "./generated/lucide-contrast.js";
|
|
86
|
+
import lucide_languages_default from "./generated/lucide-languages.js";
|
|
87
|
+
import ant_design_sync_outlined_default from "./generated/ant-design-sync-outlined.js";
|
|
88
|
+
import ic_baseline_phonelink_default from "./generated/ic-baseline-phonelink.js";
|
|
89
|
+
import ic_round_menu_open_default from "./generated/ic-round-menu-open.js";
|
|
90
|
+
export { akar_icons_check_default as akarIconsCheck, akar_icons_circle_check_default as akarIconsCircleCheck, andrsrxn_inbox_default as andrsrxnInbox, ant_design_sync_outlined_default as antDesignSyncOutlined, bi_check_default as biCheck, bi_check_lg_default as biCheckLg, fluent_tag_search_24_regular_default as fluentTagSearch24Regular, heroicons_bars_arrow_down_16_solid_default as heroiconsBarsArrowDown16Solid, heroicons_bars_arrow_up_16_solid_default as heroiconsBarsArrowUp16Solid, heroicons_check_16_solid_default as heroiconsCheck16Solid, heroicons_x_mark_16_solid_default as heroiconsXMark16Solid, ic_baseline_phonelink_default as icBaselinePhonelink, ic_outline_motion_photos_off_default as icOutlineMotionPhotosOff, ic_outline_motion_photos_on_default as icOutlineMotionPhotosOn, ic_round_menu_open_default as icRoundMenuOpen, jam_close_circle_f_default as jamCloseCircleF, lucide_accessibility_default as lucideAccessibility, lucide_arrow_down_to_line_default as lucideArrowDownToLine, lucide_arrow_up_to_line_default as lucideArrowUpToLine, lucide_bell_default as lucideBell, lucide_boxes_default as lucideBoxes, lucide_check_default as lucideCheck, lucide_chevron_down_default as lucideChevronDown, lucide_chevron_left_default as lucideChevronLeft, lucide_chevron_right_default as lucideChevronRight, lucide_chevron_up_default as lucideChevronUp, lucide_circle_alert_default as lucideCircleAlert, lucide_clapperboard_default as lucideClapperboard, lucide_clipboard_paste_default as lucideClipboardPaste, lucide_code_default as lucideCode, lucide_contrast_default as lucideContrast, lucide_copy_default as lucideCopy, lucide_download_default as lucideDownload, lucide_ellipsis_vertical_default as lucideEllipsisVertical, lucide_external_link_default as lucideExternalLink, lucide_eye_default as lucideEye, lucide_file_default as lucideFile, lucide_file_text_default as lucideFileText, lucide_film_default as lucideFilm, lucide_folder_default as lucideFolder, lucide_folder_open_default as lucideFolderOpen, lucide_globe_default as lucideGlobe, lucide_headphones_default as lucideHeadphones, lucide_heart_default as lucideHeart, lucide_image_default as lucideImage, lucide_inbox_default as lucideInbox, lucide_info_default as lucideInfo, lucide_keyboard_default as lucideKeyboard, lucide_languages_default as lucideLanguages, lucide_layout_grid_default as lucideLayoutGrid, lucide_link_default as lucideLink, lucide_list_default as lucideList, lucide_list_filter_default as lucideListFilter, lucide_list_restart_default as lucideListRestart, lucide_loader_circle_default as lucideLoaderCircle, lucide_mail_default as lucideMail, lucide_minus_default as lucideMinus, lucide_moon_default as lucideMoon, lucide_music_default as lucideMusic, lucide_package_default as lucidePackage, lucide_pen_line_default as lucidePenLine, lucide_pencil_default as lucidePencil, lucide_play_default as lucidePlay, lucide_plus_default as lucidePlus, lucide_printer_default as lucidePrinter, lucide_redo_2_default as lucideRedo2, lucide_refresh_cw_default as lucideRefreshCw, lucide_scissors_default as lucideScissors, lucide_search_default as lucideSearch, lucide_settings_default as lucideSettings, lucide_sliders_horizontal_default as lucideSlidersHorizontal, lucide_sparkles_default as lucideSparkles, lucide_star_default as lucideStar, lucide_sun_default as lucideSun, lucide_tag_default as lucideTag, lucide_tags_default as lucideTags, lucide_trash_2_default as lucideTrash2, lucide_triangle_alert_default as lucideTriangleAlert, lucide_undo_2_default as lucideUndo2, lucide_upload_default as lucideUpload, lucide_user_default as lucideUser, lucide_wrench_default as lucideWrench, lucide_x_default as lucideX, mdi_tag_search_outline_default as mdiTagSearchOutline, ooui_close_default as oouiClose, radix_icons_panel_left_minimized_default as radixIconsPanelLeftMinimized, radix_icons_reset_default as radixIconsReset, tabler_brand_typescript_default as tablerBrandTypescript, tabler_sort_ascending_letters_default as tablerSortAscendingLetters };
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","names":[],"sources":["../../../src/shared/group-management/index.ts"],"sourcesContent":["import { definePlugin } from '@greypan/js-kit'\nimport { ContextConsumer, ContextProvider, createContext, type Context } from '@lit/context'\nimport type { ReactiveController, ReactiveControllerHost } from 'lit'\n\n/*\n * 下行通道基于 @lit/context(ADR-0032):root 上的 ContextProvider 以\n * `ReadonlyMap<HTMLElement, Context>` 为载荷向全子树广播,子项侧\n * ContextConsumer 订阅并按自身元素取条目。context-request 事件 composed,\n * 可穿过中间 shadow 边界;custom element 升级顺序保证祖先先于后代升级,\n * provider 总是先于子项请求就绪。成员追踪(querySelectorAll +\n * MutationObserver/slotchange)、点击归因与 setItemSelected 上行写回\n * 不在下行通道内,仍由 GroupController 驱动。\n */\n\nexport interface SelectionGroupContext {\n readonly disabled: boolean\n readonly rovingTabStop: boolean\n readonly tabStop?: boolean\n}\n\nexport interface ButtonGroupContext {\n readonly direction: 'horizontal' | 'vertical'\n readonly isLast: boolean\n}\n\n// 载荷类型仅编译期品牌化;按载荷形状分两个 key,避免异构树串扰。\n// createContext 泛型顺序为 <ValueType, K>。\nconst SELECTION_GROUP_CONTEXT = createContext<ReadonlyMap<HTMLElement, SelectionGroupContext>, symbol>(\n Symbol('web-ui.selection-group-context')\n)\n\nconst BUTTON_GROUP_CONTEXT = createContext<ReadonlyMap<HTMLElement, ButtonGroupContext>, symbol>(\n Symbol('web-ui.button-group-context')\n)\n\n// 两个 key 的运行时形状一致(Map 载荷),泛型插件内部统一按宽松类型驱动。\ntype AnyGroupContext = Context<symbol, ReadonlyMap<HTMLElement, unknown>>\n\nconst SELECTION_GROUP_CONTEXT_LOOSE = SELECTION_GROUP_CONTEXT as unknown as AnyGroupContext\nconst BUTTON_GROUP_CONTEXT_LOOSE = BUTTON_GROUP_CONTEXT as unknown as AnyGroupContext\n\nexport const selectionGroupContextKey: AnyGroupContext = SELECTION_GROUP_CONTEXT_LOOSE\nexport const buttonGroupContextKey: AnyGroupContext = BUTTON_GROUP_CONTEXT_LOOSE\nexport const GROUP_MEMBER_DISABLED_CHANGE_EVENT = 'wui-group-member-disabled-change'\n\ninterface GroupControllerHost extends HTMLElement, ReactiveControllerHost {\n readonly renderRoot: Element | DocumentFragment\n}\n\n/**\n * 创建受管理 group 的子项侧能力:订阅最近 provider 的 context 载荷并提取\n * 自身条目。在 `make()` 时完成注册,组件无需再编写 constructor 样板。\n */\nexport function defineGroupManaged<Context>(\n item: HTMLElement & ReactiveControllerHost,\n options: {\n /** 与所属根组件使用的 context key 一致。 */\n context: AnyGroupContext\n requestUpdate: () => void\n equals?: (a: Context | undefined, b: Context | undefined) => boolean\n }\n) {\n return definePlugin(() => {\n let context: Context | undefined\n const equals = options.equals ?? Object.is\n\n const consumer = new ContextConsumer(item, {\n context: options.context,\n subscribe: true,\n callback: payload => {\n const next = (payload as ReadonlyMap<HTMLElement, Context> | undefined)?.get(item)\n if (equals(context, next)) return\n context = next\n options.requestUpdate()\n }\n })\n\n /*\n * 离开 group(被移出 provider 子树)时 ContextConsumer 只是静默退订,\n * 不会收到「条目已移除」的通知:显式清空上下文,恢复独立控件语义\n * (如 checkbox 恢复自身表单提交)。跨组移动先断连清空、再重连订阅新组。\n */\n item.addController({\n hostDisconnected() {\n if (equals(context, undefined)) return\n context = undefined\n options.requestUpdate()\n }\n })\n\n return {\n getContext(): Context | undefined {\n return context\n },\n // 供测试或特殊场景确认订阅状态。\n isSubscribed(): boolean {\n return consumer.value !== undefined\n }\n }\n })\n}\n\nexport interface GroupPresentationOptions<Item extends HTMLElement, Context> {\n readonly host: HTMLElement\n /** 与子项 defineGroupManaged 使用的 context key 一致。 */\n readonly context: AnyGroupContext\n readonly getItems: () => readonly Item[]\n readonly getContext: (item: Item, index: number, items: readonly Item[]) => Context\n}\n\n/**\n * 为分组子项注册可逆的展示上下文(@lit/context 下行通道)。不持有公开 DOM\n * 属性;sync() 以新 Map 载荷整体广播,成员变化体现为子项条目消失。\n */\nexport function defineGroupPresentation<Item extends HTMLElement, Context>(\n options: GroupPresentationOptions<Item, Context>\n) {\n return definePlugin(() => {\n const provider = new ContextProvider(options.host, {\n context: options.context,\n initialValue: new Map<HTMLElement, unknown>()\n })\n\n return {\n sync(): boolean {\n const nextItems = options.getItems()\n const payload = new Map<HTMLElement, unknown>()\n nextItems.forEach((item, index) => payload.set(item, options.getContext(item, index, nextItems)))\n // 新 Map 实例保证 Object.is 判定为变更,全量通知订阅者。\n // 每次 hostUpdated 都重播(即使成员/方向未变)是有意形态:每次新建\n // context 对象,但子项 defineGroupManaged 的 equals 门控 requestUpdate\n // (标量字段比较),重播不产生多余渲染;代价是比「仅成员变化才通知」\n // 更频繁的广播事件,换取零状态追踪的简单性(与 GroupController 的\n // 全量 sync 对齐)。\n provider.setValue(payload)\n return true\n },\n disconnect() {\n provider.setValue(new Map())\n }\n }\n })\n}\n\nexport interface GroupLifecycle {\n sync(): boolean\n disconnect(): void\n handleChange?(event: Event): void\n handleKeyDown?(event: KeyboardEvent): void\n}\n\ninterface GroupControllerOptions {\n afterSync?: () => void\n observeAttributes?: readonly string[]\n}\n\n/**\n * 把组生命周期插件接入 Lit,协调规则不落在组件生命周期方法里。\n */\nexport class GroupController implements ReactiveController {\n private connected = false\n private observer: MutationObserver | null = null\n private observedSlots = new Set<HTMLSlotElement>()\n constructor(\n private readonly host: GroupControllerHost,\n private readonly lifecycle: GroupLifecycle,\n private readonly options: GroupControllerOptions = {}\n ) {\n host.addController(this)\n }\n\n hostConnected() {\n this.connected = true\n this.host.addEventListener('change', this.handleChange, true)\n this.host.addEventListener('keydown', this.handleKeyDown, true)\n this.host.addEventListener(GROUP_MEMBER_DISABLED_CHANGE_EVENT, this.handleMemberDisabledChange, true)\n this.observeHost()\n this.observeSlots()\n this.sync()\n }\n\n hostUpdated() {\n this.observeSlots()\n this.sync()\n }\n\n hostDisconnected() {\n this.connected = false\n this.host.removeEventListener('change', this.handleChange, true)\n this.host.removeEventListener('keydown', this.handleKeyDown, true)\n this.host.removeEventListener(GROUP_MEMBER_DISABLED_CHANGE_EVENT, this.handleMemberDisabledChange, true)\n this.disconnectSlots()\n this.disconnectHostObserver()\n this.lifecycle.disconnect()\n }\n\n private readonly handleChange = (event: Event) => {\n this.lifecycle.handleChange?.(event)\n }\n\n private readonly handleKeyDown = (event: KeyboardEvent) => {\n this.lifecycle.handleKeyDown?.(event)\n }\n\n private readonly handleMemberDisabledChange = () => {\n this.sync()\n }\n\n private readonly handleSlotChange = () => {\n if (!this.connected) return\n this.sync()\n }\n\n private readonly handleMutations = () => {\n if (!this.connected) return\n this.sync()\n }\n\n sync() {\n if (!this.lifecycle.sync()) return\n this.options.afterSync?.()\n }\n\n private observeHost() {\n this.disconnectHostObserver()\n // 监听 light DOM 的增删,覆盖 Vue v-if / React && 的 comment 锚点替换与深层包裹\n this.observer = new MutationObserver(this.handleMutations)\n const observerOptions: MutationObserverInit = { childList: true, subtree: true }\n if (this.options.observeAttributes?.length) {\n observerOptions.attributes = true\n observerOptions.attributeFilter = [...this.options.observeAttributes]\n }\n this.observer.observe(this.host, observerOptions)\n }\n\n private disconnectHostObserver() {\n if (this.observer) {\n this.observer.disconnect()\n this.observer = null\n }\n }\n\n private observeSlots() {\n const root = this.host.renderRoot as Element\n const slots = root.querySelectorAll<HTMLSlotElement>('slot')\n for (const slot of slots) {\n if (!this.observedSlots.has(slot)) {\n slot.addEventListener('slotchange', this.handleSlotChange)\n this.observedSlots.add(slot)\n }\n }\n // 清理已移除的 slot(热更新等场景)\n for (const slot of this.observedSlots) {\n if (!root.contains(slot)) {\n slot.removeEventListener('slotchange', this.handleSlotChange)\n this.observedSlots.delete(slot)\n }\n }\n }\n\n private disconnectSlots() {\n for (const slot of this.observedSlots) {\n slot.removeEventListener('slotchange', this.handleSlotChange)\n }\n this.observedSlots.clear()\n }\n}\n\nexport interface GroupCoordinatorOptions<Item extends HTMLElement, Value> {\n readonly host: HTMLElement\n readonly getItems: () => readonly Item[]\n readonly getValue: () => Value\n readonly setValue: (value: Value) => void\n readonly getDisabled: () => boolean\n readonly isItem: (target: EventTarget | null) => target is Item\n readonly isItemSelected: (item: Item, value: Value) => boolean\n readonly isItemTabStop?: (item: Item, items: readonly Item[]) => boolean\n readonly getItemSelected?: (item: Item) => boolean\n readonly getNextValue: (item: Item, value: Value) => Value\n readonly valuesEqual: (a: Value, b: Value) => boolean\n readonly copyValue: (value: Value) => Value\n readonly setItemSelected: (item: Item, selected: boolean) => void\n readonly dispatchValueChange: () => void\n readonly getRovingTabStop?: (item: Item, index: number, items: readonly Item[], value: Value) => boolean\n readonly handleKeyDown?: (event: KeyboardEvent) => void\n /**\n * 交互已发生但值没有变化时的回调(例如单选组成员 value 重复:点击同值成员\n * 不会改变 value,却必须把选中态收到被点击的那一项)。缺省视为无事可做。\n */\n readonly resyncOnUnchangedValue?: (item: Item) => void\n}\n\nconst ENABLED_SELECTION_CONTEXT: SelectionGroupContext = { disabled: false, rovingTabStop: false }\nconst ENABLED_ROVING_SELECTION_CONTEXT: SelectionGroupContext = { disabled: false, rovingTabStop: true }\nconst DISABLED_SELECTION_CONTEXT: SelectionGroupContext = { disabled: true, rovingTabStop: false }\n\nfunction getSelectionContext(disabled: boolean, rovingTabStop: boolean, tabStop?: boolean): SelectionGroupContext {\n const context = disabled\n ? DISABLED_SELECTION_CONTEXT\n : rovingTabStop\n ? ENABLED_ROVING_SELECTION_CONTEXT\n : ENABLED_SELECTION_CONTEXT\n return tabStop === undefined ? context : { ...context, tabStop }\n}\n\n/**\n * 在一个内部插件接口后收敛选中态、继承禁用与受管子项成员关系。\n * 禁用态经 @lit/context 下行广播;选中态上行写回保持直写。\n */\nexport function defineGroupCoordinator<Item extends HTMLElement, Value>(options: GroupCoordinatorOptions<Item, Value>) {\n return definePlugin(() => {\n const provider = new ContextProvider(options.host, {\n context: SELECTION_GROUP_CONTEXT_LOOSE,\n initialValue: new Map<HTMLElement, SelectionGroupContext>()\n })\n\n let lastValue: Value | undefined\n let lastDisabled: boolean | undefined\n let lastItems = new Set<Item>()\n let initialized = false\n\n const sync = (): boolean => {\n const nextItems = options.getItems()\n const value = options.getValue()\n const disabled = options.getDisabled()\n // 成员变化也要重放选中写回:新成员需继承当前选中态。\n const membershipChanged = nextItems.length !== lastItems.size || [...nextItems].some(item => !lastItems.has(item))\n // 子项可能在宿主首次连接后才完成 custom-element upgrade;值变得可读时,\n // 即使组值和成员集合没变,也要修复之前写入的过期选中态。\n const itemSelectionChanged =\n options.getItemSelected !== undefined &&\n nextItems.some(item => options.getItemSelected?.(item) !== options.isItemSelected(item, value))\n const selectionChanged =\n !initialized ||\n !options.valuesEqual(value, lastValue as Value) ||\n disabled !== lastDisabled ||\n membershipChanged ||\n itemSelectionChanged\n\n // 上行选中写回:根写入子项(context 是纯下行,不承担该方向)。\n if (selectionChanged) {\n for (const item of nextItems) {\n options.setItemSelected(item, options.isItemSelected(item, value))\n }\n }\n\n // 禁用下行:每次 sync 以新 Map 载荷整体广播(成员增删与禁用变化一并覆盖,\n // 新 Map 实例保证 Object.is 判定为变更)。\n provider.setValue(\n new Map(\n nextItems.map((item, index) => [\n item as HTMLElement,\n getSelectionContext(\n disabled,\n options.getRovingTabStop?.(item, index, nextItems, value) === true,\n options.isItemTabStop?.(item, nextItems)\n )\n ])\n )\n )\n\n lastItems = new Set(nextItems)\n lastValue = options.copyValue(value)\n lastDisabled = disabled\n initialized = true\n return selectionChanged\n }\n\n return {\n sync,\n disconnect() {\n provider.setValue(new Map())\n lastItems.clear()\n lastValue = undefined\n lastDisabled = undefined\n initialized = false\n },\n handleChange(event: Event) {\n if (options.getDisabled() || !options.isItem(event.target) || !options.host.contains(event.target)) {\n return\n }\n\n const current = options.getValue()\n const next = options.getNextValue(event.target, current)\n if (options.valuesEqual(current, next)) {\n options.resyncOnUnchangedValue?.(event.target)\n if (options.resyncOnUnchangedValue) sync()\n return\n }\n\n options.setValue(next)\n options.dispatchValueChange()\n },\n handleKeyDown(event: KeyboardEvent) {\n options.handleKeyDown?.(event)\n }\n }\n })\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../../../src/shared/group-management/index.ts"],"sourcesContent":["import { definePlugin } from '@greypan/js-kit'\nimport { ContextConsumer, ContextProvider, createContext, type Context } from '@lit/context'\nimport type { ReactiveController, ReactiveControllerHost } from 'lit'\n\n/*\n * 下行通道基于 @lit/context(ADR-0006 §5):root 上的 ContextProvider 以\n * `ReadonlyMap<HTMLElement, Context>` 为载荷向全子树广播,子项侧\n * ContextConsumer 订阅并按自身元素取条目。context-request 事件 composed,\n * 可穿过中间 shadow 边界;custom element 升级顺序保证祖先先于后代升级,\n * provider 总是先于子项请求就绪。成员追踪(querySelectorAll +\n * MutationObserver/slotchange)、点击归因与 setItemSelected 上行写回\n * 不在下行通道内,仍由 GroupController 驱动。\n */\n\nexport interface SelectionGroupContext {\n readonly disabled: boolean\n readonly rovingTabStop: boolean\n readonly tabStop?: boolean\n}\n\nexport interface ButtonGroupContext {\n readonly direction: 'horizontal' | 'vertical'\n readonly isLast: boolean\n}\n\n// 载荷类型仅编译期品牌化;按载荷形状分两个 key,避免异构树串扰。\n// createContext 泛型顺序为 <ValueType, K>。\nconst SELECTION_GROUP_CONTEXT = createContext<ReadonlyMap<HTMLElement, SelectionGroupContext>, symbol>(\n Symbol('web-ui.selection-group-context')\n)\n\nconst BUTTON_GROUP_CONTEXT = createContext<ReadonlyMap<HTMLElement, ButtonGroupContext>, symbol>(\n Symbol('web-ui.button-group-context')\n)\n\n// 两个 key 的运行时形状一致(Map 载荷),泛型插件内部统一按宽松类型驱动。\ntype AnyGroupContext = Context<symbol, ReadonlyMap<HTMLElement, unknown>>\n\nconst SELECTION_GROUP_CONTEXT_LOOSE = SELECTION_GROUP_CONTEXT as unknown as AnyGroupContext\nconst BUTTON_GROUP_CONTEXT_LOOSE = BUTTON_GROUP_CONTEXT as unknown as AnyGroupContext\n\nexport const selectionGroupContextKey: AnyGroupContext = SELECTION_GROUP_CONTEXT_LOOSE\nexport const buttonGroupContextKey: AnyGroupContext = BUTTON_GROUP_CONTEXT_LOOSE\nexport const GROUP_MEMBER_DISABLED_CHANGE_EVENT = 'wui-group-member-disabled-change'\n\ninterface GroupControllerHost extends HTMLElement, ReactiveControllerHost {\n readonly renderRoot: Element | DocumentFragment\n}\n\n/**\n * 创建受管理 group 的子项侧能力:订阅最近 provider 的 context 载荷并提取\n * 自身条目。在 `make()` 时完成注册,组件无需再编写 constructor 样板。\n */\nexport function defineGroupManaged<Context>(\n item: HTMLElement & ReactiveControllerHost,\n options: {\n /** 与所属根组件使用的 context key 一致。 */\n context: AnyGroupContext\n requestUpdate: () => void\n equals?: (a: Context | undefined, b: Context | undefined) => boolean\n }\n) {\n return definePlugin(() => {\n let context: Context | undefined\n const equals = options.equals ?? Object.is\n\n const consumer = new ContextConsumer(item, {\n context: options.context,\n subscribe: true,\n callback: payload => {\n const next = (payload as ReadonlyMap<HTMLElement, Context> | undefined)?.get(item)\n if (equals(context, next)) return\n context = next\n options.requestUpdate()\n }\n })\n\n /*\n * 离开 group(被移出 provider 子树)时 ContextConsumer 只是静默退订,\n * 不会收到「条目已移除」的通知:显式清空上下文,恢复独立控件语义\n * (如 checkbox 恢复自身表单提交)。跨组移动先断连清空、再重连订阅新组。\n */\n item.addController({\n hostDisconnected() {\n if (equals(context, undefined)) return\n context = undefined\n options.requestUpdate()\n }\n })\n\n return {\n getContext(): Context | undefined {\n return context\n },\n // 供测试或特殊场景确认订阅状态。\n isSubscribed(): boolean {\n return consumer.value !== undefined\n }\n }\n })\n}\n\nexport interface GroupPresentationOptions<Item extends HTMLElement, Context> {\n readonly host: HTMLElement\n /** 与子项 defineGroupManaged 使用的 context key 一致。 */\n readonly context: AnyGroupContext\n readonly getItems: () => readonly Item[]\n readonly getContext: (item: Item, index: number, items: readonly Item[]) => Context\n}\n\n/**\n * 为分组子项注册可逆的展示上下文(@lit/context 下行通道)。不持有公开 DOM\n * 属性;sync() 以新 Map 载荷整体广播,成员变化体现为子项条目消失。\n */\nexport function defineGroupPresentation<Item extends HTMLElement, Context>(\n options: GroupPresentationOptions<Item, Context>\n) {\n return definePlugin(() => {\n const provider = new ContextProvider(options.host, {\n context: options.context,\n initialValue: new Map<HTMLElement, unknown>()\n })\n\n return {\n sync(): boolean {\n const nextItems = options.getItems()\n const payload = new Map<HTMLElement, unknown>()\n nextItems.forEach((item, index) => payload.set(item, options.getContext(item, index, nextItems)))\n // 新 Map 实例保证 Object.is 判定为变更,全量通知订阅者。\n // 每次 hostUpdated 都重播(即使成员/方向未变)是有意形态:每次新建\n // context 对象,但子项 defineGroupManaged 的 equals 门控 requestUpdate\n // (标量字段比较),重播不产生多余渲染;代价是比「仅成员变化才通知」\n // 更频繁的广播事件,换取零状态追踪的简单性(与 GroupController 的\n // 全量 sync 对齐)。\n provider.setValue(payload)\n return true\n },\n disconnect() {\n provider.setValue(new Map())\n }\n }\n })\n}\n\nexport interface GroupLifecycle {\n sync(): boolean\n disconnect(): void\n handleChange?(event: Event): void\n handleKeyDown?(event: KeyboardEvent): void\n}\n\ninterface GroupControllerOptions {\n afterSync?: () => void\n observeAttributes?: readonly string[]\n}\n\n/**\n * 把组生命周期插件接入 Lit,协调规则不落在组件生命周期方法里。\n */\nexport class GroupController implements ReactiveController {\n private connected = false\n private observer: MutationObserver | null = null\n private observedSlots = new Set<HTMLSlotElement>()\n constructor(\n private readonly host: GroupControllerHost,\n private readonly lifecycle: GroupLifecycle,\n private readonly options: GroupControllerOptions = {}\n ) {\n host.addController(this)\n }\n\n hostConnected() {\n this.connected = true\n this.host.addEventListener('change', this.handleChange, true)\n this.host.addEventListener('keydown', this.handleKeyDown, true)\n this.host.addEventListener(GROUP_MEMBER_DISABLED_CHANGE_EVENT, this.handleMemberDisabledChange, true)\n this.observeHost()\n this.observeSlots()\n this.sync()\n }\n\n hostUpdated() {\n this.observeSlots()\n this.sync()\n }\n\n hostDisconnected() {\n this.connected = false\n this.host.removeEventListener('change', this.handleChange, true)\n this.host.removeEventListener('keydown', this.handleKeyDown, true)\n this.host.removeEventListener(GROUP_MEMBER_DISABLED_CHANGE_EVENT, this.handleMemberDisabledChange, true)\n this.disconnectSlots()\n this.disconnectHostObserver()\n this.lifecycle.disconnect()\n }\n\n private readonly handleChange = (event: Event) => {\n this.lifecycle.handleChange?.(event)\n }\n\n private readonly handleKeyDown = (event: KeyboardEvent) => {\n this.lifecycle.handleKeyDown?.(event)\n }\n\n private readonly handleMemberDisabledChange = () => {\n this.sync()\n }\n\n private readonly handleSlotChange = () => {\n if (!this.connected) return\n this.sync()\n }\n\n private readonly handleMutations = () => {\n if (!this.connected) return\n this.sync()\n }\n\n sync() {\n if (!this.lifecycle.sync()) return\n this.options.afterSync?.()\n }\n\n private observeHost() {\n this.disconnectHostObserver()\n // 监听 light DOM 的增删,覆盖 Vue v-if / React && 的 comment 锚点替换与深层包裹\n this.observer = new MutationObserver(this.handleMutations)\n const observerOptions: MutationObserverInit = { childList: true, subtree: true }\n if (this.options.observeAttributes?.length) {\n observerOptions.attributes = true\n observerOptions.attributeFilter = [...this.options.observeAttributes]\n }\n this.observer.observe(this.host, observerOptions)\n }\n\n private disconnectHostObserver() {\n if (this.observer) {\n this.observer.disconnect()\n this.observer = null\n }\n }\n\n private observeSlots() {\n const root = this.host.renderRoot as Element\n const slots = root.querySelectorAll<HTMLSlotElement>('slot')\n for (const slot of slots) {\n if (!this.observedSlots.has(slot)) {\n slot.addEventListener('slotchange', this.handleSlotChange)\n this.observedSlots.add(slot)\n }\n }\n // 清理已移除的 slot(热更新等场景)\n for (const slot of this.observedSlots) {\n if (!root.contains(slot)) {\n slot.removeEventListener('slotchange', this.handleSlotChange)\n this.observedSlots.delete(slot)\n }\n }\n }\n\n private disconnectSlots() {\n for (const slot of this.observedSlots) {\n slot.removeEventListener('slotchange', this.handleSlotChange)\n }\n this.observedSlots.clear()\n }\n}\n\nexport interface GroupCoordinatorOptions<Item extends HTMLElement, Value> {\n readonly host: HTMLElement\n readonly getItems: () => readonly Item[]\n readonly getValue: () => Value\n readonly setValue: (value: Value) => void\n readonly getDisabled: () => boolean\n readonly isItem: (target: EventTarget | null) => target is Item\n readonly isItemSelected: (item: Item, value: Value) => boolean\n readonly isItemTabStop?: (item: Item, items: readonly Item[]) => boolean\n readonly getItemSelected?: (item: Item) => boolean\n readonly getNextValue: (item: Item, value: Value) => Value\n readonly valuesEqual: (a: Value, b: Value) => boolean\n readonly copyValue: (value: Value) => Value\n readonly setItemSelected: (item: Item, selected: boolean) => void\n readonly dispatchValueChange: () => void\n readonly getRovingTabStop?: (item: Item, index: number, items: readonly Item[], value: Value) => boolean\n readonly handleKeyDown?: (event: KeyboardEvent) => void\n /**\n * 交互已发生但值没有变化时的回调(例如单选组成员 value 重复:点击同值成员\n * 不会改变 value,却必须把选中态收到被点击的那一项)。缺省视为无事可做。\n */\n readonly resyncOnUnchangedValue?: (item: Item) => void\n}\n\nconst ENABLED_SELECTION_CONTEXT: SelectionGroupContext = { disabled: false, rovingTabStop: false }\nconst ENABLED_ROVING_SELECTION_CONTEXT: SelectionGroupContext = { disabled: false, rovingTabStop: true }\nconst DISABLED_SELECTION_CONTEXT: SelectionGroupContext = { disabled: true, rovingTabStop: false }\n\nfunction getSelectionContext(disabled: boolean, rovingTabStop: boolean, tabStop?: boolean): SelectionGroupContext {\n const context = disabled\n ? DISABLED_SELECTION_CONTEXT\n : rovingTabStop\n ? ENABLED_ROVING_SELECTION_CONTEXT\n : ENABLED_SELECTION_CONTEXT\n return tabStop === undefined ? context : { ...context, tabStop }\n}\n\n/**\n * 在一个内部插件接口后收敛选中态、继承禁用与受管子项成员关系。\n * 禁用态经 @lit/context 下行广播;选中态上行写回保持直写。\n */\nexport function defineGroupCoordinator<Item extends HTMLElement, Value>(options: GroupCoordinatorOptions<Item, Value>) {\n return definePlugin(() => {\n const provider = new ContextProvider(options.host, {\n context: SELECTION_GROUP_CONTEXT_LOOSE,\n initialValue: new Map<HTMLElement, SelectionGroupContext>()\n })\n\n let lastValue: Value | undefined\n let lastDisabled: boolean | undefined\n let lastItems = new Set<Item>()\n let initialized = false\n\n const sync = (): boolean => {\n const nextItems = options.getItems()\n const value = options.getValue()\n const disabled = options.getDisabled()\n // 成员变化也要重放选中写回:新成员需继承当前选中态。\n const membershipChanged = nextItems.length !== lastItems.size || [...nextItems].some(item => !lastItems.has(item))\n // 子项可能在宿主首次连接后才完成 custom-element upgrade;值变得可读时,\n // 即使组值和成员集合没变,也要修复之前写入的过期选中态。\n const itemSelectionChanged =\n options.getItemSelected !== undefined &&\n nextItems.some(item => options.getItemSelected?.(item) !== options.isItemSelected(item, value))\n const selectionChanged =\n !initialized ||\n !options.valuesEqual(value, lastValue as Value) ||\n disabled !== lastDisabled ||\n membershipChanged ||\n itemSelectionChanged\n\n // 上行选中写回:根写入子项(context 是纯下行,不承担该方向)。\n if (selectionChanged) {\n for (const item of nextItems) {\n options.setItemSelected(item, options.isItemSelected(item, value))\n }\n }\n\n // 禁用下行:每次 sync 以新 Map 载荷整体广播(成员增删与禁用变化一并覆盖,\n // 新 Map 实例保证 Object.is 判定为变更)。\n provider.setValue(\n new Map(\n nextItems.map((item, index) => [\n item as HTMLElement,\n getSelectionContext(\n disabled,\n options.getRovingTabStop?.(item, index, nextItems, value) === true,\n options.isItemTabStop?.(item, nextItems)\n )\n ])\n )\n )\n\n lastItems = new Set(nextItems)\n lastValue = options.copyValue(value)\n lastDisabled = disabled\n initialized = true\n return selectionChanged\n }\n\n return {\n sync,\n disconnect() {\n provider.setValue(new Map())\n lastItems.clear()\n lastValue = undefined\n lastDisabled = undefined\n initialized = false\n },\n handleChange(event: Event) {\n if (options.getDisabled() || !options.isItem(event.target) || !options.host.contains(event.target)) {\n return\n }\n\n const current = options.getValue()\n const next = options.getNextValue(event.target, current)\n if (options.valuesEqual(current, next)) {\n options.resyncOnUnchangedValue?.(event.target)\n if (options.resyncOnUnchangedValue) sync()\n return\n }\n\n options.setValue(next)\n options.dispatchValueChange()\n },\n handleKeyDown(event: KeyboardEvent) {\n options.handleKeyDown?.(event)\n }\n }\n })\n}\n"],"mappings":"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"}
|
|
@@ -17,7 +17,8 @@ const LABELS = {
|
|
|
17
17
|
nextImage: "Next image",
|
|
18
18
|
zoomIn: "Zoom in",
|
|
19
19
|
zoomOut: "Zoom out",
|
|
20
|
-
resetZoom: "Reset zoom"
|
|
20
|
+
resetZoom: "Reset zoom",
|
|
21
|
+
progress: "Progress"
|
|
21
22
|
};
|
|
22
23
|
/** 显式覆盖优先(trim 后非空才生效);否则回退内置英文文案。 */
|
|
23
24
|
function resolveBuiltinLabel(key, override) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"builtin-labels.js","names":[],"sources":["../../../src/shared/locale/builtin-labels.ts"],"sourcesContent":["/**\n * 内置无障碍文案的唯一样表:图标控件的可访问名必须有值(无名称的图标按钮是\n * 默认的无障碍违规),内容文案不属于这里,始终由外部传入。\n *\n * fallback 固定英文,不跟随运行环境语言;需要其他语言时经覆盖通道改写——\n * 单标签组件用专用 attribute(`aria-close-label` 这类),多 key 成套组件用\n * `ariaLabels` 对象 property。分界规则见 ADR-0016。\n */\nexport type BuiltinLabelKey =\n | 'clear'\n | 'decrease'\n | 'increase'\n | 'close'\n | 'backToTop'\n | 'collapseSidebar'\n | 'expandSidebar'\n | 'resizeSidebar'\n | 'openNavigationMenu'\n | 'mainNavigation'\n | 'unread'\n | 'unreadCount'\n | 'noUnread'\n | 'previousImage'\n | 'nextImage'\n | 'zoomIn'\n | 'zoomOut'\n | 'resetZoom'\n\nconst LABELS: Record<BuiltinLabelKey, string> = {\n clear: 'Clear',\n decrease: 'Decrease',\n increase: 'Increase',\n close: 'Close',\n backToTop: 'Back to top',\n collapseSidebar: 'Collapse sidebar',\n expandSidebar: 'Expand sidebar',\n resizeSidebar: 'Resize sidebar',\n openNavigationMenu: 'Open navigation menu',\n mainNavigation: 'Main navigation',\n unread: 'Unread',\n unreadCount: '{count} unread messages',\n noUnread: 'No unread messages',\n previousImage: 'Previous image',\n nextImage: 'Next image',\n zoomIn: 'Zoom in',\n zoomOut: 'Zoom out',\n resetZoom: 'Reset zoom'\n}\n\n/** 显式覆盖优先(trim 后非空才生效);否则回退内置英文文案。 */\nexport function resolveBuiltinLabel(key: BuiltinLabelKey, override?: string | null): string {\n const custom = override?.trim()\n if (custom) return custom\n return LABELS[key]\n}\n\n/** 成组覆盖(`ariaLabels` 对象 property)里取单个 key;未提供的 key 回退内置英文。 */\nexport function resolveBuiltinLabelSet<K extends BuiltinLabelKey>(\n labels: Partial<Record<K, string>> | undefined,\n key: K\n): string {\n return resolveBuiltinLabel(key, labels?.[key])\n}\n\n/** 把 `{count}` 这类占位替换成实参;没有对应实参的占位原样保留。 */\nexport function formatBuiltinLabel(template: string, params: Record<string, string | number>): string {\n return template.replace(/\\{(\\w+)\\}/g, (match, name: string) => (name in params ? String(params[name]) : match))\n}\n"],"mappings":";
|
|
1
|
+
{"version":3,"file":"builtin-labels.js","names":[],"sources":["../../../src/shared/locale/builtin-labels.ts"],"sourcesContent":["/**\n * 内置无障碍文案的唯一样表:图标控件的可访问名必须有值(无名称的图标按钮是\n * 默认的无障碍违规),内容文案不属于这里,始终由外部传入。\n *\n * fallback 固定英文,不跟随运行环境语言;需要其他语言时经覆盖通道改写——\n * 单标签组件用专用 attribute(`aria-close-label` 这类),多 key 成套组件用\n * `ariaLabels` 对象 property。分界规则见 ADR-0016。\n */\nexport type BuiltinLabelKey =\n | 'clear'\n | 'decrease'\n | 'increase'\n | 'close'\n | 'backToTop'\n | 'collapseSidebar'\n | 'expandSidebar'\n | 'resizeSidebar'\n | 'openNavigationMenu'\n | 'mainNavigation'\n | 'unread'\n | 'unreadCount'\n | 'noUnread'\n | 'previousImage'\n | 'nextImage'\n | 'zoomIn'\n | 'zoomOut'\n | 'resetZoom'\n | 'progress'\n\nconst LABELS: Record<BuiltinLabelKey, string> = {\n clear: 'Clear',\n decrease: 'Decrease',\n increase: 'Increase',\n close: 'Close',\n backToTop: 'Back to top',\n collapseSidebar: 'Collapse sidebar',\n expandSidebar: 'Expand sidebar',\n resizeSidebar: 'Resize sidebar',\n openNavigationMenu: 'Open navigation menu',\n mainNavigation: 'Main navigation',\n unread: 'Unread',\n unreadCount: '{count} unread messages',\n noUnread: 'No unread messages',\n previousImage: 'Previous image',\n nextImage: 'Next image',\n zoomIn: 'Zoom in',\n zoomOut: 'Zoom out',\n resetZoom: 'Reset zoom',\n progress: 'Progress'\n}\n\n/** 显式覆盖优先(trim 后非空才生效);否则回退内置英文文案。 */\nexport function resolveBuiltinLabel(key: BuiltinLabelKey, override?: string | null): string {\n const custom = override?.trim()\n if (custom) return custom\n return LABELS[key]\n}\n\n/** 成组覆盖(`ariaLabels` 对象 property)里取单个 key;未提供的 key 回退内置英文。 */\nexport function resolveBuiltinLabelSet<K extends BuiltinLabelKey>(\n labels: Partial<Record<K, string>> | undefined,\n key: K\n): string {\n return resolveBuiltinLabel(key, labels?.[key])\n}\n\n/** 把 `{count}` 这类占位替换成实参;没有对应实参的占位原样保留。 */\nexport function formatBuiltinLabel(template: string, params: Record<string, string | number>): string {\n return template.replace(/\\{(\\w+)\\}/g, (match, name: string) => (name in params ? String(params[name]) : match))\n}\n"],"mappings":";AA6BA,MAAM,SAA0C;CAC9C,OAAO;CACP,UAAU;CACV,UAAU;CACV,OAAO;CACP,WAAW;CACX,iBAAiB;CACjB,eAAe;CACf,eAAe;CACf,oBAAoB;CACpB,gBAAgB;CAChB,QAAQ;CACR,aAAa;CACb,UAAU;CACV,eAAe;CACf,WAAW;CACX,QAAQ;CACR,SAAS;CACT,WAAW;CACX,UAAU;AACZ;;AAGA,SAAgB,oBAAoB,KAAsB,UAAkC;CAC1F,MAAM,SAAS,UAAU,KAAK;CAC9B,IAAI,QAAQ,OAAO;CACnB,OAAO,OAAO;AAChB;;AAGA,SAAgB,uBACd,QACA,KACQ;CACR,OAAO,oBAAoB,KAAK,SAAS,IAAI;AAC/C;;AAGA,SAAgB,mBAAmB,UAAkB,QAAiD;CACpG,OAAO,SAAS,QAAQ,eAAe,OAAO,SAAkB,QAAQ,SAAS,OAAO,OAAO,KAAK,IAAI,KAAM;AAChH"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","names":[],"sources":["../../../src/shared/open-state/index.ts"],"sourcesContent":["import type { LitElement } from 'lit'\n\n/**\n * overlay 族 `open-change` 事件的单一发出点与契约说明。\n *\n * 同名事件存在两种 flavor
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../../../src/shared/open-state/index.ts"],"sourcesContent":["import type { LitElement } from 'lit'\n\n/**\n * overlay 族 `open-change` 事件的单一发出点与契约说明。\n *\n * 同名事件存在两种 flavor(事件模型见 ADR-0005 §2.4,勿混淆):\n * - **request 语义**(dialog / drawer / layout):controlled 属性开启时,\n * `open-change` 是用户的关闭/打开\"请求\",组件不自行修改 `open`,等待回写;\n * - **notification 语义**(popover / tooltip / dropdown / context-menu /\n * select / autocomplete / collapse):组件总是自行变更 `open`,事件只作通知。\n *\n * 两种 flavor 的机械发出在此收敛;flavor 决策(是否 controlled 门控)留在各组件。\n */\nexport interface OpenChangeEventDetail {\n open: boolean\n}\n\nexport function dispatchOpenChangeEvent(host: LitElement, open: boolean): void {\n host.dispatchEvent(\n new CustomEvent<OpenChangeEventDetail>('open-change', {\n detail: { open },\n bubbles: true,\n composed: true\n })\n )\n}\n"],"mappings":";AAiBA,SAAgB,wBAAwB,MAAkB,MAAqB;CAC7E,KAAK,cACH,IAAI,YAAmC,eAAe;EACpD,QAAQ,EAAE,KAAK;EACf,SAAS;EACT,UAAU;CACZ,CAAC,CACH;AACF"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"overlay.js","names":[],"sources":["../../../src/shared/overlay/overlay.ts"],"sourcesContent":["import {\n autoUpdate,\n computePosition,\n flip,\n offset,\n shift,\n size,\n type Middleware,\n type Placement,\n type Strategy\n} from '@floating-ui/dom'\nimport { definePlugin } from '@greypan/js-kit'\n\nimport { defineOverlayPositioningGeneration, type OverlayPositioningGeneration } from './positioning-generation'\n\nexport interface OverlayOptions {\n placement?: Placement\n offset?: number\n flip?: boolean\n shift?: boolean\n /** panel 宽度与锚点宽度保持一致。 */\n matchWidth?: boolean\n /** panel 至少与锚点同宽,同时允许内容将 panel 撑宽。 */\n minAnchorWidth?: boolean\n strategy?: Strategy\n}\n\n/** 虚拟锚点:无对应 DOM 元素的定位基准。context-menu 未走 defineOverlay(定位语义分歧见 ADR-0038)。 */\nexport interface OverlayVirtualAnchor {\n getBoundingClientRect(): DOMRect\n}\n\nexport type OverlayAnchor = HTMLElement | OverlayVirtualAnchor\n\nexport interface OverlayApi {\n isOpen(): boolean\n readonly options: Required<OverlayOptions>\n open(): void\n close(): void\n toggle(): void\n update(options: Partial<OverlayOptions>): void\n updateAnchor(anchor: OverlayAnchor): void\n dispose(): void\n}\n\nconst DEFAULT_OVERLAY_MIN_WIDTH = 120\nconst OVERLAY_MIN_WIDTH_VARIABLE = '--wui-overlay-min-width'\n\nconst DEFAULT_OPTIONS: Required<OverlayOptions> = {\n placement: 'bottom-start',\n offset: 4,\n flip: true,\n shift: true,\n matchWidth: false,\n minAnchorWidth: false,\n strategy: 'absolute'\n}\n\ninterface WidthStyleState {\n hasManagedStyles: boolean\n}\n\nfunction readOverlayMinWidth(overlay: HTMLElement): number {\n if (typeof getComputedStyle !== 'function') return DEFAULT_OVERLAY_MIN_WIDTH\n\n const minWidth = Number.parseFloat(getComputedStyle(overlay).getPropertyValue(OVERLAY_MIN_WIDTH_VARIABLE))\n return Number.isFinite(minWidth) ? minWidth : DEFAULT_OVERLAY_MIN_WIDTH\n}\n\nfunction clearManagedWidthStyles(overlay: HTMLElement) {\n overlay.style.removeProperty('width')\n overlay.style.removeProperty('min-width')\n}\n\nfunction createWidthMiddleware(\n overlay: HTMLElement,\n options: Required<OverlayOptions>,\n widthStyles: WidthStyleState,\n positioningGeneration: OverlayPositioningGeneration,\n generation: number\n): Middleware | undefined {\n const isCurrentGeneration = () => positioningGeneration.isCurrent(generation)\n if (options.matchWidth) {\n // matchWidth 必须移除之前 minAnchorWidth 写入的 min-width,才能精确跟随 trigger。\n overlay.style.removeProperty('min-width')\n widthStyles.hasManagedStyles = true\n return size({\n apply({ rects }) {\n if (!isCurrentGeneration()) return\n overlay.style.width = `${rects.reference.width}px`\n }\n })\n }\n\n if (options.minAnchorWidth) {\n const minWidth = readOverlayMinWidth(overlay)\n widthStyles.hasManagedStyles = true\n return size({\n apply({ rects }) {\n if (!isCurrentGeneration()) return\n // max-content 让内容决定宽度,min-width 再提供 trigger 与 floor 两个下限。\n overlay.style.width = 'max-content'\n overlay.style.minWidth = `${Math.max(rects.reference.width, minWidth)}px`\n }\n })\n }\n\n if (widthStyles.hasManagedStyles) {\n clearManagedWidthStyles(overlay)\n widthStyles.hasManagedStyles = false\n }\n\n return undefined\n}\n\nfunction createPositioningMiddleware(\n overlay: HTMLElement,\n options: Required<OverlayOptions>,\n widthStyles: WidthStyleState,\n positioningGeneration: OverlayPositioningGeneration,\n generation: number\n): Middleware[] {\n const middleware: Middleware[] = [offset(options.offset)]\n if (options.flip) middleware.push(flip())\n if (options.shift) {\n const side = options.placement.split('-')[0]\n middleware.push(shift({ padding: 8, crossAxis: side === 'left' || side === 'right' }))\n }\n\n const widthMiddleware = createWidthMiddleware(overlay, options, widthStyles, positioningGeneration, generation)\n if (widthMiddleware) middleware.push(widthMiddleware)\n\n return middleware\n}\n\nfunction getTransformOrigin(placement: Placement): string {\n const [side, alignment] = placement.split('-')\n const horizontalOrigin = alignment === 'start' ? 'left' : alignment === 'end' ? 'right' : 'center'\n const verticalOrigin = alignment === 'start' ? 'top' : alignment === 'end' ? 'bottom' : 'center'\n\n if (side === 'top') return `bottom ${horizontalOrigin}`\n if (side === 'bottom') return `top ${horizontalOrigin}`\n if (side === 'left') return `right ${verticalOrigin}`\n return `left ${verticalOrigin}`\n}\n\nexport const defineOverlay = () =>\n definePlugin<OverlayApi, { anchor: OverlayAnchor; overlay: HTMLElement } & OverlayOptions>(ctx => {\n const options: Required<OverlayOptions> = {\n placement: ctx.placement ?? DEFAULT_OPTIONS.placement,\n offset: ctx.offset ?? DEFAULT_OPTIONS.offset,\n flip: ctx.flip ?? DEFAULT_OPTIONS.flip,\n shift: ctx.shift ?? DEFAULT_OPTIONS.shift,\n matchWidth: ctx.matchWidth ?? DEFAULT_OPTIONS.matchWidth,\n minAnchorWidth: ctx.minAnchorWidth ?? DEFAULT_OPTIONS.minAnchorWidth,\n strategy: ctx.strategy ?? DEFAULT_OPTIONS.strategy\n }\n\n const overlay = ctx.overlay\n const widthStyles: WidthStyleState = { hasManagedStyles: false }\n let isOpen = false\n let cleanupAutoUpdate: (() => void) | null = null\n let currentAnchor = ctx.anchor\n // 每次刷新都是新定位代;open 期间 autoUpdate 的多次回调属于同一代。\n // reposition/close 会让上一代 promise 失效,避免乱序完成覆盖最新坐标。\n const positioningGeneration = defineOverlayPositioningGeneration().make()\n\n function updatePosition() {\n const generation = positioningGeneration.next()\n const middleware = createPositioningMiddleware(overlay, options, widthStyles, positioningGeneration, generation)\n\n const applyPosition = () => {\n void computePosition(currentAnchor, overlay, {\n placement: options.placement,\n strategy: options.strategy,\n middleware\n }).then(({ x, y, placement }) => {\n if (!positioningGeneration.isCurrent(generation) || !isOpen) return\n overlay.style.left = `${x}px`\n overlay.style.top = `${y}px`\n overlay.style.setProperty('--wui-internal-overlay-transform-origin', getTransformOrigin(placement))\n })\n }\n\n // 立即定位一次,避免 overlay 首帧出现在左上角;autoUpdate 负责后续滚动/尺寸变化。\n applyPosition()\n cleanupAutoUpdate?.()\n cleanupAutoUpdate = autoUpdate(currentAnchor, overlay, applyPosition)\n }\n\n return {\n isOpen() {\n return isOpen\n },\n options,\n\n open() {\n if (isOpen) return\n isOpen = true\n overlay.style.display = ''\n updatePosition()\n },\n\n close() {\n if (!isOpen) return\n isOpen = false\n positioningGeneration.invalidate()\n cleanupAutoUpdate?.()\n cleanupAutoUpdate = null\n },\n\n toggle() {\n if (isOpen) this.close()\n else this.open()\n },\n\n update(nextOptions) {\n Object.assign(options, nextOptions)\n if (isOpen) updatePosition()\n },\n\n updateAnchor(newAnchor: OverlayAnchor) {\n currentAnchor = newAnchor\n if (isOpen) updatePosition()\n },\n\n dispose() {\n this.close()\n }\n }\n })\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"overlay.js","names":[],"sources":["../../../src/shared/overlay/overlay.ts"],"sourcesContent":["import {\n autoUpdate,\n computePosition,\n flip,\n offset,\n shift,\n size,\n type Middleware,\n type Placement,\n type Strategy\n} from '@floating-ui/dom'\nimport { definePlugin } from '@greypan/js-kit'\n\nimport { defineOverlayPositioningGeneration, type OverlayPositioningGeneration } from './positioning-generation'\n\nexport interface OverlayOptions {\n placement?: Placement\n offset?: number\n flip?: boolean\n shift?: boolean\n /** panel 宽度与锚点宽度保持一致。 */\n matchWidth?: boolean\n /** panel 至少与锚点同宽,同时允许内容将 panel 撑宽。 */\n minAnchorWidth?: boolean\n strategy?: Strategy\n}\n\n/** 虚拟锚点:无对应 DOM 元素的定位基准。context-menu 未走 defineOverlay(私有定位路径的准入见 ADR-0006 §2)。 */\nexport interface OverlayVirtualAnchor {\n getBoundingClientRect(): DOMRect\n}\n\nexport type OverlayAnchor = HTMLElement | OverlayVirtualAnchor\n\nexport interface OverlayApi {\n isOpen(): boolean\n readonly options: Required<OverlayOptions>\n open(): void\n close(): void\n toggle(): void\n update(options: Partial<OverlayOptions>): void\n updateAnchor(anchor: OverlayAnchor): void\n dispose(): void\n}\n\nconst DEFAULT_OVERLAY_MIN_WIDTH = 120\nconst OVERLAY_MIN_WIDTH_VARIABLE = '--wui-overlay-min-width'\n\nconst DEFAULT_OPTIONS: Required<OverlayOptions> = {\n placement: 'bottom-start',\n offset: 4,\n flip: true,\n shift: true,\n matchWidth: false,\n minAnchorWidth: false,\n strategy: 'absolute'\n}\n\ninterface WidthStyleState {\n hasManagedStyles: boolean\n}\n\nfunction readOverlayMinWidth(overlay: HTMLElement): number {\n if (typeof getComputedStyle !== 'function') return DEFAULT_OVERLAY_MIN_WIDTH\n\n const minWidth = Number.parseFloat(getComputedStyle(overlay).getPropertyValue(OVERLAY_MIN_WIDTH_VARIABLE))\n return Number.isFinite(minWidth) ? minWidth : DEFAULT_OVERLAY_MIN_WIDTH\n}\n\nfunction clearManagedWidthStyles(overlay: HTMLElement) {\n overlay.style.removeProperty('width')\n overlay.style.removeProperty('min-width')\n}\n\nfunction createWidthMiddleware(\n overlay: HTMLElement,\n options: Required<OverlayOptions>,\n widthStyles: WidthStyleState,\n positioningGeneration: OverlayPositioningGeneration,\n generation: number\n): Middleware | undefined {\n const isCurrentGeneration = () => positioningGeneration.isCurrent(generation)\n if (options.matchWidth) {\n // matchWidth 必须移除之前 minAnchorWidth 写入的 min-width,才能精确跟随 trigger。\n overlay.style.removeProperty('min-width')\n widthStyles.hasManagedStyles = true\n return size({\n apply({ rects }) {\n if (!isCurrentGeneration()) return\n overlay.style.width = `${rects.reference.width}px`\n }\n })\n }\n\n if (options.minAnchorWidth) {\n const minWidth = readOverlayMinWidth(overlay)\n widthStyles.hasManagedStyles = true\n return size({\n apply({ rects }) {\n if (!isCurrentGeneration()) return\n // max-content 让内容决定宽度,min-width 再提供 trigger 与 floor 两个下限。\n overlay.style.width = 'max-content'\n overlay.style.minWidth = `${Math.max(rects.reference.width, minWidth)}px`\n }\n })\n }\n\n if (widthStyles.hasManagedStyles) {\n clearManagedWidthStyles(overlay)\n widthStyles.hasManagedStyles = false\n }\n\n return undefined\n}\n\nfunction createPositioningMiddleware(\n overlay: HTMLElement,\n options: Required<OverlayOptions>,\n widthStyles: WidthStyleState,\n positioningGeneration: OverlayPositioningGeneration,\n generation: number\n): Middleware[] {\n const middleware: Middleware[] = [offset(options.offset)]\n if (options.flip) middleware.push(flip())\n if (options.shift) {\n const side = options.placement.split('-')[0]\n middleware.push(shift({ padding: 8, crossAxis: side === 'left' || side === 'right' }))\n }\n\n const widthMiddleware = createWidthMiddleware(overlay, options, widthStyles, positioningGeneration, generation)\n if (widthMiddleware) middleware.push(widthMiddleware)\n\n return middleware\n}\n\nfunction getTransformOrigin(placement: Placement): string {\n const [side, alignment] = placement.split('-')\n const horizontalOrigin = alignment === 'start' ? 'left' : alignment === 'end' ? 'right' : 'center'\n const verticalOrigin = alignment === 'start' ? 'top' : alignment === 'end' ? 'bottom' : 'center'\n\n if (side === 'top') return `bottom ${horizontalOrigin}`\n if (side === 'bottom') return `top ${horizontalOrigin}`\n if (side === 'left') return `right ${verticalOrigin}`\n return `left ${verticalOrigin}`\n}\n\nexport const defineOverlay = () =>\n definePlugin<OverlayApi, { anchor: OverlayAnchor; overlay: HTMLElement } & OverlayOptions>(ctx => {\n const options: Required<OverlayOptions> = {\n placement: ctx.placement ?? DEFAULT_OPTIONS.placement,\n offset: ctx.offset ?? DEFAULT_OPTIONS.offset,\n flip: ctx.flip ?? DEFAULT_OPTIONS.flip,\n shift: ctx.shift ?? DEFAULT_OPTIONS.shift,\n matchWidth: ctx.matchWidth ?? DEFAULT_OPTIONS.matchWidth,\n minAnchorWidth: ctx.minAnchorWidth ?? DEFAULT_OPTIONS.minAnchorWidth,\n strategy: ctx.strategy ?? DEFAULT_OPTIONS.strategy\n }\n\n const overlay = ctx.overlay\n const widthStyles: WidthStyleState = { hasManagedStyles: false }\n let isOpen = false\n let cleanupAutoUpdate: (() => void) | null = null\n let currentAnchor = ctx.anchor\n // 每次刷新都是新定位代;open 期间 autoUpdate 的多次回调属于同一代。\n // reposition/close 会让上一代 promise 失效,避免乱序完成覆盖最新坐标。\n const positioningGeneration = defineOverlayPositioningGeneration().make()\n\n function updatePosition() {\n const generation = positioningGeneration.next()\n const middleware = createPositioningMiddleware(overlay, options, widthStyles, positioningGeneration, generation)\n\n const applyPosition = () => {\n void computePosition(currentAnchor, overlay, {\n placement: options.placement,\n strategy: options.strategy,\n middleware\n }).then(({ x, y, placement }) => {\n if (!positioningGeneration.isCurrent(generation) || !isOpen) return\n overlay.style.left = `${x}px`\n overlay.style.top = `${y}px`\n overlay.style.setProperty('--wui-internal-overlay-transform-origin', getTransformOrigin(placement))\n })\n }\n\n // 立即定位一次,避免 overlay 首帧出现在左上角;autoUpdate 负责后续滚动/尺寸变化。\n applyPosition()\n cleanupAutoUpdate?.()\n cleanupAutoUpdate = autoUpdate(currentAnchor, overlay, applyPosition)\n }\n\n return {\n isOpen() {\n return isOpen\n },\n options,\n\n open() {\n if (isOpen) return\n isOpen = true\n overlay.style.display = ''\n updatePosition()\n },\n\n close() {\n if (!isOpen) return\n isOpen = false\n positioningGeneration.invalidate()\n cleanupAutoUpdate?.()\n cleanupAutoUpdate = null\n },\n\n toggle() {\n if (isOpen) this.close()\n else this.open()\n },\n\n update(nextOptions) {\n Object.assign(options, nextOptions)\n if (isOpen) updatePosition()\n },\n\n updateAnchor(newAnchor: OverlayAnchor) {\n currentAnchor = newAnchor\n if (isOpen) updatePosition()\n },\n\n dispose() {\n this.close()\n }\n }\n })\n"],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@greypan/web-ui",
|
|
3
|
-
"version": "12.
|
|
3
|
+
"version": "12.1.0",
|
|
4
4
|
"description": "Lit-based web components for React, Vue, and vanilla JS",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"repository": {
|
|
@@ -48,12 +48,14 @@
|
|
|
48
48
|
"@lit/context": "^1.1.6"
|
|
49
49
|
},
|
|
50
50
|
"devDependencies": {
|
|
51
|
-
"@greypan/monorepo-kit": "0.0.
|
|
51
|
+
"@greypan/monorepo-kit": "0.0.2",
|
|
52
52
|
"@greypan/tsconfig": "0.0.0",
|
|
53
53
|
"@iconify-json/akar-icons": "^1.2.7",
|
|
54
54
|
"@iconify-json/andrsrxn": "^1.2.2",
|
|
55
55
|
"@iconify-json/bi": "^1.2.7",
|
|
56
|
+
"@iconify-json/ant-design": "^1.2.9",
|
|
56
57
|
"@iconify-json/fluent": "^1.2.58",
|
|
58
|
+
"@iconify-json/ic": "^1.2.4",
|
|
57
59
|
"@iconify-json/jam": "^1.2.3",
|
|
58
60
|
"@iconify-json/lucide": "^1.2.126",
|
|
59
61
|
"@iconify-json/mdi": "^1.2.3",
|