nillud-data-table 1.0.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.md ADDED
@@ -0,0 +1,496 @@
1
+ # [React](https://react.dev/) nillud-data-table Component [![npm version](https://img.shields.io/npm/v/data-table-lib)](https://www.npmjs.com/package/data-table-lib)
2
+
3
+ ## Возможности
4
+
5
+ ✅ Сортировка и фильтрация
6
+ ✅ Поддержка экспорта в Excel и Word
7
+ ✅ Группировка строк и заголовков
8
+ ✅ Поддержка кастомных ячеек и фильтров
9
+ ✅ Локальное сохранение состояния (localStorage)
10
+ ✅ Поддержка React и TypeScript
11
+
12
+ ## Установка
13
+
14
+ ```tsx
15
+ npm install nillud-data-table
16
+ # или
17
+ yarn add nillud-data-table
18
+ ```
19
+
20
+ ## Начало работы
21
+
22
+ #### **Быстрый пример (Quick Start)**
23
+ Сделай короткий рабочий пример (без кастомных кнопок, модалок и т. д.) — для тех, кто просто хочет запустить:
24
+
25
+ ```tsx
26
+ import { DataTable } from 'nillud-data-table'
27
+
28
+ const columns = [{ field: 'name', title: 'Имя' }]
29
+ const data = [{ name: 'Иван' }]
30
+
31
+ <DataTable tableName="my-table" columns={columns} tableData={data} />
32
+ ```
33
+
34
+ #### **Развернутый пример**
35
+
36
+ Вызов со всеми пропсами:
37
+
38
+ ```tsx
39
+ import { DataTable } from 'nillud-data-table'
40
+
41
+ const columns = [{ field: 'name', title: 'Имя' }]
42
+ const data = [{ name: 'Иван' }]
43
+
44
+ <DataTable
45
+ tableName='custom-modal'
46
+ loading={loading}
47
+ loadingElement={loadingElement}
48
+ columns={columns}
49
+ tableData={tableData}
50
+ isFooter
51
+ paginationCounts={[10, 20, 30, 40, 50, 0]}
52
+ scrollable
53
+ scrollHeight={410}
54
+ excelBtn
55
+ wordBtn
56
+ downloadSectionLeftSideContent={<button className='base-button' onClick={() => setCanvas(true)}>OffCanvas</button>}
57
+ excelCustomColumns={[
58
+ {
59
+ key: 'name',
60
+ width: 50
61
+ }
62
+ ]}
63
+ headerGroup={[{title: 'Личные данные', cols: 3}, {title: 'Объект', cols: 3}]}
64
+ groupBy={'status'}
65
+ isTitles={true}
66
+ />
67
+ ```
68
+
69
+ Доступные пропсы компонента:
70
+
71
+ | props | required | type | Описание |
72
+ | :--- | :---: | :---: | :--- |
73
+ | [columns](#columns) | true | array [\{\}] | Принимает в себя массив объектов |
74
+ | [tableData](#tabledata) | true | array [\{\}] | Принимает в себя массив объектов |
75
+ | [tableName](#tablename) | true | string | Наименование таблицы для хранения значений в localStorage |
76
+ | [loading](#loading) | - | boolean | Состояние загрузки, принимает в себя state типа boolean |
77
+ | [loadingElement](#loadingelement) | - | React Element| Кастомный лоадер |
78
+ | [isFooter](#isfooter) | - | boolean | Отображение footer |
79
+ | [paginationCounts](#paginationcounts) | - | array<number> | Принимает массив чисел, число - количество строк для пагинации, (0 это все) |
80
+ | [scrollable](#scrollable) | - | boolean | Зафиксировать высоту таблицы и добавить скролл |
81
+ | [scrollHeight](#scrollheight) | - | number | Высота тела таблицы, работает, если scrollable: true |
82
+ | [exportCustomColumns](#exportcustomcolumns) | - | array [\{\}] | Принимает в себя массив объектов (\{\ key: string, width: number \}\) |
83
+ | [excelBtn](#excelbtn) | - | boolean | Показывать кнопку экспорта Excel |
84
+ | [wordBtn](#wordbtn) | - | boolean | Показывать кнопку экспорта Word |
85
+ | [downloadSectionLeftSideContent](#downloadsectionleftsidecontent) | - | React Element| Отображать контент с левой стороны от кнопок экспорта |
86
+ | [headerGroup](#headergroup) | - | array [\{\}] | Группировка столбцов (\{\ title: string, cols: number \}\) |
87
+ | [groupBy](#groupby) | - | string | Группировка данных, указывается заголовок столбца, по которому нужна группировка |
88
+ | [isTitles](#istitles) | - | boolean | Заголовки при наведении на ячейку, по умолчанию false |
89
+
90
+ Типы описаны components/data-table/DataTable.types.ts
91
+
92
+ Далее подробно про каждый
93
+
94
+ ### columns
95
+
96
+ Обязательный параметр, принимает в себя массив объектов в формате:
97
+
98
+ ```tsx
99
+ {
100
+ field: 'city',
101
+ title: 'Город'
102
+ },
103
+ ```
104
+ Пример массива:
105
+
106
+ ```tsx
107
+ const columns = [
108
+ {
109
+ field: 'id',
110
+ title: '№',
111
+ width: 70,
112
+ autoinc: true
113
+ },
114
+ {
115
+ field: 'name',
116
+ title: 'Наименование',
117
+ filterable: false,
118
+ formatter: function (cell, row) {
119
+ return (
120
+ <div style={{ display: 'flex', alignItems: 'center' }}>
121
+ <span style={{ marginBottom: 3 }}>{cell}</span>
122
+ <span style={{ marginLeft: 5, cursor: 'pointer' }} onClick={() => { setModalShow(true); setRowData(row) }}><PenEdit /></span>
123
+ </div>
124
+ )
125
+ },
126
+ exportCustomCell: function (cell, row) {
127
+ return `${cell} - ${row.date_to}`
128
+ },
129
+ },
130
+ {
131
+ field: 'address',
132
+ title: 'Адрес',
133
+ headerFilter: headerFilterAddress
134
+ },
135
+ {
136
+ field: 'obj',
137
+ title: 'Объект',
138
+ sortable: false
139
+ },
140
+ ]
141
+ ```
142
+
143
+ Доступные ключи объекта:
144
+
145
+ | key | required | type | description |
146
+ | :--- | :---: | :---: | :--- |
147
+ | [field](#field) | true | string | Устанавливает связь по ключу в массиве данных tableData |
148
+ | [title](#title) | true | string | Устанавливает заголовок столбца |
149
+ | [width](#width) | - | number | Принимает числовое значение, ограничивает ширину столбца в пикселях |
150
+ | [autoinc](#autoinc) | - | bool | Форматирует значения в столбце по порядку в таблице, начиная с 1 |
151
+ | [formatter](#formatter) | - | func | Кастомное форматирование, принимает в себя функцию, описание далее |
152
+ | [exportCustomCell](#exportCustomCell) | - | func | Кастомное форматирование для Excel и Word, принимает в себя функцию, описание далее |
153
+ | [headerFilter](#headerFilter) | - | func | Кастомный фильтр, принимает в себя функуцию, описание далее |
154
+ | [sortable](#sortable) | - | sortable | Убирает возможность сортировки, по умолчанию true |
155
+ | [filterable](#filterable) | - | filterable | Убирает возможность фильтрации, по умолчанию true |
156
+
157
+ #### field
158
+
159
+ Обязательный параметр, устанавливает связь по ключу в массиве данных tableData
160
+
161
+ ```tsx
162
+
163
+ // columns
164
+
165
+ [
166
+ {
167
+ field: 'name',
168
+ ...
169
+ },
170
+ ...
171
+ ]
172
+
173
+ // tableData
174
+
175
+ [
176
+ {
177
+ name: 'Иван',
178
+ ...
179
+ },
180
+ ...
181
+ ]
182
+
183
+ ```
184
+
185
+ #### title
186
+
187
+ Обязательный параметр, устанавливает заголовок столбца
188
+
189
+ ```tsx
190
+
191
+ {
192
+ title: 'Имя'
193
+ }
194
+
195
+ ```
196
+
197
+ | Имя |
198
+ | --- |
199
+ | Иван |
200
+
201
+ #### width
202
+
203
+ Устанавливает значение ширины столбца в пикселях, по умолчанию ширина всех столбцов равна
204
+
205
+ #### autoinc
206
+
207
+ При значении **true** форматирует значения в столбце по порядку строк 1 ... N
208
+
209
+ | № |
210
+ | --- |
211
+ | 1 |
212
+ | 2 |
213
+ | ... |
214
+ | N |
215
+
216
+ #### formatter
217
+
218
+ Кастомное отображение ячейки. Принимает в себя функцию с аргументами cell и row, должна возвращать React Component.
219
+
220
+ ```tsx
221
+ {
222
+ ...,
223
+ formatter: function (cell, row) {
224
+ return (
225
+ <div style={{ display: 'flex', alignItems: 'center' }}>
226
+ <span style={{ marginBottom: 3 }}>{cell}</span>
227
+ <span style={{ marginLeft: 5, cursor: 'pointer' }} onClick={() => { setModalShow(true); setRowData(row) }}><PenEdit /></span>
228
+ </div>
229
+ )
230
+ },
231
+ }
232
+ ```
233
+
234
+ #### exportCustomCell
235
+
236
+ Кастомное отображение ячейки excel или ячейки таблицы word. Принимает в себя функцию с аргументами cell и row, должна возвращать значение типа string.
237
+
238
+ ```tsx
239
+ {
240
+ ...,
241
+ exportCustomCell: function (cell, row) {
242
+ return `${cell} - ${row.date_to}`
243
+ },
244
+ }
245
+ ```
246
+
247
+ #### headerFilter
248
+
249
+ Кастомный фильтр колонки. Принимает в себя функцию со значениями headerValue и rowValue
250
+
251
+ ```tsx
252
+ // Функция фильтрации
253
+
254
+ const headerFilterAddress = (headerValue, rowValue) => {
255
+ if (headerValue.includes(" ")) {
256
+ const stringArray = headerValue.split(" ")
257
+
258
+ if (!stringArray.includes('')) {
259
+ var row = rowValue.toLowerCase()
260
+
261
+ const filtered = []
262
+
263
+ for (let i = 0; i < stringArray.length; i++) {
264
+ row = rowValue.toLowerCase().includes(stringArray[i].toLowerCase())
265
+
266
+ row ? filtered.push(row) : null
267
+ }
268
+
269
+ if (filtered.length === stringArray.length) {
270
+ return rowValue
271
+ }
272
+ } else {
273
+ return rowValue.toLowerCase().includes(stringArray[0].toLowerCase())
274
+ }
275
+ } else {
276
+ return rowValue.toLowerCase().includes(headerValue.toLowerCase())
277
+ }
278
+ }
279
+
280
+ // Объект массива columns
281
+
282
+ {
283
+ ...,
284
+ headerFilter: headerFilterAddress
285
+ }
286
+ ```
287
+
288
+ #### sortable
289
+
290
+ Отображение кнопки сортировки. По умолчанию **true**
291
+
292
+ #### filterable
293
+
294
+ Отображение поля фильтрации. По умолчанию **true**
295
+
296
+ ### tableData
297
+
298
+ Обязательный параметр, принимает в себя массив объектов. В простой реализации таблицы в массиве **tableData** объекты должны содержать ключи равные значениям ключа **field** объекта в массиве **columns**
299
+
300
+ ```tsx
301
+ // объект массива columns
302
+
303
+ [
304
+ {
305
+ field: 'id',
306
+ ...
307
+ },
308
+ ]
309
+
310
+ // объект массива tableData
311
+
312
+ [
313
+ {
314
+ "id": 1,
315
+ ...
316
+ },
317
+ ]
318
+ ```
319
+
320
+ ```tsx
321
+ // Пример массива tableData
322
+
323
+ const tableData = [
324
+ {
325
+ "id": 1,
326
+ "name": "Крайний правый",
327
+ "city": "Уфа",
328
+ "address": "Менделеева д. 150",
329
+ "zav_num": "A78B4T561",
330
+ "date_to": "Февраль"
331
+ },
332
+ ]
333
+
334
+ // Пример массива columns
335
+
336
+ const columns = [
337
+ {
338
+ field: 'id',
339
+ ...
340
+ },
341
+ {
342
+ field: 'name',
343
+ ...
344
+ },
345
+ {
346
+ field: 'city',
347
+ ...
348
+ },
349
+ {
350
+ field: 'address',
351
+ ...
352
+ },
353
+ {
354
+ field: 'zav_num',
355
+ ...
356
+ },
357
+ {
358
+ field: 'date_to',
359
+ ...
360
+ },
361
+ ]
362
+ ```
363
+
364
+ ### tableName
365
+
366
+ Обязательный параметр. По умолчанию **'table-data'**. Нужен для сохранения в **localStorage** значений
367
+ - sort
368
+ - filter
369
+ - pagination-counter
370
+
371
+ ### loading
372
+
373
+ Необязательный параметр. Состояние загрузки, тип **boolean**, по умолчанию **false**. При значении **true** в теле таблицы отображается соответствующая информация о загрузке данных. Передавать значение React State
374
+
375
+ ### loadingElement
376
+
377
+ Непобязательный параметр. Используется вместе с **loading**. Принимает **React Element** - который будет отображаться, пока **loading** - **true**
378
+
379
+ ### isFooter
380
+
381
+ Необязательный параметр. По умолчанию **false**. Отображает **footer** таблицы, а именно:
382
+ - Количество строк
383
+ - Пагинацию
384
+
385
+ ### paginationCounts
386
+
387
+ Необязательный параметр. Используется вместе с **isFooter**. Принимает **массив чисел**, число - колчество отображаемых строк.
388
+
389
+ ```tsx
390
+ isFooter
391
+ paginationCounts={[10, 20, 30, 40, 50, 0]}
392
+ ```
393
+
394
+ Если указать 0, то это будет означать отображение всех строк
395
+
396
+ ### scrollable
397
+
398
+ Необязательный параметр. По умолчанию **false**. Добавляет ограниченную высоту, по умолчанию **300px** и скроллинг таблицы.
399
+
400
+ ### scrollHeight
401
+
402
+ Непобязательный параметр. Используется вместе с **scrollable**. Принимает **числовое значение** - высота в пикселях
403
+
404
+ ```tsx
405
+ scrollable
406
+ scrollHeight={410}
407
+ ```
408
+
409
+ ### exportCustomColumns
410
+
411
+ Необязательный параметр. Принимает в себя массив объектов формата.
412
+ По умолчанию:
413
+ - Ключ header содержит в себе значение **title** объекта из массива columns
414
+ - Ключ key содержит в себе значение **field** объекта из массива columns
415
+ - Ключ width по умолчанию умеет ширину 20 у.е. по системе Excel
416
+
417
+ Дополнительные параметры можно добавлять исходя из документации [exceljs](https://www.npmjs.com/package/exceljs).
418
+ Для изменения/добавления каких-либо параметров в массиве необходимо указать объект с нужным ключом **key**
419
+
420
+ ```tsx
421
+ excelCustomColumns={[
422
+ {
423
+ key: 'name',
424
+ width: 50
425
+ }
426
+ ]}
427
+ ```
428
+
429
+ ### excelBtn
430
+
431
+ Необязательный параметр. Тип **boolean**, по умолчанию **false**. При значении **true** над таблицей с правой стороны появляется кнопка экспорта Excel, которая по умолчанию принимает в себя исходный массив **tableData**
432
+
433
+ Для использования модуля Excel необходимо установить библиотеку [exceljs](https://www.npmjs.com/package/exceljs)
434
+
435
+ ```tsx
436
+ npm i exceljs
437
+ -или-
438
+ yarn add exceljs
439
+ ```
440
+
441
+ ### wordBtn
442
+
443
+ Необязательный параметр. Тип **boolean**, по умолчанию **false**. При значении **true** над таблицей с правой стороны появляется кнопка экспорта Word, которая по умолчанию принимает в себя исходный массив **tableData**
444
+
445
+ Для использования модуля Word необходимо установить библиотеки [docx](https://www.npmjs.com/package/docx) и [file-saver](https://www.npmjs.com/package/file-saver)
446
+
447
+ ```tsx
448
+ npm i docx file-saver
449
+ -или-
450
+ yarn add docx file-saver
451
+ ```
452
+
453
+ ### wordOptions
454
+
455
+ Необязательный параметр. Используется вместе с **wordBtn**. Принимает в себя объект
456
+
457
+ ```tsx
458
+ options = {
459
+ fontSize: 20, // размер шрифта,
460
+ boldHeaders: false, // Заголовки жирным начертанием,
461
+ autoLandscape: false, // делать ли альбомный формат,
462
+ maxColumnsBeforeLandscape: 5 // и от скольки столбцов.
463
+ }
464
+ ```
465
+
466
+ ### downloadSectionLeftSideContent
467
+
468
+ Необязательный параметр. Передается **React.Component**. Отображает компонент с левой стороны от кнопок экспорта. Создано для экономии места
469
+
470
+ ```tsx
471
+ downloadSectionLeftSideContent={<button className='base-button' onClick={() => setCanvas(true)}>OffCanvas</button>}
472
+ ```
473
+
474
+ ### headerGroup
475
+
476
+ Необязательный параметр. Передается **массив объектов**. Отображает сгруппированные заголовки таблицы, где title - заголовок группы, а cols - количество столбцов, на которое растягивается группа
477
+
478
+ ```tsx
479
+ headerGroup={[{ title: 'Личные данные', cols: 4 }, { title: 'Оборудование', cols: 2 }]}
480
+ ```
481
+
482
+ ### groupBy
483
+
484
+ Необязательный параметр. Передается **строка**. Отображает строки таблицы, сгруппированные по столбцу, указанному в groupBy, каждую группу можно свернуть и раскрыть
485
+
486
+ ```tsx
487
+ groupBy={'status'}
488
+ ```
489
+
490
+ ### isTitles
491
+
492
+ Необязательный параметр. Передается **boolean** значение. Отображает **html title** при наведении на ячейку, по умолчанию **false**
493
+
494
+ ```tsx
495
+ isTitles
496
+ ```
@@ -0,0 +1,58 @@
1
+ import * as react from 'react';
2
+ import { ReactElement } from 'react';
3
+
4
+ type TableElement = {
5
+ [key: string]: string | number;
6
+ };
7
+ type TableData = Array<TableElement>;
8
+ type Column = {
9
+ field: string;
10
+ title: string;
11
+ width?: number;
12
+ autoinc?: boolean;
13
+ formatter?: (cell: string, row: TableElement) => ReactElement;
14
+ exportCustomCell?: (cell: string, row: TableElement) => string;
15
+ headerFilter?: (headerValue: string, rowValue: string) => string;
16
+ sortable?: boolean;
17
+ filterable?: boolean;
18
+ };
19
+ type ExportOptions = {
20
+ fontSize?: number;
21
+ boldHeaders?: boolean;
22
+ autoLandscape?: boolean;
23
+ maxColumnsBeforeLandscape?: number;
24
+ };
25
+ type TableProps = {
26
+ tableData: TableData;
27
+ columns: Array<Column>;
28
+ tableName: string;
29
+ loading?: boolean;
30
+ loadingElement?: ReactElement | null;
31
+ isFooter?: boolean;
32
+ paginationCounts?: Array<number> | null;
33
+ scrollable?: boolean;
34
+ scrollHeight?: number;
35
+ exportCustomColumns?: Array<{
36
+ header: string;
37
+ key: string;
38
+ width: number;
39
+ }> | null;
40
+ excelBtn?: boolean;
41
+ wordBtn?: boolean;
42
+ downloadSectionLeftSideContent?: ReactElement | null;
43
+ headerGroup?: Array<{
44
+ title: string;
45
+ cols: number;
46
+ }> | null;
47
+ groupBy?: string | null;
48
+ isTitles?: boolean;
49
+ wordOptions?: ExportOptions;
50
+ };
51
+ type DataTableRef = {
52
+ getData: () => TableData;
53
+ getCurrentData: () => TableData;
54
+ };
55
+
56
+ declare const DataTable: react.ForwardRefExoticComponent<TableProps & react.RefAttributes<DataTableRef>>;
57
+
58
+ export { type Column, DataTable, type TableElement, type TableProps };
@@ -0,0 +1,58 @@
1
+ import * as react from 'react';
2
+ import { ReactElement } from 'react';
3
+
4
+ type TableElement = {
5
+ [key: string]: string | number;
6
+ };
7
+ type TableData = Array<TableElement>;
8
+ type Column = {
9
+ field: string;
10
+ title: string;
11
+ width?: number;
12
+ autoinc?: boolean;
13
+ formatter?: (cell: string, row: TableElement) => ReactElement;
14
+ exportCustomCell?: (cell: string, row: TableElement) => string;
15
+ headerFilter?: (headerValue: string, rowValue: string) => string;
16
+ sortable?: boolean;
17
+ filterable?: boolean;
18
+ };
19
+ type ExportOptions = {
20
+ fontSize?: number;
21
+ boldHeaders?: boolean;
22
+ autoLandscape?: boolean;
23
+ maxColumnsBeforeLandscape?: number;
24
+ };
25
+ type TableProps = {
26
+ tableData: TableData;
27
+ columns: Array<Column>;
28
+ tableName: string;
29
+ loading?: boolean;
30
+ loadingElement?: ReactElement | null;
31
+ isFooter?: boolean;
32
+ paginationCounts?: Array<number> | null;
33
+ scrollable?: boolean;
34
+ scrollHeight?: number;
35
+ exportCustomColumns?: Array<{
36
+ header: string;
37
+ key: string;
38
+ width: number;
39
+ }> | null;
40
+ excelBtn?: boolean;
41
+ wordBtn?: boolean;
42
+ downloadSectionLeftSideContent?: ReactElement | null;
43
+ headerGroup?: Array<{
44
+ title: string;
45
+ cols: number;
46
+ }> | null;
47
+ groupBy?: string | null;
48
+ isTitles?: boolean;
49
+ wordOptions?: ExportOptions;
50
+ };
51
+ type DataTableRef = {
52
+ getData: () => TableData;
53
+ getCurrentData: () => TableData;
54
+ };
55
+
56
+ declare const DataTable: react.ForwardRefExoticComponent<TableProps & react.RefAttributes<DataTableRef>>;
57
+
58
+ export { type Column, DataTable, type TableElement, type TableProps };