mtrl-addons 0.1.0 → 0.1.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 (92) hide show
  1. package/.cursorrules +117 -0
  2. package/AI.md +241 -0
  3. package/build.js +170 -0
  4. package/bun.lock +792 -0
  5. package/index.ts +7 -0
  6. package/package.json +10 -17
  7. package/scripts/analyze-orphaned-functions.ts +387 -0
  8. package/src/components/index.ts +45 -0
  9. package/src/components/list/api.ts +314 -0
  10. package/src/components/list/config.ts +352 -0
  11. package/src/components/list/constants.ts +56 -0
  12. package/src/components/list/features/api.ts +428 -0
  13. package/src/components/list/features/index.ts +31 -0
  14. package/src/components/list/features/list-manager.ts +502 -0
  15. package/src/components/list/features.ts +112 -0
  16. package/src/components/list/index.ts +39 -0
  17. package/src/components/list/list.ts +234 -0
  18. package/src/components/list/types.ts +513 -0
  19. package/src/core/collection/base-collection.ts +100 -0
  20. package/src/core/collection/collection-composer.ts +178 -0
  21. package/src/core/collection/collection.ts +745 -0
  22. package/src/core/collection/constants.ts +172 -0
  23. package/src/core/collection/events.ts +428 -0
  24. package/src/core/collection/features/api/loading.ts +279 -0
  25. package/src/core/collection/features/operations/data-operations.ts +147 -0
  26. package/src/core/collection/index.ts +104 -0
  27. package/src/core/collection/state.ts +497 -0
  28. package/src/core/collection/types.ts +404 -0
  29. package/src/core/compose/features/collection.ts +119 -0
  30. package/src/core/compose/features/index.ts +39 -0
  31. package/src/core/compose/features/performance.ts +161 -0
  32. package/src/core/compose/features/selection.ts +213 -0
  33. package/src/core/compose/features/styling.ts +108 -0
  34. package/src/core/compose/index.ts +31 -0
  35. package/src/core/index.ts +167 -0
  36. package/src/core/layout/config.ts +102 -0
  37. package/src/core/layout/index.ts +168 -0
  38. package/src/core/layout/jsx.ts +174 -0
  39. package/src/core/layout/schema.ts +963 -0
  40. package/src/core/layout/types.ts +92 -0
  41. package/src/core/list-manager/api.ts +599 -0
  42. package/src/core/list-manager/config.ts +593 -0
  43. package/src/core/list-manager/constants.ts +268 -0
  44. package/src/core/list-manager/features/api.ts +58 -0
  45. package/src/core/list-manager/features/collection/collection.ts +705 -0
  46. package/src/core/list-manager/features/collection/index.ts +17 -0
  47. package/src/core/list-manager/features/viewport/constants.ts +42 -0
  48. package/src/core/list-manager/features/viewport/index.ts +16 -0
  49. package/src/core/list-manager/features/viewport/item-size.ts +274 -0
  50. package/src/core/list-manager/features/viewport/loading.ts +263 -0
  51. package/src/core/list-manager/features/viewport/placeholders.ts +281 -0
  52. package/src/core/list-manager/features/viewport/rendering.ts +575 -0
  53. package/src/core/list-manager/features/viewport/scrollbar.ts +495 -0
  54. package/src/core/list-manager/features/viewport/scrolling.ts +795 -0
  55. package/src/core/list-manager/features/viewport/template.ts +220 -0
  56. package/src/core/list-manager/features/viewport/viewport.ts +654 -0
  57. package/src/core/list-manager/features/viewport/virtual.ts +309 -0
  58. package/src/core/list-manager/index.ts +279 -0
  59. package/src/core/list-manager/list-manager.ts +206 -0
  60. package/src/core/list-manager/types.ts +439 -0
  61. package/src/core/list-manager/utils/calculations.ts +290 -0
  62. package/src/core/list-manager/utils/range-calculator.ts +349 -0
  63. package/src/core/list-manager/utils/speed-tracker.ts +273 -0
  64. package/src/index.ts +17 -0
  65. package/src/styles/components/_list.scss +244 -0
  66. package/src/styles/index.scss +12 -0
  67. package/src/types/mtrl.d.ts +6 -0
  68. package/test/benchmarks/layout/advanced.test.ts +656 -0
  69. package/test/benchmarks/layout/comparison.test.ts +519 -0
  70. package/test/benchmarks/layout/performance-comparison.test.ts +274 -0
  71. package/test/benchmarks/layout/real-components.test.ts +733 -0
  72. package/test/benchmarks/layout/simple.test.ts +321 -0
  73. package/test/benchmarks/layout/stress.test.ts +990 -0
  74. package/test/collection/basic.test.ts +304 -0
  75. package/test/components/list.test.ts +256 -0
  76. package/test/core/collection/collection.test.ts +394 -0
  77. package/test/core/collection/failed-ranges.test.ts +270 -0
  78. package/test/core/compose/features.test.ts +183 -0
  79. package/test/core/layout/layout.test.ts +201 -0
  80. package/test/core/list-manager/features/collection.test.ts +704 -0
  81. package/test/core/list-manager/features/viewport.test.ts +698 -0
  82. package/test/core/list-manager/list-manager.test.ts +593 -0
  83. package/test/core/list-manager/utils/calculations.test.ts +433 -0
  84. package/test/core/list-manager/utils/range-calculator.test.ts +569 -0
  85. package/test/core/list-manager/utils/speed-tracker.test.ts +530 -0
  86. package/test/utils/dom-helpers.ts +275 -0
  87. package/test/utils/performance-helpers.ts +392 -0
  88. package/tsconfig.build.json +14 -0
  89. package/tsconfig.json +20 -0
  90. package/dist/index.d.ts +0 -5
  91. package/dist/index.js +0 -38
  92. package/dist/index.mjs +0 -8
