✏️ 正在编辑: project-media-swiper.php
路径:
/home/h359620/public_html/wp-content/themes/datis/inc/includes/project-media-swiper.php
提示:
您可以编辑任何文件(包括二进制文件),但请注意不当修改可能导致文件损坏。
<?php /** * File: class-project-media-swiper.php * Purpose: * - Render Swiper slider with thumbnails for CPT `project` * - Supports mixed media (image + video) from CMB2 group meta `_datis_project_gallery` */ if (!defined('ABSPATH')) exit; if (!class_exists('Datis_Project_Media_Swiper')) { final class Datis_Project_Media_Swiper { private static $instance = null; private $gallery_meta_key = '_datis_project_gallery'; public static function get_instance(): self { return self::$instance ?? (self::$instance = new self()); } private function __construct() { add_action('wp_enqueue_scripts', [$this, 'enqueue_assets']); } private function __clone() {} public function __wakeup() { throw new \Exception('Cannot unserialize singleton'); } public function enqueue_assets(): void { if (!is_singular('project')) return; $post_id = get_queried_object_id(); if (!$post_id) return; $gallery = get_post_meta($post_id, $this->gallery_meta_key, true); if (!is_array($gallery) || empty($gallery)) return; $ver = defined('DATIS_THEME_VERSION') ? DATIS_THEME_VERSION : '1.0.0'; wp_enqueue_style( 'datis-project-media-swiper', get_stylesheet_directory_uri() . '/assets/css/project-media-swiper.css', [], $ver ); wp_enqueue_script( 'datis-project-media-swiper', get_stylesheet_directory_uri() . '/assets/js/project-media-swiper.js', [], $ver, true ); } public function render(?int $post_id = null, array $args = []): string { $post_id = $post_id ?: get_the_ID(); if (!$post_id || get_post_type($post_id) !== 'project') return ''; $gallery = get_post_meta($post_id, $this->gallery_meta_key, true); if (!is_array($gallery) || empty($gallery)) return ''; $defaults = [ 'id' => 'datis-project-media-' . $post_id, ]; $args = wp_parse_args($args, $defaults); $slides = $this->normalize_gallery($gallery); if (empty($slides)) return ''; ob_start(); ?> <div id="<?php echo esc_attr($args['id']); ?>" class="datis-project-media" data-datis-gallery> <!-- Main --> <div class="datis-project-media-main"> <div class="swiper datis-project-media-main-swiper" data-datis-main-swiper> <div class="swiper-wrapper"> <?php foreach ($slides as $s): ?> <div class="swiper-slide datis-project-media-slide" data-type="<?php echo esc_attr($s['type']); ?>" <?php if ($s['type'] === 'video'): ?> data-video-src="<?php echo esc_url($s['video_src']); ?>" data-video-embed="<?php echo esc_attr($s['video_embed']); ?>" data-video-poster="<?php echo esc_url($s['poster']); ?>" <?php endif; ?>> <?php if ($s['type'] === 'image'): ?> <img class="datis-project-media-image" src="<?php echo esc_url($s['src']); ?>" alt="" loading="lazy" /> <?php else: ?> <?php if (!empty($s['poster'])): ?> <img class="datis-project-media-poster" src="<?php echo esc_url($s['poster']); ?>" alt="" loading="lazy" /> <?php else: ?> <div class="datis-project-media-poster-placeholder"></div> <?php endif; ?> <button type="button" class="datis-project-media-play" data-datis-play aria-label="<?php echo esc_attr__('Play video', 'datis'); ?>"> <?php echo $this->play_svg(); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped ?> </button> <?php endif; ?> </div> <?php endforeach; ?> </div> </div> </div> <!-- Thumbnails --> <div class="datis-project-media-thumbs"> <div class="swiper datis-project-media-thumbs-swiper" data-datis-thumbs-swiper> <div class="swiper-wrapper"> <?php foreach ($slides as $s): ?> <div class="swiper-slide datis-project-media-thumb"> <?php if (!empty($s['thumb'])): ?> <img src="<?php echo esc_url($s['thumb']); ?>" alt="" loading="lazy" /> <?php else: ?> <span class="datis-project-media-thumb-placeholder"></span> <?php endif; ?> <?php if ($s['type'] === 'video'): ?> <span class="datis-project-media-thumb-badge" aria-hidden="true"></span> <?php endif; ?> </div> <?php endforeach; ?> </div> </div> </div> </div> <?php return (string) ob_get_clean(); } private function normalize_gallery(array $gallery): array { $out = []; foreach ($gallery as $item) { if (!is_array($item)) continue; $type = isset($item['media_type']) ? (string) $item['media_type'] : 'image'; $file = isset($item['media_file']) ? (string) $item['media_file'] : ''; $url = isset($item['media_url']) ? (string) $item['media_url'] : ''; $cover = isset($item['video_cover']) ? (string) $item['video_cover'] : ''; $type = ($type === 'video') ? 'video' : 'image'; if ($type === 'image') { $src = $file ?: ''; if (!$src) continue; $out[] = [ 'type' => 'image', 'src' => esc_url_raw($src), 'thumb' => esc_url_raw($src), ]; continue; } $video_src = $url ?: $file; if (!$video_src) continue; $is_direct = $this->is_direct_video_file($video_src); $poster = $cover ?: ''; $thumb = $poster ?: ''; $out[] = [ 'type' => 'video', 'video_src' => esc_url_raw($video_src), 'video_embed' => $is_direct ? '' : '1', 'poster' => esc_url_raw($poster), 'thumb' => esc_url_raw($thumb), ]; } return $out; } private function is_direct_video_file(string $url): bool { $path = (string) parse_url($url, PHP_URL_PATH); $ext = strtolower(pathinfo($path, PATHINFO_EXTENSION)); return in_array($ext, ['mp4', 'webm', 'ogg', 'mov'], true); } private function play_svg(): string { return '<svg class="datis-play" width="76" height="76" viewBox="0 0 76 76" fill="none" xmlns="http://www.w3.org/2000/svg"> <rect class="datis-wave-ring" x="0.5" y="0.5" width="75" height="75" rx="37.5" stroke="var(--datis-primary-color)" stroke-opacity="1" stroke-width="3"/> <rect x="10" y="10" width="56" height="56" rx="28" fill="var(--datis-primary-color)"/> <path d="M30 37.9999V34.4399C30 30.0199 33.13 28.2099 36.96 30.4199L40.05 32.1999L43.14 33.9799C46.97 36.1899 46.97 39.8099 43.14 42.0199L40.05 43.7999L36.96 45.5799C33.13 47.7899 30 45.9799 30 41.5599V37.9999Z" stroke="white" stroke-width="1.5" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/> </svg>'; } } Datis_Project_Media_Swiper::get_instance(); }
💾 保存文件
← 返回文件管理器