mtrl 0.3.1 → 0.3.2

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 (159) hide show
  1. package/.env +15 -0
  2. package/CONTRIBUTING.md +8 -8
  3. package/DOCS.md +3 -3
  4. package/README.md +43 -20
  5. package/TESTING.md +128 -18
  6. package/dist/index.js +14865 -0
  7. package/git-user-stats.js +545 -0
  8. package/index.ts +9 -67
  9. package/package.json +8 -3
  10. package/src/components/badge/api.ts +15 -1
  11. package/src/components/badge/badge.ts +43 -4
  12. package/src/components/badge/config.ts +40 -8
  13. package/src/components/badge/index.ts +64 -3
  14. package/src/components/badge/types.ts +175 -33
  15. package/src/components/button/api.ts +63 -1
  16. package/src/components/button/button.ts +39 -3
  17. package/src/components/button/config.ts +21 -4
  18. package/src/components/button/index.ts +26 -1
  19. package/src/components/button/types.ts +7 -1
  20. package/src/components/card/api.ts +78 -9
  21. package/src/components/card/card.ts +58 -3
  22. package/src/components/card/config.ts +41 -11
  23. package/src/components/card/features.ts +39 -12
  24. package/src/components/card/index.ts +84 -19
  25. package/src/components/card/types.ts +218 -29
  26. package/src/components/carousel/carousel.ts +92 -28
  27. package/src/components/carousel/constants.ts +107 -21
  28. package/src/components/carousel/index.ts +31 -13
  29. package/src/components/checkbox/checkbox.ts +83 -16
  30. package/src/components/checkbox/index.ts +43 -1
  31. package/src/components/checkbox/types.ts +219 -32
  32. package/src/components/chips/api.ts +194 -0
  33. package/src/components/{chip → chips/chip}/api.ts +42 -2
  34. package/src/components/chips/chip/chip.ts +131 -0
  35. package/src/components/{chip → chips/chip}/config.ts +3 -3
  36. package/src/components/chips/chip/index.ts +3 -0
  37. package/src/components/chips/chips.md +481 -0
  38. package/src/components/chips/chips.ts +75 -0
  39. package/src/components/chips/config.ts +109 -0
  40. package/src/components/chips/constants.ts +61 -0
  41. package/src/components/chips/features/chip-items.ts +33 -0
  42. package/src/components/chips/features/container.ts +77 -0
  43. package/src/components/chips/features/controller.ts +448 -0
  44. package/src/components/chips/features/index.ts +5 -0
  45. package/src/components/chips/features/label.ts +108 -0
  46. package/src/components/chips/index.ts +11 -0
  47. package/src/components/chips/schema.ts +61 -0
  48. package/src/components/{chip → chips}/types.ts +203 -92
  49. package/src/components/dialog/dialog.ts +99 -16
  50. package/src/components/dialog/index.ts +97 -1
  51. package/src/components/dialog/types.ts +375 -69
  52. package/src/components/divider/config.ts +90 -6
  53. package/src/components/divider/divider.ts +32 -2
  54. package/src/components/divider/features.ts +26 -0
  55. package/src/components/divider/index.ts +30 -0
  56. package/src/components/divider/types.ts +86 -9
  57. package/src/components/extended-fab/api.ts +53 -1
  58. package/src/components/extended-fab/config.ts +29 -1
  59. package/src/components/extended-fab/extended-fab.ts +28 -0
  60. package/src/components/extended-fab/index.ts +36 -0
  61. package/src/components/extended-fab/types.ts +458 -13
  62. package/src/components/fab/api.ts +42 -2
  63. package/src/components/fab/config.ts +29 -1
  64. package/src/components/fab/fab.ts +16 -2
  65. package/src/components/fab/index.ts +35 -0
  66. package/src/components/fab/types.ts +374 -10
  67. package/src/components/list/api.ts +12 -2
  68. package/src/components/list/config.ts +21 -0
  69. package/src/components/list/features.ts +6 -0
  70. package/src/components/list/index.ts +56 -1
  71. package/src/components/list/list-item.ts +46 -2
  72. package/src/components/list/list.ts +73 -2
  73. package/src/components/list/types.ts +172 -0
  74. package/src/components/list/utils.ts +26 -2
  75. package/src/components/menu/api.ts +217 -20
  76. package/src/components/menu/config.ts +27 -0
  77. package/src/components/menu/features/visibility.ts +55 -6
  78. package/src/components/menu/index.ts +64 -0
  79. package/src/components/menu/menu-item.ts +46 -3
  80. package/src/components/menu/menu.ts +77 -1
  81. package/src/components/menu/types.ts +404 -39
  82. package/src/components/sheet/config.ts +1 -2
  83. package/src/components/sheet/features/gestures.ts +1 -1
  84. package/src/components/sheet/features/position.ts +1 -2
  85. package/src/components/sheet/features/state.ts +1 -1
  86. package/src/components/sheet/index.ts +10 -2
  87. package/src/components/sheet/sheet.ts +1 -2
  88. package/src/components/sheet/types.ts +29 -1
  89. package/src/components/slider/api.ts +1 -1
  90. package/src/components/slider/config.ts +1 -1
  91. package/src/components/slider/features/controller.ts +1 -1
  92. package/src/components/slider/features/handlers.ts +1 -1
  93. package/src/components/slider/features/states.ts +1 -1
  94. package/src/components/slider/index.ts +12 -5
  95. package/src/components/slider/schema.ts +1 -1
  96. package/src/components/slider/types.ts +31 -0
  97. package/src/components/tabs/tab-api.ts +1 -1
  98. package/src/components/tabs/types.ts +1 -1
  99. package/src/components/tooltip/api.ts +6 -2
  100. package/src/components/tooltip/config.ts +9 -28
  101. package/src/components/tooltip/index.ts +10 -1
  102. package/src/components/tooltip/types.ts +38 -3
  103. package/src/index.ts +129 -31
  104. package/src/styles/abstract/_mixins.scss +23 -9
  105. package/src/styles/abstract/_variables.scss +14 -4
  106. package/src/styles/components/_card.scss +1 -1
  107. package/src/styles/components/_chip.scss +323 -113
  108. package/src/styles/components/_tabs.scss +1 -1
  109. package/CLAUDE.md +0 -33
  110. package/src/components/checkbox/constants.ts +0 -37
  111. package/src/components/chip/chip-set.ts +0 -225
  112. package/src/components/chip/chip.ts +0 -118
  113. package/src/components/chip/constants.ts +0 -28
  114. package/src/components/chip/index.ts +0 -12
  115. package/src/components/list/constants.ts +0 -116
  116. package/src/components/sheet/constants.ts +0 -20
  117. package/src/components/slider/constants.ts +0 -32
  118. package/src/components/tooltip/constants.ts +0 -27
  119. package/test/components/badge.test.ts +0 -545
  120. package/test/components/bottom-app-bar.test.ts +0 -303
  121. package/test/components/button.test.ts +0 -233
  122. package/test/components/card.test.ts +0 -560
  123. package/test/components/carousel.test.ts +0 -951
  124. package/test/components/checkbox.test.ts +0 -462
  125. package/test/components/chip.test.ts +0 -692
  126. package/test/components/datepicker.test.ts +0 -1124
  127. package/test/components/dialog.test.ts +0 -990
  128. package/test/components/divider.test.ts +0 -412
  129. package/test/components/extended-fab.test.ts +0 -672
  130. package/test/components/fab.test.ts +0 -561
  131. package/test/components/list.test.ts +0 -365
  132. package/test/components/menu.test.ts +0 -718
  133. package/test/components/navigation.test.ts +0 -186
  134. package/test/components/progress.test.ts +0 -567
  135. package/test/components/radios.test.ts +0 -699
  136. package/test/components/search.test.ts +0 -1135
  137. package/test/components/segmented-button.test.ts +0 -732
  138. package/test/components/sheet.test.ts +0 -641
  139. package/test/components/slider.test.ts +0 -1220
  140. package/test/components/snackbar.test.ts +0 -461
  141. package/test/components/switch.test.ts +0 -452
  142. package/test/components/tabs.test.ts +0 -1369
  143. package/test/components/textfield.test.ts +0 -400
  144. package/test/components/timepicker.test.ts +0 -592
  145. package/test/components/tooltip.test.ts +0 -630
  146. package/test/components/top-app-bar.test.ts +0 -566
  147. package/test/core/dom.attributes.test.ts +0 -148
  148. package/test/core/dom.classes.test.ts +0 -152
  149. package/test/core/dom.events.test.ts +0 -243
  150. package/test/core/emitter.test.ts +0 -141
  151. package/test/core/ripple.test.ts +0 -99
  152. package/test/core/state.store.test.ts +0 -189
  153. package/test/core/utils.normalize.test.ts +0 -61
  154. package/test/core/utils.object.test.ts +0 -120
  155. package/test/setup.js +0 -371
  156. package/test/setup.ts +0 -451
  157. package/tsconfig.json +0 -22
  158. package/typedoc.json +0 -28
  159. package/typedoc.simple.json +0 -14
