Skip to content

Commit b2f7553

Browse files
authored
Merge pull request #28 from dingo-d/feature/mj-accordion
Implement mj-accordion components
2 parents 52aad8f + 03d748f commit b2f7553

File tree

5 files changed

+886
-0
lines changed

5 files changed

+886
-0
lines changed
Lines changed: 178 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,178 @@
1+
<?php
2+
3+
/**
4+
* PHP MJML Renderer library
5+
*
6+
* @package MadeByDenis\PhpMjmlRenderer
7+
* @link https://github.com/dingo-d/php-mjml-renderer
8+
* @license https://opensource.org/licenses/MIT MIT
9+
*/
10+
11+
declare(strict_types=1);
12+
13+
namespace MadeByDenis\PhpMjmlRenderer\Elements\BodyComponents;
14+
15+
use MadeByDenis\PhpMjmlRenderer\Elements\AbstractElement;
16+
17+
/**
18+
* Mjml Accordion Element
19+
*
20+
* Accordion is an interactive component to stack content in tabs,
21+
* so the information is collapsed and only the titles are visible.
22+
*
23+
* @link https://documentation.mjml.io/#mj-accordion
24+
*
25+
* @since 1.0.0
26+
*/
27+
class MjAccordion extends AbstractElement
28+
{
29+
public const string TAG_NAME = 'mj-accordion';
30+
31+
public const bool ENDING_TAG = false;
32+
33+
/**
34+
* List of allowed attributes on the element
35+
*
36+
* @var array<string, array<string, string>>
37+
*/
38+
protected array $allowedAttributes = [
39+
'border' => [
40+
'unit' => 'string',
41+
'type' => 'string',
42+
'description' => 'border',
43+
'default_value' => '2px solid black',
44+
],
45+
'container-background-color' => [
46+
'unit' => 'color',
47+
'type' => 'color',
48+
'description' => 'background color of the cell',
49+
'default_value' => '',
50+
],
51+
'css-class' => [
52+
'unit' => 'string',
53+
'type' => 'string',
54+
'description' => 'class name added to root HTML element',
55+
'default_value' => '',
56+
],
57+
'font-family' => [
58+
'unit' => 'string',
59+
'type' => 'string',
60+
'description' => 'font family',
61+
'default_value' => 'Ubuntu, Helvetica, Arial, sans-serif',
62+
],
63+
'icon-align' => [
64+
'unit' => 'string',
65+
'type' => 'string',
66+
'description' => 'icon alignment (top/middle/bottom)',
67+
'default_value' => 'middle',
68+
],
69+
'icon-height' => [
70+
'unit' => 'px',
71+
'type' => 'string',
72+
'description' => 'icon height',
73+
'default_value' => '32px',
74+
],
75+
'icon-position' => [
76+
'unit' => 'string',
77+
'type' => 'string',
78+
'description' => 'icon position (left/right)',
79+
'default_value' => 'right',
80+
],
81+
'icon-unwrapped-url' => [
82+
'unit' => 'string',
83+
'type' => 'string',
84+
'description' => 'icon when accordion is unwrapped',
85+
'default_value' => 'https://i.imgur.com/bIXv1bk.png',
86+
],
87+
'icon-wrapped-url' => [
88+
'unit' => 'string',
89+
'type' => 'string',
90+
'description' => 'icon when accordion is wrapped',
91+
'default_value' => 'https://i.imgur.com/w4uTygT.png',
92+
],
93+
'icon-width' => [
94+
'unit' => 'px',
95+
'type' => 'string',
96+
'description' => 'icon width',
97+
'default_value' => '32px',
98+
],
99+
'padding' => [
100+
'unit' => 'px',
101+
'type' => 'string',
102+
'description' => 'supports up to 4 parameters',
103+
'default_value' => '10px 25px',
104+
],
105+
'padding-bottom' => [
106+
'unit' => 'px',
107+
'type' => 'measure',
108+
'description' => 'bottom offset',
109+
'default_value' => '',
110+
],
111+
'padding-left' => [
112+
'unit' => 'px',
113+
'type' => 'measure',
114+
'description' => 'left offset',
115+
'default_value' => '',
116+
],
117+
'padding-right' => [
118+
'unit' => 'px',
119+
'type' => 'measure',
120+
'description' => 'right offset',
121+
'default_value' => '',
122+
],
123+
'padding-top' => [
124+
'unit' => 'px',
125+
'type' => 'measure',
126+
'description' => 'top offset',
127+
'default_value' => '',
128+
],
129+
];
130+
131+
protected array $defaultAttributes = [
132+
'border' => '2px solid black',
133+
'font-family' => 'Ubuntu, Helvetica, Arial, sans-serif',
134+
'icon-align' => 'middle',
135+
'icon-height' => '32px',
136+
'icon-position' => 'right',
137+
'icon-unwrapped-url' => 'https://i.imgur.com/bIXv1bk.png',
138+
'icon-wrapped-url' => 'https://i.imgur.com/w4uTygT.png',
139+
'icon-width' => '32px',
140+
'padding' => '10px 25px',
141+
];
142+
143+
public function render(): string
144+
{
145+
$children = $this->getChildren() ?? [];
146+
$content = $this->renderChildren($children, []);
147+
148+
return $content;
149+
}
150+
151+
/**
152+
* Gets the context for child elements.
153+
*
154+
* @return array<string, mixed>
155+
*/
156+
public function getChildContext(): array
157+
{
158+
return [
159+
...$this->context,
160+
'border' => $this->getAttribute('border'),
161+
'font-family' => $this->getAttribute('font-family'),
162+
'icon-align' => $this->getAttribute('icon-align'),
163+
'icon-height' => $this->getAttribute('icon-height'),
164+
'icon-position' => $this->getAttribute('icon-position'),
165+
'icon-unwrapped-url' => $this->getAttribute('icon-unwrapped-url'),
166+
'icon-wrapped-url' => $this->getAttribute('icon-wrapped-url'),
167+
'icon-width' => $this->getAttribute('icon-width'),
168+
];
169+
}
170+
171+
/**
172+
* @return array<string, array<string, string>>
173+
*/
174+
public function getStyles(): array
175+
{
176+
return [];
177+
}
178+
}
Lines changed: 158 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,158 @@
1+
<?php
2+
3+
/**
4+
* PHP MJML Renderer library
5+
*
6+
* @package MadeByDenis\PhpMjmlRenderer
7+
* @link https://github.com/dingo-d/php-mjml-renderer
8+
* @license https://opensource.org/licenses/MIT MIT
9+
*/
10+
11+
declare(strict_types=1);
12+
13+
namespace MadeByDenis\PhpMjmlRenderer\Elements\BodyComponents;
14+
15+
use MadeByDenis\PhpMjmlRenderer\Elements\AbstractElement;
16+
17+
/**
18+
* Mjml Accordion Element
19+
*
20+
* Individual accordion item that contains title and text.
21+
*
22+
* @link https://documentation.mjml.io/#mj-accordion-element
23+
*
24+
* @since 1.0.0
25+
*/
26+
class MjAccordionElement extends AbstractElement
27+
{
28+
public const string TAG_NAME = 'mj-accordion-element';
29+
30+
public const bool ENDING_TAG = false;
31+
32+
/**
33+
* List of allowed attributes on the element
34+
*
35+
* @var array<string, array<string, string>>
36+
*/
37+
protected array $allowedAttributes = [
38+
'background-color' => [
39+
'unit' => 'color',
40+
'type' => 'color',
41+
'description' => 'background color',
42+
'default_value' => '',
43+
],
44+
'border' => [
45+
'unit' => 'string',
46+
'type' => 'string',
47+
'description' => 'border',
48+
'default_value' => '',
49+
],
50+
'css-class' => [
51+
'unit' => 'string',
52+
'type' => 'string',
53+
'description' => 'class name added to root HTML element',
54+
'default_value' => '',
55+
],
56+
'font-family' => [
57+
'unit' => 'string',
58+
'type' => 'string',
59+
'description' => 'font family',
60+
'default_value' => '',
61+
],
62+
'icon-align' => [
63+
'unit' => 'string',
64+
'type' => 'string',
65+
'description' => 'icon alignment (top/middle/bottom)',
66+
'default_value' => '',
67+
],
68+
'icon-height' => [
69+
'unit' => 'px',
70+
'type' => 'string',
71+
'description' => 'icon height',
72+
'default_value' => '',
73+
],
74+
'icon-position' => [
75+
'unit' => 'string',
76+
'type' => 'string',
77+
'description' => 'icon position (left/right)',
78+
'default_value' => '',
79+
],
80+
'icon-unwrapped-url' => [
81+
'unit' => 'string',
82+
'type' => 'string',
83+
'description' => 'icon when accordion is unwrapped',
84+
'default_value' => '',
85+
],
86+
'icon-wrapped-url' => [
87+
'unit' => 'string',
88+
'type' => 'string',
89+
'description' => 'icon when accordion is wrapped',
90+
'default_value' => '',
91+
],
92+
'icon-width' => [
93+
'unit' => 'px',
94+
'type' => 'string',
95+
'description' => 'icon width',
96+
'default_value' => '',
97+
],
98+
];
99+
100+
protected array $defaultAttributes = [];
101+
102+
public function render(): string
103+
{
104+
$divAttributes = $this->getHtmlAttributes([
105+
'class' => $this->getAttribute('css-class'),
106+
'style' => 'div',
107+
]);
108+
109+
$children = $this->getChildren() ?? [];
110+
$content = $this->renderChildren($children, []);
111+
112+
return "<div $divAttributes>$content</div>";
113+
}
114+
115+
/**
116+
* Gets the context for child elements.
117+
*
118+
* @return array<string, mixed>
119+
*/
120+
public function getChildContext(): array
121+
{
122+
$fontFamily = $this->getAttribute('font-family') ?:
123+
$this->context['font-family'] ?? 'Ubuntu, Helvetica, Arial, sans-serif';
124+
125+
return [
126+
...$this->context,
127+
'background-color' => $this->getAttribute('background-color') ?:
128+
$this->context['background-color'] ?? '',
129+
'border' => $this->getAttribute('border') ?: $this->context['border'] ?? '',
130+
'font-family' => $fontFamily,
131+
'icon-align' => $this->getAttribute('icon-align') ?:
132+
$this->context['icon-align'] ?? 'middle',
133+
'icon-height' => $this->getAttribute('icon-height') ?:
134+
$this->context['icon-height'] ?? '32px',
135+
'icon-position' => $this->getAttribute('icon-position') ?:
136+
$this->context['icon-position'] ?? 'right',
137+
'icon-unwrapped-url' => $this->getAttribute('icon-unwrapped-url') ?:
138+
$this->context['icon-unwrapped-url'] ?? '',
139+
'icon-wrapped-url' => $this->getAttribute('icon-wrapped-url') ?:
140+
$this->context['icon-wrapped-url'] ?? '',
141+
'icon-width' => $this->getAttribute('icon-width') ?:
142+
$this->context['icon-width'] ?? '32px',
143+
];
144+
}
145+
146+
/**
147+
* @return array<string, array<string, string>>
148+
*/
149+
public function getStyles(): array
150+
{
151+
return [
152+
'div' => [
153+
'background-color' => $this->getAttribute('background-color'),
154+
'border' => $this->getAttribute('border'),
155+
],
156+
];
157+
}
158+
}

0 commit comments

Comments
 (0)