BaseField   A
last analyzed

Complexity

Total Complexity 25

Size/Duplication

Total Lines 171
Duplicated Lines 0 %

Test Coverage

Coverage 100%

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 64
c 1
b 0
f 0
dl 0
loc 171
ccs 76
cts 76
cp 1
rs 10
wmc 25

16 Methods

Rating   Name   Duplication   Size   Complexity  
A prepareContainerAttributes() 0 2 1
A beforeRender() 0 2 1
A renderEnd() 0 11 3
A getThemeConfig() 0 3 1
A generateBeginContent() 0 3 1
A generateEndContent() 0 3 1
A renderOpenContainerAndContent() 0 16 4
A containerAttributes() 0 5 1
A containerClass() 0 5 1
A containerId() 0 5 1
A containerTag() 0 9 2
A addContainerAttributes() 0 5 1
A addContainerClass() 0 5 1
A useContainer() 0 5 1
A begin() 0 10 1
A render() 0 23 4
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Yiisoft\Form\Field\Base;
6
7
use InvalidArgumentException;
8
use Yiisoft\Form\ThemeContainer;
9
use Yiisoft\Html\Html;
10
use Yiisoft\Html\Tag\CustomTag;
11
use Yiisoft\Widget\Widget;
12
13
abstract class BaseField extends Widget
14
{
15
    /**
16
     * @psalm-var non-empty-string
17
     */
18
    protected string $containerTag = 'div';
19
    protected array $containerAttributes = [];
20
    protected bool $useContainer = true;
21
    protected array $enrichment = [];
22
23
    private bool $isStartedByBegin = false;
24
25 53
    final public function containerTag(string $tag): static
26
    {
27 53
        if ($tag === '') {
28 1
            throw new InvalidArgumentException('Tag name cannot be empty.');
29
        }
30
31 52
        $new = clone $this;
32 52
        $new->containerTag = $tag;
33 52
        return $new;
34
    }
35
36 8
    final public function containerAttributes(array $attributes): static
37
    {
38 8
        $new = clone $this;
39 8
        $new->containerAttributes = $attributes;
40 8
        return $new;
41
    }
42
43 2
    final public function addContainerAttributes(array $attributes): static
44
    {
45 2
        $new = clone $this;
46 2
        $new->containerAttributes = array_merge($new->containerAttributes, $attributes);
47 2
        return $new;
48
    }
49
50
    /**
51
     * Set container tag ID.
52
     *
53
     * @param string|null $id Container tag ID.
54
     */
55 3
    final public function containerId(?string $id): static
56
    {
57 3
        $new = clone $this;
58 3
        $new->containerAttributes['id'] = $id;
59 3
        return $new;
60
    }
61
62
    /**
63
     * Replace container tag CSS classes with a new set of classes.
64
     *
65
     * @param string|null ...$class One or many CSS classes.
66
     */
67 10
    final public function containerClass(?string ...$class): static
68
    {
69 10
        $new = clone $this;
70 10
        $new->containerAttributes['class'] = array_filter($class, static fn ($c) => $c !== null);
71 10
        return $new;
72
    }
73
74
    /**
75
     * Add one or more CSS classes to the container tag.
76
     *
77
     * @param string|null ...$class One or many CSS classes.
78
     */
79 9
    final public function addContainerClass(?string ...$class): static
80
    {
81 9
        $new = clone $this;
82 9
        Html::addCssClass($new->containerAttributes, $class);
83 9
        return $new;
84
    }
85
86 152
    final public function useContainer(bool $use): static
87
    {
88 152
        $new = clone $this;
89 152
        $new->useContainer = $use;
90 152
        return $new;
91
    }
92
93 12
    final public function begin(): ?string
94
    {
95 12
        parent::begin();
96 12
        $this->isStartedByBegin = true;
97
98 12
        $this->beforeRender();
99
100 12
        $content = $this->generateBeginContent();
101
102 12
        return $this->renderOpenContainerAndContent($content);
103
    }
104
105 694
    final public function render(): string
106
    {
107 694
        if ($this->isStartedByBegin) {
108 10
            $this->isStartedByBegin = false;
109 10
            return $this->renderEnd();
110
        }
111
112 686
        $this->beforeRender();
113
114 686
        $content = $this->generateContent();
115 667
        if ($content === null) {
116 2
            $this->enrichment = [];
117 2
            return '';
118
        }
119
120 665
        $result = $this->renderOpenContainerAndContent($content);
121
122 665
        if ($this->useContainer) {
123 510
            $result .= "\n" . Html::closeTag($this->containerTag);
124
        }
125
126 665
        $this->enrichment = [];
127 665
        return $result;
128
    }
129
130 315
    protected function beforeRender(): void
131
    {
132 315
    }
133
134
    abstract protected function generateContent(): ?string;
135
136 2
    protected function generateBeginContent(): string
137
    {
138 2
        return '';
139
    }
140
141 2
    protected function generateEndContent(): string
142
    {
143 2
        return '';
144
    }
145
146 203
    protected function prepareContainerAttributes(array &$attributes): void
147
    {
148 203
    }
149
150 729
    final protected static function getThemeConfig(?string $theme): array
151
    {
152 729
        return ThemeContainer::getTheme($theme)?->getFieldConfig(static::class) ?? [];
153
    }
154
155 10
    private function renderEnd(): string
156
    {
157 10
        $content = $this->generateEndContent();
158
159 10
        if (!$this->useContainer) {
160 1
            return $content;
161
        }
162
163 9
        $containerTag = CustomTag::name($this->containerTag);
164
165 9
        return ($content !== '' ? $content . "\n" : '') . $containerTag->close();
166
    }
167
168 675
    private function renderOpenContainerAndContent(string $content): string
169
    {
170 675
        if (!$this->useContainer) {
171 157
            return $content;
172
        }
173
174 520
        $containerTag = CustomTag::name($this->containerTag);
175
176 520
        $attributes = $this->containerAttributes;
177 520
        $this->prepareContainerAttributes($attributes);
178 520
        if ($attributes !== []) {
179 55
            $containerTag = $containerTag->addAttributes($attributes);
180
        }
181
182 520
        return $containerTag->open()
183 520
            . ($content === '' ? '' : ("\n" . $content));
184
    }
185
}
186