/* https://github.com/hekigan/vue-directive-tooltip */
/*
* @author: laurent blanes <laurent.blanes@gmail.com>
* @tutorial: https://hekigan.github.io/vue-directive-tooltip/
*/
import Tooltip from './tooltip.js';
const BASE_CLASS = 'vue-tooltip';
const POSITIONS = ['auto', 'top', 'bottom', 'left', 'right'];
const SUB_POSITIONS = ['start', 'end'];
/**
* usage:
*
* // basic usage:
* <div v-tooltip="'my content'">
* or
* <div v-tooltip="{content: 'my content'}">
*
* // change position of tooltip
* // options: auto (default) | bottom | top | left | right
*
* // change sub-position of tooltip
* // options: start | end
*
* <div v-tooltip.top="{content: 'my content'}">
*
* // add custom class
* <div v-tooltip="{class: 'custom-class', content: 'my content'}">
*
* // toggle visibility
* <div v-tooltip="{visible: false, content: 'my content'}">
*/
export default {
name: 'tooltip',
config: {},
install (Vue, installOptions) {
Vue.directive('tooltip', {
bind (el, binding, vnode) {
if (installOptions) {
Tooltip.defaults(installOptions);
}
},
inserted (el, binding, vnode, oldVnode) {
if (installOptions) {
Tooltip.defaults(installOptions);
}
let options = filterBindings(binding, vnode);
el.tooltip = new Tooltip(el, options);
if (binding.modifiers.notrigger && binding.value.visible === true) {
el.tooltip.show();
}
if (binding.value && binding.value.visible === false) {
el.tooltip.disabled = true;
}
},
componentUpdated (el, binding, vnode, oldVnode) {
if (hasUpdated(binding.value, binding.oldValue)) {
update(el, binding, vnode, oldVnode);
}
},
unbind (el, binding, vnode, oldVnode) {
el.tooltip.destroy();
}
});
}
};
/**
*
* @param {*} vnode component's properties
* @param {*} oldvnode component's previous properties
* @return boolean
*/
function hasUpdated (value, oldValue) {
let updated = false;
if (typeof value === 'string' && value !== oldValue) {
updated = true;
} else if (isObject(value)) {
Object.keys(value).forEach(prop => {
if (value[prop] !== oldValue[prop]) {
updated = true;
}
});
}
return updated;
}
/**
* Sanitize data
* @param {*} binding
* @param {*} vnode
* @return {*} filtered data object
*/
function filterBindings (binding, vnode) {
const delay = !binding.value || isNaN(binding.value.delay) ? Tooltip._defaults.delay : binding.value.delay;
if (binding.value.ref) {
if (vnode.context.$refs[binding.value.ref]) {
binding.value.html = vnode.context.$refs[binding.value.ref];
} else {
console.error(`[Tooltip] no REF element [${binding.value.ref}]`); // eslint-disable-line
}
}
return {
class: getClass(binding),
id: (binding.value) ? binding.value.id : null,
html: (binding.value) ? binding.value.html : null,
placement: getPlacement(binding),
title: getContent(binding),
triggers: getTriggers(binding),
fixIosSafari: binding.modifiers.ios || false,
offset: (binding.value && binding.value.offset) ? binding.value.offset : Tooltip._defaults.offset,
delay
};
}
/**
* Get placement from modifiers
* @param {*} binding
*/
function getPlacement ({modifiers, value}) {
let MODS = Object.keys(modifiers);
if (MODS.length === 0 && isObject(value) && typeof value.placement === 'string') {
MODS = value.placement.split('.');
}
let head = 'bottom';
let tail = null;
for (let i = 0; i < MODS.length; i++) {
const pos = MODS[i];
if (POSITIONS.indexOf(pos) > -1) {
head = pos;
}
if (SUB_POSITIONS.indexOf(pos) > -1) {
tail = pos;
}
}
// console.log((head && tail) ? `${head}-${tail}` : head);
// return 'auto';
return (head && tail) ? `${head}-${tail}` : head;
}
/**
* Get trigger value from modifiers
* @param {*} binding
* @return String
*/
function getTriggers ({modifiers}) {
let trigger = [];
if (modifiers.notrigger) {
return trigger;
} else if (modifiers.manual) {
trigger.push('manual');
} else {
if (modifiers.click) {
trigger.push('click');
}
if (modifiers.hover) {
trigger.push('hover');
}
if (modifiers.focus) {
trigger.push('focus');
}
if (trigger.length === 0) {
trigger.push('hover', 'focus');
}
}
return trigger;
}
/**
* Check if the variable is an object
* @param {*} value
* @return Boolean
*/
function isObject (value) {
return typeof value === 'object';
}
/**
* Check if the variable is an html element
* @param {*} value
* @return Boolean
*/
function isElement (value) {
return value instanceof window.Element;
}
/**
* Get the css class
* @param {*} binding
* @return HTMLElement | String
*/
function getClass ({value}) {
if (value === null) {
return BASE_CLASS;
} else if (isObject(value) && typeof value.class === 'string') {
return `${BASE_CLASS} ${value.class}`;
} else if (Tooltip._defaults.class) {
return `${BASE_CLASS} ${Tooltip._defaults.class}`;
} else {
return BASE_CLASS;
}
}
/**
* Get the content
* @param {*} binding
* @return HTMLElement | String
*/
function getContent ({value}, vnode) {
if (value !== null && isObject(value)) {
if (value.content !== undefined) {
return `${value.content}`;
} else if (value.id && document.getElementById(value.id)) {
return document.getElementById(value.id);
} else if (value.html && document.getElementById(value.html)) {
return document.getElementById(value.html);
} else if (isElement(value.html)) {
return value.html;
} else if (value.ref && vnode) {
return vnode.context.$refs[value.ref] || '';
} else {
return '';
}
} else {
return `${value}`;
}
}
/**
* Action on element update
* @param {*} el Vue element
* @param {*} binding
*/
function update (el, binding, vnode, oldVnode) {
if (typeof binding.value === 'string') {
el.tooltip.content(binding.value);
} else {
if (binding.value && binding.value.class && binding.value.class.trim() !== el.tooltip.options.class.replace(BASE_CLASS, '').trim()) {
el.tooltip.class = `${BASE_CLASS} ${binding.value.class.trim()}`;
}
el.tooltip.content(getContent(binding, vnode));
if (!binding.modifiers.notrigger && binding.value && typeof binding.value.visible === 'boolean') {
el.tooltip.disabled = !binding.value.visible;
return;
} else if (binding.modifiers.notrigger) {
el.tooltip.disabled = false;
}
const dir = vnode.data.directives[0];
if (dir.oldValue.visible !== dir.value.visible) {
if (!el.tooltip.disabled) {
el.tooltip.toggle(dir.value.visible);
}
}
}
}
create table tbl_values (
id int unsigned not null primary key,
`Name` varchar(10),
`Group` varchar(10),
`Value` int
);
insert into tbl_values values
(1, 'Pete', 'A', 10),
(2, 'Pete', 'B', 20),
(3, 'John', 'A', 10);
-- 1. Create an expression that builds the columns
set @sql = (
select group_concat(distinct
concat(
"sum(case when `Group`='", `Group`, "' then `Value` end) as `", `Group`, "`"
)
)
from tbl_values
);
-- 2. Complete the SQL instruction
set @sql = concat("select Name, ", @sql, " from tbl_values group by `Name`");
-- 3. Create a prepared statement
prepare stmt from @sql;
-- 4. Execute the prepared statement
execute stmt;
<?php
// https://git.andweb.cz/brandcloud/app/-/blob/bcnew/app/BrandCloudModule/components/SharingForm.php#L148
$form->addSubmit('share', 'Share')
->onInvalidClick[] = function () use ($form) {
// we have to set recipients as items to revalidate recipients field
// TODO: posibly change multiselectbox to some other implementation which works only with raw value
if ($form['sharing_type']->getValue() === 'email') {
$form['recipients']->setItems((array) $form['recipients']->getRawValue(), false);
$form->validate();
}
};
$form->onValidate[] = [$this, 'validateForm'];
$form->onSubmit[] = [$this, 'submitForm'];
$form->onSuccess[] = [$this, 'successForm'];
$form->setDefaults($this->getFormDefaults());
return $form;
/* https://stackoverflow.com/questions/2797091/css-and-and-or */
/* or || */
.registration_form_right input:not([type="radio"]):not([type="checkbox"]) {}
/* and && */
.registration_form_right input:not([type="radio"]),
.registration_form_right input:not([type="checkbox"])
/* https://davidwalsh.name/external-links-css */
/* long version */
a[href^="http://"]:not([href*="mysite.com"]),
a[href^="https://"]:not([href*="mysite.com"]),
a[href^="//"]:not([href*="mysite.com"]), {
}
/* shorter version! */
a[href*="//"]:not([href*="mysite.com"]) {
/* external link styles, use :before or :after if you want! */
}
.full-width {
left: 50%;
margin-left: -50vw;
margin-right: -50vw;
max-width: 100vw;
position: relative;
right: 50%;
width: 100vw;
}
.full-width2 {
width: 100vw;
position: relative;
left: 50%;
transform: translateX(-50%);
background: coral;
}
.full-width3 {
/* max-width: 100vw; */
width: 100vw;
margin-left: 50%;
transform: translateX(-50%);
background: lime;
}
<?php
public function actionDefault($back = null)
{
if ($back)
$this->restoreRequest($back);
if ($this->presenter->navigation->navItem['alias'] == 'allOpenCalls')
{
$parentId = $this->presenter->navigation->navItem['parent__navigation_id'];
$nav = $this->navigation->getById($parentId);
$children = $nav->getChildren();
$this->config['navigation_id'] = array_keys($children);
}
$this->template->back = $this->storeRequest();
}
<template>
<div>
<h2 class="text-h4">{{ name }}</h2>
<button @click="score++" class="btn">
{{ score }} twice is {{ double }}
</button>
<hr />
<button @click="score2++" class="btn">
{{ score2 }} triple is {{ triple }}
</button>
<hr />
<ul>
<li v-for="data in dataList" :key="data.id">{{ data.name }}</li>
</ul>
<hr />
<button v-if="!divVisible" @click="showDiv">Show div</button>
<button v-if="divVisible" @click="hideDiv">Hide div</button>
<div v-if="divVisible" class="bg-red-100">My super hidden div :)</div>
<hr />
<form @submit.prevent="submitForm">
<input type="text" v-model="title" />
</form>
</div>
</template>
<script>
import { ref, computed, reactive, toRefs, onMounted } from 'vue'
import { data } from '@/frontapp/components/data.js'
export default {
components: {},
props: ['name'],
// props, context nebo { emit } nebo { emit, slots }
setup(props, { emit }) {
console.log(props, 'our props')
// data
const score = ref(1)
const dude = ref('Kcko')
const dataList = ref(data)
const state = reactive({
score2: 12,
triple: computed(() => state.score2 * 3),
divVisible: false
})
// computed
const double = computed(() => score.value * 2 + 7)
const hello = computed(() => 'Hello, I am ' + dude.value)
// methods
const showDiv = () => {
state.divVisible = true
}
const hideDiv = () => {
state.divVisible = false
}
// v nadrazenem prvku / komponentne nebo standardne -> view @new-list-coming="nejakaMetoda($event)"
const title = ref('')
const submitForm = () => {
emit('new-list-coming', title.value)
}
onMounted(() => {
console.log('Mounted yeah!')
})
return {
score,
double,
hello,
...toRefs(state),
dataList,
showDiv,
hideDiv,
submitForm
}
}
}
</script>
<?php
/*
FORK from https://gist.github.com/edewaal97/344ec108931ac4c9e8ca7874b2db83cb
*/
class iCal
{
/**
* @var string
*/
public $calendarIdent;
/**
* @var string
*/
public $title;
/**
* @var string
*/
public $description;
/**
* @var array
*/
public $events = array();
/**
* @var array
*/
protected $_eventsByDate;
public function __construct($content = null, $calendarIdent = null)
{
$this->calendarIdent = $calendarIdent;
if ($content) {
$isUrl = strpos($content, 'http') === 0 && filter_var($content, FILTER_VALIDATE_URL);
$isFile = strpos($content, "\n") === false && file_exists($content);
if ($isUrl || $isFile) {
$content = file_get_contents($content);
}
$this->parse($content);
}
}
public function title()
{
return $this->summary;
}
public function description()
{
return $this->description;
}
public function events()
{
return $this->events;
}
public function eventsByDate()
{
if (! $this->_eventsByDate) {
$this->_eventsByDate = array();
$tmpEventsByDate = array();
foreach ($this->events() as $event) {
foreach ($event->occurrences() as $occurrence) {
$date = date('Y-m-d', $occurrence);
$newevent = clone $event;
$newevent->fixOccurringDate($occurrence);
// generate key for sorting
$key = strtotime($newevent->dateStart);
while(isset($tmpEventsByDate[$date][$key])) $key++;
$tmpEventsByDate[$date][$key] = $newevent;
}
}
// sort array
ksort($tmpEventsByDate);
foreach ($tmpEventsByDate as $date => $value) {
ksort($value);
$this->_eventsByDate[$date] = $value;
}
// prevent duplicates for edited dates in recurring events
foreach ($this->_eventsByDate as $dateKey => $date) {
foreach ($date as $event) {
if(!empty($event->recurrenceId)) {
$uid = $event->uid;
foreach ($date as $eventKey => $eventValue) {
if($eventValue->uid == $uid && (empty($eventValue->recurrenceId))) {
unset($this->_eventsByDate[$dateKey][$eventKey]);
}
}
}
}
}
}
return $this->_eventsByDate;
}
public function eventsByDateBetween($start, $end, int $limit=NULL)
{
if ((string) (int) $start !== (string) $start) {
$start = strtotime($start);
}
$start = date('Y-m-d', $start);
if ((string) (int) $end !== (string) $end) {
$end = strtotime($end);
}
$end = date('Y-m-d', $end);
$return = array();
foreach ($this->eventsByDate() as $date => $events) {
if ($start <= $date && $date < $end) {
if(empty($limit) || count($return) <= $limit) {
$return[$date] = $events;
}
}
if(!empty($limit) && count($return) >= $limit){
break;
}
}
return $return;
}
public function eventsByDateSince($start, int $limit=NULL)
{
if ((string) (int) $start !== (string) $start) {
$start = strtotime($start);
}
$start = date('Y-m-d', $start);
$return = array();
foreach ($this->eventsByDate() as $date => $events) {
if ($start <= $date) {
if(empty($limit) || count($return) <= $limit) {
$return[$date] = $events;
}
}
if(!empty($limit) && count($return) >= $limit){
break;
}
}
return $return;
}
public function eventsByDateUntil($end, int $limit=NULL)
{
if ((string) (int) $end !== (string) $end) {
$end = strtotime($end);
}
$start = date('Y-m-d');
$end = date('Y-m-d', $end);
$return = array();
foreach ($this->eventsByDate() as $date => $events) {
if ($start <= $date && $end >= $date) {
if(empty($limit) || count($return) <= $limit) {
$return[$date] = $events;
}
}
if(!empty($limit) && count($return) >= $limit){
break;
}
}
return $return;
}
public function parse($content)
{
$content = str_replace("\r\n ", '', $content);
// Title
preg_match('`^X-WR-CALNAME:(.*)$`m', $content, $m);
$this->title = $m ? trim($m[1]) : null;
// Description
preg_match('`^X-WR-CALDESC:(.*)$`m', $content, $m);
$this->description = $m ? trim($m[1]) : null;
// Events
preg_match_all('`BEGIN:VEVENT(.+)END:VEVENT`Us', $content, $m);
foreach ($m[0] as $c) {
$this->events[] = new iCalEvent($c, $this->calendarIdent);
}
return $this;
}
}
<?php
namespace App\ServiceModule\Model;
class iCalEvent
{
/**
* @var string
*/
public $calendarIdent;
/**
* @var string
*/
public $uid;
/**
* @var string
*/
public $summary;
/**
* @var string
*/
public $description;
/**
* @var string
*/
public $dateStart;
/**
* @var string
*/
public $dateEnd;
/**
* @var string
*/
public $recurrenceId;
/**
* @var array
*/
public $exdate = array();
/**
* @var \stdClass
*/
public $recurrence;
/**
* @var string
*/
public $location;
/**
* @var string
*/
public $status;
/**
* @var string
*/
public $created;
/**
* @var string
*/
public $updated;
/**
* @var integer
*/
protected $_timeStart;
/**
* @var integer
*/
protected $_timeEnd;
/**
* @var integer
*/
protected $_recurrenceId;
/**
* @var array
*/
protected $_occurrences;
public function __construct($content = null, $calendarIdent = null)
{
if ($content) {
$this->parse($content);
}
$this->calendarIdent = $calendarIdent;
}
public function summary()
{
return $this->summary;
}
public function title()
{
return $this->summary;
}
public function getEventUrl()
{
$eid = explode('@', $this->uid);
$eid = base64_encode($eid[0] . ' ' . $this->calendarIdent);
$eid = str_replace('=', '', $eid);
return $eid;
}
public function getEventFullUrl()
{
return 'https://www.google.com/calendar/event?eid=' . $this->getEventUrl();
}
public function description()
{
return $this->description;
}
public function occurrences()
{
if (empty($this->_occurrences)) {
$this->_occurrences = $this->_calculateOccurrences();
}
return $this->_occurrences;
}
public function duration()
{
// if ($this->_timeEnd) {
return $this->_timeEnd - $this->_timeStart;
// }
}
public function parse($content)
{
$content = str_replace("\r\n ", '', $content);
// UID
if (preg_match('`^UID:(.*)$`m', $content, $m))
$this->uid = trim($m[1]);
// Summary
if (preg_match('`^SUMMARY:(.*)$`m', $content, $m))
$this->summary = trim($m[1]);
// Description
if (preg_match('`^DESCRIPTION:(.*)$`m', $content, $m))
$this->description = trim($m[1]);
// Date start
if (preg_match('`^DTSTART(?:;.+)?:([0-9]+(T[0-9]+Z?)?)`m', $content, $m)) {
$this->_timeStart = strtotime($m[1]);
$this->dateStart = date('Y-m-d H:i:s', $this->_timeStart);
}
// Date end
if (preg_match('`^DTEND(?:;.+)?:([0-9]+(T[0-9]+Z?)?)`m', $content, $m)) {
$this->_timeEnd = strtotime($m[1]);
$this->dateEnd = date('Y-m-d H:i:s', $this->_timeEnd);
}
// Recurrence-Id
if (preg_match('`^RECURRENCE-ID(?:;.+)?:([0-9]+(T[0-9]+Z?)?)`m', $content, $m)) {
$this->_recurrenceId = strtotime($m[1]);
$this->recurrenceId = date('Y-m-d H:i:s', $this->_recurrenceId);
}
// Exdate
if (preg_match_all('`^EXDATE(;.+)?:([0-9]+(T[0-9]+Z?)?)`m', $content, $m)) {
foreach ($m[2] as $dates) {
$dates = explode(',', $dates);
foreach ($dates as $d) {
$this->exdate[] = date('Y-m-d', strtotime($d));
}
}
}
// Recurrence
if (preg_match('`^RRULE:(.*)`m', $content, $m)) {
$rules = (object) array();
$rule = trim($m[1]);
$rule = explode(';', $rule);
foreach ($rule as $r) {
list($key, $value) = explode('=', $r);
$rules->{ strtolower($key) } = $value;
}
if (isset($rules->until)) {
$rules->until = date('Y-m-d H:i:s', strtotime($rules->until));
}
if (isset($rules->count)) {
$rules->count = intval($rules->count);
}
if (isset($rules->interval)) {
$rules->interval = intval($rules->interval);
}
if (isset($rules->byday)) {
$rules->byday = explode(',', $rules->byday);
}
// Avoid infinite recurrences
if (! isset($rules->until) && ! isset($rules->count)) {
$rules->count = 500;
}
$this->recurrence = $rules;
}
// Location
if (preg_match('`^LOCATION:(.*)$`m', $content, $m))
$this->location = trim($m[1]);
// Status
if (preg_match('`^STATUS:(.*)$`m', $content, $m))
$this->status = trim($m[1]);
// Created
if (preg_match('`^CREATED:(.*)`m', $content, $m))
$this->created = date('Y-m-d H:i:s', strtotime(trim($m[1])));
// Updated
if (preg_match('`^LAST-MODIFIED:(.*)`m', $content, $m))
$this->updated = date('Y-m-d H:i:s', strtotime(trim($m[1])));
return $this;
}
public function isRecurrent()
{
return ! empty($this->recurrence);
}
public function fixOccurringDate($timestamp)
{
if($timestamp != $this->_timeStart) {
// calculate correct start & end date if not a repeating event
$duration = $this->duration();
// get date from occurrences
$timestampCalc = new \DateTime();
$timestampCalc->setTimestamp($timestamp);
// make new startdate and start timestamp
$startCalc = new \DateTime();
$startCalc->setTimestamp($this->_timeStart);
$startCalc->setDate($timestampCalc->format('Y'), $timestampCalc->format('m'), $timestampCalc->format('d'));
$this->_timeStart = $startCalc->getTimestamp();
$this->dateStart = date('Y-m-d H:i:s', $this->_timeStart);
// calculate end date and time with duration of original event.
$this->_timeEnd += - $this->_timeStart + $duration;
$this->dateEnd = date('Y-m-d H:i:s', $this->_timeEnd);
}
}
protected function _isExdate($date)
{
if ((string) (int) $date != $date) {
$date = strtotime($date);
}
$date = date('Y-m-d', $date);
return in_array($date, $this->exdate);
}
protected function _calculateOccurrences()
{
$occurrences = array($this->_timeStart);
if ($this->isRecurrent())
{
$freq = $this->recurrence->freq;
$count = isset($this->recurrence->count) ? $this->recurrence->count : null;
$until = isset($this->recurrence->until) ? strtotime($this->recurrence->until) : null;
$callbacks = array(
'YEARLY' => '_nextYearlyOccurrence',
'MONTHLY' => '_nextMonthlyOccurrence',
'WEEKLY' => '_nextWeeklyOccurrence',
'DAILY' => '_nextDailyOccurrence'
);
$callback = $callbacks[$freq];
$offset = $this->_timeStart;
$continue = $until ? ($offset < $until) : ($count > 1);
while ($continue) {
if(isset($occurrence)) {
if (! $this->_isExdate($occurrence)) {
$occurrences[] = $occurrence;
$count--;
}
}
$occurrence = $this->{$callback}($offset);
$offset = $occurrence;
$continue = $until ? ($offset < $until) : ($count > 1);
}
}
if ($this->_isExdate($occurrences[0])) {
unset($occurrences[0]);
$occurrences = array_values($occurrences);
}
return $occurrences;
}
protected function _nextYearlyOccurrence($offset)
{
$interval = isset($this->recurrence->interval)
? $this->recurrence->interval
: 1;
return strtotime("+{$interval} year", $offset);
}
protected function _nextMonthlyOccurrence($offset)
{
$dayname = array(
'MO' => 'monday',
'TU' => 'tuesday',
'WE' => 'wednesday',
'TH' => 'thursday',
'FR' => 'friday',
'SA' => 'saturday',
'SU' => 'sunday'
);
$interval = isset($this->recurrence->interval)
? $this->recurrence->interval
: 1;
// INTERVAL IS BY (COUNT)DAYNAME
if(isset($this->recurrence->byday)){
$dates = array();
foreach ($this->recurrence->byday as $pattern) {
$offsetDateTime = new \DateTime();
$offsetDateTime->setTimestamp((int) $offset);
preg_match('`([-]?\d+)?(MO|TU|WE|TH|FR|SA|SU)`m', $pattern, $m);
$recurrenceOffset = (isset($m[1])) ? (int) $m[1] : 1;
$recurrenceDay = strtr($m[2], $dayname);
$forDateTime = clone $offsetDateTime;
for (
$month = (int) $offsetDateTime->format('Ym');
$month <= date('Ym', strtotime('+' . $interval*12 . ' months'));
$month = (int) $forDateTime->modify('+'.$interval.' months')->format('Ym')
) {
$yearMonth = $forDateTime->format('Y-m');
$firstDay = new \DateTime('first '. $recurrenceDay . ' of ' . $yearMonth);
$lastDay = new \DateTime('last '. $recurrenceDay . ' of ' . $yearMonth);
$newDate = $firstDay;
$daysInMonth = array();
while ($newDate->getTimestamp() <= $lastDay->getTimestamp()) {
$daysInMonth[] = $newDate->getTimestamp();
$newDate->modify('next '. $recurrenceDay);
}
if($recurrenceOffset < 0) {
$dates[] = $daysInMonth[count($daysInMonth) + $recurrenceOffset];
} else {
$dates[] = $daysInMonth[$recurrenceOffset - 1];
}
}
}
sort($dates);
foreach ($dates as $date) {
if ($date > $offset) {
return $date;
}
}
}
// INTERVAL IS BY DAYNUMBER OF MONTH
$bymonthday = isset($this->recurrence->bymonthday)
? explode(',', $this->recurrence->bymonthday)
: array(date('d', $offset));
$start = strtotime(date('Y-m-01 H:i:s', $offset));
$dates = array();
foreach ($bymonthday as $day) {
// this month
$dates[] = strtotime(($day-1) . ' day', $start);
// next 'interval' month
$tmp = strtotime("+{$interval} month", $start);
$time = strtotime(($day-1) . ' day', $tmp);
if ((string) (int) date('d', $time) == (int) $day) {
$dates[] = $time;
}
// 2x 'interval' month
$interval *= 2;
$tmp = strtotime("+{$interval} month", $start);
$time = strtotime(($day-1) . ' day', $tmp);
if ((string) (int) date('d', $time) === (int) $day) {
$dates[] = $time;
}
}
sort($dates);
foreach ($dates as $date) {
if ($date > $offset) {
return $date;
}
}
}
protected function _nextWeeklyOccurrence($offset)
{
$interval = isset($this->recurrence->interval)
? $this->recurrence->interval
: 1;
$byday = isset($this->recurrence->byday)
? $this->recurrence->byday
: array( substr(strtoupper(date('D', $offset)), 0, 2) );
$start = date('l', $offset) !== 'Monday'
? strtotime('last monday', $offset)
: $offset;
$daysname = array(
'MO' => 'monday',
'TU' => 'tuesday',
'WE' => 'wednesday',
'TH' => 'thursday',
'FR' => 'friday',
'SA' => 'saturday',
'SU' => 'sunday',
);
$dates = array();
foreach ($byday as $day) {
$dayname = $daysname[$day];
// this week
$dates[] = strtotime($dayname, $start);
// next 'interval' week
$tmp = strtotime("+{$interval} week", $start);
$time = strtotime($dayname, $tmp);
$dates[] = $time;
}
sort($dates);
foreach ($dates as $date) {
if ($date > $offset) {
return $date;
}
}
}
protected function _nextDailyOccurrence($offset)
{
$interval = isset($this->recurrence->interval)
? $this->recurrence->interval
: 1;
return strtotime("+{$interval} day", $offset);
}
}
<template>
<video-player v-bind="mergedVideoSettings" />
</template>
<script>
import VideoPlayer from './VideoPlayer.local.vue'
export default {
props: {
videoSettings: Object
},
components: {
VideoPlayer
},
computed: {
mergedVideoSettings() {
return {
...this.defaultVideoSettings,
...this.videoSettings
}
}
},
data() {
return {
defaultVideoSettings: {
mask: false,
colors: 'var(--primaryColor)'
}
}
},
mounted() {}
}
</script>
<style lang="scss" scoped></style>