1: <?php
2:
3: declare(strict_types=1);
4:
5: namespace Atk4\Ui\Table\Column;
6:
7: use Atk4\Data\Field;
8: use Atk4\Data\Model;
9: use Atk4\Ui\HtmlTemplate;
10: use Atk4\Ui\Table;
11:
12: /**
13: * Swaps out column decorators based on logic.
14: */
15: class Multiformat extends Table\Column
16: {
17: /** @var \Closure(Model, Field|null): array Method to execute which will return array of seeds for decorators */
18: public $callback;
19:
20: /**
21: * @param \Closure(Model, Field|null): array $callback
22: */
23: public function __construct(\Closure $callback)
24: {
25: parent::__construct();
26:
27: $this->callback = $callback;
28: }
29:
30: #[\Override]
31: public function getDataCellHtml(Field $field = null, array $attr = []): string
32: {
33: return '{$c_' . $this->shortName . '}';
34: }
35:
36: #[\Override]
37: public function getHtmlTags(Model $row, ?Field $field): array
38: {
39: $decorators = ($this->callback)($row, $field);
40: // we need to smartly wrap things up
41: $name = $field->shortName;
42: $cell = null;
43: $tdAttr = [];
44: $htmlTags = [];
45: foreach ($decorators as $cKey => $c) {
46: if (!is_object($c)) {
47: $c = $this->getOwner()->decoratorFactory($field, $c);
48: }
49: $c = Table\Column::assertInstanceOf($c);
50:
51: if ($cKey !== array_key_last($decorators)) {
52: $html = $c->getDataCellTemplate($field);
53: $tdAttr = $c->getTagAttributes('body', $tdAttr);
54: } else {
55: // last formatter, ask it to give us whole rendering
56: $html = $c->getDataCellHtml($field, $tdAttr);
57: }
58:
59: if ($cell) {
60: if ($name) {
61: // if name is set, we can wrap things
62: $cell = str_replace('{$' . $name . '}', $cell, $html);
63: } else {
64: $cell .= ' ' . $html;
65: }
66: } else {
67: $cell = $html;
68: }
69:
70: $htmlTags = array_merge($c->getHtmlTags($row, $field), $htmlTags);
71: }
72:
73: $template = new HtmlTemplate($cell);
74: $template->setApp($this->getApp());
75: $template->set($row);
76: $template->dangerouslySetHtml($htmlTags);
77:
78: $val = $template->renderToHtml();
79:
80: return ['c_' . $this->shortName => $val];
81: }
82: }
83: