timefield.module in Timefield 1.0.x
Same filename and directory in other branches
Contains timefield.module.
File
timefield.moduleView source
<?php
/**
* @file
* Contains timefield.module.
*/
use Drupal\Core\Routing\RouteMatchInterface;
use Drupal\Component\Render\FormattableMarkup;
/**
* Timefield js settings.
*
* @param $class
* @param $settings
* @return array
*/
function _timefield_js_settings($class, $settings) {
$js_settings = array(
'showLeadingZero' => $settings['showLeadingZero'],
'timeSeparator' => $settings['separator'],
'showPeriod' => $settings['showPeriod'],
'showPeriodLabels' => $settings['showPeriod'],
'periodSeparator' => $settings['periodSeparator'],
'amPmText' => array(
$settings['am_text'],
$settings['pm_text'],
),
'showMinutesLeadingZero' => TRUE,
'showCloseButton' => $settings['showCloseButton'],
'closeButtonText' => $settings['closeButtonText'],
'showNowButton' => $settings['showNowButton'],
'nowButtonText' => $settings['nowButtonText'],
'showDeselectButton' => $settings['showDeselectButton'],
'deselectButtonText' => $settings['deselectButtonText'],
'myPosition' => $settings['myPosition'],
'atPosition' => $settings['atPosition'],
);
return $js_settings;
}
/**
* Helper function to return time value from a timefield integer.
*
* @param array $settings
* Field formatter settings. This is a structured array used to format a date
* with PHP's date() function. This array has the following keys:
* -separator
* The character(s) the go(es) between the hour and minute value
* -period_separator
* The character(s) the go(es) between the time string and the period
* (AM/PM)
* -period
* The PHP formatting option for period, or "none" to omit display
* -hour
* The PHP formatting option for hour
* -minute
* The PHP formatting option for minute
* @see _timefield_time_part_format() for some possible options. It is worth
* noting that no assumptions are made about how one wishes to format date
* output, e.g., 24-hour formatted times are not assumed to not have AM/PM
* period information.
* @param integer $value
* Integer offset from midnight to be converted to human-readable time. This
* value is basically number of seconds from midnight. If you wish to
* to show a time +1 day, your value can be greater than 86400.
*
* @return string
* Human-readable time string
*/
function timefield_integer_to_time($settings, $value) {
$format = timefield_build_time_format($settings);
if (isset($value)) {
if ($value >= 86400) {
$value = $value - 86400;
}
return date($format, mktime(0, 0, $value));
}
else {
return '';
}
}
/**
* Helper function to return duration value from a timefield integer value, in
* specified format.
*
* @param integer $value
* Time value in seconds
* @param string $format
* Out format options. Possible options are:
* -hours
* -minutes
* -seconds
* -time
*
* @return string
* Integer cast to string or string depending on $format passed.
*/
function timefield_integer_to_duration($value, $format) {
switch ($format) {
case 'hours':
return (string) round($value / 60 / 60, 2);
break;
case 'minutes':
return (string) round($value / 60, 2);
break;
case 'seconds':
return (string) $value;
break;
case 'time':
return date('g:i', mktime(NULL, NULL, $value));
break;
}
}
/**
* Helper function to return integer value offset from midnight from time
* format.
*
* @param string $value
* Time format that should be parsable via date_parse().
*/
function timefield_time_to_integer($value) {
$time = date_parse($value);
$output = 0;
if ($time['error_count'] == 0) {
$output += $time['hour'] * 60 * 60;
$output += $time['minute'] * 60;
$output += $time['second'];
return $output;
}
else {
return 0;
}
}
/**
* Helper function to return duration value from 2 values, in specified format.
*
* @param integer $value
* First time value
* @param integer $value2
* Second time value
* @param string $format
* Out format options. Possible options are:
* -hours
* -minutes
* -seconds
* -time
*
* @return mixed
* Integer or string depending on $format passed
*/
function timefield_time_to_duration($value, $value2, $format) {
if ($value2 < $value) {
$value2 += 86400;
}
$duration = $value2 - $value;
switch ($format) {
case 'hours':
return round($duration / 60 / 60, 2);
break;
case 'minutes':
return round($duration / 60, 2);
break;
case 'seconds':
return $duration;
break;
case 'time':
return date('g:i', mktime(NULL, NULL, $duration));
break;
}
return 0;
}
function template_preprocess_timefield(&$variables) {
if ($variables['format'] == 'default') {
// Encode the time elements.
$variables['time']['value'] = \Drupal\Component\Utility\Html::escape($variables['time']['value']);
$variables['time']['formatted_value'] = trim(timefield_integer_to_time($variables['settings']['display_format'], $variables['time']['value']));
$variables['time']['time'] = $variables['time']['formatted_value'];
if (isset($variables['time']['value2'])) {
$variables['time']['value2'] = \Drupal\Component\Utility\Html::escape($variables['time']['value2']);
$variables['time']['formatted_value2'] = trim(timefield_integer_to_time($variables['settings']['display_format'], $variables['time']['value2']));
$variables['time']['time'] .= ' - ' . $variables['time']['formatted_value2'];
}
if ($variables['settings']['weekly_summary'] || $variables['settings']['weekly_summary_with_label']) {
foreach (_timefield_weekly_summary_days() as $day => $day_text) {
$days = array();
if ((bool) $variables['time'][$day]) {
$days[$day] = $day_text;
}
}
if ($days) {
$variables['time']['days'] = $days;
$variables['time']['time'] = implode(', ', $days) . ' ' . $variables['time']['time'];
}
}
}
}
function _timefield_display_format_form($name, $fieldset_header, $settings) {
$element[$name] = array(
'#title' => \Drupal\Component\Utility\Html::escape($fieldset_header),
'#type' => 'fieldset',
);
$element[$name]['hour'] = array(
'#title' => t('Hour Format'),
'#type' => 'select',
'#default_value' => isset($settings[$name]['hour']) ? $settings[$name]['hour'] : 'g',
'#options' => _timefield_time_part_format('hour'),
);
$element[$name]['minute'] = array(
'#title' => t('Minute Format'),
'#type' => 'select',
'#default_value' => isset($settings[$name]['minute']) ? $settings[$name]['minute'] : 'i',
'#options' => _timefield_time_part_format('minute'),
);
$element[$name]['separator'] = array(
'#title' => t('Hour and Minute Separator'),
'#type' => 'textfield',
'#default_value' => isset($settings[$name]['separator']) ? $settings[$name]['separator'] : ':',
'#size' => 10,
);
$element[$name]['period'] = array(
'#title' => t('AM/PM format'),
'#type' => 'select',
'#default_value' => isset($settings[$name]['period']) ? $settings[$name]['period'] : 'a',
'#options' => _timefield_time_part_format('period'),
);
$element[$name]['periodSeparator'] = array(
'#title' => t('Minute and period separtor'),
'#type' => 'textfield',
'#default_value' => isset($settings[$name]['periodSeparator']) ? $settings[$name]['periodSeparator'] : '',
'#size' => 10,
'#description' => t('The character used to separate the time from the time period (AM/PM)'),
);
return $element;
}
function _timefield_time_part_format($part) {
$values = array(
'hour' => array(
'g' => t('12-hour format of an hour without leading zeros'),
'G' => t('24-hour format of an hour without leading zeros'),
'h' => t('12-hour format of an hour with leading zeros'),
'H' => t('24-hour format of an hour with leading zeros'),
),
'minute' => array(
'i' => t('Minutes with leading Zeros'),
'none' => t('Do not display minutes'),
),
'period' => array(
'a' => t('Lowercase Ante meridiem and Post meridiem (am/pm)'),
'A' => t('Uppercase Ante meridiem and Post meridiem (AM/PM)'),
'none' => t('Do not display period'),
),
);
return $values[$part];
}
function timefield_build_time_format($settings) {
if (isset($settings['showPeriod'])) {
$format = $settings['showLeadingZero'] ? 'h' : 'g';
//convert to 12/24 format based on period
$format = $settings['showPeriod'] ? strtolower($format) : strtoupper($format);
$format .= $settings['separator'] . 'i';
$format .= $settings['periodSeparator'] != '' && $settings['showPeriod'] ? strtolower($settings['periodSeparator']) : '';
$format .= $settings['showPeriod'] ? 'a' : '';
}
else {
$format = $settings['hour'];
$format .= $settings['minute'] == 'none' ? '' : $settings['separator'] . $settings['minute'];
$format .= $settings['period'] == 'none' ? '' : (isset($settings['periodSeparator']) ? $settings['periodSeparator'] : '') . $settings['period'];
}
return $format;
}
/**
* Map first day of week
*/
function _timefield_weekly_summary_days_map($item) {
$days = _timefield_weekly_summary_days();
$output = array();
foreach ($days as $day => $label) {
$output[$day] = $item->{$day} === 0 || $item->{$day} == "0" ? 0 : $day;
}
return $output;
}
/**
* Helper function days array
*/
function _timefield_weekly_summary_days() {
$days = array(
'mon' => t('Monday'),
'tue' => t('Tuesday'),
'wed' => t('Wednesday'),
'thu' => t('Thursday'),
'fri' => t('Friday'),
'sat' => t('Saturday'),
'sun' => t('Sunday'),
);
return $days;
}
/**
* Implements hook_theme().
*/
function timefield_theme() {
return array(
'timefield_formatter' => array(
'render element' => 'element',
'variables' => array(
'label' => NULL,
'label_display' => NULL,
'label_hidden' => NULL,
'items' => NULL,
'settings' => NULL,
'format' => NULL,
),
'template' => 'timefield',
),
'timefield_duration' => array(
'render element' => 'element',
'variables' => array(
'label' => NULL,
'label_display' => NULL,
'label_hidden' => NULL,
'items' => NULL,
'settings' => NULL,
'format' => NULL,
),
'template' => 'timefield-duration',
),
'timefield_weekly_summary_minical_box' => array(
'render element' => 'element',
'variables' => array(
'label' => NULL,
'label_display' => NULL,
'label_hidden' => NULL,
'items' => NULL,
'settings' => NULL,
'format' => NULL,
'time' => NULL,
),
'template' => 'timefield-weekly-minical-box',
),
'timefield_mini_calendar' => array(
'render element' => 'element',
'variables' => array(
'label' => NULL,
'label_display' => NULL,
'label_hidden' => NULL,
'header' => NULL,
'rows' => NULL,
'content' => NULL,
),
'template' => 'timefield-mini-calendar',
),
);
}
/**
* Helper function to build options array
*/
function _timefield_duration_options($current_option = NULL) {
$values = array(
'hours' => t('Duration in decimal hours, e.g. 1.5'),
'seconds' => t('Duration in seconds'),
'minutes' => t('Duration in minutes'),
'time' => t('Duration in time format hours, e.g. 1:30'),
);
if (is_null($current_option)) {
return $values;
}
else {
return $values[$current_option];
}
}
/**
* Build a header for a schedule table
*/
function _timefield_weekly_summary_build_header($first_day) {
$days = _timefield_weekly_summary_days();
$day_list = $days;
$header = array(
'time' => t('Time'),
);
$found_header = FALSE;
foreach ($days as $index => $day) {
if ($index == $first_day) {
$found_header = TRUE;
}
if ($found_header) {
$header[$index] = $day;
unset($day_list[$index]);
}
}
$header += $day_list;
return $header;
}
/**
* Add rows to the table
*/
function timefield_weekly_summary_build_rows($item, $header, $settings) {
_timefield_weekly_summary_explode_items($item);
$times = _timefield_weekly_summary_build_time_column($settings);
$abs_start = timefield_time_to_integer($settings['absolute_start']);
$abs_end = timefield_time_to_integer($settings['absolute_end']);
$total_range = $abs_end - $abs_start;
$cell_data = array();
$count = 0;
foreach ($times as $time_index => $time) {
$row['time'] = array(
'data' => $time['display'],
);
if (!isset($cell_data[$time_index])) {
$cell_data[$time_index] = array();
}
foreach ($header as $index => $label) {
if ($index == 'time') {
continue;
}
if (!isset($cell_data[$time_index][$index])) {
$cell_data[$time_index][$index] = array();
}
foreach ($item as $i => $v) {
if ($v['value'] >= $time['start'] && $v['value'] < $time['stop'] && $v[$index] == '1') {
$row_data = array(
'element' => $v,
'settings' => $settings,
'day' => array(
$index => $label,
),
);
$row_data['span_time'] = ($v['value2'] - $v['value']) / $total_range * 100;
$row_data['offset_time'] = ($v['value'] - $abs_start) / $total_range * 100;
$start_time = trim(timefield_integer_to_time($settings['display_format'], $v['value']));
$end_time = trim(timefield_integer_to_time($settings['display_format'], $v['value2']));
$renderer = \Drupal::service('renderer');
$t = array(
'#theme' => 'timefield_weekly_summary_minical_box',
'#label' => $v['label'],
'#time' => $start_time . '-' . $end_time,
);
$cell_data[$time_index][$index][] = new FormattableMarkup($renderer
->renderPlain($t), []);
}
}
$row[$index] = array(
'data' => [
'#markup' => !empty($cell_data[$time_index][$index]) ? implode(' ', $cell_data[$time_index][$index]) : '',
],
);
}
$rows[] = array(
'data' => $row,
'class' => array(
'row-' . $count,
),
);
$count += 1;
}
return $rows;
}
/**
* Helper function to explode all items in a timefield value array so that
* we can sort across multivalue fields
*/
function _timefield_weekly_summary_explode_items(&$items) {
$new_array = array();
foreach ($items as $item) {
foreach (array_keys(_timefield_weekly_summary_days()) as $day) {
if ($item->{$day}) {
$ar = array(
'label' => isset($item->label) ? $item->label : '',
'mon' => FALSE,
'tue' => FALSE,
'wed' => FALSE,
'thu' => FALSE,
'fri' => FALSE,
'sat' => FALSE,
'sun' => FALSE,
'value' => $item->value,
'value2' => $item->value2,
);
$ar[$day] = TRUE;
$new_array[] = $ar;
}
}
}
// Sort our new array.
uasort($new_array, '_timefield_weekly_summary_time_sort');
$items = $new_array;
}
/**
* Uasort callback function
*/
function _timefield_weekly_summary_time_sort($a, $b) {
$calca = _timefield_weekly_summary_week_time_offset($a);
$calcb = _timefield_weekly_summary_week_time_offset($b);
if ($calca == $calcb) {
return 0;
}
return $calca < $calcb ? -1 : 1;
}
/**
* Calculate offset from beginning of week.
*/
function _timefield_weekly_summary_week_time_offset($elem) {
$multiplier = 60 * 60 * 24;
if ($elem['mon']) {
$mult = 0;
}
if ($elem['tue']) {
$mult = 1;
}
if ($elem['wed']) {
$mult = 2;
}
if ($elem['thu']) {
$mult = 3;
}
if ($elem['fri']) {
$mult = 4;
}
if ($elem['sat']) {
$mult = 5;
}
if ($elem['sun']) {
$mult = 6;
}
return $multiplier * $mult + $elem['value'];
}
/**
* Helper function to build the time column for the minical table.
*/
function _timefield_weekly_summary_build_time_column($settings, $start_times = array()) {
$time_array = array();
$start = timefield_time_to_integer($settings['absolute_start']);
$end = timefield_time_to_integer($settings['absolute_end']);
$total_range = $end - $start;
$step_amount = $settings['range'] * 60;
$steps = ceil($total_range / $step_amount);
for ($index = 0; $index < $steps; $index++) {
if ($index == 0) {
$current = $start;
}
$time_array[$current] = array(
'start' => $current,
'stop' => $current + $step_amount,
'display' => timefield_integer_to_time($settings['column_format'], $current) . ' - ' . timefield_integer_to_time($settings['column_format'], $current + $step_amount),
'last_row' => $index + 1 == $steps ? TRUE : FALSE,
);
$current += $step_amount;
}
return $time_array;
}
/**
* Implements hook_help().
*/
function timefield_help($route_name, RouteMatchInterface $route_match) {
if ($route_name === 'help.page.timefield') {
$path = __DIR__ . '/README.md';
if (file_exists($path)) {
return '<pre>' . file_get_contents($path) . '</pre>';
}
}
return NULL;
}
Functions
Name![]() |
Description |
---|---|
template_preprocess_timefield | |
timefield_build_time_format | |
timefield_help | Implements hook_help(). |
timefield_integer_to_duration | Helper function to return duration value from a timefield integer value, in specified format. |
timefield_integer_to_time | Helper function to return time value from a timefield integer. |
timefield_theme | Implements hook_theme(). |
timefield_time_to_duration | Helper function to return duration value from 2 values, in specified format. |
timefield_time_to_integer | Helper function to return integer value offset from midnight from time format. |
timefield_weekly_summary_build_rows | Add rows to the table |
_timefield_display_format_form | |
_timefield_duration_options | Helper function to build options array |
_timefield_js_settings | Timefield js settings. |
_timefield_time_part_format | |
_timefield_weekly_summary_build_header | Build a header for a schedule table |
_timefield_weekly_summary_build_time_column | Helper function to build the time column for the minical table. |
_timefield_weekly_summary_days | Helper function days array |
_timefield_weekly_summary_days_map | Map first day of week |
_timefield_weekly_summary_explode_items | Helper function to explode all items in a timefield value array so that we can sort across multivalue fields |
_timefield_weekly_summary_time_sort | Uasort callback function |
_timefield_weekly_summary_week_time_offset | Calculate offset from beginning of week. |