Passed
Pull Request — master (#35)
by Bruno
08:34
created

FrameworkComposer::setFooterElements()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 5
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
eloc 2
c 0
b 0
f 0
dl 0
loc 5
rs 10
ccs 0
cts 0
cp 0
cc 1
nc 1
nop 1
crap 2
1
<?php declare(strict_types=1);
2
3
namespace Formularium;
4
5
use Formularium\Exception\ClassNotFoundException;
6
use Formularium\Factory\FrameworkFactory;
7
use Formularium\HTMLNode;
8
9
class FrameworkComposer
10
{
11
    /**
12
     * @var Framework[]
13
     */
14
    protected $frameworks = [];
15
16
    /**
17
     *
18
     * @param HTMLNode[]
19 6
     */
20
    protected $headerElements = [];
21 6
22 6
    /**
23
     *
24
     * @param HTMLNode[]
25
     */
26
    protected $footerElements = [];
27 5
28
    /**
29 5
     * @param Framework[]|string[] $frameworks
30
     */
31
    public function __construct(array $frameworks = [])
32
    {
33
        $this->setFrameworks($frameworks);
34
    }
35
36 5
    /**
37
     * @param Framework[]|string[] $frameworks
38 5
     */
39
    public static function create(array $frameworks = []): FrameworkComposer
40
    {
41
        return new self($frameworks);
42
    }
43
44
    /**
45 2
     *
46
     * @return Framework[]
47 2
     */
48 2
    public function getFrameworks(): array
49 2
    {
50
        return $this->frameworks;
51
    }
52 1
53
    /**
54
     *
55
     * @return Framework|null
56
     */
57
    public function getByName(string $name): ?Framework
58
    {
59 6
        foreach ($this->frameworks as $f) {
60
            if ($f->getName() === $name) {
61 6
                return $f;
62 6
            }
63 6
        }
64
        return null;
65 6
    }
66
67
    /**
68
     * @param Framework[]|string[] $frameworks
69
     * @return void
70
     */
71
    public function setFrameworks(array $frameworks = [])
72
    {
73 6
        $this->frameworks = [];
74
        foreach ($frameworks as $f) {
75 6
            $this->append($f);
76 5
        }
77
    }
78
79
    /**
80
     * Appends a framework to the queue
81
     *
82
     * @param string|Framework $framework
83 1
     * @return void
84
     */
85 1
    public function append($framework)
86 1
    {
87 1
        $this->frameworks[] = ($framework instanceof Framework ? $framework : FrameworkFactory::factory($framework));
88
    }
89 1
90
    /**
91
     * Returns the html <head> contents for all frameworks.
92 1
     *
93
     * @return string
94 1
     */
95 1
    public function htmlHead(): string
96 1
    {
97
        $head = new HTMLNode('');
98 1
        foreach ($this->getFrameworks() as $framework) {
99
            $framework->htmlHead($head);
100
        }
101
        return $head->getRenderHTML();
102
    }
103
104
    public function htmlFooter(): string
105
    {
106
        $footer = new HTMLNode('');
107
        foreach ($this->getFrameworks() as $framework) {
108 1
            $framework->htmlFooter($footer);
109
        }
110 1
        return $footer->getRenderHTML();
111 1
    }
112 1
113
    /**
114 1
     * Renders an element
115 1
     *
116 1
     * @param string $elementName
117
     * @param array $parameters
118
     * @return HTMLNode The element HTMLNode
119
     */
120
    public function nodeElement(string $elementName, array $parameters = []): HTMLNode
121 1
    {
122
        $node = new HTMLNode('');
123
        $found = false;
124 1
        foreach ($this->getFrameworks() as $framework) {
125
            try {
126
                $element = $framework->getElement($elementName, $this);
127
                $found = true;
128
                $node = $element->render($parameters, $node);
129
            } catch (ClassNotFoundException $e) {
130
                continue; // element default
131
            }
132
        }
133
        if (!$found) {
134 1
            throw new ClassNotFoundException("Element $elementName not found");
135
        }
136 1
        return $node;
137
    }
138
139
    /**
140
     * Renders an element to a string
141
     *
142
     * @param string $elementName
143
     * @param array $parameters
144
     * @return string The rendered HTML
145
     */
146 2
    public function element(string $elementName, array $parameters = []): string
147
    {
148 2
        return $this->nodeElement($elementName, $parameters)->getRenderHTML();
149 2
    }
150 2
151 2
    /**
152 2
     * Renders a Model with the loaded frameworks.
153
     *
154 2
     * @param Model $m
155 2
     * @param array $modelData Actual data for the fields to render. Can be empty.
156
     * @return HTMLNode[]
157
     */
158
    public function viewableNodes(Model $m, array $modelData): array
159
    {
160 2
        $elements = [];
161
        foreach ($m->getFields() as $field) {
162 2
            $value = $modelData[$field->getName()] ?? $field->getDataType()->getDefault(); // TODO: values?
163
            $html = new HTMLNode('');
164
            foreach ($this->getFrameworks() as $framework) {
165
                try {
166
                    $r = $framework->getRenderable($field->getDatatype(), $this);
167
                    $html = $r->viewable($value, $field, $html);
168
                } catch (ClassNotFoundException $e) {
169
                    continue; // renderable default
170
                }
171
            }
172 2
            $elements[$field->getName()] = $html;
173
        }
174 2
        return $elements;
175 2
    }
176 2
177 2
    /**
178
     * Renders a Model with the loaded frameworks.
179 2
     *
180
     * @param Model $m
181
     * @param array $modelData Actual data for the fields to render. Can be empty.
182
     * @return string
183
     */
184
    public function viewable(Model $m, array $modelData): string
185
    {
186
        $elements = array_merge(
187
            $this->headerElements,
188
            $this->viewableNodes($m, $modelData),
189
            $this->footerElements
190
        );
191
        $output = '';
192
        foreach ($this->getFrameworks() as $framework) {
193
            $output = $framework->viewableCompose($m, $elements, $output, $this);
194
        }
195
        return $output;
196
    }
197
198
    /**
199
     * Renders a Model as an editable form with the loaded frameworks.
200
     *
201
     * @param Model $m
202
     * @param array $modelData Actual data for the fields to render. Can be empty.
203
     * @return HTMLNode[]
204
     */
205
    public function editableNodes(Model $m, array $modelData): array
206
    {
207
        $elements = [];
208
        foreach ($m->getFields() as $field) {
209
            $value = $modelData[$field->getName()] ?? $field->getDataType()->getDefault(); // TODO: values?
210
            $html = new HTMLNode('');
211
            foreach ($this->getFrameworks() as $framework) {
212
                try {
213
                    $r = $framework->getRenderable($field->getDatatype(), $this);
214
                    $html = $r->editable($value, $field, $html);
215
                } catch (ClassNotFoundException $e) {
216
                    continue; // renderable default
217
                }
218
            }
219
            $elements[$field->getName()] = $html;
220
        }
221
        return $elements;
222
    }
223
224
    /**
225
     * Renders a Model as an editable form with the loaded frameworks.
226
     *
227
     * @param Model $m
228
     * @param array $modelData Actual data for the fields to render. Can be empty.
229
     * @return string
230
     */
231
    public function editable(Model $m, array $modelData): string
232
    {
233
        $elements = array_merge(
234
            $this->headerElements,
235
            $this->editableNodes($m, $modelData),
236
            $this->footerElements
237
        );
238
239
        $output = '';
240
241
        foreach ($this->getFrameworks() as $framework) {
242
            $output = $framework->editableCompose($m, $elements, $output, $this);
243
        }
244
        return $output;
245
    }
246
247
    /**
248
     * Get the value of footerElements
249
     * @return HTMLNode[]
250
     */
251
    public function getFooterElements(): array
252
    {
253
        return $this->footerElements;
254
    }
255
256
    /**
257
     * Set the value of footerElements
258
     *
259
     * @param HTMLNode[] $footerElements
260
     * @return  self
261
     */
262
    public function setFooterElements(array $footerElements): self
263
    {
264
        $this->footerElements = $footerElements;
265
266
        return $this;
267
    }
268
269
    /**
270
     * Appends an element to the footer
271
     *
272
     * @return self
273
     */
274
    public function appendFooterElement(HTMLNode $node): self
275
    {
276
        $this->footerElements[] = $node;
277
        return $this;
278
    }
279
280
    /**
281
     * Get the value of headerElements
282
     * @return HTMLNode[]
283
     */
284
    public function getHeaderElements(): array
285
    {
286
        return $this->headerElements;
287
    }
288
289
    /**
290
     * Set the value of headerElements
291
     * @param HTMLNode[] $footerElements
292
     * @return  self
293
     */
294
    public function setHeaderElements($headerElements)
295
    {
296
        $this->headerElements = $headerElements;
297
298
        return $this;
299
    }
300
301
    /**
302
     * Appends an element to the footer
303
     *
304
     * @return self
305
     */
306
    public function appendHeaderElement(HTMLNode $node): self
307
    {
308
        $this->headerElements[] = $node;
309
        return $this;
310
    }
311
}
312