| @@ -1,11 +1,12 @@ | ||
| 1 | 1 | <?php |
| 2 | 2 | /** |
| 3 | - * Server-side rendering for the Flexible Marquee block. | |
| 3 | + * Marquee: the page output (see \GutSlider\Blocks\Marquee). | |
| 4 | 4 | * |
| 5 | - * @param array $attributes Block attributes. | |
| 6 | - * @param string $content Block content (inner blocks HTML). | |
| 7 | - * @param WP_Block $block Block instance. | |
| 5 | + * @var array $attributes Block attributes. | |
| 6 | + * @var string $content Rendered items. | |
| 7 | + * | |
| 8 | + * @package GutSlider | |
| 8 | 9 | */ |
| 9 | 10 | |
| 10 | 11 | if ( ! defined( 'ABSPATH' ) ) { |
| 11 | 12 | exit; |
| @@ -10,143 +11,5 @@ | ||
| 10 | 11 | if ( ! defined( 'ABSPATH' ) ) { |
| 11 | 12 | exit; |
| 12 | 13 | } |
| 13 | 14 | |
| 14 | -// --------------------------------------------------------------------------- | |
| 15 | -// Allowed values for enumerated attributes. | |
| 16 | -// --------------------------------------------------------------------------- | |
| 17 | -$gutslider_allowed_directions = array( 'left', 'right', 'up', 'down' ); | |
| 18 | -$gutslider_allowed_orientations = array( 'horizontal', 'vertical' ); | |
| 19 | -$gutslider_allowed_units = array( 'px', 'em', 'rem', 'vh', 'vw', '%' ); | |
| 20 | - | |
| 21 | -// --------------------------------------------------------------------------- | |
| 22 | -// Sanitize scalar attributes. | |
| 23 | -// --------------------------------------------------------------------------- | |
| 24 | -$gutslider_unique_id = isset( $attributes['uniqueId'] ) | |
| 25 | - ? sanitize_html_class( $attributes['uniqueId'] ) | |
| 26 | - : ''; | |
| 27 | - | |
| 28 | -$gutslider_speed = isset( $attributes['speed'] ) | |
| 29 | - ? max( 1, intval( $attributes['speed'] ) ) | |
| 30 | - : 30; | |
| 31 | - | |
| 32 | -$gutslider_direction = ( isset( $attributes['direction'] ) && in_array( $attributes['direction'], $gutslider_allowed_directions, true ) ) | |
| 33 | - ? $attributes['direction'] | |
| 34 | - : 'left'; | |
| 35 | - | |
| 36 | -$gutslider_orientation = ( isset( $attributes['orientation'] ) && in_array( $attributes['orientation'], $gutslider_allowed_orientations, true ) ) | |
| 37 | - ? $attributes['orientation'] | |
| 38 | - : 'horizontal'; | |
| 39 | - | |
| 40 | -$gutslider_pause_on_hover = ! empty( $attributes['pauseOnHover'] ); | |
| 41 | -$gutslider_is_vertical = ( 'vertical' === $gutslider_orientation ); | |
| 42 | - | |
| 43 | -// --------------------------------------------------------------------------- | |
| 44 | -// Sanitize responsive range attributes. | |
| 45 | -// --------------------------------------------------------------------------- | |
| 46 | -$gutslider_gap_ranges = ( isset( $attributes['columnsGapRanges'] ) && is_array( $attributes['columnsGapRanges'] ) ) | |
| 47 | - ? $attributes['columnsGapRanges'] | |
| 48 | - : array(); | |
| 49 | - | |
| 50 | -$gutslider_gap_units = ( isset( $attributes['columnsGapUnits'] ) && is_array( $attributes['columnsGapUnits'] ) ) | |
| 51 | - ? $attributes['columnsGapUnits'] | |
| 52 | - : array(); | |
| 53 | - | |
| 54 | -$gutslider_height_ranges = ( isset( $attributes['slideHeightRanges'] ) && is_array( $attributes['slideHeightRanges'] ) ) | |
| 55 | - ? $attributes['slideHeightRanges'] | |
| 56 | - : array(); | |
| 57 | - | |
| 58 | -$gutslider_height_units = ( isset( $attributes['slideHeightUnits'] ) && is_array( $attributes['slideHeightUnits'] ) ) | |
| 59 | - ? $attributes['slideHeightUnits'] | |
| 60 | - : array(); | |
| 61 | - | |
| 62 | -// --------------------------------------------------------------------------- | |
| 63 | -// Build CSS custom properties for the wrapper element. | |
| 64 | -// | |
| 65 | -// style.scss reads these via var(--marquee-gap-desk) etc. inside media queries, | |
| 66 | -// so responsive behaviour lives entirely in the stylesheet — no <style> tag needed. | |
| 67 | -// --------------------------------------------------------------------------- | |
| 68 | -$gutslider_css_vars = array(); | |
| 69 | - | |
| 70 | -foreach ( array( 'desk', 'tab', 'mob' ) as $bp ) { | |
| 71 | - $val = isset( $gutslider_gap_ranges[ $bp ] ) && is_numeric( $gutslider_gap_ranges[ $bp ] ) ? $gutslider_gap_ranges[ $bp ] : null; | |
| 72 | - $unit = ( isset( $gutslider_gap_units[ $bp ] ) && in_array( $gutslider_gap_units[ $bp ], $gutslider_allowed_units, true ) ) | |
| 73 | - ? $gutslider_gap_units[ $bp ] | |
| 74 | - : 'px'; | |
| 75 | - | |
| 76 | - if ( null !== $val ) { | |
| 77 | - $gutslider_css_vars[] = '--marquee-gap-' . $bp . ':' . floatval( $val ) . $unit; | |
| 78 | - } | |
| 79 | -} | |
| 80 | - | |
| 81 | -if ( $gutslider_is_vertical ) { | |
| 82 | - foreach ( array( 'desk', 'tab', 'mob' ) as $bp ) { | |
| 83 | - $val = isset( $gutslider_height_ranges[ $bp ] ) && is_numeric( $gutslider_height_ranges[ $bp ] ) ? $gutslider_height_ranges[ $bp ] : null; | |
| 84 | - $unit = ( isset( $gutslider_height_units[ $bp ] ) && in_array( $gutslider_height_units[ $bp ], $gutslider_allowed_units, true ) ) | |
| 85 | - ? $gutslider_height_units[ $bp ] | |
| 86 | - : 'px'; | |
| 87 | - | |
| 88 | - if ( null !== $val ) { | |
| 89 | - $gutslider_css_vars[] = '--marquee-height-' . $bp . ':' . floatval( $val ) . $unit; | |
| 90 | - } | |
| 91 | - } | |
| 92 | -} | |
| 93 | - | |
| 94 | -// --------------------------------------------------------------------------- | |
| 95 | -// Build wrapper attributes. | |
| 96 | -// --------------------------------------------------------------------------- | |
| 97 | -$gutslider_wrapper_class = implode( | |
| 98 | - ' ', | |
| 99 | - array( | |
| 100 | - 'marquee-wrapper', | |
| 101 | - esc_attr( $gutslider_unique_id ), | |
| 102 | - 'marquee-' . esc_attr( $gutslider_orientation ), | |
| 103 | - ) | |
| 104 | -); | |
| 105 | - | |
| 106 | -$gutslider_wrapper_attrs = array( 'class' => $gutslider_wrapper_class ); | |
| 107 | - | |
| 108 | -if ( ! empty( $gutslider_css_vars ) ) { | |
| 109 | - // All var names are hardcoded; values use floatval() + whitelisted units — no raw user input. | |
| 110 | - $gutslider_wrapper_attrs['style'] = implode( ';', $gutslider_css_vars ); | |
| 111 | -} | |
| 112 | - | |
| 113 | -// --------------------------------------------------------------------------- | |
| 114 | -// Build container attributes. | |
| 115 | -// --------------------------------------------------------------------------- | |
| 116 | -$gutslider_container_classes = array( | |
| 117 | - 'marquee-container', | |
| 118 | - 'marquee-' . esc_attr( $gutslider_orientation ), | |
| 119 | -); | |
| 120 | - | |
| 121 | -if ( $gutslider_pause_on_hover ) { | |
| 122 | - $gutslider_container_classes[] = 'pause-on-hover'; | |
| 123 | -} | |
| 124 | - | |
| 125 | -// --------------------------------------------------------------------------- | |
| 126 | -// Determine animation name from orientation + direction. | |
| 127 | -// --------------------------------------------------------------------------- | |
| 128 | -if ( $gutslider_is_vertical ) { | |
| 129 | - $gutslider_animation_name = ( 'up' === $gutslider_direction || 'left' === $gutslider_direction ) | |
| 130 | - ? 'marquee-scroll-up' | |
| 131 | - : 'marquee-scroll-down'; | |
| 132 | -} else { | |
| 133 | - $gutslider_animation_name = 'marquee-scroll-' . $gutslider_direction; | |
| 134 | -} | |
| 135 | -?> | |
| 136 | -<div <?php echo wp_kses_data( get_block_wrapper_attributes( $gutslider_wrapper_attrs ) ); ?>> | |
| 137 | - <div | |
| 138 | - class="<?php echo esc_attr( implode( ' ', $gutslider_container_classes ) ); ?>" | |
| 139 | - style="--animation-duration:<?php echo intval( $gutslider_speed ); ?>s;--animation-name:<?php echo esc_attr( $gutslider_animation_name ); ?>" | |
| 140 | - > | |
| 141 | - <div class="marquee-content"> | |
| 142 | - <?php | |
| 143 | - echo wp_kses_post( $content ); | |
| 144 | - ?> | |
| 145 | - </div> | |
| 146 | - <div class="marquee-content" aria-hidden="true"> | |
| 147 | - <?php | |
| 148 | - echo wp_kses_post( $content ); | |
| 149 | - ?> | |
| 150 | - </div> | |
| 151 | - </div> | |
| 152 | -</div> | |
| 15 | +echo \GutSlider\Blocks\Marquee::render( $attributes, $content, $block ?? null ); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped | |