<?php
/**
* @file
* Views TimelineJS API, theming, libraries, etc.
*/
use Drupal\Component\Utility\Html;
use Drupal\Core\Routing\RouteMatchInterface;
use Drupal\Core\Template\Attribute;
/**
* Implements hook_library_info_alter().
*
* Provides backward compatibility for sites that originally installed version
* 8.x-3.0 which gave the TimelineJS CSS libraries a weight of "theme."
*
* @todo Remove this in the next major version.
*
* @see https://www.drupal.org/node/2856403
*/
function views_timelinejs_library_info_alter(&$libraries, $extension) {
$config = \Drupal::config('views_timelinejs.settings');
$library_group = $config->get('css_library_group');
$valid_groups = [
'component',
'state',
'theme',
];
// Verify that the group has been set and that it is a valid group key.
if ($extension == 'views_timelinejs' && isset($library_group) && in_array($library_group, $valid_groups)) {
$libraries['timelinejs.cdn']['css'] = [
$library_group => [
'https://cdn.knightlab.com/libs/timeline3/latest/css/timeline.css' => [
'type' => 'external',
],
],
];
$libraries['timelinejs.local']['css'] = [
$library_group => [
'/libraries/timeline3/css/timeline.css' => [],
],
];
}
}
/**
* Returns an array of font set options that are supported by TimelineJS3.
*
* @return array
* An array of font set names, keyed by the name section of the set's CSS
* filename, i.e. 'font.set-name.css'.
*/
function _views_timelinejs_list_font_sets() {
return [
'abril-droidsans' => 'Abril Fatface & Droid Sans',
'amatic-andika' => 'Amatic & Andika',
'bevan-pontanosans' => 'Bevan & Pontano Sans',
'bitter-raleway' => 'Bitter & Raleway',
'clicker-garamond' => 'Clicker & Garamond',
'dancing-ledger' => 'Dancing & Ledger',
'default' => 'Default',
'fjalla-average' => 'Fjalla & Average',
'georgia-helvetica' => 'Georgia & Helvetica',
'knightlab' => 'Knight Lab',
'lustria-lato' => 'Lustria Lato',
'medula-lato' => 'Medula One & Lato',
'oldstandard' => 'Old Standard',
'opensans-gentiumbook' => 'Open Sans & Gentium Book Basic',
'playfair-faunaone' => 'Playfair & Fauna One',
'playfair' => 'Playfair SC & Playfair',
'pt' => 'PT Sans / PT Serif / PT Sans Narrow',
'roboto-megrim' => 'Roboto Slab & Megrim',
'rufina-sintony' => 'Rufina & Sintony',
'ubuntu' => 'Ubuntu',
'unicaone-vollkorn' => 'Unica One & Vollkorn',
];
}
/**
* Returns an array of language options that are supported by TimelineJS3.
*
* @return array
* An array of language names, keyed by language code.
*/
function _views_timelinejs_list_languages() {
return [
'af' => t('Afrikaans'),
'ar' => t('Arabic'),
'hy' => t('Armenian'),
'eu' => t('Basque'),
'be' => t('Belarusian'),
'bg' => t('Bulgarian'),
'ca' => t('Catalan'),
'zh-cn' => t('Chinese'),
'hr' => t('Croatian / Hrvatski'),
'cz' => t('Czech'),
'da' => t('Danish'),
'nl' => t('Dutch'),
'en' => t('English'),
'en-24hr' => t('English (24-hour time)'),
'en-week' => t('English (display weeks)'),
'eo' => t('Esperanto'),
'et' => t('Estonian'),
'fo' => t('Faroese'),
'fa' => t('Farsi'),
'fi' => t('Finnish'),
'fr' => t('French'),
'fy' => t('Frisian'),
'gl' => t('Galician'),
'ka' => t('Georgian'),
'de' => t('German / Deutsch'),
'el' => t('Greek'),
'he' => t('Hebrew'),
'hi' => t('Hindi'),
'hu' => t('Hungarian'),
'is' => t('Icelandic'),
'id' => t('Indonesian'),
'ga' => t('Irish'),
'it' => t('Italian'),
'ja' => t('Japanese'),
'ko' => t('Korean'),
'lv' => t('Latvian'),
'lt' => t('Lithuanian'),
'lb' => t('Luxembourgish'),
'ms' => t('Malay'),
'ne' => t('Nepali'),
'no' => t('Norwegian'),
'pl' => t('Polish'),
'pt' => t('Portuguese'),
'pt-br' => t('Portuguese (Brazilian)'),
'ro' => t('Romanian'),
'rm' => t('Romansh'),
'ru' => t('Russian'),
'sr-cy' => t('Serbian - Cyrillic'),
'sr' => t('Serbian - Latin'),
'si' => t('Sinhalese'),
'sk' => t('Slovak'),
'sl' => t('Slovenian'),
'es' => t('Spanish'),
'sv' => t('Swedish'),
'tl' => t('Tagalog'),
'ta' => t('Tamil'),
'zh-tw' => t('Taiwanese'),
'te' => t('Telugu'),
'th' => t('Thai'),
'tr' => t('Turkish'),
'uk' => t('Ukrainian'),
'ur' => t('Urdu'),
];
}
/**
* Returns an array of Drupal language codes mapped to TimelineJS codes.
*
* @return array
* An array of language codes supported by TimelineJS, keyed by the equivalent
* Drupal language code.
*/
function _views_timelinejs_language_map() {
return [
'cs' => 'cz',
'nb' => 'no',
'nn' => 'no',
'pt-pt' => 'pt',
'zh-hans' => 'zh-cn',
'zh-hant' => 'zh-cn',
];
}
/**
* Implements hook_help().
*/
function views_timelinejs_help($route_name, RouteMatchInterface $route_match) {
switch ($route_name) {
// Help for the settings form.
case 'views_timelinejs.admin':
return '<p>' . t('Configure how the Views TimelineJS plugin behaves on the site. Select whether to use a CDN or serve the library locally.') . '</p>';
}
}
/**
* Prepares variables for the TimelineJS style template.
*
* Default template: views-timelinejs-view-timelinejs.html.twig.
*
* @param array $vars
* An associative array containing:
* - view: A ViewExecutable object.
* - rows: The raw row data.
* - timeline_options: TimelineJS presentation options.
* - timeline_font: The name of a TimelineJS font set.
*/
function template_preprocess_views_timelinejs_view_timelinejs(array &$vars) {
$config = \Drupal::config('views_timelinejs.settings');
$library_location = $config->get('library_location');
$view = $vars['view'];
// Set a unique id attribute for the timeline embed div. Also set a width and
// height for the div. This is required for proper styling of the timeline.
// See https://timeline.knightlab.com/docs/instantiate-a-timeline.html.
$id = Html::getId('timelinejs_' . $view->storage->id() . '_' . $view->current_display);
$style = 'width: ' . $vars['options']['timeline_options']['width'] . '; height: ' . $vars['options']['timeline_options']['height'] . ';';
$vars['attributes'] = new Attribute(['id' => $id, 'style' => $style]);
// Load required libraries and styles.
$vars['#attached']['library'][] = 'views_timelinejs/timelinejs.' . $library_location;
$vars['#attached']['library'][] = 'views_timelinejs/create_timeline';
$vars['#attached']['drupalSettings']['TimelineJS'][] = [
'options' => _sanitize_timeline_options($vars['options']['timeline_options']),
'source' => $vars['rows'],
'embed_id' => $id,
'processed' => TRUE,
];
}
/**
* Sanitizes the timeline options.
*/
function _sanitize_timeline_options($options) {
// Sanitize the options.
$options = array_map(['Drupal\Component\Utility\Html', 'escape'], $options);
// Remove empty values from the options before returning.
return array_filter($options);
}