@@ -1,452 +0,0 @@
1
- // test/components/switch.test.ts
2
- import { describe, test, expect, mock } from 'bun:test';
3
- import { JSDOM } from 'jsdom';
4
-
5
- // Set up JSDOM
6
- const dom = new JSDOM(`<!DOCTYPE html><html><body></body></html>`);
7
- global.document = dom.window.document;
8
- global.window = dom.window;
9
- global.Element = dom.window.Element;
10
- global.HTMLElement = dom.window.HTMLElement;
11
- global.Event = dom.window.Event;
12
- global.CustomEvent = dom.window.CustomEvent;
13
-
14
- // Import types directly to avoid circular dependencies
15
- import type {
16
- SwitchComponent,
17
- SwitchConfig,
18
- SwitchLabelPosition
19
- } from '../../src/components/switch/types';
20
-
21
- // Define constants here to avoid circular dependencies
22
- const SWITCH_LABEL_POSITION = {
23
- START: 'start',
24
- END: 'end'
25
- } as const;
26
-
27
- // Create a mock switch implementation
28
- const createMockSwitch = (config: SwitchConfig = {}): SwitchComponent => {
29
- // Default configuration
30
- const defaultConfig: SwitchConfig = {
31
- label: '',
32
- labelPosition: 'end',
33
- checked: false,
34
- disabled: false,
35
- required: false,
36
- prefix: 'mtrl',
37
- componentName: 'switch'
38
- };
39
-
40
- // Merge with user configuration
41
- const mergedConfig = {
42
- ...defaultConfig,
43
- ...config
44
- };
45
-
46
- // Create main element
47
- const element = document.createElement('div');
48
- element.className = `${mergedConfig.prefix}-switch`;
49
-
50
- // Add custom class if provided
51
- if (mergedConfig.class) {
52
- element.className += ` ${mergedConfig.class}`;
53
- }
54
-
55
- // Create input element
56
- const input = document.createElement('input');
57
- input.type = 'checkbox';
58
- input.className = `${mergedConfig.prefix}-switch-input`;
59
- input.checked = Boolean(mergedConfig.checked);
60
- input.disabled = Boolean(mergedConfig.disabled);
61
- input.required = Boolean(mergedConfig.required);
62
-
63
- if (mergedConfig.name) {
64
- input.name = mergedConfig.name;
65
- }
66
-
67
- if (mergedConfig.value) {
68
- input.value = mergedConfig.value;
69
- }
70
-
71
- // Create track element
72
- const track = document.createElement('div');
73
- track.className = `${mergedConfig.prefix}-switch-track`;
74
-
75
- // Create thumb element
76
- const thumb = document.createElement('div');
77
- thumb.className = `${mergedConfig.prefix}-switch-thumb`;
78
- track.appendChild(thumb);
79
-
80
- // Create label if provided
81
- let labelElement: HTMLLabelElement | null = null;
82
-
83
- if (mergedConfig.label) {
84
- labelElement = document.createElement('label');
85
- labelElement.className = `${mergedConfig.prefix}-switch-label`;
86
- labelElement.textContent = mergedConfig.label;
87
-
88
- // Position the label appropriately
89
- if (mergedConfig.labelPosition) {
90
- element.classList.add(`${mergedConfig.prefix}-switch--label-${mergedConfig.labelPosition}`);
91
- }
92
- }
93
-
94
- // Add elements to main element
95
- if (labelElement && mergedConfig.labelPosition === 'start') {
96
- element.appendChild(labelElement);
97
- }
98
-
99
- element.appendChild(input);
100
- element.appendChild(track);
101
-
102
- if (labelElement && mergedConfig.labelPosition !== 'start') {
103
- element.appendChild(labelElement);
104
- }
105
-
106
- // Create supporting text element if provided
107
- let supportingTextElement: HTMLElement | null = null;
108
-
109
- if (mergedConfig.supportingText) {
110
- supportingTextElement = document.createElement('div');
111
- supportingTextElement.className = `${mergedConfig.prefix}-switch-helper`;
112
- supportingTextElement.textContent = mergedConfig.supportingText;
113
-
114
- if (mergedConfig.error) {
115
- supportingTextElement.classList.add(`${mergedConfig.prefix}-switch-helper--error`);
116
- element.classList.add(`${mergedConfig.prefix}-switch--error`);
117
- }
118
-
119
- element.appendChild(supportingTextElement);
120
- }
121
-
122
- // Event handlers
123
- const eventHandlers: Record<string, Function[]> = {};
124
-
125
- // Create the label manager
126
- const label = {
127
- setText: (text: string) => {
128
- if (labelElement) {
129
- labelElement.textContent = text;
130
- }
131
- mergedConfig.label = text;
132
- return label;
133
- },
134
- getText: () => {
135
- if (labelElement) {
136
- return labelElement.textContent || '';
137
- }
138
- return mergedConfig.label || '';
139
- },
140
- getElement: () => {
141
- return labelElement as HTMLElement;
142
- }
143
- };
144
-
145
- // Create the switch instance
146
- const switchComp: SwitchComponent = {
147
- element,
148
- input,
149
- config: mergedConfig,
150
- supportingTextElement,
151
-
152
- getValue: () => input.value,
153
- setValue: (value: string) => {
154
- input.value = value;
155
- return switchComp;
156
- },
157
-
158
- check: () => {
159
- input.checked = true;
160
- return switchComp;
161
- },
162
-
163
- uncheck: () => {
164
- input.checked = false;
165
- return switchComp;
166
- },
167
-
168
- toggle: () => {
169
- input.checked = !input.checked;
170
- return switchComp;
171
- },
172
-
173
- isChecked: () => input.checked,
174
-
175
- setLabel: (text: string) => {
176
- mergedConfig.label = text;
177
- if (labelElement) {
178
- labelElement.textContent = text;
179
- } else if (text) {
180
- labelElement = document.createElement('label');
181
- labelElement.className = `${mergedConfig.prefix}-switch-label`;
182
- labelElement.textContent = text;
183
- element.appendChild(labelElement);
184
- }
185
- return switchComp;
186
- },
187
-
188
- getLabel: () => {
189
- if (labelElement) {
190
- return labelElement.textContent || '';
191
- }
192
- return '';
193
- },
194
-
195
- setSupportingText: (text: string, isError = false) => {
196
- if (!supportingTextElement) {
197
- supportingTextElement = document.createElement('div');
198
- supportingTextElement.className = `${mergedConfig.prefix}-switch-helper`;
199
- element.appendChild(supportingTextElement);
200
- }
201
-
202
- supportingTextElement.textContent = text;
203
- supportingTextElement.classList.toggle(`${mergedConfig.prefix}-switch-helper--error`, isError);
204
- element.classList.toggle(`${mergedConfig.prefix}-switch--error`, isError);
205
-
206
- return switchComp;
207
- },
208
-
209
- removeSupportingText: () => {
210
- if (supportingTextElement && supportingTextElement.parentNode) {
211
- supportingTextElement.remove();
212
- supportingTextElement = null;
213
- }
214
- return switchComp;
215
- },
216
-
217
- on: (event: string, handler: Function) => {
218
- if (!eventHandlers[event]) {
219
- eventHandlers[event] = [];
220
- }
221
-
222
- eventHandlers[event].push(handler);
223
- return switchComp;
224
- },
225
-
226
- off: (event: string, handler: Function) => {
227
- if (!eventHandlers[event]) return switchComp;
228
-
229
- eventHandlers[event] = eventHandlers[event].filter(h => h !== handler);
230
- return switchComp;
231
- },
232
-
233
- emit: (event: string, data: any = {}) => {
234
- if (!eventHandlers[event]) return;
235
-
236
- eventHandlers[event].forEach(handler => handler(data));
237
- },
238
-
239
- enable: () => {
240
- input.disabled = false;
241
- element.classList.remove(`${mergedConfig.prefix}-switch--disabled`);
242
- return switchComp;
243
- },
244
-
245
- disable: () => {
246
- input.disabled = true;
247
- element.classList.add(`${mergedConfig.prefix}-switch--disabled`);
248
- return switchComp;
249
- },
250
-
251
- destroy: () => {
252
- // Clear event handlers
253
- Object.keys(eventHandlers).forEach(key => {
254
- eventHandlers[key] = [];
255
- });
256
-
257
- // Remove from DOM if attached
258
- if (element.parentNode) {
259
- element.parentNode.removeChild(element);
260
- }
261
- }
262
- };
263
-
264
- return switchComp;
265
- };
266
-
267
- describe('Switch Component', () => {
268
- test('should create a switch element', () => {
269
- const switchComp = createMockSwitch();
270
- expect(switchComp.element).toBeDefined();
271
- expect(switchComp.element.tagName).toBe('DIV');
272
- expect(switchComp.element.className).toContain('mtrl-switch');
273
- });
274
-
275
- test('should create input element with type checkbox', () => {
276
- const switchComp = createMockSwitch();
277
-
278
- // Check for input through direct property
279
- expect(switchComp.input).toBeDefined();
280
- expect(switchComp.input.type).toBe('checkbox');
281
- });
282
-
283
- test('should apply custom class', () => {
284
- const customClass = 'custom-switch';
285
- const switchComp = createMockSwitch({
286
- class: customClass
287
- });
288
-
289
- expect(switchComp.element.className).toContain(customClass);
290
- });
291
-
292
- test('should add label content through config', () => {
293
- const labelText = 'Toggle me';
294
- const switchComp = createMockSwitch({
295
- label: labelText
296
- });
297
-
298
- // Check config has label
299
- expect(switchComp.config.label).toBe(labelText);
300
- });
301
-
302
- test('should position label correctly', () => {
303
- // Test if the configuration is stored correctly
304
- const startPos = SWITCH_LABEL_POSITION.START;
305
- const startSwitch = createMockSwitch({
306
- label: 'Label at Start',
307
- labelPosition: startPos
308
- });
309
-
310
- // Check label position in config
311
- expect(startSwitch.config.labelPosition).toBe(startPos);
312
-
313
- // Check class is applied
314
- expect(startSwitch.element.className).toContain('mtrl-switch--label-start');
315
-
316
- // Default position (end)
317
- const endSwitch = createMockSwitch({
318
- label: 'Label at End'
319
- });
320
-
321
- expect(endSwitch.element.className).toContain('mtrl-switch--label-end');
322
- });
323
-
324
- test('should handle change events', () => {
325
- const switchComp = createMockSwitch();
326
- const handleChange = mock(() => {});
327
-
328
- // Check if the event handler is registered
329
- switchComp.on('change', handleChange);
330
-
331
- // Simulate change by calling the emit method if it exists
332
- if (switchComp.emit) {
333
- switchComp.emit('change', {});
334
- expect(handleChange).toHaveBeenCalled();
335
- }
336
- });
337
-
338
- test('should support disabled state', () => {
339
- const switchComp = createMockSwitch();
340
-
341
- // Check API methods
342
- expect(typeof switchComp.disable).toBe('function');
343
- expect(typeof switchComp.enable).toBe('function');
344
-
345
- // Test the API methods without making assumptions about implementation
346
- switchComp.disable();
347
- switchComp.enable();
348
-
349
- // Test initially disabled through config
350
- const disabledSwitch = createMockSwitch({ disabled: true });
351
- expect(disabledSwitch.config.disabled).toBe(true);
352
- });
353
-
354
- test('should support checked state', () => {
355
- // Check API methods
356
- const switchComp = createMockSwitch();
357
- expect(typeof switchComp.check).toBe('function');
358
- expect(typeof switchComp.uncheck).toBe('function');
359
- expect(typeof switchComp.toggle).toBe('function');
360
-
361
- // Initial unchecked state
362
- const uncheckedSwitch = createMockSwitch();
363
- expect(uncheckedSwitch.config.checked).toBeFalsy();
364
-
365
- // Initial checked state
366
- const checkedSwitch = createMockSwitch({ checked: true });
367
- expect(checkedSwitch.config.checked).toBe(true);
368
-
369
- // Verify methods execute without errors
370
- switchComp.check();
371
- switchComp.uncheck();
372
- switchComp.toggle();
373
- });
374
-
375
- test('should set name attribute correctly', () => {
376
- const name = 'theme-toggle';
377
- const switchComp = createMockSwitch({ name });
378
-
379
- // Check config
380
- expect(switchComp.config.name).toBe(name);
381
- });
382
-
383
- test('should set value attribute correctly', () => {
384
- const value = 'dark-mode';
385
- const switchComp = createMockSwitch({ value });
386
-
387
- // Check config
388
- expect(switchComp.config.value).toBe(value);
389
- });
390
-
391
- test('should set required attribute correctly', () => {
392
- const switchComp = createMockSwitch({ required: true });
393
-
394
- // Check config
395
- expect(switchComp.config.required).toBe(true);
396
- });
397
-
398
- test('should allow updating label', () => {
399
- const initialLabel = 'Initial Label';
400
- const switchComp = createMockSwitch({
401
- label: initialLabel
402
- });
403
-
404
- // Check initial label in config
405
- expect(switchComp.config.label).toBe(initialLabel);
406
-
407
- // Check setLabel method exists
408
- expect(typeof switchComp.setLabel).toBe('function');
409
-
410
- // Update label
411
- const newLabel = 'Updated Label';
412
- switchComp.setLabel(newLabel);
413
-
414
- // Check if label was updated
415
- expect(switchComp.getLabel()).toBe(newLabel);
416
- });
417
-
418
- test('should include track and thumb elements', () => {
419
- const switchComp = createMockSwitch();
420
-
421
- // Check for track - it might be directly accessible or through the DOM
422
- const hasTrack = switchComp.element.querySelector('.mtrl-switch-track') !== null;
423
-
424
- expect(hasTrack).toBe(true);
425
- });
426
-
427
- test('should have value getter and setter', () => {
428
- const switchComp = createMockSwitch();
429
-
430
- // Check API methods
431
- expect(typeof switchComp.getValue).toBe('function');
432
- expect(typeof switchComp.setValue).toBe('function');
433
-
434
- // Set a value
435
- const testValue = 'test-value';
436
- switchComp.setValue(testValue);
437
-
438
- // Check value
439
- expect(switchComp.getValue()).toBe(testValue);
440
- });
441
-
442
- test('should properly clean up resources', () => {
443
- const switchComp = createMockSwitch();
444
- const parentElement = document.createElement('div');
445
- parentElement.appendChild(switchComp.element);
446
-
447
- // Destroy should remove the element and clean up resources
448
- switchComp.destroy();
449
-
450
- expect(parentElement.children.length).toBe(0);
451
- });
452
- });