directory(); if (is_dir($directory) && !in_array($directory, $loader->getPaths('plugins'), true)) { $loader->addPath($directory, 'plugins'); } } public function getFunctions(): array { return [ new TwigFunction('kant_plugin_block', $this->plugins->block(...)), new TwigFunction('kant_plugin_props', $this->props(...)), new TwigFunction('kant_plugin_media', $this->mediaItem(...)), new TwigFunction('kant_plugin_settings', $this->plugins->settingsOf(...)), new TwigFunction('kant_media', $this->adminMedia(...)), ]; } /** * Ein Bild fuer ein Bildfeld der Verwaltung - auch ein archiviertes: es ist noch gewaehlt und * wird noch ausgeliefert, also soll es auch zu sehen sein. */ public function adminMedia(string $id): ?array { return 1 === preg_match('/^[a-f0-9]{32}$/D', $id) ? $this->media->find($id) : null; } /** Die geprüften Eigenschaften eines Bausteins - oder null, wenn sie nicht ins Schema passen. */ public function props(array $block): ?array { try { return $this->plugins->validateProps((string) ($block['type'] ?? ''), is_array($block['props'] ?? null) ? $block['props'] : []); } catch (InvalidDocument) { return null; } } /** * Ein Bild der Mediathek für eine Vorlage: Kennung, Titel, Alternativtext und die Fassungen * (src, width, height), die kleinste zuerst. */ public function mediaItem(string $id): ?array { if (1 !== preg_match('/^[a-f0-9]{32}$/D', $id)) { return null; } $item = $this->media->find($id); if (null === $item || ($item['archived'] ?? false)) { return null; } return ['id' => $item['id'], 'title' => (string) ($item['title'] ?? ''), 'alt' => (string) ($item['alt'] ?? ''), 'variants' => $item['variants']]; } }