vanilla-jui 1.3.11 → 1.4.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (106) hide show
  1. package/dist/index.d.ts +2921 -0
  2. package/dist/index.js +1 -1
  3. package/dist/index.umd.js +1 -1
  4. package/dist/style.css +1 -1
  5. package/package.json +4 -3
  6. package/src/components/accordion.ts +522 -0
  7. package/src/components/drop.ts +497 -0
  8. package/src/components/flow.ts +1579 -0
  9. package/src/components/form.ts +953 -0
  10. package/src/components/{icons.js → icons.ts} +24 -11
  11. package/src/components/menu.ts +615 -0
  12. package/src/components/{modal.js → modal.ts} +560 -237
  13. package/src/components/offcanvas.ts +457 -0
  14. package/src/components/{pagination.js → pagination.ts} +251 -76
  15. package/src/components/parabola.ts +335 -0
  16. package/src/components/{sticky.js → sticky.ts} +123 -98
  17. package/src/components/{swiper.js → swiper.ts} +510 -232
  18. package/src/components/tabs.ts +984 -0
  19. package/src/components/theme.ts +437 -0
  20. package/src/components/toast.ts +371 -0
  21. package/src/components/toc.ts +385 -0
  22. package/src/components/tooltip.ts +179 -0
  23. package/src/components/validator.ts +596 -0
  24. package/src/core/{Component.js → Component.ts} +134 -27
  25. package/src/css/accordion.css +0 -45
  26. package/src/css/animation.css +31 -1
  27. package/src/css/avatar.css +7 -33
  28. package/src/css/badge.css +11 -59
  29. package/src/css/breadcrumb.css +9 -32
  30. package/src/css/button.css +23 -224
  31. package/src/css/card.css +1 -1
  32. package/src/css/color.css +863 -1013
  33. package/src/css/color_p3.css +822 -975
  34. package/src/css/components.css +1 -0
  35. package/src/css/drop.css +7 -7
  36. package/src/css/flow.css +1 -1
  37. package/src/css/form.css +1 -1
  38. package/src/css/icon.css +7 -12
  39. package/src/css/index.css +5 -2
  40. package/src/css/loading.css +36 -20
  41. package/src/css/menu.css +1 -1
  42. package/src/css/modal.css +15 -44
  43. package/src/css/offcanvas.css +14 -40
  44. package/src/css/popup.css +4 -4
  45. package/src/css/status.css +0 -2
  46. package/src/css/swiper.css +35 -50
  47. package/src/css/tabs.css +9 -31
  48. package/src/css/tag.css +16 -77
  49. package/src/css/themes/default/accordion.css +62 -0
  50. package/src/css/themes/default/avatar.css +39 -0
  51. package/src/css/themes/default/badge.css +63 -0
  52. package/src/css/themes/default/breadcrumb.css +28 -0
  53. package/src/css/themes/default/button.css +204 -0
  54. package/src/css/themes/default/drop.css +11 -0
  55. package/src/css/themes/default/index.css +16 -0
  56. package/src/css/themes/default/loading.css +23 -0
  57. package/src/css/themes/default/modal.css +40 -0
  58. package/src/css/themes/default/offcanvas.css +13 -0
  59. package/src/css/themes/default/popup.css +7 -0
  60. package/src/css/themes/default/swiper.css +35 -0
  61. package/src/css/themes/default/tabs.css +37 -0
  62. package/src/css/themes/default/tag.css +85 -0
  63. package/src/css/themes/default/tip.css +49 -0
  64. package/src/css/themes/default/toast.css +70 -0
  65. package/src/css/themes/default/tooltip.css +14 -0
  66. package/src/css/themes/index.css +1 -0
  67. package/src/css/tip.css +20 -39
  68. package/src/css/toast.css +18 -80
  69. package/src/css/tokens.css +8 -3
  70. package/src/css/tooltip.css +10 -10
  71. package/src/index.ts +37 -0
  72. package/src/locales/{index.js → index.ts} +1 -2
  73. package/src/types.d.ts +1 -0
  74. package/src/utilities/browser.ts +131 -0
  75. package/src/utilities/cache.ts +57 -0
  76. package/src/utilities/core.ts +614 -0
  77. package/src/utilities/dom.ts +468 -0
  78. package/src/utilities/events.ts +106 -0
  79. package/src/utilities/http.ts +35 -0
  80. package/src/utilities/storage.ts +46 -0
  81. package/src/components/accordion.js +0 -373
  82. package/src/components/components.js +0 -0
  83. package/src/components/drop.js +0 -437
  84. package/src/components/flow.js +0 -1133
  85. package/src/components/form.js +0 -585
  86. package/src/components/menu.js +0 -422
  87. package/src/components/offcanvas.js +0 -332
  88. package/src/components/parabola.js +0 -295
  89. package/src/components/tabs.js +0 -746
  90. package/src/components/theme.js +0 -353
  91. package/src/components/toast.js +0 -329
  92. package/src/components/toc.js +0 -226
  93. package/src/components/tooltip.js +0 -86
  94. package/src/components/validator.js +0 -586
  95. package/src/index.js +0 -45
  96. package/src/locales/index.min.js +0 -1
  97. package/src/utilities/browser.js +0 -111
  98. package/src/utilities/cache.js +0 -159
  99. package/src/utilities/core.js +0 -502
  100. package/src/utilities/debug.js +0 -103
  101. package/src/utilities/dom.js +0 -313
  102. package/src/utilities/events.js +0 -69
  103. package/src/utilities/http.js +0 -30
  104. package/src/utilities/legacy-dom.js +0 -179
  105. package/src/utilities/storage.js +0 -46
  106. /package/src/icons/{index.js → index.ts} +0 -0
