Display count 'bubble' for open pending invitations (#3268)
This commit is contained in:
parent
e618f0093c
commit
0ab0b797b8
9 changed files with 248 additions and 19 deletions
|
@ -132,6 +132,7 @@ class calendar extends rcube_plugin
|
||||||
$this->register_action('index', array($this, 'calendar_view'));
|
$this->register_action('index', array($this, 'calendar_view'));
|
||||||
$this->register_action('event', array($this, 'event_action'));
|
$this->register_action('event', array($this, 'event_action'));
|
||||||
$this->register_action('calendar', array($this, 'calendar_action'));
|
$this->register_action('calendar', array($this, 'calendar_action'));
|
||||||
|
$this->register_action('count', array($this, 'count_events'));
|
||||||
$this->register_action('load_events', array($this, 'load_events'));
|
$this->register_action('load_events', array($this, 'load_events'));
|
||||||
$this->register_action('export_events', array($this, 'export_events'));
|
$this->register_action('export_events', array($this, 'export_events'));
|
||||||
$this->register_action('import_events', array($this, 'import_events'));
|
$this->register_action('import_events', array($this, 'import_events'));
|
||||||
|
@ -1138,6 +1139,27 @@ class calendar extends rcube_plugin
|
||||||
exit;
|
exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler for requests fetching event counts for calendars
|
||||||
|
*/
|
||||||
|
public function count_events()
|
||||||
|
{
|
||||||
|
// don't update session on these requests (avoiding race conditions)
|
||||||
|
$this->rc->session->nowrite = true;
|
||||||
|
|
||||||
|
$start = rcube_utils::get_input_value('start', rcube_utils::INPUT_GET);
|
||||||
|
if (!$start)
|
||||||
|
$start = (new DateTime('today 00:00:00', $this->timezone))->format('U');
|
||||||
|
|
||||||
|
$counts = $this->driver->count_events(
|
||||||
|
rcube_utils::get_input_value('source', rcube_utils::INPUT_GET),
|
||||||
|
$start,
|
||||||
|
rcube_utils::get_input_value('end', rcube_utils::INPUT_GET)
|
||||||
|
);
|
||||||
|
|
||||||
|
$this->rc->output->command('plugin.update_counts', array('counts' => $counts));
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Load event data from an iTip message attachment
|
* Load event data from an iTip message attachment
|
||||||
*/
|
*/
|
||||||
|
@ -1187,6 +1209,8 @@ class calendar extends rcube_plugin
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$counts = array();
|
||||||
|
|
||||||
foreach ($this->driver->list_calendars(true) as $cal) {
|
foreach ($this->driver->list_calendars(true) as $cal) {
|
||||||
$events = $this->driver->load_events(
|
$events = $this->driver->load_events(
|
||||||
rcube_utils::get_input_value('start', rcube_utils::INPUT_GPC),
|
rcube_utils::get_input_value('start', rcube_utils::INPUT_GPC),
|
||||||
|
@ -1201,6 +1225,16 @@ class calendar extends rcube_plugin
|
||||||
$this->rc->output->command('plugin.refresh_calendar',
|
$this->rc->output->command('plugin.refresh_calendar',
|
||||||
array('source' => $cal['id'], 'update' => $this->_client_event($event)));
|
array('source' => $cal['id'], 'update' => $this->_client_event($event)));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// refresh count for this calendar
|
||||||
|
if ($cal['counts']) {
|
||||||
|
$today = new DateTime('today 00:00:00', $this->timezone);
|
||||||
|
$counts += $this->driver->count_events($cal['id'], $today->format('U'));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!empty($counts)) {
|
||||||
|
$this->rc->output->command('plugin.update_counts', array('counts' => $counts));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -67,6 +67,7 @@ function rcube_calendar_ui(settings)
|
||||||
var freebusy_ui = { workinhoursonly:false, needsupdate:false };
|
var freebusy_ui = { workinhoursonly:false, needsupdate:false };
|
||||||
var freebusy_data = {};
|
var freebusy_data = {};
|
||||||
var current_view = null;
|
var current_view = null;
|
||||||
|
var count_sources = [];
|
||||||
var exec_deferred = bw.ie6 ? 5 : 1;
|
var exec_deferred = bw.ie6 ? 5 : 1;
|
||||||
var sensitivitylabels = { 'public':rcmail.gettext('public','calendar'), 'private':rcmail.gettext('private','calendar'), 'confidential':rcmail.gettext('confidential','calendar') };
|
var sensitivitylabels = { 'public':rcmail.gettext('public','calendar'), 'private':rcmail.gettext('private','calendar'), 'confidential':rcmail.gettext('confidential','calendar') };
|
||||||
var ui_loading = rcmail.set_busy(true, 'loading');
|
var ui_loading = rcmail.set_busy(true, 'loading');
|
||||||
|
@ -3123,6 +3124,8 @@ function rcube_calendar_ui(settings)
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
fc.fullCalendar('refetchEvents', source);
|
fc.fullCalendar('refetchEvents', source);
|
||||||
|
|
||||||
|
fetch_counts();
|
||||||
}
|
}
|
||||||
// add/update single event object
|
// add/update single event object
|
||||||
else if (source && p.update) {
|
else if (source && p.update) {
|
||||||
|
@ -3145,6 +3148,7 @@ function rcube_calendar_ui(settings)
|
||||||
// refetch all calendars
|
// refetch all calendars
|
||||||
else if (p.refetch) {
|
else if (p.refetch) {
|
||||||
fc.fullCalendar('refetchEvents');
|
fc.fullCalendar('refetchEvents');
|
||||||
|
fetch_counts();
|
||||||
}
|
}
|
||||||
|
|
||||||
// remove temp events
|
// remove temp events
|
||||||
|
@ -3165,6 +3169,28 @@ function rcube_calendar_ui(settings)
|
||||||
return query;
|
return query;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// callback from server providing event counts
|
||||||
|
this.update_counts = function(p)
|
||||||
|
{
|
||||||
|
$.each(p.counts, function(cal, count) {
|
||||||
|
var li = calendars_list.get_item(cal),
|
||||||
|
bubble = $(li).children('.calendar').find('span.count');
|
||||||
|
|
||||||
|
if (!bubble.length && count > 0) {
|
||||||
|
bubble = $('<span>')
|
||||||
|
.addClass('count')
|
||||||
|
.appendTo($(li).children('.calendar').first())
|
||||||
|
}
|
||||||
|
|
||||||
|
if (count > 0) {
|
||||||
|
bubble.text(count).show();
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
bubble.text('').hide();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
// callback after an iTip message event was imported
|
// callback after an iTip message event was imported
|
||||||
this.itip_message_processed = function(data)
|
this.itip_message_processed = function(data)
|
||||||
{
|
{
|
||||||
|
@ -3415,6 +3441,16 @@ function rcube_calendar_ui(settings)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// fetch counts for some calendars from the server
|
||||||
|
var fetch_counts = function()
|
||||||
|
{
|
||||||
|
if (count_sources.length) {
|
||||||
|
setTimeout(function() {
|
||||||
|
rcmail.http_request('calendar/count', { source:count_sources });
|
||||||
|
}, 500);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
/*** startup code ***/
|
/*** startup code ***/
|
||||||
|
|
||||||
|
@ -3431,6 +3467,9 @@ function rcube_calendar_ui(settings)
|
||||||
if (active) {
|
if (active) {
|
||||||
event_sources.push(this.calendars[id]);
|
event_sources.push(this.calendars[id]);
|
||||||
}
|
}
|
||||||
|
if (cal.counts) {
|
||||||
|
count_sources.push(id);
|
||||||
|
}
|
||||||
|
|
||||||
if (!cal.readonly && !this.selected_calendar) {
|
if (!cal.readonly && !this.selected_calendar) {
|
||||||
this.selected_calendar = id;
|
this.selected_calendar = id;
|
||||||
|
@ -4005,6 +4044,9 @@ function rcube_calendar_ui(settings)
|
||||||
// initialize more UI elements (deferred)
|
// initialize more UI elements (deferred)
|
||||||
window.setTimeout(init_calendar_ui, exec_deferred);
|
window.setTimeout(init_calendar_ui, exec_deferred);
|
||||||
|
|
||||||
|
// fetch counts for some calendars
|
||||||
|
fetch_counts();
|
||||||
|
|
||||||
// add proprietary css styles if not IE
|
// add proprietary css styles if not IE
|
||||||
if (!bw.ie)
|
if (!bw.ie)
|
||||||
$('div.fc-content').addClass('rcube-fc-content');
|
$('div.fc-content').addClass('rcube-fc-content');
|
||||||
|
@ -4055,6 +4097,7 @@ window.rcmail && rcmail.addEventListener('init', function(evt) {
|
||||||
rcmail.addEventListener('plugin.refresh_calendar', function(p){ cal.refresh(p); });
|
rcmail.addEventListener('plugin.refresh_calendar', function(p){ cal.refresh(p); });
|
||||||
rcmail.addEventListener('plugin.import_success', function(p){ cal.import_success(p); });
|
rcmail.addEventListener('plugin.import_success', function(p){ cal.import_success(p); });
|
||||||
rcmail.addEventListener('plugin.import_error', function(p){ cal.import_error(p); });
|
rcmail.addEventListener('plugin.import_error', function(p){ cal.import_error(p); });
|
||||||
|
rcmail.addEventListener('plugin.update_counts', function(p){ cal.update_counts(p); });
|
||||||
rcmail.addEventListener('plugin.reload_view', function(p){ cal.reload_view(p); });
|
rcmail.addEventListener('plugin.reload_view', function(p){ cal.reload_view(p); });
|
||||||
rcmail.addEventListener('plugin.resource_data', function(p){ cal.resource_data_load(p); });
|
rcmail.addEventListener('plugin.resource_data', function(p){ cal.resource_data_load(p); });
|
||||||
rcmail.addEventListener('plugin.resource_owner', function(p){ cal.resource_owner_load(p); });
|
rcmail.addEventListener('plugin.resource_owner', function(p){ cal.resource_owner_load(p); });
|
||||||
|
|
|
@ -268,8 +268,8 @@ abstract class calendar_driver
|
||||||
/**
|
/**
|
||||||
* Get events from source.
|
* Get events from source.
|
||||||
*
|
*
|
||||||
* @param integer Event's new start (unix timestamp)
|
* @param integer Date range start (unix timestamp)
|
||||||
* @param integer Event's new end (unix timestamp)
|
* @param integer Date range end (unix timestamp)
|
||||||
* @param string Search query (optional)
|
* @param string Search query (optional)
|
||||||
* @param mixed List of calendar IDs to load events from (either as array or comma-separated string)
|
* @param mixed List of calendar IDs to load events from (either as array or comma-separated string)
|
||||||
* @param boolean Include virtual/recurring events (optional)
|
* @param boolean Include virtual/recurring events (optional)
|
||||||
|
@ -278,6 +278,16 @@ abstract class calendar_driver
|
||||||
*/
|
*/
|
||||||
abstract function load_events($start, $end, $query = null, $calendars = null, $virtual = 1, $modifiedsince = null);
|
abstract function load_events($start, $end, $query = null, $calendars = null, $virtual = 1, $modifiedsince = null);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get number of events in the given calendar
|
||||||
|
*
|
||||||
|
* @param mixed List of calendar IDs to count events (either as array or comma-separated string)
|
||||||
|
* @param integer Date range start (unix timestamp)
|
||||||
|
* @param integer Date range end (unix timestamp)
|
||||||
|
* @return array Hash array with counts grouped by calendar ID
|
||||||
|
*/
|
||||||
|
abstract function count_events($calendars, $start, $end = null);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get a list of pending alarms to be displayed to the user
|
* Get a list of pending alarms to be displayed to the user
|
||||||
*
|
*
|
||||||
|
|
|
@ -843,6 +843,20 @@ class database_driver extends calendar_driver
|
||||||
return $events;
|
return $events;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get number of events in the given calendar
|
||||||
|
*
|
||||||
|
* @param mixed List of calendar IDs to count events (either as array or comma-separated string)
|
||||||
|
* @param integer Date range start (unix timestamp)
|
||||||
|
* @param integer Date range end (unix timestamp)
|
||||||
|
* @return array Hash array with counts grouped by calendar ID
|
||||||
|
*/
|
||||||
|
public function count_events($calendars, $start, $end = null)
|
||||||
|
{
|
||||||
|
// not implemented
|
||||||
|
return array();
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Convert sql record into a rcube style event object
|
* Convert sql record into a rcube style event object
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -334,6 +334,51 @@ class kolab_calendar extends kolab_storage_folder_api
|
||||||
return $events;
|
return $events;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param integer Date range start (unix timestamp)
|
||||||
|
* @param integer Date range end (unix timestamp)
|
||||||
|
* @param array Additional query to filter events
|
||||||
|
* @return integer Count
|
||||||
|
*/
|
||||||
|
public function count_events($start, $end = null, $filter_query = null)
|
||||||
|
{
|
||||||
|
// convert to DateTime for comparisons
|
||||||
|
try {
|
||||||
|
$start = new DateTime('@'.$start);
|
||||||
|
}
|
||||||
|
catch (Exception $e) {
|
||||||
|
$start = new DateTime('@0');
|
||||||
|
}
|
||||||
|
if ($end) {
|
||||||
|
try {
|
||||||
|
$end = new DateTime('@'.$end);
|
||||||
|
}
|
||||||
|
catch (Exception $e) {
|
||||||
|
$end = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// query Kolab storage
|
||||||
|
$query[] = array('dtend', '>=', $start);
|
||||||
|
|
||||||
|
if ($end)
|
||||||
|
$query[] = array('dtstart', '<=', $end);
|
||||||
|
|
||||||
|
// add query to exclude pending/declined invitations
|
||||||
|
if (empty($filter_query)) {
|
||||||
|
foreach ($this->cal->get_user_emails() as $email) {
|
||||||
|
$query[] = array('tags', '!=', 'x-partstat:' . $email . ':needs-action');
|
||||||
|
$query[] = array('tags', '!=', 'x-partstat:' . $email . ':declined');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (is_array($filter_query)) {
|
||||||
|
$query = array_merge($query, $filter_query);
|
||||||
|
}
|
||||||
|
|
||||||
|
// we rely the Kolab storage query (no post-filtering)
|
||||||
|
return $this->storage->count($query);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create a new event record
|
* Create a new event record
|
||||||
|
|
|
@ -243,6 +243,10 @@ class kolab_driver extends calendar_driver
|
||||||
'children' => false,
|
'children' => false,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
if ($id == self::INVITATIONS_CALENDAR_PENDING) {
|
||||||
|
$calendars[$id]['counts'] = true;
|
||||||
|
}
|
||||||
|
|
||||||
if (is_object($tree)) {
|
if (is_object($tree)) {
|
||||||
$tree->children[] = $cal;
|
$tree->children[] = $cal;
|
||||||
}
|
}
|
||||||
|
@ -1029,6 +1033,32 @@ class kolab_driver extends calendar_driver
|
||||||
return $events;
|
return $events;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get number of events in the given calendar
|
||||||
|
*
|
||||||
|
* @param mixed List of calendar IDs to count events (either as array or comma-separated string)
|
||||||
|
* @param integer Date range start (unix timestamp)
|
||||||
|
* @param integer Date range end (unix timestamp)
|
||||||
|
* @return array Hash array with counts grouped by calendar ID
|
||||||
|
*/
|
||||||
|
public function count_events($calendars, $start, $end = null)
|
||||||
|
{
|
||||||
|
$counts = array();
|
||||||
|
|
||||||
|
if ($calendars && is_string($calendars))
|
||||||
|
$calendars = explode(',', $calendars);
|
||||||
|
else if (!$calendars)
|
||||||
|
$calendars = array_keys($this->calendars);
|
||||||
|
|
||||||
|
foreach ($calendars as $cid) {
|
||||||
|
if ($storage = $this->get_calendar($cid)) {
|
||||||
|
$counts[$cid] = $storage->count_events($start, $end);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return $counts;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get a list of pending alarms to be displayed to the user
|
* Get a list of pending alarms to be displayed to the user
|
||||||
*
|
*
|
||||||
|
|
|
@ -199,20 +199,6 @@ class kolab_invitation_calendar
|
||||||
*/
|
*/
|
||||||
public function list_events($start, $end, $search = null, $virtual = 1, $query = array())
|
public function list_events($start, $end, $search = null, $virtual = 1, $query = array())
|
||||||
{
|
{
|
||||||
// convert to DateTime for comparisons
|
|
||||||
try {
|
|
||||||
$start_dt = new DateTime('@'.$start);
|
|
||||||
}
|
|
||||||
catch (Exception $e) {
|
|
||||||
$start_dt = new DateTime('@0');
|
|
||||||
}
|
|
||||||
try {
|
|
||||||
$end_dt = new DateTime('@'.$end);
|
|
||||||
}
|
|
||||||
catch (Exception $e) {
|
|
||||||
$end_dt = new DateTime('today +10 years');
|
|
||||||
}
|
|
||||||
|
|
||||||
// get email addresses of the current user
|
// get email addresses of the current user
|
||||||
$user_emails = $this->cal->get_user_emails();
|
$user_emails = $this->cal->get_user_emails();
|
||||||
$subquery = array();
|
$subquery = array();
|
||||||
|
@ -232,7 +218,7 @@ class kolab_invitation_calendar
|
||||||
foreach ($cal->list_events($start, $end, $search, 1, $query, array(array($subquery, 'OR'))) as $event) {
|
foreach ($cal->list_events($start, $end, $search, 1, $query, array(array($subquery, 'OR'))) as $event) {
|
||||||
$match = false;
|
$match = false;
|
||||||
|
|
||||||
// post-filter events to skip pending and declined invitations
|
// post-filter events to match out partstats
|
||||||
if (is_array($event['attendees'])) {
|
if (is_array($event['attendees'])) {
|
||||||
foreach ($event['attendees'] as $attendee) {
|
foreach ($event['attendees'] as $attendee) {
|
||||||
if (in_array($attendee['email'], $user_emails) && in_array($attendee['status'], $this->partstats)) {
|
if (in_array($attendee['email'], $user_emails) && in_array($attendee['status'], $this->partstats)) {
|
||||||
|
@ -254,6 +240,36 @@ class kolab_invitation_calendar
|
||||||
return $events;
|
return $events;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param integer Date range start (unix timestamp)
|
||||||
|
* @param integer Date range end (unix timestamp)
|
||||||
|
* @return integer Count
|
||||||
|
*/
|
||||||
|
public function count_events($start, $end = null)
|
||||||
|
{
|
||||||
|
// get email addresses of the current user
|
||||||
|
$user_emails = $this->cal->get_user_emails();
|
||||||
|
$subquery = array();
|
||||||
|
foreach ($user_emails as $email) {
|
||||||
|
foreach ($this->partstats as $partstat) {
|
||||||
|
$subquery[] = array('tags', '=', 'x-partstat:' . $email . ':' . strtolower($partstat));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// aggregate counts from all calendar folders
|
||||||
|
$count = 0;
|
||||||
|
foreach (kolab_storage::list_folders('', '*', 'event', null) as $foldername) {
|
||||||
|
$cal = new kolab_calendar($foldername, $this->cal);
|
||||||
|
if ($cal->get_namespace() == 'other')
|
||||||
|
continue;
|
||||||
|
|
||||||
|
$count += $cal->count_events($start, $end, array(array($subquery, 'OR')));
|
||||||
|
}
|
||||||
|
|
||||||
|
return $count;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper method to modify some event properties
|
* Helper method to modify some event properties
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -239,6 +239,18 @@ class kolab_user_calendar extends kolab_calendar
|
||||||
return $events;
|
return $events;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param integer Date range start (unix timestamp)
|
||||||
|
* @param integer Date range end (unix timestamp)
|
||||||
|
* @return integer Count
|
||||||
|
*/
|
||||||
|
public function count_events($start, $end = null)
|
||||||
|
{
|
||||||
|
// not implemented
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper method to fetch free/busy data for the user and turn it into calendar data
|
* Helper method to fetch free/busy data for the user and turn it into calendar data
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -221,7 +221,7 @@ pre {
|
||||||
right: 45px;
|
right: 45px;
|
||||||
cursor: default;
|
cursor: default;
|
||||||
background: url(images/calendars.png) right 20px no-repeat;
|
background: url(images/calendars.png) right 20px no-repeat;
|
||||||
overflow: hidden;
|
overflow-x: hidden;
|
||||||
text-overflow: ellipsis;
|
text-overflow: ellipsis;
|
||||||
white-space: nowrap;
|
white-space: nowrap;
|
||||||
color: #004458;
|
color: #004458;
|
||||||
|
@ -275,9 +275,10 @@ pre {
|
||||||
top: 2px;
|
top: 2px;
|
||||||
right: 22px;
|
right: 22px;
|
||||||
padding: 5px 20px 0 6px;
|
padding: 5px 20px 0 6px;
|
||||||
min-width: 40px;
|
/* min-width: 40px; */
|
||||||
height: 19px;
|
height: 19px;
|
||||||
text-align: right;
|
text-align: right;
|
||||||
|
z-index: 4;
|
||||||
}
|
}
|
||||||
|
|
||||||
#calendars .treelist div:hover span.actions {
|
#calendars .treelist div:hover span.actions {
|
||||||
|
@ -425,6 +426,30 @@ pre {
|
||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#calendars .treelist .calendar .count {
|
||||||
|
position: absolute;
|
||||||
|
display: inline-block;
|
||||||
|
top: 5px;
|
||||||
|
right: 68px;
|
||||||
|
min-width: 1.3em;
|
||||||
|
padding: 2px 4px;
|
||||||
|
background: #005d76;
|
||||||
|
background: -moz-linear-gradient(top, #005d76 0%, #004558 100%);
|
||||||
|
background: -webkit-gradient(linear, left top, left bottom, color-stop(0%,#005d76), color-stop(100%,#004558));
|
||||||
|
background: -o-linear-gradient(top, #005d76 0%, #004558 100%);
|
||||||
|
background: -ms-linear-gradient(top, #005d76 0%, #004558 100%);
|
||||||
|
background: linear-gradient(to bottom, #005d76 0%, #004558 100%);
|
||||||
|
-webkit-box-shadow: inset 0 1px 1px 0 #002635;
|
||||||
|
box-shadow: inset 0 1px 1px 0 #002635;
|
||||||
|
border-radius: 10px;
|
||||||
|
color: #fff;
|
||||||
|
text-align: center;
|
||||||
|
font-style: normal;
|
||||||
|
font-weight: bold;
|
||||||
|
text-shadow: none;
|
||||||
|
z-index: 3;
|
||||||
|
}
|
||||||
|
|
||||||
#calendars .searchresults {
|
#calendars .searchresults {
|
||||||
background: #b0ccd7;
|
background: #b0ccd7;
|
||||||
margin-top: 8px;
|
margin-top: 8px;
|
||||||
|
|
Loading…
Add table
Reference in a new issue