PluginProbe
Tableberg – Simple Gutenberg Table Block / 1.0.5
Tableberg – Simple Gutenberg Table Block v1.0.5
1.1.5 1.1.4 1.1.3 1.1.2 1.1.1 1.1.0 1.0.5 1.0.4 1.0.3 1.0.2 1.0.1 trunk 0.0.2 0.2.1 0.3.2 0.3.3 0.4.1 0.5.0 0.5.1 0.5.2 0.5.3 0.5.4 0.5.5 0.5.6 0.5.7 All 42 releases
tableberg / renderer / Table / TableAttrs.php

TableAttrs.php in Tableberg – Simple Gutenberg Table Block 1.0.5, at renderer/Table/TableAttrs.php

769 lines 21.2 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 namespace Tableberg\Renderer\Table;
4
5 use Tableberg\Renderer\Attrs\NumberAttr;
6 use Tableberg\Renderer\Attrs\BoolAttr;
7 use Tableberg\Renderer\Attrs\StringAttr;
8 use Tableberg\Renderer\Attrs\Sides;
9 use Tableberg\Renderer\Attrs\Corners;
10
11 use function Tableberg\Renderer\getOrNull;
12
13 class TableAttrs {
14 /** @var NumberAttr */
15 public $version;
16
17 /** @var BoolAttr */
18 public $isExample;
19
20 /** @var TableConfig */
21 public $table;
22
23 /** @var array<int, RowConfig> */
24 public $rows;
25
26 /** @var array<int, ColumnConfig> */
27 public $columns;
28
29 /** @var array<string, CellData> */
30 public $cells;
31
32 /** @var array<string, array<string, mixed>> */
33 public $bindings;
34
35 /** @var CellDefaults */
36 public $cellDefaults;
37
38 /**
39 * @param array $data
40 * @return self
41 */
42 public static function from_array($data) {
43 $data = is_array($data) ? $data : [];
44 $defaults = Defaults::get_defaults();
45
46 $instance = new self();
47 $instance->version = new NumberAttr(
48 getOrNull($data['version']),
49 $defaults['version']
50 );
51 $instance->isExample = new BoolAttr(getOrNull($data['isExample']), $defaults['isExample']);
52 $instance->table = TableConfig::from_array(getOrNull($data['table']));
53 $instance->rows = self::parse_row_configs(getOrNull($data['rows']));
54 $instance->columns = self::parse_columns(getOrNull($data['columns']));
55 $instance->cells = self::parse_cells(getOrNull($data['cells']));
56 $instance->bindings = self::parse_bindings(getOrNull($data['bindings']));
57 $instance->cellDefaults = CellDefaults::from_array(getOrNull($data['cellDefaults']));
58
59 return $instance;
60 }
61
62 /** @return array<string, mixed> */
63 public static function get_table_defaults() {
64 $defaults = Defaults::get_defaults();
65
66 if (isset($defaults['table']) && is_array($defaults['table'])) {
67 return $defaults['table'];
68 }
69
70 if (isset($defaults['tableConfig']) && is_array($defaults['tableConfig'])) {
71 return $defaults['tableConfig'];
72 }
73
74 return [];
75 }
76
77 /** @return array<string, mixed> */
78 public static function get_cell_style_defaults() {
79 $defaults = Defaults::get_defaults();
80
81 if (
82 isset($defaults['cellDefaults']) &&
83 is_array($defaults['cellDefaults']) &&
84 isset($defaults['cellDefaults']['styles']) &&
85 is_array($defaults['cellDefaults']['styles'])
86 ) {
87 return array_merge(
88 ['cells' => []],
89 $defaults['cellDefaults']['styles']
90 );
91 }
92
93 if (isset($defaults['cellStyles']) && is_array($defaults['cellStyles'])) {
94 return array_merge(['cells' => []], $defaults['cellStyles']);
95 }
96
97 return ['cells' => []];
98 }
99
100 /** @return array<int, array{array{int, int}, array<int, mixed>}> */
101 public static function get_data_defaults() {
102 $defaults = Defaults::get_defaults();
103
104 if (
105 isset($defaults['data']) &&
106 is_array($defaults['data']) &&
107 isset($defaults['data']['cells']) &&
108 is_array($defaults['data']['cells'])
109 ) {
110 return $defaults['data']['cells'];
111 }
112
113 return [];
114 }
115
116 /** @return array<int, RowConfig> */
117 private static function parse_row_configs($data) {
118 if (!is_array($data)) {
119 return [];
120 }
121
122 $row_configs = [];
123
124 foreach ($data as $row => $row_config) {
125 $row_configs[(int) $row] = RowConfig::from_array($row_config);
126 }
127
128 return $row_configs;
129 }
130
131 /** @return array<int, ColumnConfig> */
132 private static function parse_columns($data) {
133 if (!is_array($data)) {
134 return [];
135 }
136
137 $columns = [];
138
139 foreach ($data as $column => $column_config) {
140 $columns[(int) $column] = ColumnConfig::from_array(
141 $column_config,
142 'text',
143 true
144 );
145 }
146
147 return $columns;
148 }
149
150 /** @return array<string, CellData> */
151 private static function parse_cells($data) {
152 if (!is_array($data)) {
153 return [];
154 }
155
156 $cells = [];
157
158 foreach ($data as $key => $cell) {
159 if (!is_string($key)) {
160 continue;
161 }
162
163 $cells[$key] = CellData::from_array($cell);
164 }
165
166 return $cells;
167 }
168
169 /** @return array<string, array<string, mixed>> */
170 private static function parse_bindings($data) {
171 if (!is_array($data)) {
172 return [];
173 }
174
175 $bindings = [];
176
177 foreach ($data as $key => $binding) {
178 if (!is_string($key) || !is_array($binding)) {
179 continue;
180 }
181
182 $bindings[$key] = $binding;
183 }
184
185 return $bindings;
186 }
187 }
188
189 class Data {
190 /** @var array<int, array{array{int, int}, array<int, CellElement>}> */
191 public $cells;
192
193 /** @return self */
194 public static function from_array($data) {
195 $data = is_array($data) ? $data : [];
196 $default_cells = TableAttrs::get_data_defaults();
197
198 $instance = new self();
199 $instance->cells = self::parse_cells(getOrNull($data['cells']), $default_cells);
200
201 return $instance;
202 }
203
204 /** @return array<int, array{array{int, int}, array<int, CellElement>}> */
205 private static function parse_cells($data, $default) {
206 if (!is_array($data)) {
207 return $default;
208 }
209
210 $cells = [];
211
212 foreach ($data as $cell) {
213 if (!is_array($cell[0])) {
214 continue;
215 }
216
217 $coords = [(int) $cell[0][0], (int) $cell[0][1]];
218 $elements = [];
219
220 if (is_array($cell[1])) {
221 foreach ($cell[1] as $element) {
222 $elements[] = CellElement::from_array($element);
223 }
224 }
225
226 $cells[] = [$coords, $elements];
227 }
228
229 return $cells;
230 }
231 }
232
233 class PaginationConfig {
234 /** @var BoolAttr */
235 public $enabled;
236
237 /** @var NumberAttr */
238 public $pageSize;
239
240 /** @var BoolAttr */
241 public $showPageNumbers;
242
243 /** @var BoolAttr */
244 public $showPrevNext;
245
246 /** @return self */
247 public static function from_array($data) {
248 $data = is_array($data) ? $data : [];
249 $table_defaults = TableAttrs::get_table_defaults();
250 $d = isset($table_defaults['pagination']) && is_array($table_defaults['pagination'])
251 ? $table_defaults['pagination']
252 : [];
253
254 $instance = new self();
255 $instance->enabled = new BoolAttr(getOrNull($data['enabled']), $d['enabled']);
256 $instance->pageSize = new NumberAttr(getOrNull($data['pageSize']), $d['pageSize']);
257 $instance->showPageNumbers = new BoolAttr(getOrNull($data['showPageNumbers']), $d['showPageNumbers']);
258 $instance->showPrevNext = new BoolAttr(getOrNull($data['showPrevNext']), $d['showPrevNext']);
259
260 return $instance;
261 }
262 }
263
264 class SearchConfig {
265 /** @var BoolAttr */
266 public $enabled;
267
268 /** @var StringAttr */
269 public $placeholder;
270
271 /** @var StringAttr */
272 public $highlightColor;
273
274 /** @var StringAttr */
275 public $position;
276
277 /** @return self */
278 public static function from_array($data) {
279 $data = is_array($data) ? $data : [];
280 $table_defaults = TableAttrs::get_table_defaults();
281 $d = isset($table_defaults['search']) && is_array($table_defaults['search'])
282 ? $table_defaults['search']
283 : [];
284
285 $instance = new self();
286 $instance->enabled = new BoolAttr(getOrNull($data['enabled']), $d['enabled']);
287 $instance->placeholder = new StringAttr(getOrNull($data['placeholder']), $d['placeholder']);
288 $instance->highlightColor = new StringAttr(getOrNull($data['highlightColor']), $d['highlightColor']);
289 $instance->position = new StringAttr(getOrNull($data['position']), $d['position'], ['left', 'right']);
290
291 return $instance;
292 }
293 }
294
295 class ResponsiveBreakpointConfig {
296 /** @var BoolAttr */
297 public $enabled;
298
299 /** @var NumberAttr */
300 public $maxWidth;
301
302 /** @var StringAttr */
303 public $mode;
304
305 /** @var BoolAttr */
306 public $transpose;
307
308 /** @var NumberAttr */
309 public $stackCount;
310
311 /** @var BoolAttr */
312 public $repeatFirstCol;
313
314 /**
315 * @param array|null $data
316 * @param array<string, mixed> $defaults
317 * @return self
318 */
319 public static function from_array($data, $defaults) {
320 $data = is_array($data) ? $data : [];
321
322 $instance = new self();
323 $instance->enabled = new BoolAttr(getOrNull($data['enabled']), $defaults['enabled']);
324 $instance->maxWidth = new NumberAttr(getOrNull($data['maxWidth']), $defaults['maxWidth']);
325 $instance->mode = new StringAttr(
326 getOrNull($data['mode']),
327 $defaults['mode'],
328 ['', 'scroll', 'stack']
329 );
330 $transposeInput = getOrNull($data['transpose']);
331 $legacyDirectionInput = getOrNull($data['direction']);
332 if ($transposeInput === null && is_string($legacyDirectionInput)) {
333 $transposeInput = $legacyDirectionInput === 'row';
334 }
335
336 $instance->transpose = new BoolAttr(
337 $transposeInput,
338 $defaults['transpose']
339 );
340 $instance->stackCount = new NumberAttr(
341 getOrNull($data['stackCount']),
342 $defaults['stackCount']
343 );
344
345 $repeatFirstColInput = getOrNull($data['repeatFirstCol']);
346 if ($repeatFirstColInput === null) {
347 $repeatFirstColInput = getOrNull($data['headerAsCol']);
348 }
349
350 $instance->repeatFirstCol = new BoolAttr(
351 $repeatFirstColInput,
352 $defaults['repeatFirstCol']
353 );
354
355 return $instance;
356 }
357 }
358
359 class ResponsiveConfig {
360 /** @var ResponsiveBreakpointConfig */
361 public $tablet;
362
363 /** @var ResponsiveBreakpointConfig */
364 public $mobile;
365
366 /** @return self */
367 public static function from_array($data) {
368 $data = is_array($data) ? $data : [];
369 $table_defaults = TableAttrs::get_table_defaults();
370 $defaults = isset($table_defaults['responsive']) && is_array($table_defaults['responsive'])
371 ? $table_defaults['responsive']
372 : [];
373
374 $instance = new self();
375 $instance->tablet = ResponsiveBreakpointConfig::from_array(
376 getOrNull($data['tablet']),
377 $defaults['tablet']
378 );
379 $instance->mobile = ResponsiveBreakpointConfig::from_array(
380 getOrNull($data['mobile']),
381 $defaults['mobile']
382 );
383
384 return $instance;
385 }
386 }
387
388 class CellSpacingConfig {
389 /** @var StringAttr */
390 public $horizontal;
391
392 /** @var StringAttr */
393 public $vertical;
394
395 /** @return self */
396 public static function from_array($data) {
397 $data = is_array($data) ? $data : [];
398 $table_defaults = TableAttrs::get_table_defaults();
399 $defaults = isset($table_defaults['cellSpacing']) && is_array($table_defaults['cellSpacing'])
400 ? $table_defaults['cellSpacing']
401 : [];
402
403 $instance = new self();
404 $instance->horizontal = new StringAttr(
405 getOrNull($data['horizontal']),
406 $defaults['horizontal']
407 );
408 $instance->vertical = new StringAttr(
409 getOrNull($data['vertical']),
410 $defaults['vertical']
411 );
412
413 return $instance;
414 }
415 }
416
417 class CellDefaults {
418 /** @var CellStyles */
419 public $styles;
420
421 /** @return self */
422 public static function from_array($data) {
423 $data = is_array($data) ? $data : [];
424
425 $instance = new self();
426 $instance->styles = CellStyles::from_array(getOrNull($data['styles']));
427
428 return $instance;
429 }
430 }
431
432 class CellData {
433 /** @var Span */
434 public $span;
435
436 /** @var StringAttr */
437 public $className;
438
439 /** @var array<int, CellElement> */
440 public $elements;
441
442 /** @var array<string, mixed>|null */
443 public $styles;
444
445 /** @var array<string, mixed>|null */
446 public $ribbon;
447
448 /** @return self */
449 public static function from_array($data) {
450 $data = is_array($data) ? $data : [];
451
452 $instance = new self();
453 $instance->span = Span::from_array(getOrNull($data['span']));
454 $instance->className = new StringAttr(getOrNull($data['className']), '');
455 $instance->elements = [];
456
457 $elements = getOrNull($data['elements']);
458 if (is_array($elements)) {
459 foreach ($elements as $element) {
460 $instance->elements[] = CellElement::from_array($element);
461 }
462 }
463
464 $styles = getOrNull($data['styles']);
465 $instance->styles = is_array($styles) ? $styles : null;
466
467 $ribbon = getOrNull($data['ribbon']);
468 $instance->ribbon = is_array($ribbon) ? $ribbon : null;
469
470 return $instance;
471 }
472 }
473
474 class TableConfig {
475 /** @var NumberAttr */
476 public $rows;
477
478 /** @var NumberAttr */
479 public $cols;
480
481 /** @var StringAttr */
482 public $className;
483
484 /** @var BoolAttr */
485 public $headerEnabled;
486
487 /** @var BoolAttr */
488 public $footerEnabled;
489
490 /** @var BoolAttr */
491 public $stickyHeader;
492
493 /** @var StringAttr */
494 public $caption;
495
496 /** @var StringAttr */
497 public $tableWidth;
498
499 /** @var StringAttr */
500 public $tableAlignment;
501
502 /** @var CellSpacingConfig */
503 public $cellSpacing;
504
505 /** @var Sides */
506 public $tableBorder;
507
508 /** @var Sides */
509 public $margin;
510
511 /** @var Sides */
512 public $padding;
513
514 /** @var BoolAttr */
515 public $fixedColumnWidths;
516
517 /** @var PaginationConfig */
518 public $pagination;
519
520 /** @var SearchConfig */
521 public $search;
522
523 /** @var ResponsiveConfig */
524 public $responsive;
525
526 /** @return self */
527 public static function from_array($data) {
528 $data = is_array($data) ? $data : [];
529 $d = TableAttrs::get_table_defaults();
530
531 $instance = new self();
532 $instance->rows = new NumberAttr(getOrNull($data['rows']), $d['rows']);
533 $instance->cols = new NumberAttr(getOrNull($data['cols']), $d['cols']);
534 $instance->className = new StringAttr(getOrNull($data['className']), '');
535 $instance->headerEnabled = new BoolAttr(getOrNull($data['headerEnabled']), $d['headerEnabled']);
536 $instance->footerEnabled = new BoolAttr(getOrNull($data['footerEnabled']), $d['footerEnabled']);
537 $instance->stickyHeader = new BoolAttr(getOrNull($data['stickyHeader']), $d['stickyHeader']);
538 $instance->caption = new StringAttr(getOrNull($data['caption']), $d['caption']);
539 $instance->tableWidth = new StringAttr(
540 getOrNull($data['tableWidth']),
541 $d['tableWidth']
542 );
543 $instance->tableAlignment = new StringAttr(
544 getOrNull($data['tableAlignment']),
545 $d['tableAlignment'],
546 ['left', 'center', 'right']
547 );
548 $instance->cellSpacing = CellSpacingConfig::from_array(getOrNull($data['cellSpacing']));
549 $instance->tableBorder = Sides::from_array(
550 getOrNull($data['tableBorder']),
551 $d['tableBorder']
552 );
553 $emptySides = ['top' => '', 'right' => '', 'bottom' => '', 'left' => ''];
554 $instance->margin = Sides::from_array(
555 getOrNull($data['margin']),
556 isset($d['margin']) && is_array($d['margin']) ? $d['margin'] : $emptySides
557 );
558 $instance->padding = Sides::from_array(
559 getOrNull($data['padding']),
560 isset($d['padding']) && is_array($d['padding']) ? $d['padding'] : $emptySides
561 );
562 $instance->fixedColumnWidths = new BoolAttr(
563 getOrNull($data['fixedColumnWidths']),
564 $d['fixedColumnWidths']
565 );
566 $instance->pagination = PaginationConfig::from_array(getOrNull($data['pagination']));
567 $instance->search = SearchConfig::from_array(getOrNull($data['search']));
568 $instance->responsive = ResponsiveConfig::from_array(getOrNull($data['responsive']));
569
570 return $instance;
571 }
572 }
573
574 class CellStyles {
575 /** @var Sides */
576 public $padding;
577
578 /** @var StringAttr */
579 public $orientation;
580
581 /** @var StringAttr */
582 public $elementGap;
583
584 /** @var StringAttr */
585 public $wrap;
586
587 /** @var StringAttr */
588 public $verticalAlign;
589
590 /** @var StringAttr */
591 public $backgroundColor;
592
593 /** @var Sides */
594 public $border;
595
596 /** @var Corners */
597 public $borderRadius;
598
599 /** @var array<int, array{array{int, int}, array<string, mixed>}> */
600 public $cells;
601
602 /** @return self */
603 public static function from_array($data) {
604 $data = is_array($data) ? $data : [];
605 $d = TableAttrs::get_cell_style_defaults();
606
607 $instance = new self();
608 $instance->padding = Sides::from_array(getOrNull($data['padding']), $d['padding']);
609 $instance->orientation = new StringAttr(
610 getOrNull($data['orientation']),
611 $d['orientation'],
612 ['vertical', 'horizontal']
613 );
614 $instance->elementGap = new StringAttr(
615 getOrNull($data['elementGap']),
616 $d['elementGap']
617 );
618 $instance->wrap = new StringAttr(
619 getOrNull($data['wrap']),
620 $d['wrap'],
621 ['wrap', 'nowrap']
622 );
623 $instance->verticalAlign = new StringAttr(
624 getOrNull($data['verticalAlign']),
625 $d['verticalAlign'],
626 ['top', 'middle', 'bottom']
627 );
628 $instance->backgroundColor = new StringAttr(getOrNull($data['backgroundColor']), $d['backgroundColor']);
629 $instance->border = Sides::from_array(getOrNull($data['border']), $d['border']);
630 $instance->borderRadius = Corners::from_array(getOrNull($data['borderRadius']), $d['borderRadius']);
631 $instance->cells = is_array(getOrNull($data['cells'])) ? $data['cells'] : $d['cells'];
632
633 return $instance;
634 }
635 }
636
637 class Span {
638 /** @var NumberAttr */
639 public $rowSpan;
640
641 /** @var NumberAttr */
642 public $colSpan;
643
644 /**
645 * @param array|null $data
646 * @param array<string, int> $defaults
647 * @return self
648 */
649 public static function from_array($data, $defaults = ['rowSpan' => 1, 'colSpan' => 1]) {
650 $data = is_array($data) ? $data : [];
651
652 $defaultRowSpan = $defaults['rowSpan'];
653 $defaultColSpan = $defaults['colSpan'];
654
655 $instance = new self();
656 $instance->rowSpan = new NumberAttr(getOrNull($data['rowSpan']), $defaultRowSpan);
657 $instance->colSpan = new NumberAttr(getOrNull($data['colSpan']), $defaultColSpan);
658
659 return $instance;
660 }
661 }
662
663 class ColumnConfig {
664 /** @var StringAttr|null */
665 public $sortable;
666
667 /** @var StringAttr|null */
668 public $width;
669
670 /**
671 * @param array|null $data
672 * @param string $defaultSortable
673 * @param bool $allowNull
674 * @return self
675 */
676 public static function from_array($data, $defaultSortable = 'text', $allowNull = false) {
677 $data = is_array($data) ? $data : [];
678 $sortable = getOrNull($data['sortable']);
679 $width = getOrNull($data['width']);
680
681 $instance = new self();
682
683 if ($allowNull && ($sortable === null || $sortable === '')) {
684 $instance->sortable = null;
685 } else {
686 $instance->sortable = new StringAttr(
687 $sortable,
688 $defaultSortable,
689 ['text', 'number', 'date']
690 );
691 }
692
693 if ($width === null || $width === '') {
694 $instance->width = null;
695 } else {
696 $instance->width = new StringAttr($width, '');
697 }
698
699 return $instance;
700 }
701 }
702
703 class RowConfig {
704 /** @var StringAttr|null */
705 public $height;
706
707 /**
708 * @param array|null $data
709 * @return self
710 */
711 public static function from_array($data) {
712 $data = is_array($data) ? $data : [];
713 $height = getOrNull($data['height']);
714
715 $instance = new self();
716
717 if ($height === null || $height === '') {
718 $instance->height = null;
719 } else {
720 $instance->height = new StringAttr($height, '');
721 }
722
723 return $instance;
724 }
725 }
726
727 class CellElement {
728 /** @var StringAttr */
729 public $name;
730
731 /** @var array<string, mixed> */
732 public $attributes;
733
734 /** @var array<string, mixed>|null */
735 public $bindings;
736
737 /**
738 * @param array|null $data
739 * @param string $defaultName
740 * @param array<int, string>|null $allowedNames
741 * @return self
742 */
743 public static function from_array($data, $defaultName = 'text', $allowedNames = null) {
744 $data = is_array($data) ? $data : [];
745
746 if (!is_array($allowedNames)) {
747 $allowedNames = [
748 'text',
749 'button',
750 'image',
751 'list',
752 'icon',
753 'star-rating',
754 'custom-html',
755 'styled-list',
756 ];
757 }
758
759 $instance = new self();
760 $instance->name = new StringAttr(getOrNull($data['name']), $defaultName, $allowedNames);
761 $attributes = getOrNull($data['attributes']);
762 $instance->attributes = is_array($attributes) ? $attributes : [];
763 $bindings = getOrNull($data['bindings']);
764 $instance->bindings = is_array($bindings) ? $bindings : null;
765
766 return $instance;
767 }
768 }
769