PluginProbe
FluentCart A New Era of eCommerce – Faster, Lighter, and Simpler / 1.6.4
FluentCart A New Era of eCommerce – Faster, Lighter, and Simpler v1.6.4
1.6.4 1.6.3 1.6.2 1.6.1 1.6.0 1.5.4 1.5.5 1.5.3 1.5.2 1.5.1 1.5.0 1.4.2 1.4.1 1.4.0 1.3.28 1.3.27 1.3.26 1.3.25 1.3.23 1.3.22 1.3.21 1.3.20 1.3.19 trunk 1.2.0 All 47 releases
fluent-cart / app / Services / Email / BlockEditorHelper.php

BlockEditorHelper.php in FluentCart A New Era of eCommerce – Faster, Lighter, and Simpler 1.6.4, at app/Services/Email/BlockEditorHelper.php

327 lines 10.3 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 namespace FluentCart\App\Services\Email;
4
5 class BlockEditorHelper
6 {
7 /**
8 * All editor style presets in email-safe values (px, hex).
9 * Used by both the Gutenberg editor settings and the email block renderer.
10 *
11 * @return array{spacing: array, font-family: array, font-size: array, color: array}
12 */
13 public static function getStyleDefaults()
14 {
15 return [
16 'spacing' => [
17 [
18 'name' => '2X-Small',
19 'slug' => 'fct-xx-small',
20 'size' => '5px',
21 ],
22 [
23 'name' => 'X-Small',
24 'slug' => 'fct-x-small',
25 'size' => '10px',
26 ],
27 [
28 'name' => 'Small',
29 'slug' => 'fct-small',
30 'size' => '14px',
31 ],
32 [
33 'name' => 'Medium',
34 'slug' => 'fct-medium',
35 'size' => '20px',
36 ],
37 [
38 'name' => 'Large',
39 'slug' => 'fct-large',
40 'size' => '30px',
41 ],
42 [
43 'name' => 'X-Large',
44 'slug' => 'fct-x-large',
45 'size' => '45px',
46 ],
47 [
48 'name' => '2X-Large',
49 'slug' => 'fct-xx-large',
50 'size' => '60px',
51 ],
52 ],
53 'font-family' => [
54 [
55 'name' => 'System UI',
56 'slug' => 'system-ui',
57 'fontFamily' => "-apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Helvetica, Arial, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol'",
58 ],
59 [
60 'name' => 'Arial',
61 'slug' => 'arial',
62 'fontFamily' => "Arial, 'Helvetica Neue', Helvetica, sans-serif",
63 ],
64 [
65 'name' => 'Georgia',
66 'slug' => 'georgia',
67 'fontFamily' => "Georgia, Times, 'Times New Roman', serif",
68 ],
69 [
70 'name' => 'Helvetica',
71 'slug' => 'helvetica',
72 'fontFamily' => "Helvetica, Arial, Verdana, sans-serif",
73 ],
74 [
75 'name' => 'Courier New',
76 'slug' => 'courier-new',
77 'fontFamily' => "'Courier New', Courier, 'Lucida Sans Typewriter', monospace",
78 ],
79 [
80 'name' => 'Times New Roman',
81 'slug' => 'times-new-roman',
82 'fontFamily' => "'Times New Roman', Times, Baskerville, Georgia, serif",
83 ],
84 [
85 'name' => 'Trebuchet MS',
86 'slug' => 'trebuchet-ms',
87 'fontFamily' => "'Trebuchet MS', 'Lucida Grande', 'Lucida Sans Unicode', Tahoma, sans-serif",
88 ],
89 [
90 'name' => 'Verdana',
91 'slug' => 'verdana',
92 'fontFamily' => "Verdana, Geneva, sans-serif",
93 ],
94 ],
95 'font-size' => [
96 [
97 'name' => 'Small',
98 'slug' => 'fct-small',
99 'size' => '13px',
100 ],
101 [
102 'name' => 'Regular',
103 'slug' => 'fct-regular',
104 'size' => '16px',
105 ],
106 [
107 'name' => 'Medium',
108 'slug' => 'fct-medium',
109 'size' => '18px',
110 ],
111 [
112 'name' => 'Large',
113 'slug' => 'fct-large',
114 'size' => '26px',
115 ],
116 [
117 'name' => 'Extra Large',
118 'slug' => 'fct-x-large',
119 'size' => '32px',
120 ],
121 ],
122 'color' => [
123 [
124 'name' => 'Black',
125 'slug' => 'black',
126 'color' => '#000000',
127 ],
128 [
129 'name' => 'Cyan bluish gray',
130 'slug' => 'cyan-bluish-gray',
131 'color' => '#abb8c3',
132 ],
133 [
134 'name' => 'White',
135 'slug' => 'white',
136 'color' => '#ffffff',
137 ],
138 [
139 'name' => 'Pale pink',
140 'slug' => 'pale-pink',
141 'color' => '#f78da7',
142 ],
143 [
144 'name' => 'Vivid red',
145 'slug' => 'vivid-red',
146 'color' => '#cf2e2e',
147 ],
148 [
149 'name' => 'Luminous vivid orange',
150 'slug' => 'luminous-vivid-orange',
151 'color' => '#ff6900',
152 ],
153 [
154 'name' => 'Luminous vivid amber',
155 'slug' => 'luminous-vivid-amber',
156 'color' => '#fcb900',
157 ],
158 [
159 'name' => 'Light green cyan',
160 'slug' => 'light-green-cyan',
161 'color' => '#7bdcb5',
162 ],
163 [
164 'name' => 'Vivid green cyan',
165 'slug' => 'vivid-green-cyan',
166 'color' => '#00d084',
167 ],
168 [
169 'name' => 'Pale cyan blue',
170 'slug' => 'pale-cyan-blue',
171 'color' => '#8ed1fc',
172 ],
173 [
174 'name' => 'Vivid cyan blue',
175 'slug' => 'vivid-cyan-blue',
176 'color' => '#0693e3',
177 ],
178 [
179 'name' => 'Vivid purple',
180 'slug' => 'vivid-purple',
181 'color' => '#9b51e0',
182 ],
183 ],
184 ];
185 }
186
187 /**
188 * Get a single preset category.
189 *
190 * @param string $key One of: spacing, font-family, font-size, color
191 * @return array
192 */
193 public static function getDefaultPreset($key = '')
194 {
195 $defaults = self::getStyleDefaults();
196
197 if ($key && isset($defaults[$key])) {
198 return $defaults[$key];
199 }
200
201 return [];
202 }
203
204 /**
205 * Generate CSS custom properties for spacing presets.
206 *
207 * @return string
208 */
209 public static function getStyleDefaultPresets()
210 {
211 $defaults = self::getStyleDefaults();
212 $cssProps = '';
213
214 foreach ($defaults['spacing'] as $item) {
215 $cssProps .= '--wp--preset--spacing--' . $item['slug'] . ': ' . $item['size'] . ';';
216 }
217
218 return $cssProps;
219 }
220
221 /**
222 * Replace CSS variable references with actual values for email rendering.
223 *
224 * @param string $css
225 * @return string
226 */
227 public static function replaceStyleSlugsWithValues($css = '')
228 {
229 if (!$css) {
230 return '';
231 }
232
233 $defaults = self::getStyleDefaults();
234
235 $replaces = [
236 'var(--wp--preset--color--white)' => 'white',
237 ];
238
239 foreach ($defaults as $key => $value) {
240 if (!is_array($value)) {
241 continue;
242 }
243
244 foreach ($value as $item) {
245 if ($key === 'spacing') {
246 $replaces['var(--wp--preset--spacing--' . $item['slug'] . ')'] = $item['size'];
247 } elseif ($key === 'font-size') {
248 $replaces['var(--wp--preset--font-size--' . $item['slug'] . ')'] = $item['size'];
249 } elseif ($key === 'color') {
250 $replaces['var(--wp--preset--color--' . $item['slug'] . ')'] = $item['color'];
251 } elseif ($key === 'font-family') {
252 $replaces['var(--wp--preset--font-family--' . $item['slug'] . ')'] = $item['fontFamily'];
253 }
254 }
255 }
256
257 return str_replace(array_keys($replaces), array_values($replaces), $css);
258 }
259
260 /**
261 * Generate dynamic CSS for the editor to support font-family classes.
262 *
263 * @return string
264 */
265 public static function getDynamicCssForEditor()
266 {
267 $fonts = self::getDefaultPreset('font-family');
268 $css = '';
269
270 foreach ($fonts as $font) {
271 $css .= '.editor-styles-wrapper .has-' . $font['slug'] . '-font-family { font-family: ' . $font['fontFamily'] . ' !important; }';
272 }
273
274 return $css;
275 }
276
277 /**
278 * Get theme color palette from editor-color-palette support or theme.json.
279 *
280 * @return array
281 */
282 public static function getThemeColorPalette()
283 {
284 $color_palette = current((array)get_theme_support('editor-color-palette'));
285 $theme_json_path = get_theme_file_path('theme.json');
286
287 if (file_exists($theme_json_path)) {
288 $theme_json = json_decode(file_get_contents($theme_json_path), true);
289
290 if (isset($theme_json['settings']['color']['palette'])) {
291 $color_palette = $theme_json['settings']['color']['palette'];
292 }
293 }
294 if (!$color_palette) {
295 $color_palette = [];
296 }
297
298 return (array)$color_palette;
299 }
300
301 /**
302 * Get theme preference scheme (colors + font sizes).
303 *
304 * @return array
305 */
306 public static function getThemePrefScheme()
307 {
308 static $pref;
309 if (!$pref) {
310 $color_palette = self::getDefaultPreset('color');
311 $font_sizes = self::getDefaultPreset('font-size');
312
313 /**
314 * Filter the theme preferences for FluentCart.
315 *
316 * @param array $pref The theme preferences with colors and font_sizes.
317 */
318 $pref = apply_filters('fluent_cart/theme_pref', [
319 'colors' => (array)$color_palette,
320 'font_sizes' => (array)$font_sizes
321 ]);
322 }
323
324 return $pref;
325 }
326 }
327