PluginProbe ʕ •ᴥ•ʔ
Kubio AI Page Builder / 2.7.2
Kubio AI Page Builder v2.7.2
2.8.1 trunk 1.0.0 1.0.1 1.1.0 1.2.0 1.2.1 1.2.2 1.2.3 1.3.0 1.3.1 1.3.2 1.4.0 1.4.1 1.4.2 1.4.3 1.5.0 1.6.0 1.6.1 1.6.2 1.6.3 1.6.4 1.7.0 1.7.1 1.7.2 1.7.3 1.8.0 1.8.1 1.8.2 1.9.0 2.0.0 2.1.1 2.1.2 2.1.3 2.2.0 2.2.3 2.2.4 2.2.5 2.3.0 2.3.1 2.3.3 2.3.4 2.4.0 2.4.1 2.4.2 2.4.3 2.4.5 2.5.0 2.5.1 2.5.2 2.5.3 2.6.0 2.6.1 2.6.2 2.6.3 2.6.5 2.6.6 2.6.7 2.7.0 2.7.1 2.7.2 2.7.3 2.8.0
kubio / lib / src / Core / Blocks / BlockBase.php
kubio / lib / src / Core / Blocks Last commit date
Query 1 year ago BlockBase.php 1 year ago BlockContainerBase.php 1 year ago BlockElement.php 3 years ago BlockStyle.php 4 years ago DataHelper.php 1 year ago TemplatePartBlockBase.php 1 year ago
BlockBase.php
423 lines
1 <?php
2
3 namespace Kubio\Core\Blocks;
4
5 use Exception;
6 use Kubio\Config;
7 use Kubio\Core\LodashBasic;
8 use Kubio\Core\Registry;
9 use Kubio\Core\StyleManager\BlockStyleRender;
10 use Kubio\Core\StyleManager\StyleManager;
11 use IlluminateAgnostic\Arr\Support\Arr;
12 use Kubio\Core\Utils;
13 use WP_Block_Type_Registry;
14
15 /**
16 * @package Kubio\Core\Blocks
17 *
18 * @method serverSideRender( string $wp_block )
19 *
20 */
21 class BlockBase extends DataHelper {
22
23 public $block_data = null;
24 public $block_type = null;
25 public $parent_block_ = null;
26 public $block_context = null;
27
28 public $elements = array();
29 public $styledElementsByName = array();
30 private $defaultElement;
31
32 private $local_id = null;
33
34
35 private $mapped_props_with_defaults = null;
36
37 public function __construct( $block, $autoload = true, $context = array() ) {
38 $this->block_context = $context;
39 $this->block_data = $block;
40 $this->block_type = WP_Block_Type_Registry::get_instance()->get_registered(
41 $block['blockName']
42 );
43
44 $this->styledElementsByName = $this->getBlockStyledElementsByName();
45 $this->defaultElement = $this->getDefaultElement();
46
47 if ( ! $this->defaultElement ) {
48 throw new Exception(
49 // phpcs:ignore WordPress.Security.EscapeOutput.ExceptionNotEscaped
50 "Kubio \"{$block['name']}\" has no default element defined"
51 );
52 }
53
54 $attributesDefinitions = $this->block_type->attributes;
55 $attributesDefaults = LodashBasic::mapValues(
56 $attributesDefinitions,
57 'default'
58 );
59 $attributesValues = LodashBasic::get( $this->block_data, 'attrs' );
60
61 parent::__construct(
62 $this->getBlockSupport( 'default' ),
63 LodashBasic::mergeSkipSeqArray(
64 $attributesDefaults,
65 $attributesValues
66 )
67 );
68
69 if ( $autoload ) {
70 $this->create();
71 }
72
73 $this->local_id = Utils::uniqueId();
74 }
75
76 public function localId() {
77 return $this->local_id;
78 }
79
80 public function getBlockStyledElementsByName() {
81 $styledElementsByName = $this->getBlockSupport( Config::$elementsKey );
82 // allow empty elements to be skiped in elementsEnum//
83 $allElements = $this->getBlockSupport( Config::$elementsEnum );
84 foreach ( $allElements as $elementName ) {
85 if ( ! isset( $styledElementsByName[ $elementName ] ) ) {
86 $styledElementsByName[ $elementName ] = array();
87 }
88 }
89
90 return $styledElementsByName;
91 }
92
93 public function getBlockSupport( $path, $default = null ) {
94 return LodashBasic::get(
95 $this->block_type->supports,
96 Config::$mainAttributeKey . '.' . $path,
97 $default
98 );
99 }
100
101 public function getDefaultElement() {
102 if ( ! $this->defaultElement ) {
103 $this->defaultElement = $this->findElementBy(
104 'default',
105 true,
106 false
107 );
108 }
109
110 return $this->defaultElement;
111 }
112
113 public function getLinkAttribute() {
114 return $this->getAttribute( 'link', null );
115 }
116
117 public function findElementBy( $path, $value, $fallbackToDefault = true ) {
118 $elements = $this->styledElementsByName;
119
120 foreach ( (array) $elements as $name => $element ) {
121 if ( LodashBasic::get( $element, $path ) === $value ) {
122 return $name;
123 }
124 }
125
126 if ( $fallbackToDefault ) {
127 return $this->defaultElement;
128 }
129 }
130
131 public function create() {
132 $template = $this->getBlockSupport( 'template', null );
133 if ( ! $template ) {
134 $template = array(
135 'type' => 'element',
136 );
137 }
138
139 $this->createFromJson( $template );
140 }
141
142 public function createFromJson( $element ) {
143 $wrapper_element = $this->getWrapperElementName();
144 $this->elements[0] = $this->toElement( $element, $wrapper_element );
145 }
146
147
148 public function getWrapperElementName() {
149 return $this->findElementBy( 'wrapper', true, true );
150 }
151 public function toElement( $element, $wrapper_element, $level = 0 ) {
152 $children = array();
153 if ( isset( $element['children'] ) ) {
154 foreach ( $element['children'] as $child ) {
155 $children[] = $this->toElement(
156 $child,
157 $wrapper_element,
158 $level + 1
159 );
160 }
161 }
162
163 $element_name = LodashBasic::get( $element, 'props.name', null );
164 $props = LodashBasic::get( $element, 'props', array() );
165
166 $has_data_debug_attribute = apply_filters( 'kubio/blocks/element_add_data_debug_attribute', Utils::isDebug() );
167 $is_wrapper = $element_name === $wrapper_element;
168 if ( $is_wrapper ) {
169 $props = LodashBasic::merge(
170 array_merge(
171 array(
172 'className' => array(
173 'wp-block',
174 $this->blockClass(),
175 implode( ' ', $this->getAppliedMigrationsClasses() ),
176 ),
177 'data-kubio' => $this->block_data['blockName'],
178 ),
179 $has_data_debug_attribute ? array( 'data-debug' => json_encode( $this->block_data ) ) : array() // add data-debug attribute
180 ),
181 $props
182 );
183
184 $hidden = $this->getPropByMedia(
185 'isHidden',
186 false,
187 array(
188 'fromRoot' => true,
189 )
190 );
191
192 foreach ( $hidden as $media => $is_hidden ) {
193 if ( $is_hidden ) {
194 $props['className'] = array_merge(
195 isset( $props['className'] )
196 ? Arr::wrap( $props['className'] )
197 : array(),
198 array( "kubio-hide-on-{$media}" )
199 );
200 } else {
201 $appearanceEffect = $this->getAttribute( 'appearanceEffect' );
202 if ( $appearanceEffect && $appearanceEffect !== 'none' ) {
203 $props = LodashBasic::merge( array( 'data-kubio-aos' => $appearanceEffect ), $props );
204 }
205 }
206 }
207 }
208
209 $element = $this->createElement( $element['type'], $props, $children );
210
211 return $element;
212 }
213
214 public function getAppliedMigrations() {
215 return $this->getAttribute( 'kubio.migrations', array() );
216 }
217
218 public function getAppliedMigrationsClasses() {
219 $result = array();
220
221 $migrations = $this->getAppliedMigrations();
222 foreach ( $migrations as $migration_id ) {
223 $result[] = "kubio-migration--{$migration_id}";
224 }
225
226 return $result;
227 }
228
229 public function blockClass() {
230 return 'wp-block-' . $this->kebabBlockName();
231 }
232
233 public function kebabBlockName() {
234 return LodashBasic::kebabCase( str_replace( '/', '-', $this->name() ) );
235 }
236
237 public function name() {
238 return $this->block_type->name;
239 }
240
241 public function createElement( $type, $props, $children ) {
242 return Registry::getInstance()->createElement(
243 $type,
244 $props,
245 $children,
246 $this
247 );
248 }
249
250
251 public function elementClass( $element ) {
252 return 'wp-block-' . $this->kebabBlockName() . '__' . $element;
253 }
254
255 public function getStyledElementConfig( $name, $path = '', $defaultValue = null ) {
256 return LodashBasic::get( $this->styledElementsByName, array( $name, $path ), $defaultValue );
257 }
258
259 public function getLocalIdClass( $styledComponentName ) {
260 $localId = $this->localId();
261 $stylePrefix = apply_filters( 'kubio/element-style-class-prefix', 'style-' );
262 $stylePrefix = "{$stylePrefix}local-";
263 $localStyleClass = "{$stylePrefix}{$localId}-{$styledComponentName}";
264 return $localStyleClass;
265 }
266
267 public function render( $wp_block ) {
268 $this->parent_block_ = Registry::getInstance()->getParentBlock();
269 $content = '';
270 if ( $this->canRender() ) {
271
272 if ( $this->canRegisterStyle() ) {
273 $this->registerStyle();
274 }
275
276 $content = $this->elements[0] . '';
277 $inner_block_content = $this->renderInnerBlocks( $wp_block );
278 $content = str_replace( '<InnerBlocks/>', $inner_block_content, $content );
279 }
280
281 return $content;
282 }
283
284 public function wrapperStyledComponent() {
285 $wrapperElement = null;
286 $styledElementsByName = $this->styledElementsByName;
287 foreach ( $styledElementsByName as $name => $styledElement ) {
288 $wrapper = LodashBasic::get( $styledElement, 'wrapper', false );
289 if ( $wrapper ) {
290 $wrapperElement = $name;
291 }
292 }
293
294 return $wrapperElement;
295 }
296
297 public function canRender() {
298 global $wp;
299
300 $is_rest_call = defined( 'REST_REQUEST' ) && REST_REQUEST;
301 $route = Arr::get( $wp->query_vars, 'rest_route', '' );
302
303 if ( strpos( $route, '/block-renderer/' ) !== false ) {
304 return true;
305 }
306
307 $can_render = apply_filters( 'kubio/can_render_block', ! $is_rest_call && ! is_admin(), $this );
308
309 return $can_render;
310 }
311
312 public function canRegisterStyle() {
313 $is_rest_call = defined( 'REST_REQUEST' ) && REST_REQUEST;
314
315 return ! $is_rest_call;
316 }
317
318 public function registerStyle() {
319 $style = new BlockStyleRender( $this, $this->parent_block_ );
320 $styleByType = $style->export( $this->getDynamicStyle() );
321 StyleManager::getInstance()->registerBlockStyle( $styleByType );
322 }
323
324 public function getDynamicStyle() {
325 return $this->mapDynamicStyleToElements();
326 }
327
328 public function mapDynamicStyleToElements() {
329 return array();
330 }
331
332 public function renderInnerBlocks( $wp_block ) {
333 $block_content = '';
334 foreach ( $wp_block->inner_blocks as $inner_block ) {
335 $block_content .= $inner_block->render();
336 }
337
338 return $block_content;
339 }
340
341 public function mapPropsToElements() {
342 return array();
343 }
344
345
346 public function mapPropsToElementsWithDefaults() {
347 if ( ! $this->mapped_props_with_defaults ) {
348
349 $mapPropsToElements = $this->mapPropsToElements();
350
351 if ( ! $mapPropsToElements ) {
352 $mapPropsToElements = array();
353 }
354 $basicAttributes = \WP_Block_Supports::get_instance()->apply_block_supports();
355
356 if ( ! $basicAttributes ) {
357 $basicAttributes = array();
358 }
359 //rename class to className to make it compatible with kubio classes
360 if ( isset( $basicAttributes['class'] ) ) {
361 $classList = array( $basicAttributes['class'] );
362 LodashBasic::set( $basicAttributes, 'className', $classList );
363 LodashBasic::unsetValue( $basicAttributes, 'class' );
364 }
365
366 /**
367 * Set anchor. Kubio sets anchor without the source and attribute parameters in the gutenberg attribute. If you
368 * set source attribute the anchor will not work anymore. When you publish any changes the anchor gets removed.
369 * Because of this when we register the anchor we only set the type: "string" paramter and we set the attribute from
370 * here
371 */
372 $anchor = LodashBasic::get( $this->block_data, array( 'attrs', 'anchor' ) );
373 if ( ! ! $anchor ) {
374 $basicAttributes['id'] = $anchor;
375 }
376
377 $wrapperStyledComponentName = $this->getWrapperElementName();
378
379 $wrapperData = LodashBasic::get( $mapPropsToElements, $wrapperStyledComponentName, array() );
380
381 foreach ( $basicAttributes as $attributeName => $attributeValue ) {
382 if ( is_array( $attributeValue ) ) {
383 $propValue = LodashBasic::get( $wrapperData, $attributeName, array() );
384
385 //if block value is string convert it to array
386 if ( ! is_array( $propValue ) ) {
387 $propValue = array( $propValue );
388 }
389 $mergedValue = array_merge( $attributeValue, $propValue );
390 LodashBasic::set( $wrapperData, $attributeName, $mergedValue );
391 }
392 if ( ! isset( $wrapperData[ $attributeName ] ) ) {
393 LodashBasic::set( $wrapperData, $attributeName, $attributeValue );
394 }
395 }
396
397 LodashBasic::set( $mapPropsToElements, $wrapperStyledComponentName, $wrapperData );
398
399 $this->mapped_props_with_defaults = $mapPropsToElements;
400
401 }
402
403 return $this->mapped_props_with_defaults;
404 }
405
406 public function getParentColibriContext() {
407 return Arr::get( $this->block_context, 'kubio/parentKubio', array() );
408 }
409
410
411 public function getBlockInnerHtml() {
412
413 $content = trim( $this->block_data['innerHTML'] );
414 $content = str_replace( array( "\r\n", "\r", "\n", "\\n" ), '<br/>', $content );
415
416 return $content;
417 }
418
419 public function isSandboxRender() {
420 return apply_filters( 'kubio/sandboxed_render', false );
421 }
422 }
423