@@ -1,226 +0,0 @@
1
- import { createDeepStore } from 'vanilla-signal';
2
-
3
- import Component from '../core/Component.js';
4
- import { randomId, resolveProps } from '../utilities/core.js';
5
- import { requireContainer, requireRenderDOM } from '../utilities/dom.js';
6
-
7
- const TOC_PROPS_SCHEMA = {
8
- container: { default: null },
9
- target: { default: '.j-content' },
10
- headings: { default: 'h2, h3', type: 'string' },
11
- offset: {
12
- default: 80,
13
- type: 'number',
14
- validate: (value) => value >= 0,
15
- message: 'expects a positive number or 0.',
16
- },
17
- onUpdate: { default: null, types: ['function', 'null'] },
18
- };
19
-
20
- function resolveHeadingLevel(element) {
21
- const match = /^H([1-6])$/.exec(element.tagName);
22
- return match ? Number(match[1]) : 1;
23
- }
24
-
25
- function normalizeHeading(element, index) {
26
- if (!element.id) element.id = `toc-${randomId()}-${index}`;
27
- return {
28
- id: element.id,
29
- text: element.textContent || '',
30
- level: resolveHeadingLevel(element),
31
- element,
32
- };
33
- }
34
-
35
- /**
36
- * 页面目录组件。
37
- *
38
- * 扫描内容区域内的标题,生成锚点列表,并随页面滚动更新 active 状态。
39
- */
40
- export class Toc extends Component {
41
- /**
42
- * 创建 Toc 实例。
43
- * @param {object} [input={}] Toc 配置。
44
- */
45
- constructor(input = {}) {
46
- const props = resolveProps(input, TOC_PROPS_SCHEMA, 'Toc.props');
47
- super(props);
48
-
49
- this.dom.container = null;
50
- this.dom.target = null;
51
- this.dom.list = null;
52
- this.dom.headings = [];
53
- this.dom.links = [];
54
-
55
- this.runtime.built = false;
56
- this.runtime.ticking = false;
57
-
58
- this.state = createDeepStore({
59
- items: [],
60
- current: {
61
- index: -1,
62
- item: null,
63
- },
64
- });
65
- }
66
-
67
- /**
68
- * 构建 Toc DOM 和滚动监听。
69
- * @returns {Toc} 当前实例。
70
- */
71
- build() {
72
- if (this.runtime.destroyed)
73
- throw new Error('Toc.build: instance destroyed');
74
- if (this.runtime.built) return this;
75
-
76
- requireRenderDOM('Toc');
77
-
78
- this.init(this.props);
79
- this.dom.container = requireContainer(
80
- this.props.container,
81
- 'Toc.container'
82
- );
83
- this.dom.target = requireContainer(this.props.target, 'Toc.target');
84
- this.root = document.createElement('nav');
85
- this.root.className = 'j-toc';
86
- this.dom.list = document.createElement('div');
87
- this.dom.list.className = 'toc-list';
88
- this.root.appendChild(this.dom.list);
89
- this.dom.container.innerHTML = '';
90
- this.dom.container.appendChild(this.root);
91
-
92
- this.runtime.built = true;
93
- this.refresh();
94
- return this;
95
- }
96
-
97
- _bindEvents() {
98
- this.cleanup.events.on('scroll', window, 'scroll', () => this._onScroll(), {
99
- passive: true,
100
- });
101
- }
102
-
103
- _onScroll() {
104
- if (this.runtime.ticking) return;
105
-
106
- requestAnimationFrame(() => {
107
- this._updateActive();
108
- this.runtime.ticking = false;
109
- });
110
- this.runtime.ticking = true;
111
- }
112
-
113
- _buildLink(item) {
114
- const link = document.createElement('a');
115
- link.href = `#${item.id}`;
116
- link.className = `toc-link is-level-${item.level}`;
117
- link.textContent = item.text;
118
- link.dataset.tocTarget = item.id;
119
-
120
- return link;
121
- }
122
-
123
- _updateActive() {
124
- if (!this.runtime.built) return;
125
-
126
- let index = -1;
127
- for (let i = this.dom.headings.length - 1; i >= 0; i--) {
128
- if (
129
- this.dom.headings[i].getBoundingClientRect().top <= this.props.offset
130
- ) {
131
- index = i;
132
- break;
133
- }
134
- }
135
-
136
- if (index === this.state.current.index) return;
137
-
138
- const current = this.state.items[index] || null;
139
- this.setState({
140
- current: { index, item: current },
141
- });
142
-
143
- this.dom.links.forEach((link, i) => {
144
- const active = i === index;
145
- link.dataset.active = active ? '1' : '0';
146
- link.className = `toc-link is-level-${this.state.items[i].level}${
147
- active ? ' is-active' : ''
148
- }`;
149
- });
150
-
151
- if (typeof this.props.onUpdate === 'function') {
152
- this.props.onUpdate(current, index, this);
153
- }
154
- }
155
-
156
- /**
157
- * 重新扫描标题并重建目录列表。
158
- * @returns {Toc} 当前实例。
159
- */
160
- refresh() {
161
- if (this.runtime.destroyed || !this.runtime.built) return this;
162
-
163
- this.cleanup.events.clear();
164
-
165
- this.dom.headings = Array.from(
166
- this.dom.target.querySelectorAll(this.props.headings)
167
- );
168
- const items = this.dom.headings.map(normalizeHeading);
169
- this.dom.links = items.map((item) => this._buildLink(item));
170
-
171
- this.dom.list.innerHTML = '';
172
- for (const link of this.dom.links) this.dom.list.appendChild(link);
173
-
174
- this.setState({
175
- items,
176
- current: { index: -1, item: null },
177
- });
178
-
179
- this._bindEvents();
180
- this._updateActive();
181
- return this;
182
- }
183
-
184
- /**
185
- * 激活并滚动到指定目录项。
186
- * @param {number} index 目录项索引。
187
- * @returns {Toc} 当前实例。
188
- */
189
- activate(index) {
190
- if (!this.runtime.built) return this;
191
- if (
192
- !Number.isInteger(index) ||
193
- index < 0 ||
194
- index >= this.dom.links.length
195
- ) {
196
- return this;
197
- }
198
-
199
- this.dom.links[index].scrollIntoView({
200
- behavior: 'smooth',
201
- block: 'start',
202
- });
203
- return this;
204
- }
205
-
206
- /**
207
- * 销毁实例并清空渲染内容。
208
- * @private
209
- */
210
- onDestroy() {
211
- this.cleanup.events.clear();
212
- if (this.dom.container) this.dom.container.innerHTML = '';
213
-
214
- this.runtime.built = false;
215
- this.runtime.ticking = false;
216
- this.dom.container = null;
217
- this.dom.target = null;
218
- this.dom.list = null;
219
- this.dom.headings = [];
220
- this.dom.links = [];
221
- }
222
- }
223
-
224
- export function createToc(props = {}) {
225
- return new Toc(props);
226
- }
@@ -1,86 +0,0 @@
1
- import { jsx } from 'vanilla-signal';
2
-
3
- import { resolveProps } from '../utilities/core.js';
4
- import { Drop } from './drop.js';
5
-
6
- const TOOLTIP_OPTIONS_SCHEMA = {
7
- name: { default: null, types: ['string', 'null'] },
8
- mode: { default: 'hover', type: 'string' },
9
- position: { default: 'auto', type: 'string' },
10
- offset: { default: 8, type: 'number' },
11
- message: {
12
- default: '',
13
- type: 'string',
14
- normalize: (value) => String(value || '').trim(),
15
- validate: (value) => value.length > 0,
16
- message: 'expects a non-empty string.',
17
- },
18
- className: { default: null, types: ['string', 'null'] },
19
- id: { default: null, types: ['string', 'null'] },
20
- delay: { default: 100, types: ['number', 'object'] },
21
- hoverIntent: { default: true, type: 'boolean' },
22
- };
23
-
24
- /**
25
- * Tooltip 提示组件。
26
- *
27
- * 基于 Drop 实现,提供更轻量的文本提示封装。
28
- */
29
- export class Tooltip {
30
- /**
31
- * 创建 Tooltip 实例。
32
- * @param {HTMLElement} element 目标元素。
33
- * @param {object} [props={}] 提示配置。
34
- */
35
- constructor(element, props = {}) {
36
- const settings = resolveProps(
37
- props,
38
- TOOLTIP_OPTIONS_SCHEMA,
39
- 'Tooltip.props'
40
- );
41
-
42
- this.drop = new Drop(element, {
43
- ...settings,
44
- content: this._buildContent(settings),
45
- });
46
- }
47
-
48
- /**
49
- * 创建 Tooltip 内容节点。
50
- * @private
51
- */
52
- _buildContent(settings) {
53
- const cls = settings.className
54
- ? `j-tooltip ${settings.className}`
55
- : 'j-tooltip';
56
- return jsx('div', {
57
- className: cls,
58
- children: jsx('div', {
59
- className: 'tooltip-message',
60
- children: settings.message,
61
- }),
62
- });
63
- }
64
-
65
- show(useDelay = true) {
66
- this.drop.show(useDelay);
67
- }
68
-
69
- hide(useDelay = true) {
70
- this.drop.hide(useDelay);
71
- }
72
-
73
- toggle() {
74
- this.drop.toggle();
75
- }
76
-
77
- destroy() {
78
- if (!this.drop) return;
79
- this.drop.destroy();
80
- this.drop = null;
81
- }
82
- }
83
-
84
- export function createTooltip(element, props = {}) {
85
- return new Tooltip(element, props);
86
- }