@@ -0,0 +1,234 @@
1
+ /**
2
+ * mtrl-addons List Component
3
+ *
4
+ * Next-generation list component built on the collection system.
5
+ * Uses mtrl's compose system with addons-specific features.
6
+ * Follows mtrl patterns for component architecture.
7
+ */
8
+
9
+ import type {
10
+ ListConfig,
11
+ ListComponent,
12
+ ListItem,
13
+ ListPerformanceMetrics,
14
+ } from "./types";
15
+
16
+ // Import mtrl compose system
17
+ import { pipe } from "mtrl/src/core/compose/pipe";
18
+ import { createBase, withElement } from "mtrl/src/core/compose/component";
19
+ import { withEvents, withLifecycle } from "mtrl/src/core/compose/features";
20
+
21
+ // Import list-specific utilities
22
+ import { createBaseConfig, getElementConfig, getApiConfig } from "./config";
23
+ import { LIST_CLASSES } from "./constants";
24
+ import { withListManager } from "./features/list-manager";
25
+ import { withAPI } from "./api";
26
+
27
+ /**
28
+ * Creates list-specific configuration from user config
29
+ */
30
+ function createListConfig<T extends ListItem = ListItem>(
31
+ config: ListConfig<T>
32
+ ) {
33
+ return {
34
+ ...config,
35
+ componentName: "list",
36
+ prefix: "mtrl",
37
+ className: config.className || "addons-list",
38
+ ariaLabel: config.ariaLabel || "List",
39
+ interactive: true, // Enable touch support
40
+ };
41
+ }
42
+
43
+ /**
44
+ * Default list item template
45
+ */
46
+ function getDefaultListTemplate() {
47
+ return {
48
+ tag: "div",
49
+ className: "mtrl-list-item",
50
+ attributes: { "data-id": "{{id}}", role: "listitem" },
51
+ children: [
52
+ {
53
+ tag: "div",
54
+ className: "mtrl-list-item__content",
55
+ textContent: "{{name || id}}",
56
+ },
57
+ ],
58
+ };
59
+ }
60
+
61
+ /**
62
+ * Creates a new List component using the 3-layer architecture
63
+ *
64
+ * The List component provides high-performance virtual scrolling with:
65
+ * - Collection (Data Layer): Pure data management with API integration
66
+ * - List Manager (Performance Layer): Virtual scrolling, element recycling
67
+ * - List Component (Presentation Layer): mtrl integration and user interface
68
+ *
69
+ * This component supports both static data and API-driven dynamic data with
70
+ * infinite scrolling, intelligent caching, and optimal DOM performance.
71
+ *
72
+ * @param {ListConfig<T>} config - List configuration options
73
+ * @returns {ListComponent<T>} A fully configured list component instance
74
+ *
75
+ * @throws {Error} If list creation fails due to invalid configuration
76
+ *
77
+ * @example
78
+ * ```typescript
79
+ * // Create a simple static list
80
+ * const simpleList = createList({
81
+ * items: ['Apple', 'Banana', 'Cherry'],
82
+ * container: '#my-list'
83
+ * });
84
+ *
85
+ * // Create an API-driven list with virtual scrolling
86
+ * const apiList = createList({
87
+ * collection: {
88
+ * baseUrl: 'https://api.example.com',
89
+ * endpoint: '/items',
90
+ * pageSize: 50
91
+ * },
92
+ * scroll: {
93
+ * virtual: true,
94
+ * itemSize: 60,
95
+ * overscan: 5
96
+ * },
97
+ * selection: {
98
+ * enabled: true,
99
+ * mode: 'multiple'
100
+ * },
101
+ * template: (item, index) => `
102
+ * <div class="item">
103
+ * <h3>${item.title}</h3>
104
+ * <p>${item.description}</p>
105
+ * </div>
106
+ * `,
107
+ * on: {
108
+ * onItemClick: (item, index) => {
109
+ * console.log('Clicked:', item);
110
+ * },
111
+ * onLoadMore: async (direction) => {
112
+ * console.log('Load more:', direction);
113
+ * }
114
+ * }
115
+ * });
116
+ *
117
+ * // Add to DOM
118
+ * document.querySelector('#app').appendChild(apiList.element);
119
+ *
120
+ * // Use API methods
121
+ * await apiList.loadData();
122
+ * apiList.selectItems([0, 1, 2]);
123
+ * await apiList.scrollToIndex(100);
124
+ * ```
125
+ *
126
+ * @category Components
127
+ * @module components/list
128
+ */
129
+ export const createList = <T = any>(
130
+ config: ListConfig<T> = {}
131
+ ): ListComponent<T> => {
132
+ try {
133
+ // Validate and create base configuration
134
+ const baseConfig = createBaseConfig(config as any);
135
+
136
+ console.log(`📋 Creating List component with simplified architecture:
137
+ - List Manager (with built-in Collection): ${
138
+ baseConfig.items && baseConfig.items.length > 0 ? "Static" : "API"
139
+ } data source
140
+ - Virtual scrolling: true, Element recycling: true
141
+ - Template: ${!!baseConfig.template}, Selection: ${!!baseConfig.selection
142
+ ?.enabled}`);
143
+
144
+ // Create the List component through functional composition
145
+ const component = pipe(
146
+ // 1. Foundation layer
147
+ createBase, // Base component with event system
148
+ withEvents(), // Event handling capabilities
149
+ withElement(getElementConfig(baseConfig)), // DOM element creation
150
+
151
+ // 2. Core integration layer
152
+ withListManager<T>(baseConfig as any), // Simplified List Manager with built-in Collection
153
+
154
+ // 3. Component lifecycle
155
+ withLifecycle(), // Lifecycle management
156
+
157
+ // 4. Public API layer
158
+ (comp) => withAPI({ component: comp as any, config: baseConfig })(comp) // Clean public API
159
+ )(baseConfig);
160
+
161
+ // Set up initial event handlers from config
162
+ if (baseConfig.on && typeof component.on === "function") {
163
+ // Data events
164
+ if (baseConfig.on.onLoadMore) {
165
+ component.on("load:more", ({ direction }: { direction: string }) => {
166
+ baseConfig.on!.onLoadMore!(direction as any);
167
+ });
168
+ }
169
+
170
+ // Scroll events
171
+ if (baseConfig.on.onScroll) {
172
+ component.on(
173
+ "scroll:change",
174
+ ({
175
+ scrollTop,
176
+ direction,
177
+ }: {
178
+ scrollTop: number;
179
+ direction: string;
180
+ }) => {
181
+ baseConfig.on!.onScroll!(scrollTop, direction as any);
182
+ }
183
+ );
184
+ }
185
+
186
+ // Viewport events
187
+ if (baseConfig.on.onViewportChange) {
188
+ component.on(
189
+ "viewport:change",
190
+ ({ visibleRange }: { visibleRange: any }) => {
191
+ baseConfig.on!.onViewportChange!(visibleRange);
192
+ }
193
+ );
194
+ }
195
+
196
+ // Selection events
197
+ if (baseConfig.on.onSelectionChange) {
198
+ component.on(
199
+ "selection:change",
200
+ ({
201
+ selectedItems,
202
+ selectedIndices,
203
+ }: {
204
+ selectedItems: T[];
205
+ selectedIndices: number[];
206
+ }) => {
207
+ baseConfig.on!.onSelectionChange!(
208
+ selectedItems as any,
209
+ selectedIndices
210
+ );
211
+ }
212
+ );
213
+ }
214
+
215
+ // Item events are handled in orchestration layer
216
+ }
217
+
218
+ // Initialize component
219
+ if (component.lifecycle?.init) {
220
+ component.lifecycle.init();
221
+ }
222
+
223
+ console.log("✅ List component created successfully");
224
+ return component as ListComponent<T>;
225
+ } catch (error) {
226
+ console.error("❌ List creation error:", error);
227
+ throw new Error(`Failed to create list: ${(error as Error).message}`);
228
+ }
229
+ };
230
+
231
+ /**
232
+ * Export the main component creation function
233
+ */
234
+ export default createList;