263 lines
8.8 KiB
PHP
263 lines
8.8 KiB
PHP
<?php
|
|
namespace Grav\Plugin;
|
|
|
|
use Grav\Common\Plugin;
|
|
|
|
class JsonExportPlugin extends Plugin
|
|
{
|
|
public static function getSubscribedEvents()
|
|
{
|
|
return [
|
|
'onPluginsInitialized' => ['onPluginsInitialized', 0]
|
|
];
|
|
}
|
|
|
|
public function onPluginsInitialized()
|
|
{
|
|
if ($this->isAdmin()) {
|
|
return;
|
|
}
|
|
|
|
$this->enable([
|
|
'onPagesInitialized' => ['onPagesInitialized', 0]
|
|
]);
|
|
}
|
|
|
|
public function onPagesInitialized()
|
|
{
|
|
$uri = $this->grav['uri'];
|
|
$path = $uri->path();
|
|
|
|
if (strpos($path, '/api/') !== 0) {
|
|
return;
|
|
}
|
|
|
|
$lang = $_GET['lang'] ?? 'en';
|
|
|
|
header('Content-Type: application/json');
|
|
header('Access-Control-Allow-Origin: *');
|
|
|
|
if ($path === '/api/stations') {
|
|
echo json_encode($this->getStationsList($lang), JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE);
|
|
exit;
|
|
}
|
|
|
|
if (preg_match('#^/api/station/([a-zA-Z0-9-]+)$#', $path, $matches)) {
|
|
$station = $this->getStation($matches[1], $lang);
|
|
if ($station) {
|
|
echo json_encode($station, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE);
|
|
} else {
|
|
http_response_code(404);
|
|
echo json_encode(['error' => 'Station not found']);
|
|
}
|
|
exit;
|
|
}
|
|
|
|
if ($path === '/api/translations') {
|
|
echo json_encode($this->getTranslations($lang), JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE);
|
|
exit;
|
|
}
|
|
}
|
|
|
|
private function getStationsList($lang)
|
|
{
|
|
$pages = $this->grav['pages'];
|
|
$stations = [];
|
|
|
|
foreach ($pages->all() as $page) {
|
|
if ($page->template() === 'station') {
|
|
$header = $page->header();
|
|
if (!($header->active ?? true)) continue;
|
|
|
|
$stations[] = [
|
|
'id' => $header->station_id ?? $page->slug(),
|
|
'type' => $header->station_type ?? 'exhibit',
|
|
'title' => $this->getTranslated($header->title_translations ?? [], $lang),
|
|
'description' => $this->getTranslated($header->description_translations ?? [], $lang),
|
|
'order' => $header->order ?? 0
|
|
];
|
|
}
|
|
}
|
|
|
|
usort($stations, fn($a, $b) => $a['order'] <=> $b['order']);
|
|
return $stations;
|
|
}
|
|
|
|
private function getStation($stationId, $lang)
|
|
{
|
|
$pages = $this->grav['pages'];
|
|
|
|
foreach ($pages->all() as $page) {
|
|
if ($page->template() === 'station') {
|
|
$header = $page->header();
|
|
$id = $header->station_id ?? $page->slug();
|
|
|
|
if ($id === $stationId) {
|
|
return $this->formatStation($page, $lang);
|
|
}
|
|
}
|
|
}
|
|
return null;
|
|
}
|
|
|
|
private function formatStation($page, $lang)
|
|
{
|
|
$header = $page->header();
|
|
|
|
$station = [
|
|
'id' => $header->station_id ?? $page->slug(),
|
|
'type' => $header->station_type ?? 'exhibit',
|
|
'language' => $lang,
|
|
'title' => $this->getTranslated($header->title_translations ?? [], $lang),
|
|
'description' => $this->getTranslated($header->description_translations ?? [], $lang),
|
|
'components' => []
|
|
];
|
|
|
|
if (isset($header->components) && is_array($header->components)) {
|
|
foreach ($header->components as $comp) {
|
|
$station['components'][] = $this->formatComponent($comp, $lang);
|
|
}
|
|
}
|
|
|
|
return $station;
|
|
}
|
|
|
|
private function formatComponent($comp, $lang)
|
|
{
|
|
$out = [
|
|
'id' => $comp['id'] ?? uniqid(),
|
|
'type' => $comp['type'] ?? 'text'
|
|
];
|
|
|
|
switch ($comp['type']) {
|
|
case 'heading':
|
|
$out['level'] = $comp['level'] ?? 'h2';
|
|
$out['content'] = $this->getTranslated($comp['content'] ?? [], $lang);
|
|
break;
|
|
case 'text':
|
|
$out['content'] = $this->getTranslated($comp['content'] ?? [], $lang);
|
|
break;
|
|
case 'video':
|
|
$out['src'] = $this->getTranslated($comp['src'] ?? [], $lang);
|
|
$out['poster'] = $comp['poster'] ?? null;
|
|
$out['caption'] = $this->getTranslated($comp['caption'] ?? [], $lang);
|
|
break;
|
|
case 'audio':
|
|
$out['src'] = $this->getTranslated($comp['src'] ?? [], $lang);
|
|
$out['caption'] = $this->getTranslated($comp['caption'] ?? [], $lang);
|
|
break;
|
|
case 'tabs':
|
|
$out['tabs'] = [];
|
|
foreach ($comp['tabs'] ?? [] as $tab) {
|
|
$out['tabs'][] = [
|
|
'title' => $this->getTranslated($tab['title'] ?? [], $lang),
|
|
'content' => $this->getTranslated($tab['content'] ?? [], $lang)
|
|
];
|
|
}
|
|
break;
|
|
case 'slideshow':
|
|
$out['slides'] = [];
|
|
foreach ($comp['slides'] ?? [] as $slide) {
|
|
$out['slides'][] = [
|
|
'image' => $slide['image'] ?? '',
|
|
'caption' => $this->getTranslated($slide['caption'] ?? [], $lang)
|
|
];
|
|
}
|
|
break;
|
|
}
|
|
|
|
return $out;
|
|
}
|
|
|
|
private function getTranslated($field, $lang)
|
|
{
|
|
if (is_string($field)) return $field;
|
|
return $field[$lang] ?? $field['en'] ?? reset($field) ?: '';
|
|
}
|
|
|
|
private function getTranslations($lang)
|
|
{
|
|
$t = [
|
|
'en' => [
|
|
'appTitle' => 'EU Media Guide',
|
|
'scanQR' => 'Scan QR Code',
|
|
'selectLanguage' => 'Select Language',
|
|
'contentLibrary' => 'Content Library',
|
|
'loading' => 'Loading...',
|
|
'play' => 'Play',
|
|
'pause' => 'Pause',
|
|
'next' => 'Next',
|
|
'previous' => 'Previous',
|
|
'menu' => 'Menu',
|
|
'close' => 'Close'
|
|
],
|
|
'fr' => [
|
|
'appTitle' => 'Guide Média UE',
|
|
'scanQR' => 'Scanner le code QR',
|
|
'selectLanguage' => 'Choisir la langue',
|
|
'contentLibrary' => 'Bibliothèque',
|
|
'loading' => 'Chargement...',
|
|
'play' => 'Lecture',
|
|
'pause' => 'Pause',
|
|
'next' => 'Suivant',
|
|
'previous' => 'Précédent',
|
|
'menu' => 'Menu',
|
|
'close' => 'Fermer'
|
|
],
|
|
'de' => [
|
|
'appTitle' => 'EU Medienführer',
|
|
'scanQR' => 'QR-Code scannen',
|
|
'selectLanguage' => 'Sprache wählen',
|
|
'contentLibrary' => 'Inhaltsbibliothek',
|
|
'loading' => 'Laden...',
|
|
'play' => 'Abspielen',
|
|
'pause' => 'Pause',
|
|
'next' => 'Weiter',
|
|
'previous' => 'Zurück',
|
|
'menu' => 'Menü',
|
|
'close' => 'Schließen'
|
|
],
|
|
'nl' => [
|
|
'appTitle' => 'EU Mediagids',
|
|
'scanQR' => 'QR-code scannen',
|
|
'selectLanguage' => 'Taal selecteren',
|
|
'contentLibrary' => 'Inhoudsbibliotheek',
|
|
'loading' => 'Laden...',
|
|
'play' => 'Afspelen',
|
|
'pause' => 'Pauze',
|
|
'next' => 'Volgende',
|
|
'previous' => 'Vorige',
|
|
'menu' => 'Menu',
|
|
'close' => 'Sluiten'
|
|
],
|
|
'it' => [
|
|
'appTitle' => 'Guida Media UE',
|
|
'scanQR' => 'Scansiona codice QR',
|
|
'selectLanguage' => 'Seleziona lingua',
|
|
'contentLibrary' => 'Libreria contenuti',
|
|
'loading' => 'Caricamento...',
|
|
'play' => 'Riproduci',
|
|
'pause' => 'Pausa',
|
|
'next' => 'Successivo',
|
|
'previous' => 'Precedente',
|
|
'menu' => 'Menu',
|
|
'close' => 'Chiudi'
|
|
],
|
|
'es' => [
|
|
'appTitle' => 'Guía de Medios UE',
|
|
'scanQR' => 'Escanear código QR',
|
|
'selectLanguage' => 'Seleccionar idioma',
|
|
'contentLibrary' => 'Biblioteca de contenido',
|
|
'loading' => 'Cargando...',
|
|
'play' => 'Reproducir',
|
|
'pause' => 'Pausa',
|
|
'next' => 'Siguiente',
|
|
'previous' => 'Anterior',
|
|
'menu' => 'Menú',
|
|
'close' => 'Cerrar'
|
|
]
|
|
];
|
|
return $t[$lang] ?? $t['en'];
|
|
}
|
|
}
|