@timlassiter11/yatl 1.0.2 → 1.0.4

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.md CHANGED
@@ -1,6 +1,9 @@
1
- # YATL
1
+ # YATL (Yet Another Table Library)
2
2
 
3
- **Yet Another Table Library**
3
+ [![NPM Version](https://img.shields.io/npm/v/@timlassiter11/yatl)](https://www.npmjs.com/package/@timlassiter11/yatl)
4
+ [![API Docs](https://img.shields.io/badge/docs-typedoc-blue)](https://timlassiter11.github.io/YATL/docs/index.html)
5
+ [![Live Demo](https://img.shields.io/badge/demo-online-green)](https://timlassiter11.github.io/YATL/examples/advanced.html)
6
+ [![License](https://img.shields.io/npm/l/@timlassiter11/yatl)](LICENSE)
4
7
 
5
8
  YATL is a powerful, feature-rich, and lightweight Web Component data table built with Lit. It handles large datasets with ease using virtual scrolling, offers advanced fuzzy search capabilities, supports state persistence, and works in any framework (React, Vue, Angular, or Vanilla JS).
6
9
 
@@ -62,11 +65,14 @@ class MyComponent extends LitElement {
62
65
  ];
63
66
 
64
67
  protected override render() {
65
- return html`<yatl-table
66
- .columns=${this._columns}
67
- .data=${this._tableData}
68
- enable-virtual-scroll
69
- @dt.row.clicked=${(event) => console.log(event.detail.row)}></yatl-table>`
68
+ return html`
69
+ <yatl-table
70
+ .columns=${this._columns}
71
+ .data=${this._tableData}
72
+ enable-virtual-scroll
73
+ @yatl-row-click=${this.handleRowClicked}>
74
+ </yatl-table>
75
+ `;
70
76
  }
71
77
 
72
78
  private handleRowClicked = (event) => {
@@ -75,11 +81,9 @@ class MyComponent extends LitElement {
75
81
  }
76
82
  ```
77
83
 
78
- ### npm
79
-
80
- ```ts
81
- import '@timlassiter11/yatl';
84
+ ### js
82
85
 
86
+ ```js
83
87
  const table = document.querySelector('yatl-table');
84
88
 
85
89
  table.columns = [
@@ -104,42 +108,52 @@ table.data = [
104
108
  ### Vanilla JS
105
109
 
106
110
  ```html
107
- <!DOCTYPE html>
111
+ <!doctype html>
108
112
  <html lang="en">
109
113
  <head>
110
- <meta charset="UTF-8" />
111
- <title>YATL Demo</title>
112
- <script src="yatl.min.global.js"></script>
113
-
114
+ <meta charset="utf-8" />
115
+ <title>Basic Example</title>
114
116
  <style>
115
- yatl-table {
116
- height: 500px;
117
- display: block;
118
- border: 1px solid #ddd;
117
+ body {
118
+ height: 100vh;
119
+ width: 100vw;
120
+ margin: 0;
121
+ padding: 20px;
122
+ box-sizing: border-box;
119
123
  }
120
124
  </style>
121
125
  </head>
122
- <body>
123
- <yatl-table id="my-table" enable-footer enable-column-reorder></yatl-table>
124
126
 
127
+ <body>
128
+ <yatl-table sortable resizable enable-footer></yatl-table>
129
+ <script src="../dist/yatl.min.global.js"></script>
125
130
  <script>
126
- const table = document.getElementById('my-table');
127
-
128
- // Define Columns
129
- table.columns = [
130
- { field: 'id', title: 'ID', width: 50 },
131
- { field: 'firstName', title: 'First Name', sortable: true },
132
- { field: 'lastName', title: 'Last Name', sortable: true },
133
- { field: 'email', title: 'Email', width: 200 },
134
- ];
135
-
136
- // Load some data
137
- table.data = Array.from({ length: 1000 }, (_, i) => ({
138
- id: i + 1,
139
- firstName: `User ${i}`,
140
- lastName: `Doe`,
141
- email: `user${i}@example.com`,
142
- }));
131
+ window.addEventListener('load', () => {
132
+ const table = document.querySelector('yatl-table');
133
+ table.columns = [
134
+ {
135
+ field: 'index',
136
+ title: 'ID',
137
+ },
138
+ {
139
+ field: 'name',
140
+ },
141
+ {
142
+ field: 'value',
143
+ },
144
+ ];
145
+
146
+ // Generate random rows of data
147
+ table.data = new Array(100).fill(null).map((v, i) => ({
148
+ index: i,
149
+ name: `Row ${i}`,
150
+ value: Math.random() * 1000,
151
+ }));
152
+
153
+ table.addEventListener('yatl-row-click', event => {
154
+ console.log(event.detail);
155
+ });
156
+ });
143
157
  </script>
144
158
  </body>
145
159
  </html>
@@ -286,12 +300,4 @@ Most of the time this isn't ideal though and instead we'd like to let the layout
286
300
  <div>... Some boring footer info or something</div>
287
301
  </div>
288
302
  </body>
289
- ```
290
-
291
- ### Docs
292
-
293
- Full API docs can be found [here](https://timlassiter11.github.io/YATL/docs/index.html).
294
-
295
- # Examples
296
-
297
- Examples can be found in the examples directoy and are also hosted [here](https://timlassiter11.github.io/YATL/examples/index.html) to view live.
303
+ ```
package/dist/index.d.mts CHANGED
@@ -5,18 +5,10 @@ type NestedKeyOf<ObjectType> = ObjectType extends object ? {
5
5
  [Key in keyof ObjectType & (string | number)]: NonNullable<ObjectType[Key]> extends unknown[] ? `${Key}` : NonNullable<ObjectType[Key]> extends object ? // Recurse with the non-nullable type
6
6
  `${Key}` | `${Key}.${NestedKeyOf<NonNullable<ObjectType[Key]>>}` : `${Key}`;
7
7
  }[keyof ObjectType & (string | number)] : never;
8
- declare const createRegexTokenizer: (exp?: string) => (value: string) => {
9
- value: string;
10
- quoted: boolean;
11
- }[];
12
- declare const whitespaceTokenizer: (value: string) => {
13
- value: string;
14
- quoted: boolean;
15
- }[];
16
- declare function findColumn<T extends {
17
- field: string;
18
- }>(field: string, columns: T[]): T | undefined;
19
-
8
+ /**
9
+ * Default type for the table.
10
+ */
11
+ type UnspecifiedRecord = Record<string, any>;
20
12
  /**
21
13
  * Defines the possible sorting orders for columns.
22
14
  */
@@ -122,22 +114,29 @@ interface SortState {
122
114
  */
123
115
  priority: number;
124
116
  }
117
+ type ColumnRole = 'display' | 'internal';
125
118
  /**
126
- * Column options for the table.
119
+ * Shared options between both internal and displayed columns.
127
120
  */
128
- interface ColumnOptions<T> {
121
+ interface BaseColumnOptions<T> {
129
122
  /**
130
123
  * The field name in the data object.
131
124
  */
132
125
  field: NestedKeyOf<T>;
133
126
  /**
134
- * The title to display in the header.
127
+ * Determines if a column is intended to be displayed,
128
+ * or just for searching and filtering.
135
129
  */
136
- title?: string;
130
+ role?: ColumnRole;
137
131
  /**
138
132
  * Whether the column is sortable.
139
133
  */
140
134
  sortable?: boolean;
135
+ /**
136
+ * A function to use for sorting the column.
137
+ * This overrides the default sorting behavior.
138
+ */
139
+ sorter?: SortValueCallback;
141
140
  /**
142
141
  * Whether the column is searchable.
143
142
  */
@@ -146,15 +145,34 @@ interface ColumnOptions<T> {
146
145
  * Whether the column's data should be tokenized for searching.
147
146
  */
148
147
  tokenize?: boolean;
149
- /**
150
- * Whether the column should be resizable.
151
- */
152
- resizable?: boolean;
153
148
  /**
154
149
  * A function for tokenizing this column's data.
155
150
  * Fallback to the main table tokenizer if not provided.
156
151
  */
157
152
  searchTokenizer?: TokenizerCallback;
153
+ /**
154
+ * A custom function to determine if a cell's value in this column matches a given filter criterion.
155
+ * This is used when `DataTable.filter()` is called with an object-based filter that targets this column's field.
156
+ */
157
+ filter?: ColumnFilterCallback;
158
+ }
159
+ /**
160
+ * Column options for the table.
161
+ */
162
+ interface DisplayColumnOptions<T> extends BaseColumnOptions<T> {
163
+ /**
164
+ * Determines if a column is intended to be displayed,
165
+ * or just for searching and filtering.
166
+ */
167
+ role?: 'display';
168
+ /**
169
+ * The title to display in the header.
170
+ */
171
+ title?: string;
172
+ /**
173
+ * Whether the column should be resizable.
174
+ */
175
+ resizable?: boolean;
158
176
  /**
159
177
  * A function to format the value for display.
160
178
  */
@@ -168,22 +186,18 @@ interface ColumnOptions<T> {
168
186
  * NOTE: Search highlighting will not work for this cell when used.
169
187
  */
170
188
  cellRenderer?: CellRenderCallback<T>;
189
+ }
190
+ /**
191
+ * Internal column definition used for searching and filtering
192
+ */
193
+ interface InternalColumnOptions<T> extends BaseColumnOptions<T> {
171
194
  /**
172
- * A function to use for sorting the column.
173
- * This overrides the default sorting behavior.
174
- */
175
- sorter?: ComparatorCallback;
176
- /**
177
- * A function to derive a comparable value from the cell's original value, specifically for sorting this column.
178
- * This can be used to preprocess and cache values (e.g., convert to lowercase, extract numbers) before comparison.
179
- */
180
- sortValue?: SortValueCallback;
181
- /**
182
- * A custom function to determine if a cell's value in this column matches a given filter criterion.
183
- * This is used when `DataTable.filter()` is called with an object-based filter that targets this column's field.
195
+ * Marks this column as internal-only.
196
+ * It will be indexed for search and filtering, but strictly excluded from the UI.
184
197
  */
185
- filter?: ColumnFilterCallback;
198
+ display: 'internal';
186
199
  }
200
+ type ColumnOptions<T> = DisplayColumnOptions<T> | InternalColumnOptions<T>;
187
201
  /**
188
202
  * Represents the current state of a column.
189
203
  */
@@ -315,23 +329,32 @@ declare class YatlStateChangeEvent<T> extends YatlEvent<{
315
329
  constructor(state: TableState<T>, triggers: string[]);
316
330
  }
317
331
 
332
+ declare const createRegexTokenizer: (exp?: string) => (value: string) => {
333
+ value: string;
334
+ quoted: boolean;
335
+ }[];
336
+ declare const whitespaceTokenizer: (value: string) => {
337
+ value: string;
338
+ quoted: boolean;
339
+ }[];
340
+
318
341
  /**
319
342
  * Represents a dynamic and interactive table with features like sorting, searching, filtering,
320
343
  * column resizing, column rearranging, and virtual scrolling.
321
344
  */
322
- declare class YatlTable<T extends object> extends LitElement {
345
+ declare class YatlTable<T extends object = UnspecifiedRecord> extends LitElement {
323
346
  static styles: lit.CSSResult[];
324
347
  private tableElement;
325
348
  private virtualizer?;
326
349
  private _enableSearchTokenization;
327
350
  private _enableSearchScoring;
328
351
  private _columns;
329
- private _columnStates;
352
+ private _columnDefinitionMap;
353
+ private _columnStateMap;
330
354
  private _columnOrder;
331
355
  private _storageOptions;
332
356
  private _data;
333
357
  private _searchQuery;
334
- private _searchIncludedFields;
335
358
  private _searchTokenizer;
336
359
  private _filters;
337
360
  private _filteredData;
@@ -344,6 +367,20 @@ declare class YatlTable<T extends object> extends LitElement {
344
367
  private queryTokens;
345
368
  private resizeState;
346
369
  private dragColumn;
370
+ /**
371
+ * Default sortability for all columns.
372
+ * Can be overridden by setting `sortable` on the specific column definition.
373
+ * * **NOTE:** Changing this will not clear sorted column states.
374
+ * @default false
375
+ */
376
+ sortable: boolean;
377
+ /**
378
+ * Default resizability for all columns.
379
+ * Can be overridden by setting `resizable` on the specific column definition.
380
+ * * **NOTE:** Changing this will not clear current column widths.
381
+ * @default false
382
+ */
383
+ resizable: boolean;
347
384
  /**
348
385
  * Enables virtual scrolling for the table.
349
386
  * When enabled, only the visible rows are rendered to the DOM, significantly improving
@@ -408,8 +445,17 @@ declare class YatlTable<T extends object> extends LitElement {
408
445
  */
409
446
  get columns(): ColumnOptions<T>[];
410
447
  set columns(columns: ColumnOptions<T>[]);
448
+ get displayColumns(): DisplayColumnOptions<T>[];
449
+ /**
450
+ * The current order of the columns.
451
+ * * **NOTE:** This includes hidden columns but not internal columns
452
+ */
411
453
  get columnOrder(): NestedKeyOf<T>[];
412
454
  set columnOrder(columns: NestedKeyOf<T>[]);
455
+ /**
456
+ * The current visibility state of all columns.
457
+ * **This will always be ordered by {@link YatlTable.columnOrder}**
458
+ */
413
459
  get columnVisibility(): {
414
460
  field: NestedKeyOf<T>;
415
461
  visible: boolean;
@@ -418,6 +464,10 @@ declare class YatlTable<T extends object> extends LitElement {
418
464
  field: NestedKeyOf<T>;
419
465
  visible: boolean;
420
466
  }[]);
467
+ /**
468
+ * The current sort state of all columns.
469
+ * **This will always be orderd by {@link YatlTable.columnOrder}**
470
+ */
421
471
  get columnSort(): {
422
472
  field: NestedKeyOf<T>;
423
473
  sort: SortState | null;
@@ -426,6 +476,10 @@ declare class YatlTable<T extends object> extends LitElement {
426
476
  field: NestedKeyOf<T>;
427
477
  sort: SortState | null;
428
478
  }[]);
479
+ /**
480
+ * The current width of all columns.
481
+ * **This will always be ordered by {@link YatlTable.columnOrder}**
482
+ */
429
483
  get columnWidths(): {
430
484
  field: NestedKeyOf<T>;
431
485
  width: number | null;
@@ -440,12 +494,6 @@ declare class YatlTable<T extends object> extends LitElement {
440
494
  */
441
495
  get searchQuery(): string;
442
496
  set searchQuery(query: string);
443
- /**
444
- * A list of extra data fields to include in the search index, even if they are not
445
- * displayed as visible columns. Useful for searching by ID, hidden keywords, or tags.
446
- */
447
- get searchIncludedFields(): NestedKeyOf<T>[];
448
- set searchIncludedFields(fields: NestedKeyOf<T>[]);
449
497
  /**
450
498
  * A function that splits the search query into tokens.
451
499
  * Only used if `enableSearchTokenization` is true.
@@ -487,6 +535,8 @@ declare class YatlTable<T extends object> extends LitElement {
487
535
  get data(): T[];
488
536
  set data(value: T[]);
489
537
  get filteredData(): T[];
538
+ getColumn(field: NestedKeyOf<T>): ColumnOptions<T> | undefined;
539
+ getDisplayColumn(field: NestedKeyOf<T>): DisplayColumnOptions<T> | undefined;
490
540
  /**
491
541
  * Gets a copy of the current state of the table.
492
542
  */
@@ -580,12 +630,12 @@ declare class YatlTable<T extends object> extends LitElement {
580
630
  * @param index - The original index of the row to delete.
581
631
  */
582
632
  deleteRow(index: number): void;
583
- protected renderColumnSortIcon(column: ColumnOptions<T>, state: ColumnState<T>): TemplateResult<1> | typeof nothing;
584
- protected renderColumnResizer(column: ColumnOptions<T>, _state: ColumnState<T>): TemplateResult<1> | typeof nothing;
633
+ protected renderColumnSortIcon(column: DisplayColumnOptions<T>, state: ColumnState<T>): TemplateResult<1> | typeof nothing;
634
+ protected renderColumnResizer(column: DisplayColumnOptions<T>, _state: ColumnState<T>): TemplateResult<1> | typeof nothing;
585
635
  protected renderHeaderCell(field: NestedKeyOf<T>): TemplateResult<1> | typeof nothing;
586
636
  protected renderHeader(): TemplateResult<1>;
587
- protected renderCellContents(value: unknown, column: ColumnOptions<T>, row: T): unknown;
588
- protected renderCell(field: NestedKeyOf<T>, row: T): TemplateResult<1> | typeof nothing;
637
+ protected renderCellContents(value: unknown, column: DisplayColumnOptions<T>, row: T): unknown;
638
+ protected renderCell(field: NestedKeyOf<T>, row: T): TemplateResult<1> | typeof nothing | undefined;
589
639
  protected renderRow(row: T, index: number): TemplateResult<1>;
590
640
  protected renderBody(): TemplateResult<1>;
591
641
  protected renderFooter(): TemplateResult<1> | typeof nothing;
@@ -616,14 +666,17 @@ declare class YatlTable<T extends object> extends LitElement {
616
666
  private sortRows;
617
667
  private createMetadata;
618
668
  private updateInternalQuery;
619
- private get columnData();
620
669
  /**
621
670
  * Gets the width of each column in the
622
671
  * order they will appear in the grid.
623
672
  */
624
673
  private getGridWidths;
625
674
  private scheduleSave;
626
- private getColumnState;
675
+ /**
676
+ * Gets the column state associated with the given field.
677
+ * If the state doesn't exist, a default state will be created.
678
+ */
679
+ private getOrCreateColumnState;
627
680
  private saveStateToStorage;
628
681
  private loadStateFromStorage;
629
682
  private handleHeaderClicked;
@@ -657,8 +710,8 @@ interface EventMap<T> {
657
710
  }
658
711
  declare global {
659
712
  interface HTMLElementTagNameMap {
660
- 'yatl-table': YatlTable<object>;
713
+ 'yatl-table': YatlTable;
661
714
  }
662
715
  }
663
716
 
664
- export { type CellPartsCallback, type CellRenderCallback, type ColumnFilterCallback, type ColumnInitOptions, type ColumnOptions, type ColumnState, type ComparatorCallback, type Compareable, type FilterCallback, type Filters, type NestedKeyOf, type QueryToken, type RestorableColumnState, type RestorableTableState, type RowPartsCallback, type SortOrder, type SortState, type SortValueCallback, type StorageOptions, type TableState, type TokenizerCallback, type ValueFormatterCallback, YatlChangeEvent, YatlColumnReorderEvent, YatlColumnResizeEvent, YatlColumnToggleEvent, YatlEvent, YatlRowClickEvent, YatlSearchEvent, YatlSortEvent, YatlStateChangeEvent, YatlTable, createRegexTokenizer, findColumn, whitespaceTokenizer };
717
+ export { type BaseColumnOptions, type CellPartsCallback, type CellRenderCallback, type ColumnFilterCallback, type ColumnInitOptions, type ColumnOptions, type ColumnRole, type ColumnState, type ComparatorCallback, type Compareable, type DisplayColumnOptions, type FilterCallback, type Filters, type InternalColumnOptions, type NestedKeyOf, type QueryToken, type RestorableColumnState, type RestorableTableState, type RowPartsCallback, type SortOrder, type SortState, type SortValueCallback, type StorageOptions, type TableState, type TokenizerCallback, type UnspecifiedRecord, type ValueFormatterCallback, YatlChangeEvent, YatlColumnReorderEvent, YatlColumnResizeEvent, YatlColumnToggleEvent, YatlEvent, YatlRowClickEvent, YatlSearchEvent, YatlSortEvent, YatlStateChangeEvent, YatlTable, createRegexTokenizer, whitespaceTokenizer };