aboutsummaryrefslogtreecommitdiff
path: root/radicale_web/web/infcloud/lib
diff options
context:
space:
mode:
authorUnrud <unrud@openaliasbox.org>2017-06-04 17:16:11 +0200
committerUnrud <unrud@openaliasbox.org>2017-06-04 17:16:36 +0200
commit10eef51a0f086ad148928ba965c330599b4765cb (patch)
treed0283e55f1b4e66c49bf17461b5fee211b78768a /radicale_web/web/infcloud/lib
parentUpdate license (diff)
downloadradicaleinfcloud-10eef51a0f086ad148928ba965c330599b4765cb.tar.gz
radicaleinfcloud-10eef51a0f086ad148928ba965c330599b4765cb.tar.bz2
radicaleinfcloud-10eef51a0f086ad148928ba965c330599b4765cb.zip
Update package for new web plugin interface
Diffstat (limited to 'radicale_web/web/infcloud/lib')
-rw-r--r--radicale_web/web/infcloud/lib/fullcalendar.js7196
-rw-r--r--radicale_web/web/infcloud/lib/ie_base64.js176
-rw-r--r--radicale_web/web/infcloud/lib/jquery-2.1.4.min.js4
-rw-r--r--radicale_web/web/infcloud/lib/jquery-ui-1.11.4.custom.js8226
-rw-r--r--radicale_web/web/infcloud/lib/jquery.autosize.js258
-rw-r--r--radicale_web/web/infcloud/lib/jquery.browser.js43
-rw-r--r--radicale_web/web/infcloud/lib/jquery.placeholder-1.1.9.js195
-rw-r--r--radicale_web/web/infcloud/lib/jquery.quicksearch.js205
-rw-r--r--radicale_web/web/infcloud/lib/jquery.tagsinput.js436
-rw-r--r--radicale_web/web/infcloud/lib/rrule.js1910
-rw-r--r--radicale_web/web/infcloud/lib/sha256.js16
-rw-r--r--radicale_web/web/infcloud/lib/spectrum.js2027
12 files changed, 0 insertions, 20692 deletions
diff --git a/radicale_web/web/infcloud/lib/fullcalendar.js b/radicale_web/web/infcloud/lib/fullcalendar.js
deleted file mode 100644
index 8effe83..0000000
--- a/radicale_web/web/infcloud/lib/fullcalendar.js
+++ /dev/null
@@ -1,7196 +0,0 @@
-/**
- * @preserve
- * FullCalendar v1.5.4
- * http://arshaw.com/fullcalendar/
- *
- * Use fullcalendar.css for basic styling.
- * For event drag & drop, requires jQuery UI draggable.
- * For event resizing, requires jQuery UI resizable.
- *
- * Copyright (c) 2011 Adam Shaw
- * Dual licensed under the MIT and GPL licenses, located in
- * MIT-LICENSE.txt and GPL-LICENSE.txt respectively.
- *
- * Date: Tue Sep 4 23:38:33 2012 -0700
- *
- */
-
-(function($, undefined) {
-
-var defaults = {
-
- // display
- defaultView: 'month',
- aspectRatio: 1.35,
- header: {
- left: 'title',
- center: '',
- right: 'today prev,next'
- },
- weekends: true,
- currentTimeIndicator: false,
-
- // editing
- //editable: false,
- //disableDragging: false,
- //disableResizing: false,
-
- allDayDefault: true,
- ignoreTimezone: true,
-
- // event ajax
- lazyFetching: true,
- startParam: 'start',
- endParam: 'end',
-
- // time formats
- titleFormat: {
- month: 'MMMM yyyy',
- multiWeek: "MMM d[ yyyy]{ '–'[ MMM] d yyyy}",
- week: "MMM d[ yyyy]{ '–'[ MMM] d yyyy}",
- day: 'dddd, MMM d, yyyy',
- list: 'MMM d, yyyy',
- table: "MMM d[ yyyy]{ '–'[ MMM] d yyyy}",
- todo: "MMM d[ yyyy]{ '–'[ MMM] d yyyy}",
- },
- columnFormat: {
- month: 'ddd',
- multiWeek: 'ddd',
- week: 'ddd M/d',
- day: 'dddd M/d',
- list: 'dddd, MMM d, yyyy',
- table: 'MMM d, yyyy',
- todo: 'MMM d, yyyy',
- },
- timeFormat: { // for event elements
- '': 'h(:mm)t', // default
- agenda: 'h:mm{ – h:mm}', //agenda views
- list: 'hh:mm{ – hh:mm}', //list and table views
- listFull: 'hh:mm M d yyyy{ – hh:mm M d yyyy}', //list and table views for events that span multiple days
- listFullAllDay: 'M d yyyy{ – M d yyyy}', //list and table views for allday events that span multiple days
- },
-
- // locale
- isRTL: false,
- firstDay: 0,
- weekendDays: [0, 6],
- monthNames: ['January','February','March','April','May','June','July','August','September','October','November','December'],
- monthNamesShort: ['Jan','Feb','Mar','Apr','May','Jun','Jul','Aug','Sep','Oct','Nov','Dec'],
- dayNames: ['Sunday','Monday','Tuesday','Wednesday','Thursday','Friday','Saturday'],
- dayNamesShort: ['Sun','Mon','Tue','Wed','Thu','Fri','Sat'],
- buttonText: {
- prev: '&nbsp;❮&nbsp;',
- next: '&nbsp;❯&nbsp;',
- prevYear: '&nbsp;&lt;&lt;&nbsp;',
- nextYear: '&nbsp;&gt;&gt;&nbsp;',
- today: 'today',
- month: 'month',
- multiWeek: 'mweek',
- week: 'week',
- day: 'day',
- list: 'list',
- table: 'table',
- todo: 'todo',
- prevMonth: 'Load previous month',
- nextMonth: 'Load next month',
- filtersHeader: 'Filters',
- filtersFooter: '* completed at or after %date%',
- filterAction: 'Needs action',
- filterProgress: 'In progress',
- filterCompleted: 'Completed',
- filterCanceled: 'Canceled'
- },
-
- listTexts: {
- until: 'until',
- past: 'Past events',
- today: 'Today',
- tomorrow: 'Tomorrow',
- thisWeek: 'This week',
- nextWeek: 'Next week',
- thisMonth: 'This month',
- nextMonth: 'Next month',
- future: 'Future events',
- week: 'W'
- },
-
- // list/table options
- listSections: 'smart', // false|'day'|'week'|'month'|'smart'
- listRange: 30, // number of days to be displayed
- listPage: 7, // number of days to jump when paging
- tableCols: ['handle', 'date', 'time', 'title'],
- todoCols: ['handle', 'check', 'priority', 'time', 'title', 'location', 'status', 'percent'],
- todoColThresholds: [],
- todoOptionalCols: [],
- //defaultFilters: ['filterAction', 'filterProgress', 'filterCompleted', 'filterCanceled'],
- defaultFilters: [],
-
- // jquery-ui theming
- theme: false,
- buttonIcons: {
- prev: 'circle-triangle-w',
- next: 'circle-triangle-e'
- },
-
- //selectable: false,
- unselectAuto: true,
-
- dropAccept: '*',
-
- headerContainer: false,
- bindingMode: 'single',
- dayEventSizeStrict: false,
- startOfBusiness: 0,
- endOfBusiness: 0,
- showWeekNumbers: true,
- multiWeekSize: 3,
- showDatepicker: false,
- eventMode: true,
- showUnstartedEvents: false,
- simpleFilters: false,
-};
-
-// right-to-left defaults
-var rtlDefaults = {
- header: {
- left: 'next,prev today',
- center: '',
- right: 'title'
- },
- headerContainer: '',
- buttonText: {
- prev: '&nbsp;&#9658;&nbsp;',
- next: '&nbsp;&#9668;&nbsp;',
- prevYear: '&nbsp;&gt;&gt;&nbsp;',
- nextYear: '&nbsp;&lt;&lt;&nbsp;'
- },
- buttonIcons: {
- prev: 'circle-triangle-e',
- next: 'circle-triangle-w'
- }
-};
-
-var fc = $.fullCalendar = { version: "1.5.4" };
-var fcViews = fc.views = {};
-
-$.fn.fullCalendar = function(options) {
- // method calling
- if (typeof options == 'string') {
- var args = Array.prototype.slice.call(arguments, 1);
- var res;
- this.each(function() {
- var calendar = $.data(this, 'fullCalendar');
- if (calendar && $.isFunction(calendar[options])) {
- var r = calendar[options].apply(calendar, args);
- if (res === undefined) {
- res = r;
- }
- if (options == 'destroy') {
- $.removeData(this, 'fullCalendar');
- }
- }
- });
- if (res !== undefined) {
- return res;
- }
- return this;
- }
-
- // would like to have this logic in EventManager, but needs to happen before options are recursively extended
- var eventSources = options.eventSources || [];
- delete options.eventSources;
- if (options.events) {
- eventSources.push(options.events);
- delete options.events;
- }
-
- options = $.extend(true, {},
- defaults,
- (options.isRTL || options.isRTL===undefined && defaults.isRTL) ? rtlDefaults : {},
- options
- );
-
- this.each(function(i, _element) {
- var element = $(_element);
- var calendar = new Calendar(element, options, eventSources);
- element.data('fullCalendar', calendar); // TODO: look into memory leak implications
- calendar.render();
- });
-
- return this;
-};
-
-// function for adding/overriding defaults
-function setDefaults(d) {
- $.extend(true, defaults, d);
-}
-
-function Calendar(element, options, eventSources) {
- var t = this;
-
- // exports
- t.options = options;
- t.render = render;
- t.destroy = destroy;
- t.refetchEvents = refetchEvents;
- t.reportEvents = reportEvents;
- t.reportEventChange = reportEventChange;
- t.rerenderEvents = rerenderEvents;
- t.changeView = changeView;
- t.select = select;
- t.unselect = unselect;
- t.prev = prev;
- t.next = next;
- t.prevYear = prevYear;
- t.nextYear = nextYear;
- t.today = today;
- t.findToday = findToday;
- t.gotoDate = gotoDate;
- t.incrementDate = incrementDate;
- t.formatDate = function(format, date) { return formatDate(format, date, options) };
- t.formatDates = function(format, date1, date2) { return formatDates(format, date1, date2, options) };
- t.getDate = getDate;
- t.getView = getView;
- t.option = option;
- t.trigger = trigger;
- t.selectEvent = selectEvent;
- t.allowSelectEvent = allowSelectEvent;
- t.updateToday = updateToday;
- t.updateGrid = updateGrid;
- t.renderViews = renderViews;
- t.setOptions = setOptions;
- t.getOption = getOption;
- t.viewInstances = {};
-
- // imports
- EventManager.call(t, options, eventSources);
- var isFetchNeeded = t.isFetchNeeded;
- var fetchEvents = t.fetchEvents;
-
- // locals
- var _element = element[0];
- var header;
- var headerElement;
- var content;
- var tm; // for making theme classes
- var currentView;
- var elementOuterWidth;
- var suggestedViewHeight;
- var absoluteViewElement;
- var resizeUID = 0;
- var ignoreWindowResize = 0;
- var date = new Date();
- var events = [];
- var _dragElement;
-
- /* Main Rendering
- -----------------------------------------------------------------------------*/
-
- setYMD(date, options.year, options.month, options.date);
-
- function render(inc) {
- if (!content) {
- initialRender();
- }else{
- calcSize();
- markSizesDirty();
- markEventsDirty();
- renderView(inc);
- }
- }
-
- function initialRender() {
- tm = options.theme ? 'ui' : 'fc';
- element.addClass('fc');
- if (options.isRTL) {
- element.addClass('fc-rtl');
- }
- if (options.theme) {
- element.addClass('ui-widget');
- }
- content = $("<div class='fc-content' style='position:relative'/>")
- .prependTo(element);
- header = new Header(t, options);
- headerElement = header.render();
- if (headerElement) {
- options.headerContainer ? options.headerContainer.prepend(headerElement) : element.prepend(headerElement);
- }
- changeView(options.defaultView);
- $(window).resize(windowResize);
- // needed for IE in a 0x0 iframe, b/c when it is resized, never triggers a windowResize
- if (!bodyVisible()) {
- lateRender();
- }
- }
-
- // called when we know the calendar couldn't be rendered when it was initialized,
- // but we think it's ready now
- function lateRender() {
- setTimeout(function() { // IE7 needs this so dimensions are calculated correctly
- if (!currentView.start && bodyVisible()) { // !currentView.start makes sure this never happens more than once
- renderView();
- }
- },0);
- }
-
- function updateToday()
- {
- for(var view in t.viewInstances)
- t.viewInstances[view].updateToday();
- }
-
- function updateGrid()
- {
- for(var view in t.viewInstances)
- t.viewInstances[view].updateGrid();
- }
-
- function renderViews()
- {
- //Force rerender of all views
- for(var view in t.viewInstances)
- t.viewInstances[view].start=null;
- renderView();
- }
-
- function setOptions(newOptions)
- {
- var rerender=false;
-
- $.each(newOptions, function(key,value){
- if($.isPlainObject(value))
- $.extend(options[key],value);
- else
- options[key]=value;
-
- if(key=='firstDay' || key=='timeFormat')
- rerender=true;
- else
- {
- for(var view in t.viewInstances)
- t.viewInstances[view]['set'+key.charAt(0).toUpperCase()+key.slice(1)]();
- }
- });
-
- if(rerender)
- renderViews();
- }
-
- function getOption(option)
- {
- return options[option];
- }
-
- function destroy() {
- $(window).unbind('resize', windowResize);
- header.destroy();
- content.remove();
- element.removeClass('fc fc-rtl ui-widget');
- }
-
- function elementVisible() {
- return _element.offsetWidth !== 0;
- }
-
- function bodyVisible() {
- return $('body')[0].offsetWidth !== 0;
- }
-
- /* View Rendering
- -----------------------------------------------------------------------------*/
-
- // TODO: improve view switching (still weird transition in IE, and FF has whiteout problem)
-
- function changeView(newViewName) {
- if (!currentView || newViewName != currentView.name) {
- ignoreWindowResize++; // because setMinHeight might change the height before render (and subsequently setSize) is reached
-
- unselect();
-
- var oldView = currentView;
- var newViewElement;
-
- if (oldView) {
- (oldView.beforeHide || noop)(); // called before changing min-height. if called after, scroll state is reset (in Opera)
- //setMinHeight(content, content.height()); why is this necessary?
- oldView.element.hide();
- if(oldView.addedView) {
- oldView.addedView.element.hide();
- }
- }else{
- setMinHeight(content, 1); // needs to be 1 (not 0) for IE7, or else view dimensions miscalculated
- }
- content.css('overflow', 'hidden');
-
- currentView = t.viewInstances[newViewName];
- if (currentView) {
- currentView.element.show();
- }else{
- currentView = t.viewInstances[newViewName] = new fcViews[newViewName](
- newViewElement = absoluteViewElement =
- $("<div class='fc-view fc-view-" + newViewName + "' style='position:absolute'/>")
- .appendTo(content),
- t // the calendar object
- );
- }
-
- if(newViewName == 'agendaDay') {
- addedView = t.viewInstances['table'];
- if (addedView) {
- addedView.element.show();
- }else{
- addedView = t.viewInstances['table'] = new fcViews['table'](
- addedNewViewElement = addedAbsoluteViewElement =
- $("<div class='fc-view fc-view-" + 'table' + "' style='position:absolute'/>")
- .appendTo(content),
- t // the calendar object
- );
- currentView.addedView = addedView;
- }
- }
-
- if (oldView) {
- header.deactivateButton(oldView.name);
- }
- header.activateButton(newViewName);
-
- renderView(); // after height has been set, will make absoluteViewElement's position=relative, then set to null
-
- content.css('overflow', '');
- if (oldView) {
- setMinHeight(content, 1);
- }
-
- if (!newViewElement) {
- (currentView.afterShow || noop)(); // called after setting min-height/overflow, so in final scroll state (for Opera)
- }
-
- ignoreWindowResize--;
- currentView.trigger('viewChanged', _element);
- }
- }
-
- function renderView(inc) {
- if (elementVisible()) {
- currentView.trigger('beforeViewDisplay', _element);
- ignoreWindowResize++; // because renderEvents might temporarily change the height before setSize is reached
-
- unselect();
-
- if (suggestedViewHeight === undefined) {
- calcSize();
- }
-
- if(currentView.addedView && currentView.start && cloneDate(date, true).getTime() == currentView.start.getTime()) {
- currentView.addedView.scrollToDate(date);
- }
-
- var forceEventRender = false;
- if (!currentView.start || inc || date < currentView.start || date >= currentView.end) {
- // view must render an entire new date range (and refetch/render events)
- currentView.render(date, inc || 0); // responsible for clearing events
- setSize(true);
- forceEventRender = true;
- }
- else if (currentView.sizeDirty) {
- // view must resize (and rerender events)
- currentView.clearEvents();
- setSize();
- forceEventRender = true;
- }
- else if (currentView.eventsDirty) {
- currentView.clearEvents();
- forceEventRender = true;
- }
-
- currentView.sizeDirty = false;
- currentView.eventsDirty = false;
- updateEvents(forceEventRender);
-
- elementOuterWidth = element.outerWidth();
-
- header.updateTitle(currentView.title);
- var today = new Date();
- if (today >= currentView.start && today < currentView.end) {
- //header.disableButton('today');
- header.setTodayScroll(element);
- findToday();
- }else{
- //header.enableButton('today');
- header.setTodayDefault();
- }
-
- ignoreWindowResize--;
- currentView.trigger('viewDisplay', _element);
- }
- }
-
- /* Resizing
- -----------------------------------------------------------------------------*/
-
- function updateSize() {
- markSizesDirty();
- if (elementVisible()) {
- calcSize();
- setSize();
- if(currentView.name!='todo')
- {
- unselect();
- currentView.clearEvents();
- currentView.renderEvents(events);
- }
- currentView.sizeDirty = false;
- }
- }
-
- function markSizesDirty() {
- $.each(t.viewInstances, function(i, inst) {
- inst.sizeDirty = true;
- });
- }
-
- function calcSize() {
- if (options.contentHeight) {
- suggestedViewHeight = options.contentHeight;
- }
- else if (options.height) {
- suggestedViewHeight = options.height - (headerElement ? headerElement.height() : 0) - vsides(content);
- }
- else {
- suggestedViewHeight = Math.round(content.width() / Math.max(options.aspectRatio, .5));
- }
- }
-
- function setSize(dateChanged) { // todo: dateChanged?
- ignoreWindowResize++;
- currentView.setWidth(content.width(), dateChanged);
- currentView.setHeight(suggestedViewHeight, dateChanged);
- if (absoluteViewElement) {
- absoluteViewElement.css('position', 'relative');
- absoluteViewElement = null;
- }
- /*if(currentView.addedView) {
- currentView.addedView.setWidth(content.width(), dateChanged);
- var tmpContentWidth = Math.floor(content.width() / 2);
- currentView.element.width(tmpContentWidth);
- currentView.addedView.element.css({'left' : tmpContentWidth,
- 'width' : tmpContentWidth - 2});
- }*/
- ignoreWindowResize--;
- }
-
- function windowResize() {
- if (!ignoreWindowResize) {
- if (currentView.start) { // view has already been rendered
- var uid = ++resizeUID;
- //setTimeout(function() { // add a delay
- if (uid == resizeUID && !ignoreWindowResize && elementVisible()) {
- if (elementOuterWidth != (elementOuterWidth = element.outerWidth())) {
- ignoreWindowResize++; // in case the windowResize callback changes the height
- updateSize();
- currentView.trigger('windowResize', _element);
- ignoreWindowResize--;
- }
- }
- //}, 200);
- }else{
- // calendar must have been initialized in a 0x0 iframe that has just been resized
- lateRender();
- }
- }
- }
-
- /* Event Fetching/Rendering
- -----------------------------------------------------------------------------*/
-
- // fetches events if necessary, rerenders events if necessary (or if forced)
- function updateEvents(forceRender) {
- if (!options.lazyFetching || isFetchNeeded(currentView.visStart, currentView.visEnd)) {
- refetchEvents();
- }
- else if (forceRender) {
- rerenderEvents();
- }
- }
-
- function refetchEvents() {
- fetchEvents(currentView.visStart, currentView.visEnd); // will call reportEvents
- }
-
- // called when event data arrives
- function reportEvents(_events) {
- events = _events;
- rerenderEvents();
- }
-
- // called when a single event's data has been changed
- function reportEventChange(eventID) {
- rerenderEvents(eventID);
- }
-
- // attempts to rerenderEvents
- function rerenderEvents(modifiedEventID) {
- markEventsDirty();
- if (elementVisible()) {
- currentView.clearEvents();
- currentView.renderEvents(events, modifiedEventID);
- currentView.eventsDirty = false;
- }
- }
-
- function markEventsDirty() {
- $.each(t.viewInstances, function(i, inst) {
- inst.eventsDirty = true;
- });
- }
-
- /* Selection
- -----------------------------------------------------------------------------*/
-
- function select(start, end, allDay) {
- currentView.select(start, end, allDay===undefined ? true : allDay);
- }
-
- function unselect() { // safe to be called before renderView
- if(currentView)
- currentView.unselect();
- }
-
- /* Date
- -----------------------------------------------------------------------------*/
-
- function prev() {
- renderView(-1);
- trigger('prevClick');
- }
-
- function next() {
- renderView(1);
- trigger('nextClick');
- }
-
- function prevYear() {
- addYears(date, -1);
- renderView();
- }
-
- function nextYear() {
- addYears(date, 1);
- renderView();
- }
-
- function today() {
- date = new Date();
- renderView();
- findToday();
- trigger('todayClick');
- }
-
- function findToday() {
- if(currentView.addedView) {
- if(currentView.addedView.getDaySegmentContainer().find('.fc-today').length>0) {
- if(new Date().getDate()==1) {
- currentView.addedView.getDaySegmentContainer().parent().scrollTop(0);
- }
- else {
- offset = currentView.addedView.getDaySegmentContainer().find('.fc-today').position().top;
- var top = currentView.addedView.getDaySegmentContainer().parent().scrollTop();
- currentView.addedView.getDaySegmentContainer().parent().scrollTop(top + offset);
- }
- }
- }
- else if(currentView.name == 'todo') {
- if(currentView.getDaySegmentContainer().find('.fc-today').length>0) {
- offset = currentView.getDaySegmentContainer().find('.fc-today').position().top;
- var top = currentView.getDaySegmentContainer().parent().scrollTop();
- currentView.getDaySegmentContainer().parent().scrollTop(top + offset);
- }
- }
- else {
- var todayElem = currentView.element.find('.fc-today');
- if(todayElem.length>0) {
- var offset = 0;
- if(!todayElem.parent().hasClass('fc-week0')) {
- offset = todayElem.position().top;
- }
- element.parent().scrollTop(offset);
- }
- }
- }
-
- function gotoDate(year, month, dateOfMonth) {
- if (year instanceof Date)
- date = cloneDate(year); // provided 1 argument, a Date
- else
- setYMD(date, year, month, dateOfMonth);
- renderView();
- }
-
- function incrementDate(years, months, days) {
- if(years !== undefined)
- addYears(date, years);
- if(months !== undefined)
- addMonths(date, months);
- if(days !== undefined)
- addDays(date, days);
- renderView();
- }
-
- function getDate() {
- return cloneDate(date);
- }
-
- /* Misc
- -----------------------------------------------------------------------------*/
-
- function getView() {
- return currentView;
- }
-
- function option(name, value) {
- if (value === undefined) {
- return options[name];
- }
- if (name == 'height' || name == 'contentHeight' || name == 'aspectRatio') {
- options[name] = value;
- updateSize();
- } else if (name.indexOf('list') == 0 || name == 'tableCols') {
- options[name] = value;
- currentView.start = null; // force re-render
- }
- }
-
- function trigger(name, thisObj) {
- if (options[name]) {
- return options[name].apply(
- thisObj || _element,
- Array.prototype.slice.call(arguments, 2)
- );
- }
- }
-
- function selectEvent(eventElement, noClick) {
- currentView.selectEvent(eventElement, noClick);
- }
-
- function allowSelectEvent(value) {
- currentView.allowSelectEvent(value);
- }
-
- /* External Dragging
- ------------------------------------------------------------------------*/
-
- if (options.droppable) {
- $(document)
- .bind('dragstart', function(ev, ui) {
- var _e = ev.target;
- var e = $(_e);
- if (!e.parents('.fc').length) { // not already inside a calendar
- var accept = options.dropAccept;
- if ($.isFunction(accept) ? accept.call(_e, e) : e.is(accept)) {
- _dragElement = _e;
- currentView.dragStart(_dragElement, ev, ui);
- }
- }
- })
- .bind('dragstop', function(ev, ui) {
- if (_dragElement) {
- currentView.dragStop(_dragElement, ev, ui);
- _dragElement = null;
- }
- });
- }
-}
-
-function Header(calendar, options) {
- var t = this;
-
- // exports
- t.render = render;
- t.destroy = destroy;
- t.updateTitle = updateTitle;
- t.activateButton = activateButton;
- t.deactivateButton = deactivateButton;
- t.disableButton = disableButton;
- t.enableButton = enableButton;
- t.setTodayDefault = setTodayDefault;
- t.setTodayScroll = setTodayScroll;
-
- // locals
- var element = $([]);
- var tm;
-
- function render() {
- tm = options.theme ? 'ui' : 'fc';
- var sections = options.header;
- if (sections) {
- element = $("<table class='fc-header' style='width:100%'/>")
- .append(
- $("<tr/>")
- .append(renderSection('left'))
- .append(renderSection('center'))
- .append(renderSection('right'))
- );
- return element;
- }
- }
-
- function destroy() {
- element.remove();
- }
-
- function renderSection(position) {
- var e = $("<td class='fc-header-" + position + "'/>");
- var buttonStr = options.header[position];
- if (buttonStr) {
- $.each(buttonStr.split(' '), function(i) {
- if (i > 0) {
- e.append("<span class='fc-header-space'/>");
- }
- var prevButton;
- $.each(this.split(','), function(j, buttonName) {
- if (buttonName == 'title') {
- e.append("<span class='fc-header-title'><h2>&nbsp;</h2></span>");
- if (prevButton) {
- prevButton.addClass(tm + '-corner-right');
- }
- prevButton = null;
- }else{
- var buttonClick;
- if (calendar[buttonName]) {
- buttonClick = calendar[buttonName]; // calendar method
- }
- else if (fcViews[buttonName]) {
- buttonClick = function() {
- button.removeClass(tm + '-state-hover'); // forget why
- calendar.changeView(buttonName);
- };
- }
- if (buttonClick) {
-// var icon = options.theme ? smartProperty(options.buttonIcons, buttonName) : null; // why are we using smartProperty here?
- var icon = (buttonName=='prev' || buttonName=='next') ? buttonName : null;
- var text = smartProperty(options.buttonText, buttonName); // why are we using smartProperty here?
- var button = $(
- "<span class='fc-button fc-button-" + buttonName + " " + tm + "-state-default'>" +
- "<span class='fc-button-inner'>" +
- "<span class='fc-button-content'>" +
- (icon ?
- "<img src='images/arrow_" + icon + ".svg'/>" :
- text
- ) +
- "</span>" +
- "<span class='fc-button-effect'><span></span></span>" +
- "</span>" +
- "</span>"
- );
- if (button) {
- button
- .click(function() {
- if (!button.hasClass(tm + '-state-disabled')) {
- buttonClick();
- }
- })
- .mousedown(function() {
- button
- .not('.' + tm + '-state-active')
- .not('.' + tm + '-state-disabled')
- .addClass(tm + '-state-down');
- })
- .mouseup(function() {
- button.removeClass(tm + '-state-down');
- })
- .hover(
- function() {
- button
- .not('.' + tm + '-state-active')
- .not('.' + tm + '-state-disabled')
- .addClass(tm + '-state-hover');
- },
- function() {
- button
- .removeClass(tm + '-state-hover')
- .removeClass(tm + '-state-down');
- }
- )
- .appendTo(e);
- if (!prevButton) {
- button.addClass(tm + '-corner-left');
- }
- prevButton = button;
- }
- }
- }
- });
- if (prevButton) {
- prevButton.addClass(tm + '-corner-right');
- }
- });
- }
- return e;
- }
-
- function updateTitle(html) {
- element.find('h2')
- .html(html)
- .attr('title', $("<div/>").html(html).text());
- }
-
- function activateButton(buttonName) {
- element.find('span.fc-button-' + buttonName)
- .addClass(tm + '-state-active');
- }
-
- function deactivateButton(buttonName) {
- element.find('span.fc-button-' + buttonName)
- .removeClass(tm + '-state-active');
- }
-
- function disableButton(buttonName) {
- element.find('span.fc-button-' + buttonName)
- .addClass(tm + '-state-disabled');
- }
-
- function enableButton(buttonName) {
- element.find('span.fc-button-' + buttonName)
- .removeClass(tm + '-state-disabled');
- }
-
- function setTodayDefault() {
- var todayBt = element.find('span.fc-button-' + 'today');
- var todayBtClc = calendar['today'];
-
- todayBt.unbind('click');
- todayBt.click(function(){
- if(!todayBt.hasClass(tm + '-state-disabled')) {
- todayBtClc();
- }
- });
- }
-
- function setTodayScroll(body) {
- var todayBt = element.find('span.fc-button-' + 'today');
- var todayBtClc = calendar['findToday'];
-
- todayBt.unbind('click');
- todayBt.click(function(){
- if(!todayBt.hasClass(tm + '-state-disabled'))
- todayBtClc();
- });
- }
-
-}
-
-fc.sourceNormalizers = [];
-fc.sourceFetchers = [];
-
-var ajaxDefaults = {
- dataType: 'json',
- cache: false
-};
-
-var eventGUID = 1;
-
-function EventManager(options, _sources) {
- var t = this;
-
- // exports
- t.isFetchNeeded = isFetchNeeded;
- t.fetchEvents = fetchEvents;
- t.addEventSource = addEventSource;
- t.removeEventSource = removeEventSource;
- t.removeEventSources = removeEventSources;
- t.updateEvent = updateEvent;
- t.renderEvent = renderEvent;
- t.removeEvents = removeEvents;
- t.clientEvents = clientEvents;
- t.normalizeEvent = normalizeEvent;
-
- // imports
- var trigger = t.trigger;
- var getView = t.getView;
- var reportEvents = t.reportEvents;
-
- // locals
- var stickySource = { events: [] };
- var sources = [ stickySource ];
- var rangeStart, rangeEnd;
- var currentFetchID = 0;
- var pendingSourceCnt = 0;
- var loadingLevel = 0;
- var cache = [];
-
- for (var i=0; i<_sources.length; i++) {
- _addEventSource(_sources[i]);
- }
-
- /* Fetching
- -----------------------------------------------------------------------------*/
-
- function isFetchNeeded(start, end) {
- return !rangeStart || start < rangeStart || end > rangeEnd;
- }
-
- function fetchEvents(start, end) {
- rangeStart = start;
- rangeEnd = end;
- cache = [];
- var fetchID = ++currentFetchID;
- var len = sources.length;
- pendingSourceCnt = len;
- for (var i=0; i<len; i++) {
- fetchEventSource(sources[i], fetchID);
- }
- }
-
- function fetchEventSource(source, fetchID) {
- _fetchEventSource(source, function(events) {
- if (fetchID == currentFetchID) {
- if (events) {
- for (var i=0; i<events.length; i++) {
- events[i].source = source;
- normalizeEvent(events[i]);
- }
- cache = cache.concat(events);
- }
- pendingSourceCnt--;
- if (!pendingSourceCnt) {
- reportEvents(cache);
- }
- }
- });
- }
-
- function _fetchEventSource(source, callback) {
- var i;
- var fetchers = fc.sourceFetchers;
- var res;
- for (i=0; i<fetchers.length; i++) {
- res = fetchers[i](source, rangeStart, rangeEnd, callback);
- if (res === true) {
- // the fetcher is in charge. made its own async request
- return;
- }
- else if (typeof res == 'object') {
- // the fetcher returned a new source. process it
- _fetchEventSource(res, callback);
- return;
- }
- }
- var events = source.events;
- if (events) {
- if ($.isFunction(events)) {
- pushLoading();
- events(cloneDate(rangeStart), cloneDate(rangeEnd), function(events) {
- callback(events);
- popLoading();
- });
- }
- else if ($.isArray(events)) {
- callback(events);
- }
- else {
- callback();
- }
- }else{
- var url = source.url;
- if (url) {
- var success = source.success;
- var error = source.error;
- var complete = source.complete;
- var data = $.extend({}, source.data || {});
- var startParam = firstDefined(source.startParam, options.startParam);
- var endParam = firstDefined(source.endParam, options.endParam);
- if (startParam) {
- data[startParam] = Math.round(+rangeStart / 1000);
- }
- if (endParam) {
- data[endParam] = Math.round(+rangeEnd / 1000);
- }
- pushLoading();
- $.ajax($.extend({}, ajaxDefaults, source, {
- data: data,
- success: function(events) {
- events = events || [];
- var res = applyAll(success, this, arguments);
- if ($.isArray(res)) {
- events = res;
- }
- callback(events);
- },
- error: function() {
- applyAll(error, this, arguments);
- callback();
- },
- complete: function() {
- applyAll(complete, this, arguments);
- popLoading();
- }
- }));
- }else{
- callback();
- }
- }
- }
-
- /* Sources
- -----------------------------------------------------------------------------*/
-
- function addEventSource(source) {
- source = _addEventSource(source);
- if (source) {
- pendingSourceCnt++;
- fetchEventSource(source, currentFetchID); // will eventually call reportEvents
- }
- return source;
- }
-
- function _addEventSource(source) {
- if ($.isFunction(source) || $.isArray(source)) {
- source = { events: source };
- }
- else if (typeof source == 'string') {
- source = { url: source };
- }
- if (typeof source == 'object') {
- normalizeSource(source);
- sources.push(source);
- return source;
- }
- }
-
- function removeEventSource(source) {
- sources = $.grep(sources, function(src) {
- return !isSourcesEqual(src, source);
- });
- // remove all client events from that source
- cache = $.grep(cache, function(e) {
- return !isSourcesEqual(e.source, source);
- });
- reportEvents(cache);
- }
-
- function removeEventSources() {
- while(source = sources.shift()) {
- // remove all client events from that source
- cache = $.grep(cache, function(e) {
- return !isSourcesEqual(e.source, source);
- });
- reportEvents(cache);
- }
- }
-
- /* Manipulation
- -----------------------------------------------------------------------------*/
-
- function updateEvent(event) { // update an existing event
- var i, len = cache.length, e,
- defaultEventEnd = getView().defaultEventEnd, // getView???
- startDelta = event.start - event._start,
- endDelta = event.end ?
- (event.end - (event._end || defaultEventEnd(event))) // event._end would be null if event.end
- : 0; // was null and event was just resized
- for (i=0; i<len; i++) {
- e = cache[i];
- if (e._id == event._id && e != event) {
- e.start = new Date(+e.start + startDelta);
- if (event.end) {
- if (e.end) {
- e.end = new Date(+e.end + endDelta);
- }else{
- e.end = new Date(+defaultEventEnd(e) + endDelta);
- }
- }else{
- e.end = null;
- }
- e.title = event.title;
- e.url = event.url;
- e.allDay = event.allDay;
- e.className = event.className;
- e.editable = event.editable;
- e.color = event.color;
- e.backgroudColor = event.backgroudColor;
- e.borderColor = event.borderColor;
- e.textColor = event.textColor;
- normalizeEvent(e);
- }
- }
- normalizeEvent(event);
- reportEvents(cache);
- }
-
- function renderEvent(event, stick) {
- normalizeEvent(event);
- if (!event.source) {
- if (stick) {
- stickySource.events.push(event);
- event.source = stickySource;
- }
- }
- // always push event to cache (issue #1112:)
- cache.push(event);
- reportEvents(cache);
- }
-
- function removeEvents(filter) {
- var oldCache = cache;
- if (!filter) { // remove all
- cache = [];
- // clear all array sources
- /*for (var i=0; i<sources.length; i++) {
- if ($.isArray(sources[i].events)) {
- sources[i].events = [];
- }
- }*/
- }else{
- if (!$.isFunction(filter)) { // an event ID
- var id = filter + '';
- filter = function(e) {
- return e._id == id;
- };
- }
- cache = $.grep(cache, filter, true);
- // remove events from array sources
- /*for (var i=0; i<sources.length; i++) {
- if ($.isArray(sources[i].events)) {
- sources[i].events = $.grep(sources[i].events, filter, true);
- }
- }*/
- }
- if(oldCache.length != cache.length)
- reportEvents(cache);
- }
-
- function clientEvents(filter) {
- if ($.isFunction(filter)) {
- return $.grep(cache, filter);
- }
- else if (filter) { // an event ID
- filter += '';
- return $.grep(cache, function(e) {
- return e._id == filter;
- });
- }
- return cache; // else, return all
- }
-
- /* Loading State
- -----------------------------------------------------------------------------*/
-
- function pushLoading() {
- if (!loadingLevel++) {
- trigger('loading', null, true);
- }
- }
-
- function popLoading() {
- if (!--loadingLevel) {
- trigger('loading', null, false);
- }
- }
-
- /* Event Normalization
- -----------------------------------------------------------------------------*/
-
- function normalizeEvent(event) {
- var source = event.source || {};
- var ignoreTimezone = firstDefined(source.ignoreTimezone, options.ignoreTimezone);
- event._id = event._id || (event.id === undefined ? '_fc' + eventGUID++ : event.id + '');
- if (event.date) {
- if (!event.start) {
- event.start = event.date;
- }
- delete event.date;
- }
- event._start = cloneDate(event.start = parseDate(event.start, ignoreTimezone));
- event.end = parseDate(event.end, ignoreTimezone);
- if (event.end && ((options.eventMode && event.end <= event.start) || (!options.eventMode && event.end < event.start))) {
- event.end = null;
- }
- event._end = event.end ? cloneDate(event.end) : null;
- if (event.allDay === undefined) {
- event.allDay = firstDefined(source.allDayDefault, options.allDayDefault);
- }
- if (event.className) {
- if (typeof event.className == 'string') {
- event.className = event.className.split(/\s+/);
- }
- }else{
- event.className = [];
- }
- // TODO: if there is no start date, return false to indicate an invalid event
- }
-
- /* Utils
- ------------------------------------------------------------------------------*/
-
- function normalizeSource(source) {
- if (source.className) {
- // TODO: repeat code, same code for event classNames
- if (typeof source.className == 'string') {
- source.className = source.className.split(/\s+/);
- }
- }else{
- source.className = [];
- }
- var normalizers = fc.sourceNormalizers;
- for (var i=0; i<normalizers.length; i++) {
- normalizers[i](source);
- }
- }
-
- function isSourcesEqual(source1, source2) {
- return source1 && source2 && getSourcePrimitive(source1) == getSourcePrimitive(source2);
- }
-
- function getSourcePrimitive(source) {
- return ((typeof source == 'object') ? (source.events || source.url) : '') || source;
- }
-}
-
-fc.addDays = addDays;
-fc.cloneDate = cloneDate;
-fc.parseDate = parseDate;
-fc.parseISO8601 = parseISO8601;
-fc.parseTime = parseTime;
-fc.formatDate = formatDate;
-fc.formatDates = formatDates;
-
-/* Date Math
------------------------------------------------------------------------------*/
-
-var dayIDs = ['sun', 'mon', 'tue', 'wed', 'thu', 'fri', 'sat'],
- DAY_MS = 86400000,
- HOUR_MS = 3600000,
- MINUTE_MS = 60000;
-
-function addYears(d, n, keepTime) {
- d.setFullYear(d.getFullYear() + n);
- if (!keepTime) {
- clearTime(d);
- }
- return d;
-}
-
-function addMonths(d, n, keepTime) { // prevents day overflow/underflow
- if (+d) { // prevent infinite looping on invalid dates
- var m = d.getMonth() + n,
- check = cloneDate(d);
- check.setDate(1);
- check.setMonth(m);
- d.setMonth(m);
- if (!keepTime) {
- clearTime(d);
- }
- while (d.getMonth() != check.getMonth()) {
- d.setDate(d.getDate() + (d < check ? 1 : -1));
- }
- }
- return d;
-}
-
-function addDays(d, n, keepTime) { // deals with daylight savings
- if (+d) {
- var dd = d.getDate() + n,
- check = cloneDate(d);
- check.setHours(9); // set to middle of day
- check.setDate(dd);
- d.setDate(dd);
- if (!keepTime) {
- clearTime(d);
- }
- fixDate(d, check);
- }
- return d;
-}
-
-function fixDate(d, check) { // force d to be on check's YMD, for daylight savings purposes
- if (+d) { // prevent infinite looping on invalid dates
- while (d.getDate() != check.getDate()) {
- d.setTime(+d + (d < check ? 1 : -1) * HOUR_MS);
- }
- }
-}
-
-function addMinutes(d, n) {
- d.setMinutes(d.getMinutes() + n);
- return d;
-}
-
-function clearTime(d) {
- d.setHours(0);
- d.setMinutes(0);
- d.setSeconds(0);
- d.setMilliseconds(0);
- return d;
-}
-
-function cloneDate(d, dontKeepTime) {
- if(d==null) {
- return null;
- }
- else if (dontKeepTime) {
- return clearTime(new Date(+d));
- }
- return new Date(+d);
-}
-
-function zeroDate() { // returns a Date with time 00:00:00 and dateOfMonth=1
- var i=0, d;
- do {
- d = new Date(1970, i++, 1);
- } while (d.getHours()); // != 0
- return d;
-}
-
-function skipWeekend(date, inc, excl) {
- inc = inc || 1;
- while (!date.getDay() || (excl && date.getDay()==1 || !excl && date.getDay()==6)) {
- addDays(date, inc);
- }
- return date;
-}
-
-function dayDiff(d1, d2) { // d1 - d2
- return Math.round((cloneDate(d1, true) - cloneDate(d2, true)) / DAY_MS);
-}
-
-function minDiff(d1, d2) { // d1 - d2
- return Math.round((cloneDate(d1, false) - cloneDate(d2, false)) / MINUTE_MS);
-}
-
-function setYMD(date, y, m, d) {
- if (y !== undefined && y != date.getFullYear()) {
- date.setDate(1);
- date.setMonth(0);
- date.setFullYear(y);
- }
- if (m !== undefined && m != date.getMonth()) {
- date.setDate(1);
- date.setMonth(m);
- }
- if (d !== undefined) {
- date.setDate(d);
- }
-}
-
-/* Date Parsing
------------------------------------------------------------------------------*/
-
-function parseDate(s, ignoreTimezone) { // ignoreTimezone defaults to true
- if (typeof s == 'object') { // already a Date object
- return s;
- }
- if (typeof s == 'number') { // a UNIX timestamp
- return new Date(s * 1000);
- }
- if (typeof s == 'string') {
- if (s.match(/^\d+(\.\d+)?$/)) { // a UNIX timestamp
- return new Date(parseFloat(s) * 1000);
- }
- if (ignoreTimezone === undefined) {
- ignoreTimezone = true;
- }
- return parseISO8601(s, ignoreTimezone) || (s ? new Date(s) : null);
- }
- // TODO: never return invalid dates (like from new Date(<string>)), return null instead
- return null;
-}
-
-function parseISO8601(s, ignoreTimezone) { // ignoreTimezone defaults to false
- // derived from http://delete.me.uk/2005/03/iso8601.html
- // TODO: for a know glitch/feature, read tests/issue_206_parseDate_dst.html
- var m = s.match(/^([0-9]{4})(-([0-9]{2})(-([0-9]{2})([T ]([0-9]{2}):([0-9]{2})(:([0-9]{2})(\.([0-9]+))?)?(Z|(([-+])([0-9]{2})(:?([0-9]{2}))?))?)?)?)?$/);
- if (!m) {
- return null;
- }
- var date = new Date(m[1], 0, 1);
- if (ignoreTimezone || !m[13]) {
- var check = new Date(m[1], 0, 1, 12, 0);
- fixDate(date, check);
- if (m[3]) {
- date.setMonth(m[3] - 1);
- check.setMonth(m[3] - 1);
- }
- if (m[5]) {
- date.setDate(m[5]);
- check.setDate(m[5]);
- }
- fixDate(date, check);
- if (m[7]) {
- date.setHours(m[7]);
- }
- if (m[8]) {
- date.setMinutes(m[8]);
- }
- if (m[10]) {
- date.setSeconds(m[10]);
- }
- if (m[12]) {
- date.setMilliseconds(Number("0." + m[12]) * 1000);
- }
- fixDate(date, check);
- }else{
- date.setUTCFullYear(
- m[1],
- m[3] ? m[3] - 1 : 0,
- m[5] || 1
- );
- date.setUTCHours(
- m[7] || 0,
- m[8] || 0,
- m[10] || 0,
- m[12] ? Number("0." + m[12]) * 1000 : 0
- );
- if (m[14]) {
- var offset = Number(m[16]) * 60 + (m[18] ? Number(m[18]) : 0);
- offset *= m[15] == '-' ? 1 : -1;
- date = new Date(+date + (offset * 60 * 1000));
- }
- }
- return date;
-}
-
-function parseTime(s) { // returns minutes since start of day
- if (typeof s == 'number') { // an hour
- return s * 60;
- }
- if (typeof s == 'object') { // a Date object
- return s.getHours() * 60 + s.getMinutes();
- }
- var m = s.match(/(\d+)(?::(\d+))?\s*(\w+)?/);
- if (m) {
- var h = parseInt(m[1], 10);
- if (m[3]) {
- h %= 12;
- if (m[3].toLowerCase().charAt(0) == 'p') {
- h += 12;
- }
- }
- return h * 60 + (m[2] ? parseInt(m[2], 10) : 0);
- }
-}
-
-/* Date Formatting
------------------------------------------------------------------------------*/
-// TODO: use same function formatDate(date, [date2], format, [options])
-
-function formatDate(date, format, options) {
- return formatDates(date, null, format, options);
-}
-
-function formatDates(date1, date2, format, options) {
- options = options || defaults;
- var date = date1,
- otherDate = date2,
- i, len = format.length, c,
- i2, formatter,
- res = '';
- for (i=0; i<len; i++) {
- c = format.charAt(i);
- if (c == "'") {
- for (i2=i+1; i2<len; i2++) {
- if (format.charAt(i2) == "'") {
- if (date) {
- if (i2 == i+1) {
- res += "'";
- }else{
- res += format.substring(i+1, i2);
- }
- i = i2;
- }
- break;
- }
- }
- }
- else if (c == '(') {
- for (i2=i+1; i2<len; i2++) {
- if (format.charAt(i2) == ')') {
- var subres = formatDate(date, format.substring(i+1, i2), options);
- if (parseInt(subres.replace(/\D/, ''), 10)) {
- res += subres;
- }
- i = i2;
- break;
- }
- }
- }
- else if (c == '[') {
- for (i2=i+1; i2<len; i2++) {
- if (format.charAt(i2) == ']') {
- var subformat = format.substring(i+1, i2);
- var subres = formatDate(date, subformat, options);
- if (subres != formatDate(otherDate, subformat, options)) {
- res += subres;
- }
- i = i2;
- break;
- }
- }
- }
- else if (c == '{') {
- date = date2;
- otherDate = date1;
- }
- else if (c == '}') {
- date = date1;
- otherDate = date2;
- }
- else {
- for (i2=len; i2>i; i2--) {
- if (formatter = dateFormatters[format.substring(i, i2)]) {
- if (date) {
- res += formatter(date, options);
- }
- i = i2 - 1;
- break;
- }
- }
- if (i2 == i) {
- if (date) {
- res += c;
- }
- }
- }
- }
- return res;
-};
-
-var dateFormatters = {
- s : function(d) {return d.getSeconds() },
- ss : function(d) {return zeroPad(d.getSeconds())},
- m : function(d) {return d.getMinutes()},
- mm : function(d) {return zeroPad(d.getMinutes())},
- h : function(d) {return d.getHours() % 12 || 12},
- hh : function(d) {return zeroPad(d.getHours() % 12 || 12)},
- H : function(d) {return d.getHours()},
- HH : function(d) {return zeroPad(d.getHours())},
- d : function(d) {return d.getDate()},
- dd : function(d) {return zeroPad(d.getDate())},
- ddd : function(d,o) {return o.dayNamesShort[d.getDay()]},
- dddd: function(d,o) {return o.dayNames[d.getDay()]},
- W : function(d) {return getWeekNumber(d)},
- M : function(d) {return d.getMonth() + 1},
- MM : function(d) {return zeroPad(d.getMonth() + 1)},
- MMM : function(d,o) {return o.monthNamesShort[d.getMonth()]},
- MMMM: function(d,o) {return o.monthNames[d.getMonth()]},
- yy : function(d) {return (d.getFullYear()+'').substring(2)},
- yyyy: function(d) {return d.getFullYear()},
- t : function(d) {return d.getHours() < 12 ? 'a' : 'p'},
- tt : function(d) {return d.getHours() < 12 ? 'am' : 'pm'},
- T : function(d) {return d.getHours() < 12 ? 'A' : 'P'},
- TT : function(d) {return d.getHours() < 12 ? 'AM' : 'PM'},
- u : function(d) {return formatDate(d, "yyyy-MM-dd'T'HH:mm:ss'Z'")},
- S : function(d) {
- var date = d.getDate();
- if (date > 10 && date < 20) {
- return 'th';
- }
- return ['st', 'nd', 'rd'][date%10-1] || 'th';
- }
-};
-
-fc.applyAll = applyAll;
-
-/* Event Date Math
------------------------------------------------------------------------------*/
-
-function exclEndDay(event) {
- if (event.end) {
- return _exclEndDay(event.end, event.allDay);
- }else{
- return addDays(cloneDate(event.start), 1);
- }
-}
-
-function _exclEndDay(end, allDay) {
- end = cloneDate(end);
- return allDay || end.getHours() || end.getMinutes() ? addDays(end, 1) : clearTime(end);
-}
-
-function segCmp(a, b) {
- return (b.msLength - a.msLength) * 100 + (a.event.start - b.event.start);
-}
-
-function segsCollide(seg1, seg2) {
- return seg1.end > seg2.start && seg1.start < seg2.end;
-}
-
-/* Event Sorting
------------------------------------------------------------------------------*/
-
-// event rendering utilities
-function sliceSegs(events, visEventEnds, start, end) {
- var segs = [],
- i, len=events.length, event,
- eventStart, eventEnd,
- segStart, segEnd,
- isStart, isEnd;
- for (i=0; i<len; i++) {
- event = events[i];
- eventStart = event.start;
- eventEnd = visEventEnds[i];
- if (eventEnd > start && eventStart < end) {
- if (eventStart < start) {
- segStart = cloneDate(start);
- isStart = false;
- }else{
- segStart = eventStart;
- isStart = true;
- }
- if (eventEnd > end) {
- segEnd = cloneDate(end);
- isEnd = false;
- }else{
- segEnd = eventEnd;
- isEnd = true;
- }
- segs.push({
- event: event,
- start: segStart,
- end: segEnd,
- isStart: isStart,
- isEnd: isEnd,
- msLength: segEnd - segStart
- });
- }
- }
- return segs.sort(segCmp);
-}
-
-// event rendering calculation utilities
-function stackSegs(segs) {
- var levels = [],
- i, len = segs.length, seg,
- j, collide, k;
- for (i=0; i<len; i++) {
- seg = segs[i];
- j = 0; // the level index where seg should belong
- while (true) {
- collide = false;
- if (levels[j]) {
- for (k=0; k<levels[j].length; k++) {
- if (segsCollide(levels[j][k], seg)) {
- collide = true;
- break;
- }
- }
- }
- if (collide) {
- j++;
- }else{
- break;
- }
- }
- if (levels[j]) {
- levels[j].push(seg);
- }else{
- levels[j] = [seg];
- }
- }
- return levels;
-}
-
-/* Event Element Binding
------------------------------------------------------------------------------*/
-
-function lazySegBind(container, segs, bindHandlers) {
- container.unbind('mouseover').mouseover(function(ev) {
- var parent=ev.target, e,
- i, seg;
- while (parent != this) {
- e = parent;
- parent = parent.parentNode;
- }
- if ((i = e._fci) !== undefined) {
- e._fci = undefined;
- seg = segs[i];
- bindHandlers(seg.event, seg.element, seg);
- $(ev.target).trigger(ev);
- }
- ev.stopPropagation();
- });
-}
-
-/* Element Dimensions
------------------------------------------------------------------------------*/
-
-function setOuterWidth(element, width, includeMargins) {
- for (var i=0, e; i<element.length; i++) {
- e = $(element[i]);
- e.width(Math.max(0, width - hsides(e, includeMargins)));
- }
-}
-
-function setOuterHeight(element, height, includeMargins) {
- for (var i=0, e; i<element.length; i++) {
- e = $(element[i]);
- e.height(Math.max(0, height - vsides(e, includeMargins)));
- }
-}
-
-function hsides(element, includeMargins) {
- return hpadding(element) + hborders(element) + (includeMargins ? hmargins(element) : 0);
-}
-
-function hpadding(element) {
- return (parseFloat($.css(element[0], 'paddingLeft', true)) || 0) +
- (parseFloat($.css(element[0], 'paddingRight', true)) || 0);
-}
-
-function hmargins(element) {
- return (parseFloat($.css(element[0], 'marginLeft', true)) || 0) +
- (parseFloat($.css(element[0], 'marginRight', true)) || 0);
-}
-
-function hborders(element) {
- return (parseFloat($.css(element[0], 'borderLeftWidth', true)) || 0) +
- (parseFloat($.css(element[0], 'borderRightWidth', true)) || 0);
-}
-
-function vsides(element, includeMargins) {
- return vpadding(element) + vborders(element) + (includeMargins ? vmargins(element) : 0);
-}
-
-function vpadding(element) {
- return (parseFloat($.css(element[0], 'paddingTop', true)) || 0) +
- (parseFloat($.css(element[0], 'paddingBottom', true)) || 0);
-}
-
-function vmargins(element) {
- return (parseFloat($.css(element[0], 'marginTop', true)) || 0) +
- (parseFloat($.css(element[0], 'marginBottom', true)) || 0);
-}
-
-function vborders(element) {
- return (parseFloat($.css(element[0], 'borderTopWidth', true)) || 0) +
- (parseFloat($.css(element[0], 'borderBottomWidth', true)) || 0);
-}
-
-function setMinHeight(element, height) {
- height = (typeof height == 'number' ? height + 'px' : height);
- element.each(function(i, _element) {
- _element.style.cssText += ';min-height:' + height + ';_height:' + height;
- // why can't we just use .css() ? i forget
- });
-}
-
-/* Misc Utils
------------------------------------------------------------------------------*/
-
-//TODO: arraySlice
-//TODO: isFunction, grep ?
-
-function noop() { }
-
-function cmp(a, b) {
- return a - b;
-}
-
-function arrayMax(a) {
- return Math.max.apply(Math, a);
-}
-
-function zeroPad(n) {
- return (n < 10 ? '0' : '') + n;
-}
-
-function smartProperty(obj, name) { // get a camel-cased/namespaced property of an object
- if (obj[name] !== undefined) {
- return obj[name];
- }
- var parts = name.split(/(?=[A-Z])/),
- i=parts.length-1, res;
- for (; i>=0; i--) {
- res = obj[parts[i].toLowerCase()];
- if (res !== undefined) {
- return res;
- }
- }
- return obj[''];
-}
-
-function htmlEscape(s) {
- return s.replace(/&/g, '&amp;')
- .replace(/</g, '&lt;')
- .replace(/>/g, '&gt;')
- .replace(/'/g, '&#039;')
- .replace(/"/g, '&quot;')
- .replace(/\n/g, '<br />');
-}
-
-function cssKey(_element) {
- return _element.id + '/' + _element.className + '/' + _element.style.cssText.replace(/(^|;)\s*(top|left|width|height)\s*:[^;]*/ig, '');
-}
-
-function disableTextSelection(element) {
- element
- .attr('unselectable', 'on')
- .css('MozUserSelect', 'none')
- .bind('selectstart.ui', function() { return false; });
-}
-
-/*
-function enableTextSelection(element) {
- element
- .attr('unselectable', 'off')
- .css('MozUserSelect', '')
- .unbind('selectstart.ui');
-}
-*/
-
-function markFirstLast(e) {
- e.children()
- .removeClass('fc-first fc-last')
- .filter(':first-child')
- .addClass('fc-first')
- .end()
- .filter(':last-child')
- .addClass('fc-last');
-}
-
-function setDayID(cell, date, opt) {
- cell.each(function(i, _cell) {
- _cell.className = _cell.className.replace(/^fc-\w*( fc-weekend-day)?/, 'fc-' + dayIDs[date.getDay()] + (opt('weekendDays').length>0 && opt('weekendDays').indexOf(date.getDay())!=-1 ? ' fc-weekend-day' : ''));
- // TODO: make a way that doesn't rely on order of classes
- });
-}
-
-function getSkinCss(event, opt) {
- var source = event.source || {};
- var eventColor = event.color;
- var sourceColor = source.color;
- var optionColor = opt('eventColor');
- var backgroundColor =
- event.backgroundColor ||
- eventColor ||
- source.backgroundColor ||
- sourceColor ||
- opt('eventBackgroundColor') ||
- optionColor;
- var borderColor =
- event.borderColor ||
- eventColor ||
- source.borderColor ||
- sourceColor ||
- opt('eventBorderColor') ||
- optionColor;
- var textColor =
- event.textColor ||
- source.textColor ||
- opt('eventTextColor');
- var statements = [];
- if (backgroundColor) {
- statements.push('background-color:' + backgroundColor);
- }
- if (borderColor) {
- statements.push('border-color:' + borderColor);
- }
- if (textColor) {
- statements.push('color:' + textColor);
- }
- return statements.join(';');
-}
-
-function applyAll(functions, thisObj, args) {
- if ($.isFunction(functions)) {
- functions = [ functions ];
- }
- if (functions) {
- var i;
- var ret;
- for (i=0; i<functions.length; i++) {
- ret = functions[i].apply(thisObj, args) || ret;
- }
- return ret;
- }
-}
-
-function firstDefined() {
- for (var i=0; i<arguments.length; i++) {
- if (arguments[i] !== undefined) {
- return arguments[i];
- }
- }
-}
-
-fcViews.month = MonthView;
-
-function MonthView(element, calendar) {
- var t = this;
-
- // exports
- t.render = render;
-
- // imports
- BasicView.call(t, element, calendar, 'month');
- var opt = t.opt;
- var renderBasic = t.renderBasic;
- var formatDate = calendar.formatDate;
-
- function render(date, delta) {
- if (delta) {
- addMonths(date, delta);
- date.setDate(1);
- }
- var start = cloneDate(date, true);
- start.setDate(1);
- var end = addMonths(cloneDate(start), 1);
- var visStart = cloneDate(start);
- var visEnd = cloneDate(end);
- var firstDay = opt('firstDay');
- var nwe = opt('weekends') ? 0 : 1;
- if (nwe) {
- skipWeekend(visStart);
- skipWeekend(visEnd, -1, true);
- }
- addDays(visStart, -((visStart.getDay() - Math.max(firstDay, nwe) + 7) % 7));
- addDays(visEnd, (7 - visEnd.getDay() + Math.max(firstDay, nwe)) % 7);
- var rowCnt = Math.round((visEnd - visStart) / (DAY_MS * 7));
- if (opt('weekMode') == 'fixed') {
- addDays(visEnd, (6 - rowCnt) * 7);
- rowCnt = 6;
- }
- t.title = formatDate(start, opt('titleFormat'));
- t.start = start;
- t.end = end;
- t.visStart = visStart;
- t.visEnd = visEnd;
- renderBasic(6, rowCnt, nwe ? 5 : 7, true);
- }
-}
-
-fcViews.multiWeek = MultiWeekView;
-
-function MultiWeekView(element, calendar) {
- var t = this;
-
- // exports
- t.render = render;
-
- // imports
- BasicView.call(t, element, calendar, 'multiWeek');
- var opt = t.opt;
- var renderBasic = t.renderBasic;
- var formatDates = calendar.formatDates;
-
- function render(date, delta) {
- if (delta) {
- addDays(date, delta * opt('multiWeekSize') * 7);
- }
- //Adjust displayed date-range, to make sure today will always stay in the top row
- var currentDate = cloneDate(new Date(), true);
- var dateWeekStart = addDays(cloneDate(date), -((date.getDay() - opt('firstDay') + 7) % 7));
- var currentWeekStart = addDays(cloneDate(currentDate), -((currentDate.getDay() - opt('firstDay') + 7) % 7));
- if(opt('multiWeekSize')>0)
- addDays(date, -(( - (Math.abs(Math.ceil(dayDiff(dateWeekStart, currentWeekStart) / 7)) % opt('multiWeekSize'))) % opt('multiWeekSize')) * 7);
-
- //var start = addDays(cloneDate(date), -((date.getDay() - opt('firstDay') + 7) % 7));
- var start = cloneDate(date);
- //var end = addDays(cloneDate(start), opt('multiWeekSize') * 7);
- //var visStart = cloneDate(start);
- var visStart = addDays(cloneDate(date), -((date.getDay() - opt('firstDay') + 7) % 7));
- var end = addDays(cloneDate(visStart), opt('multiWeekSize') * 7);
- var visEnd = cloneDate(end);
-
- var firstDay = opt('firstDay');
- var nwe = opt('weekends') ? 0 : 1;
- if (nwe) {
- skipWeekend(visStart);
- skipWeekend(visEnd, -1, true);
- }
-
- addDays(visStart, -((visStart.getDay() - Math.max(firstDay, nwe) + 7) % 7));
- addDays(visEnd, (7 - visEnd.getDay() + Math.max(firstDay, nwe)) % 7);
-
- t.title = formatDates(
- visStart,
- addDays(cloneDate(visEnd), -1),
- opt('titleFormat')
- );
- t.start = start;
- t.end = end;
- t.visStart = visStart;
- t.visEnd = visEnd;
- renderBasic(opt('multiWeekSize'), opt('multiWeekSize'), nwe ? 5 : 7, true);
- }
-}
-
-fcViews.basicWeek = BasicWeekView;
-
-function BasicWeekView(element, calendar) {
- var t = this;
-
- // exports
- t.render = render;
-
- // imports
- BasicView.call(t, element, calendar, 'basicWeek');
- var opt = t.opt;
- var renderBasic = t.renderBasic;
- var formatDates = calendar.formatDates;
-
- function render(date, delta) {
- if (delta) {
- addDays(date, delta * 7);
- }
- var start = addDays(cloneDate(date), -((date.getDay() - opt('firstDay') + 7) % 7));
- var end = addDays(cloneDate(start), 7);
- var visStart = cloneDate(start);
- var visEnd = cloneDate(end);
- var weekends = opt('weekends');
- if (!weekends) {
- skipWeekend(visStart);
- skipWeekend(visEnd, -1, true);
- }
- t.title = formatDates(
- visStart,
- addDays(cloneDate(visEnd), -1),
- opt('titleFormat')
- );
- t.start = start;
- t.end = end;
- t.visStart = visStart;
- t.visEnd = visEnd;
- renderBasic(1, 1, weekends ? 7 : 5, false);
- }
-}
-
-fcViews.basicDay = BasicDayView;
-
-//TODO: when calendar's date starts out on a weekend, shouldn't happen
-
-function BasicDayView(element, calendar) {
- var t = this;
-
- // exports
- t.render = render;
-
- // imports
- BasicView.call(t, element, calendar, 'basicDay');
- var opt = t.opt;
- var renderBasic = t.renderBasic;
- var formatDate = calendar.formatDate;
-
- function render(date, delta) {
- if (delta) {
- addDays(date, delta);
- if (!opt('weekends')) {
- skipWeekend(date, delta < 0 ? -1 : 1);
- }
- }
- t.title = formatDate(date, opt('titleFormat'));
- t.start = t.visStart = cloneDate(date, true);
- t.end = t.visEnd = addDays(cloneDate(t.start), 1);
- renderBasic(1, 1, 1, false);
- }
-}
-
-setDefaults({
- weekMode: 'fixed'
-});
-
-function BasicView(element, calendar, viewName) {
- var t = this;
-
- // exports
- t.renderBasic = renderBasic;
- t.setHeight = setHeight;
- t.setWidth = setWidth;
- t.renderDayOverlay = renderDayOverlay;
- t.defaultSelectionEnd = defaultSelectionEnd;
- t.renderSelection = renderSelection;
- t.clearSelection = clearSelection;
- t.reportDayClick = reportDayClick; // for selection (kinda hacky)
- t.dragStart = dragStart;
- t.dragStop = dragStop;
- t.defaultEventEnd = defaultEventEnd;
- t.getHoverListener = function() { return hoverListener };
- t.colContentLeft = colContentLeft;
- t.colContentRight = colContentRight;
- t.dayOfWeekCol = dayOfWeekCol;
- t.dateCell = dateCell;
- t.cellDate = cellDate;
- t.cellIsAllDay = function() { return true };
- t.allDayRow = allDayRow;
- t.allDayBounds = allDayBounds;
- t.getRowCnt = function() { return rowCnt };
- t.getColCnt = function() { return colCnt };
- t.getColWidth = function() { return colWidth };
- t.getDaySegmentContainer = function() { return daySegmentContainer };
- t.updateGrid = updateGrid;
- t.updateToday = updateToday;
- t.setAxisFormat = setAxisFormat;
- t.setStartOfBusiness = setStartOfBusiness;
- t.setEndOfBusiness = setEndOfBusiness;
- t.setWeekendDays = setWeekendDays;
- t.setBindingMode = setBindingMode;
- t.setSelectable = setSelectable;
-
- // imports
- View.call(t, element, calendar, viewName);
- OverlayManager.call(t);
- SelectionManager.call(t);
- BasicEventRenderer.call(t);
- var opt = t.opt;
- var trigger = t.trigger;
- var clearEvents = t.clearEvents;
- var renderOverlay = t.renderOverlay;
- var clearOverlays = t.clearOverlays;
- var daySelectionMousedown = t.daySelectionMousedown;
- var formatDate = calendar.formatDate;
-
- // locals
- var head;
- var headCells;
- var body;
- var bodyRows;
- var bodyCells;
- var bodyFirstCells;
- var bodyCellTopInners;
- var daySegmentContainer;
-
- var viewWidth;
- var viewHeight;
- var colWidth;
-
- var rowCnt, colCnt;
- var coordinateGrid;
- var hoverListener;
- var colContentPositions;
-
- var rtl, dis, dit;
- var firstDay;
- var nwe;
- var tm;
- var colFormat;
-
- /* Rendering
- ------------------------------------------------------------*/
-
- disableTextSelection(element.addClass('fc-grid'));
-
- function renderBasic(maxr, r, c, showNumbers) {
- rowCnt = r;
- colCnt = c;
- updateOptions();
- var firstTime = !body;
- if (firstTime) {
- buildSkeleton(maxr, showNumbers);
- }else{
- clearEvents();
- }
- updateCells(true);
- }
-
- function updateOptions() {
- rtl = opt('isRTL');
- if (rtl) {
- dis = -1;
- dit = colCnt - 1;
- }else{
- dis = 1;
- dit = 0;
- }
- firstDay = opt('firstDay');
- nwe = opt('weekends') ? 0 : 1;
- tm = opt('theme') ? 'ui' : 'fc';
- colFormat = opt('columnFormat');
- }
-
- function buildSkeleton(maxRowCnt, showNumbers) {
- var s;
- var headerClass = tm + "-widget-header";
- var contentClass = tm + "-widget-content";
- var i, j;
- var table;
-
- s =
- "<table class='fc-border-separate' style='width:100%' cellspacing='0'>" +
- "<thead>" +
- "<tr>";
- for (i=0; i<colCnt; i++) {
- s +=
- "<th class='fc- " + headerClass + "'/>"; // need fc- for setDayID
- }
- s +=
- "</tr>" +
- "</thead>" +
- "<tbody>";
- for (i=0; i<maxRowCnt; i++) {
- s +=
- "<tr class='fc-week" + i + "'>";
- for (j=0; j<colCnt; j++) {
- s +=
- "<td class='fc- " + contentClass + " fc-day" + (i*colCnt+j) + "'>" + // need fc- for setDayID
- "<div>" +
- (showNumbers ?
- "<div class='fc-day-header'><div class='fc-week-number'/><div class='fc-day-text'/><div class='fc-day-number'/></div>" :
- ''
- ) +
- "<div class='fc-day-content'>" +
- "<div style='position:relative'>&nbsp;</div>" +
- "</div>" +
- "</div>" +
- "</td>";
- }
- s +=
- "</tr>";
- }
- s +=
- "</tbody>" +
- "</table>";
- table = $(s).appendTo(element);
-
- head = table.find('thead');
- headCells = head.find('th');
- body = table.find('tbody');
- bodyRows = body.find('tr');
- bodyCells = body.find('td');
- bodyFirstCells = bodyCells.filter(':first-child');
- bodyCellTopInners = bodyRows.eq(0).find('div.fc-day-content div');
-
- markFirstLast(head.add(head.find('tr'))); // marks first+last tr/th's
- markFirstLast(bodyRows); // marks first+last td's
- bodyRows.eq(0).addClass('fc-first'); // fc-last is done in updateCells
-
- dayBind(bodyCells);
- daySegmentContainer =
- $("<div style='position:absolute;z-index:8;top:0;left:0'/>")
- .appendTo(element);
- }
-
- function updateCells(firstTime) {
- var dowDirty = firstTime || rowCnt == 1; // could the cells' day-of-weeks need updating?
- var month = t.start.getMonth();
- var today = clearTime(new Date());
- var cell;
- var date;
- var row;
-
- if (dowDirty) {
- headCells.each(function(i, _cell) {
- cell = $(_cell);
- date = indexDate(i);
- cell.html(formatDate(date, colFormat));
- setDayID(cell, date, opt);
- });
- }
-
- bodyCells.each(function(i, _cell) {
- cell = $(_cell);
- date = indexDate(i);
- if (date.getMonth() == month) {
- cell.removeClass('fc-other-month');
- }else{
- cell.addClass('fc-other-month');
- }
- if(opt('showWeekNumbers') && (i % 7 == 0)) {
- removeWeekNumber(cell, date);
- addWeekNumber(cell, date);
- }
- if (+date == +today) {
- cell.addClass(tm + '-state-highlight fc-today');
- removeTodayText(cell, opt('buttonText', 'today'));
- addTodayText(cell, opt('buttonText', 'today'));
- }else{
- cell.removeClass(tm + '-state-highlight fc-today');
- removeTodayText(cell, opt('buttonText', 'today'));
- }
- cell.find('div.fc-day-number').text(date.getDate());
- if (dowDirty) {
- setDayID(cell, date, opt);
- }
- });
-
- bodyRows.each(function(i, _row) {
- row = $(_row);
- if (i < rowCnt) {
- row.show();
- if (i == rowCnt-1) {
- row.addClass('fc-last');
- }else{
- row.removeClass('fc-last');
- }
- }else{
- row.hide();
- }
- });
- }
-
- function updateGrid()
- {
- updateToday();
- setAxisFormat();
- setStartOfBusiness();
- setEndOfBusiness();
- setWeekendDays();
- setBindingMode();
- setSelectable();
- }
-
- function updateToday()
- {
- var today = clearTime(new Date());
- var cell;
- var date;
-
- bodyCells.each(function(i, _cell) {
- cell = $(_cell);
- date = indexDate(i);
-
- if (+date == +today) {
- cell.addClass(tm + '-state-highlight fc-today');
- removeTodayText(cell, opt('buttonText', 'today'));
- addTodayText(cell, opt('buttonText', 'today'));
- }else{
- cell.removeClass(tm + '-state-highlight fc-today');
- removeTodayText(cell, opt('buttonText', 'today'));
- }
- });
- }
-
- function setAxisFormat()
- {
- // dummy
- }
-
- function setStartOfBusiness()
- {
- // dummy
- }
-
- function setEndOfBusiness()
- {
- // dummy
- }
-
- function setWeekendDays()
- {
- headCells.each(function(i, _cell) {
- setDayID($(_cell), indexDate(i), opt);
- });
-
- bodyCells.each(function(i, _cell) {
- setDayID($(_cell), indexDate(i), opt);
- });
- }
-
- function setBindingMode()
- {
- dayBind(bodyCells);
- }
-
- function setSelectable()
- {
- dayBind(bodyCells);
- }
-
- function setHeight(height) {
- viewHeight = height;
- var bodyHeight = viewHeight - head.height();
- var rowHeight;
- var rowHeightLast;
- var cell;
-
- if (opt('weekMode') == 'variable') {
- rowHeight = rowHeightLast = Math.floor(bodyHeight / (rowCnt==1 ? 2 : 6));
- }else{
- rowHeight = Math.floor(bodyHeight / rowCnt);
- rowHeightLast = bodyHeight - rowHeight * (rowCnt-1);
- }
-
- bodyFirstCells.each(function(i, _cell) {
- if (i < rowCnt) {
- cell = $(_cell);
- setMinHeight(
- cell.find('> div'),
- (i==rowCnt-1 ? rowHeightLast : rowHeight) - vsides(cell)
- );
- }
- });
- }
-
- function setWidth(width) {
- viewWidth = width;
- colContentPositions.clear();
- colWidth = Math.floor(viewWidth / colCnt);
- setOuterWidth(headCells.slice(0, -1), colWidth);
- }
-
- /* Day clicking and binding
- -----------------------------------------------------------*/
-
- function dayBind(days) {
- days.unbind('click dblclick');
- if(opt('bindingMode') == 'double')
- days.dblclick(dayClick).mousedown(daySelectionMousedown);
- else
- days.click(dayClick).mousedown(daySelectionMousedown);
- }
-
- function dayClick(ev) {
- //if (!opt('selectable')) { // if selectable, SelectionManager will worry about dayClick
- var index = parseInt(this.className.match(/fc\-day(\d+)/)[1]); // TODO: maybe use .data
- var date = indexDate(index);
- trigger('dayClick', this, date, true, ev);
- //}
- }
-
- /* Semi-transparent Overlay Helpers
- ------------------------------------------------------*/
-
- function renderDayOverlay(overlayStart, overlayEnd, refreshCoordinateGrid) { // overlayEnd is exclusive
- if (refreshCoordinateGrid) {
- coordinateGrid.build();
- }
- var rowStart = cloneDate(t.visStart);
- var rowEnd = addDays(cloneDate(rowStart), colCnt);
- for (var i=0; i<rowCnt; i++) {
- var stretchStart = new Date(Math.max(rowStart, overlayStart));
- var stretchEnd = new Date(Math.min(rowEnd, overlayEnd));
- if (stretchStart < stretchEnd) {
- var colStart, colEnd;
- if (rtl) {
- colStart = dayDiff(stretchEnd, rowStart)*dis+dit+1;
- colEnd = dayDiff(stretchStart, rowStart)*dis+dit+1;
- }else{
- colStart = dayDiff(stretchStart, rowStart);
- colEnd = dayDiff(stretchEnd, rowStart);
- }
- dayBind(
- renderCellOverlay(i, colStart, i, colEnd-1)
- );
- }
- addDays(rowStart, 7);
- addDays(rowEnd, 7);
- }
- }
-
- function renderCellOverlay(row0, col0, row1, col1) { // row1,col1 is inclusive
- var rect = coordinateGrid.rect(row0, col0, row1, col1, element);
- return renderOverlay(rect, element);
- }
-
- /* Selection
- -----------------------------------------------------------------------*/
-
- function defaultSelectionEnd(startDate, allDay) {
- return cloneDate(startDate);
- }
-
- function renderSelection(startDate, endDate, allDay) {
- renderDayOverlay(startDate, addDays(cloneDate(endDate), 1), true); // rebuild every time???
- }
-
- function clearSelection() {
- clearOverlays();
- }
-
- function reportDayClick(date, allDay, ev) {
- var cell = dateCell(date);
- var _element = bodyCells[cell.row*colCnt + cell.col];
- trigger('dayClick', _element, date, allDay, ev);
- }
-
- /* External Dragging
- -----------------------------------------------------------------------*/
-
- function dragStart(_dragElement, ev, ui) {
- hoverListener.start(function(cell) {
- clearOverlays();
- if (cell) {
- renderCellOverlay(cell.row, cell.col, cell.row, cell.col);
- }
- }, ev);
- }
-
- function dragStop(_dragElement, ev, ui) {
- var cell = hoverListener.stop();
- clearOverlays();
- if (cell) {
- var d = cellDate(cell);
- trigger('drop', _dragElement, d, true, ev, ui);
- }
- }
-
- /* Utilities
- --------------------------------------------------------*/
-
- function defaultEventEnd(event) {
- return cloneDate(event.start);
- }
-
- coordinateGrid = new CoordinateGrid(function(rows, cols) {
- var e, n, p;
- headCells.each(function(i, _e) {
- e = $(_e);
- n = e.offset().left;
- if (i) {
- p[1] = n;
- }
- p = [n];
- cols[i] = p;
- });
- p[1] = n + e.outerWidth();
- bodyRows.each(function(i, _e) {
- if (i < rowCnt) {
- e = $(_e);
- n = e.offset().top;
- if (i) {
- p[1] = n;
- }
- p = [n];
- rows[i] = p;
- }
- });
- p[1] = n + e.outerHeight();
- });
-
- hoverListener = new HoverListener(coordinateGrid);
-
- colContentPositions = new HorizontalPositionCache(function(col) {
- return bodyCellTopInners.eq(col);
- });
-
- function colContentLeft(col) {
- return colContentPositions.left(col);
- }
-
- function colContentRight(col) {
- return colContentPositions.right(col);
- }
-
- function dateCell(date) {
- return {
- row: Math.floor(dayDiff(date, t.visStart) / 7),
- col: dayOfWeekCol(date.getDay())
- };
- }
-
- function cellDate(cell) {
- return _cellDate(cell.row, cell.col);
- }
-
- function _cellDate(row, col) {
- return addDays(cloneDate(t.visStart), row*7 + col*dis+dit);
- // what about weekends in middle of week?
- }
-
- function indexDate(index) {
- return _cellDate(Math.floor(index/colCnt), index%colCnt);
- }
-
- function dayOfWeekCol(dayOfWeek) {
- return ((dayOfWeek - Math.max(firstDay, nwe) + colCnt) % colCnt) * dis + dit;
- }
-
- function allDayRow(i) {
- return bodyRows.eq(i);
- }
-
- function allDayBounds(i) {
- return {
- left: 0,
- right: viewWidth
- };
- }
-
-}
-
-function BasicEventRenderer() {
- var t = this;
-
- // exports
- t.renderEvents = renderEvents;
- t.compileDaySegs = compileSegs; // for DayEventRenderer
- t.clearEvents = clearEvents;
- t.bindDaySeg = bindDaySeg;
-
- // imports
- DayEventRenderer.call(t);
- var opt = t.opt;
- var trigger = t.trigger;
- //var setOverflowHidden = t.setOverflowHidden;
- var isEventDraggable = t.isEventDraggable;
- var isEventResizable = t.isEventResizable;
- var reportEvents = t.reportEvents;
- var reportEventClear = t.reportEventClear;
- var eventElementHandlers = t.eventElementHandlers;
- var showEvents = t.showEvents;
- var hideEvents = t.hideEvents;
- var eventDrop = t.eventDrop;
- var getDaySegmentContainer = t.getDaySegmentContainer;
- var getHoverListener = t.getHoverListener;
- var renderDayOverlay = t.renderDayOverlay;
- var clearOverlays = t.clearOverlays;
- var getRowCnt = t.getRowCnt;
- var getColCnt = t.getColCnt;
- var renderDaySegs = t.renderDaySegs;
- var resizableDayEvent = t.resizableDayEvent;
-
- /* Rendering
- --------------------------------------------------------------------*/
-
- function renderEvents(events, modifiedEventId) {
- reportEvents(events);
- renderDaySegs(compileSegs(events), modifiedEventId, false);
- }
-
- function clearEvents() {
- reportEventClear();
- getDaySegmentContainer().empty();
- }
-
- function compileSegs(events) {
- var rowCnt = getRowCnt(),
- colCnt = getColCnt(),
- d1 = cloneDate(t.visStart),
- d2 = addDays(cloneDate(d1), colCnt),
- visEventsEnds = $.map(events, exclEndDay),
- i, row,
- j, level,
- k, seg,
- segs=[];
- for (i=0; i<rowCnt; i++) {
- row = stackSegs(sliceSegs(events, visEventsEnds, d1, d2));
- for (j=0; j<row.length; j++) {
- level = row[j];
- for (k=0; k<level.length; k++) {
- seg = level[k];
- seg.row = i;
- seg.level = j; // not needed anymore
- segs.push(seg);
- }
- }
- addDays(d1, 7);
- addDays(d2, 7);
- }
- return segs;
- }
-
- function bindDaySeg(event, eventElement, seg) {
- if (isEventDraggable(event)) {
- draggableDayEvent(event, eventElement);
- }
- if (seg.isEnd && isEventResizable(event)) {
- resizableDayEvent(event, eventElement, seg);
- }
- eventElementHandlers(event, eventElement);
- // needs to be after, because resizableDayEvent might stopImmediatePropagation on click
- }
-
- /* Dragging
- ----------------------------------------------------------------------------*/
-
- function draggableDayEvent(event, eventElement) {
- var hoverListener = getHoverListener();
- var dayDelta;
- eventElement.draggable({
- zIndex: 9,
- delay: 50,
- scroll: false,
- opacity: opt('dragOpacity'),
- revertDuration: opt('dragRevertDuration'),
- start: function(ev, ui) {
- trigger('eventDragStart', eventElement, event, ev, ui);
- //hideEvents(event, eventElement);
- hoverListener.start(function(cell, origCell, rowDelta, colDelta) {
- eventElement.draggable('option', 'revert', !cell || !rowDelta && !colDelta);
- clearOverlays();
- if (cell) {
- //setOverflowHidden(true);
- dayDelta = rowDelta*7 + colDelta * (opt('isRTL') ? -1 : 1);
- renderDayOverlay(
- addDays(cloneDate(event.start), dayDelta),
- addDays(exclEndDay(event), dayDelta)
- );
- }else{
- //setOverflowHidden(false);
- dayDelta = 0;
- }
- }, ev, 'drag');
- },
- stop: function(ev, ui) {
- hoverListener.stop();
- clearOverlays();
- trigger('eventDragStop', eventElement, event, ev, ui);
- if (dayDelta) {
- eventDrop(this, event, dayDelta, 0, event.allDay, ev, ui);
- }else{
- eventElement.css('filter', ''); // clear IE opacity side-effects
- //showEvents(event, eventElement);
- }
- //setOverflowHidden(false);
- }
- });
- }
-}
-
-fcViews.agendaWeek = AgendaWeekView;
-
-function AgendaWeekView(element, calendar) {
- var t = this;
-
- // exports
- t.render = render;
-
- // imports
- AgendaView.call(t, element, calendar, 'agendaWeek');
- var opt = t.opt;
- var renderAgenda = t.renderAgenda;
- var formatDates = calendar.formatDates;
-
- function render(date, delta) {
- if (delta) {
- addDays(date, delta * 7);
- }
- var start = addDays(cloneDate(date), -((date.getDay() - opt('firstDay') + 7) % 7));
- var end = addDays(cloneDate(start), 7);
- var visStart = cloneDate(start);
- var visEnd = cloneDate(end);
- var weekends = opt('weekends');
- if (!weekends) {
- skipWeekend(visStart);
- skipWeekend(visEnd, -1, true);
- }
- t.title = formatDates(
- visStart,
- addDays(cloneDate(visEnd), -1),
- opt('titleFormat')
- );
- t.start = start;
- t.end = end;
- t.visStart = visStart;
- t.visEnd = visEnd;
- renderAgenda(weekends ? 7 : 5);
- }
-}
-
-fcViews.agendaDay = AgendaDayView;
-
-function AgendaDayView(element, calendar) {
- var t = this;
-
- // exports
- t.render = render;
- t.addedView = null;
-
- // imports
- AgendaView.call(t, element, calendar, 'agendaDay');
- var opt = t.opt;
- var renderAgenda = t.renderAgenda;
- var formatDate = calendar.formatDate;
-
- function render(date, delta) {
- if (delta) {
- addDays(date, delta);
- if (!opt('weekends')) {
- skipWeekend(date, delta < 0 ? -1 : 1);
- }
- }
- var start = cloneDate(date, true);
- var end = addDays(cloneDate(start), 1);
- t.title = formatDate(date, opt('titleFormat'));
- t.start = t.visStart = start;
- t.end = t.visEnd = end;
- renderAgenda(1);
-
- if(t.addedView) {
- t.addedView.render(date);
- }
- }
-}
-
-setDefaults({
- allDaySlot: true,
- allDayText: 'all-day',
- firstHour: 6,
- slotMinutes: 30,
- defaultEventMinutes: 120,
- axisFormat: 'h(:mm)tt',
- timeFormat: {
- agenda: 'h:mm{ – h:mm}'
- },
- dragOpacity: {
- agenda: .5
- },
- minTime: 0,
- maxTime: 24
-});
-
-// TODO: make it work in quirks mode (event corners, all-day height)
-// TODO: test liquid width, especially in IE6
-
-function AgendaView(element, calendar, viewName) {
- var t = this;
-
- // exports
- t.renderAgenda = renderAgenda;
- t.setWidth = setWidth;
- t.setHeight = setHeight;
- t.beforeHide = beforeHide;
- t.afterShow = afterShow;
- t.defaultEventEnd = defaultEventEnd;
- t.timePosition = timePosition;
- t.dayOfWeekCol = dayOfWeekCol;
- t.dateCell = dateCell;
- t.cellDate = cellDate;
- t.cellIsAllDay = cellIsAllDay;
- t.allDayRow = getAllDayRow;
- t.allDayBounds = allDayBounds;
- t.getHoverListener = function() { return hoverListener };
- t.colContentLeft = colContentLeft;
- t.colContentRight = colContentRight;
- t.getDaySegmentContainer = function() { return daySegmentContainer };
- t.getSlotJumpersTop = function() { return slotJumpersTop };
- t.getSlotJumpersBottom = function() { return slotJumpersBottom };
- t.getslotScroller = function() { return slotScroller };
- t.getSlotContent = function() { return slotContent };
- t.getSlotSegmentContainer = function() { return slotSegmentContainer };
- t.getMinMinute = function() { return minMinute };
- t.getMaxMinute = function() { return maxMinute };
- t.getBodyContent = function() { return slotContent }; // !!??
- t.getRowCnt = function() { return 1 };
- t.getColCnt = function() { return colCnt };
- t.getColWidth = function() { return colWidth };
- t.getSlotHeight = function() { return slotHeight };
- t.defaultSelectionEnd = defaultSelectionEnd;
- t.renderDayOverlay = renderDayOverlay;
- t.renderSelection = renderSelection;
- t.renderSlotSelection = renderSlotSelection;
- t.clearSelection = clearSelection;
- t.reportDayClick = reportDayClick; // selection mousedown hack
- t.dragStart = dragStart;
- t.dragStop = dragStop;
- t.updateGrid = updateGrid;
- t.updateToday = updateToday;
- t.setAxisFormat = setAxisFormat;
- t.setStartOfBusiness = setStartOfBusiness;
- t.setEndOfBusiness = setEndOfBusiness;
- t.setWeekendDays = setWeekendDays;
- t.setBindingMode = setBindingMode;
- t.setSelectable = setSelectable;
-
- // imports
- View.call(t, element, calendar, viewName);
- OverlayManager.call(t);
- SelectionManager.call(t);
- AgendaEventRenderer.call(t);
- var opt = t.opt;
- var trigger = t.trigger;
- var clearEvents = t.clearEvents;
- var renderOverlay = t.renderOverlay;
- var clearOverlays = t.clearOverlays;
- var reportSelection = t.reportSelection;
- var unselect = t.unselect;
- var daySelectionMousedown = t.daySelectionMousedown;
- var slotSegHtml = t.slotSegHtml;
- var formatDate = calendar.formatDate;
- var setTimeIndicator = t.setTimeIndicator;
-
- // locals
- var dayTable;
- var dayHead;
- var dayHeadCells;
- var dayBody;
- var dayBodyCells;
- var dayBodyCellInners;
- var dayBodyFirstCell;
- var dayBodyFirstCellStretcher;
- var slotLayer;
- var daySegmentContainer;
- var allDayTable;
- var allDayRow;
- var slotJumpersTopContainer;
- var slotJumpersTop;
- var slotJumpersBottomContainer;
- var slotJumpersBottom;
- var slotScroller;
- var slotContent;
- var slotSegmentContainer;
- var dayScroller;
- var dayContent;
- var daySegmentContainer;
- var slotTable;
- var slotTableFirstInner;
- var axisFirstCells;
- var gutterCells;
- var divider;
- var selectionHelper;
- var viewWidth;
- var viewHeight;
- var axisWidth;
- var colWidth;
- var gutterWidth;
- //var gutterAck = false;
- var slotHeight; // TODO: what if slotHeight changes? (see issue 650)
- var savedScrollTop;
- var colCnt;
- var slotCnt;
- var coordinateGrid;
- var hoverListener;
- var colContentPositions;
- var slotTopCache = {};
- var tm;
- var firstDay;
- var nwe; // no weekends (int)
- var rtl, dis, dit; // day index sign / translate
- var minMinute, maxMinute;
- var colFormat;
-
- /* Rendering
- -----------------------------------------------------------------------------*/
-
- disableTextSelection(element.addClass('fc-agenda'));
-
- function renderAgenda(c) {
- colCnt = c;
- updateOptions();
- if (!dayTable) {
- buildSkeleton();
- }else{
- clearEvents();
- }
- updateCells();
- }
-
- function updateOptions() {
- tm = opt('theme') ? 'ui' : 'fc';
- nwe = opt('weekends') ? 0 : 1;
- firstDay = opt('firstDay');
- if (rtl = opt('isRTL')) {
- dis = -1;
- dit = colCnt - 1;
- }else{
- dis = 1;
- dit = 0;
- }
- minMinute = parseTime(opt('minTime'));
- maxMinute = parseTime(opt('maxTime'));
- colFormat = opt('columnFormat');
- }
-
- function buildSkeleton() {
- var headerClass = tm + "-widget-header";
- var contentClass = tm + "-widget-content";
- var s;
- var i;
- var d;
- var maxd;
- var minutes;
- var slotNormal = opt('slotMinutes') % 15 == 0;
-
- s =
- "<table style='width:100%' class='fc-agenda-days fc-border-separate' cellspacing='0'>" +
- "<thead>" +
- "<tr>" +
- "<th class='fc-agenda-axis " + headerClass + "'><div class='fc-week-number'/></th>";
- for (i=0; i<colCnt; i++) {
- s +=
- "<th class='fc- fc-col" + i + ' ' + headerClass + "'/>"; // fc- needed for setDayID
- }
- s +=
- "<th class='fc-agenda-gutter " + headerClass + "'>&nbsp;</th>" +
- "</tr>" +
- "</thead>" +
- "<tbody>" +
- "<tr>" +
- "<th class='fc-agenda-axis " + headerClass + "'>&nbsp;</th>";
- for (i=0; i<colCnt; i++) {
- s +=
- "<td class='fc- fc-col" + i + ' ' + contentClass + "'>" + // fc- needed for setDayID
- "<div>" +
- "<div class='fc-day-content'>" +
- "<div style='position:relative'>&nbsp;</div>" +
- "</div>" +
- "</div>" +
- "</td>";
- }
- s +=
- "<td class='fc-agenda-gutter " + contentClass + "'>&nbsp;</td>" +
- "</tr>" +
- "</tbody>" +
- "</table>";
- dayTable = $(s).appendTo(element);
- dayHead = dayTable.find('thead');
- dayHeadCells = dayHead.find('th').slice(1, -1);
- dayBody = dayTable.find('tbody');
- dayBodyCells = dayBody.find('td').slice(0, -1);
- dayBodyCellInners = dayBodyCells.find('div.fc-day-content div');
- dayBodyFirstCell = dayBodyCells.eq(0);
- dayBodyFirstCellStretcher = dayBodyFirstCell.find('> div');
-
- markFirstLast(dayHead.add(dayHead.find('tr')));
- markFirstLast(dayBody.add(dayBody.find('tr')));
-
- axisFirstCells = dayHead.find('th:first');
- gutterCells = dayTable.find('.fc-agenda-gutter');
-
- slotLayer =
- $("<div style='position:absolute;z-index:2;left:0;width:100%'/>")
- .appendTo(element);
-
- if(opt('allDaySlot')) {
- dayScroller = $("<div style='position:absolute;width:100%;overflow-x:hidden;overflow-y:auto;'/>").appendTo(slotLayer);
- dayContent = $("<div style='position:relative;width:100%;overflow:hidden;min-height:37px'/>").appendTo(dayScroller);
- daySegmentContainer = $("<div style='position:absolute;z-index:8;top:0;left:0'/>").appendTo(dayContent);
-
- s =
- "<table style='width:100%;' class='fc-agenda-allday' cellspacing='0'>" +
- "<tr>" +
- "<th class='" + headerClass + " fc-agenda-axis'>" + opt('allDayText') + "</th>" +
- "<td>" +
- "<div class='fc-day-content'><div style='position:relative;min-height:34px'/></div>" +
- "</td>" +
- "</tr>" +
- "</table>";
-
- allDayTable = $(s).appendTo(dayScroller);
- allDayRow = allDayTable.find('tr');
- dayBind(allDayRow.find('td'));
- axisFirstCells = axisFirstCells.add(allDayTable.find('th:first'));
- gutterCells = gutterCells.add(allDayTable.find('th.fc-agenda-gutter'));
-
- divider = $(
- "<div class='fc-agenda-divider " + headerClass + "'>" +
- "<div class='fc-agenda-divider-inner'/>" +
- "</div>"
- ).appendTo(slotLayer);
-
- }else{
- daySegmentContainer = $([]); // in jQuery 1.4, we can just do $()
- }
-
- slotJumpersTopContainer = $("<div style='position:relative;width:100%;'/>").appendTo(slotLayer);
- slotJumpersBottomContainer = $("<div style='position:relative;width:100%;'/>").appendTo(slotLayer);
- slotScroller = $("<div style='position:absolute;width:100%;overflow-x:hidden;overflow-y:auto'/>").appendTo(slotLayer);
- slotContent = $("<div style='position:relative;width:100%;overflow:hidden'/>").appendTo(slotScroller);
- slotSegmentContainer = $("<div style='position:absolute;z-index:8;top:0;left:0'/>").appendTo(slotContent);
-
- for (i=0; i<colCnt; i++) {
- slotJumpersTopContainer.append($('<div class="fc-slot-jumper-top"/>'));
- slotJumpersBottomContainer.append($('<div class="fc-slot-jumper-bottom"/>'));
- }
- slotJumpersTop = slotJumpersTopContainer.children();
- slotJumpersBottom = slotJumpersBottomContainer.children();
-
- s =
- "<table class='fc-agenda-slots' style='width:100%' cellspacing='0'>" +
- "<tbody>";
- d = zeroDate();
- maxd = addMinutes(cloneDate(d), maxMinute);
- addMinutes(d, minMinute);
- slotCnt = 0;
-
- var startOfBusiness = opt("startOfBusiness") * (60/opt("slotMinutes"));
- var endOfBusiness = (opt("endOfBusiness") - (opt("slotMinutes")/60)) * (60/opt("slotMinutes"));
- for (i=0; d < maxd; i++) {
- minutes = d.getMinutes();
- var nonBusinessHours = (i < startOfBusiness || i > endOfBusiness) ? " fc-non-business-hours" : "";
- s +=
- "<tr class='fc-slot" + i + ' ' + (!minutes ? '' : 'fc-minor') + nonBusinessHours + "'>" +
- "<th class='fc-agenda-axis " + headerClass + "'>" +
- ((!slotNormal || !minutes) ? formatDate(d, opt('axisFormat')) : '&nbsp;') +
- "</th>" +
- "<td class='" + contentClass + "'>" +
- "<div style='position:relative'>&nbsp;</div>" +
- "</td>" +
- "</tr>";
- addMinutes(d, opt('slotMinutes'));
- slotCnt++;
- }
- s +=
- "</tbody>" +
- "</table>";
- slotTable = $(s).appendTo(slotContent);
- slotTableFirstInner = slotTable.find('div:first');
- slotBind(slotTable.find('td'));
- axisFirstCells = axisFirstCells.add(slotTable.find('th:first'));
- }
-
- function updateCells() {
- var i;
- var headCell;
- var bodyCell;
- var axisCell;
- var date;
- var today = clearTime(new Date());
- axisCell = axisFirstCells[0];
-
- if(opt('showWeekNumbers')) {
- removeWeekNumber($(axisCell), colDate(0));
- addWeekNumber($(axisCell), colDate(0));
- }
- for (i=0; i<colCnt; i++) {
- date = colDate(i);
- headCell = dayHeadCells.eq(i);
- headCell.html(formatDate(date, colFormat));
- bodyCell = dayBodyCells.eq(i);
- setDayID(headCell.add(bodyCell), date, opt);
- if (+date == +today) {
- bodyCell.addClass(tm + '-state-highlight fc-today');
- addTodayClass(bodyCell);
- }else{
- bodyCell.removeClass(tm + '-state-highlight fc-today');
- removeTodayClass(bodyCell);
- }
- }
- }
-
- function updateGrid()
- {
- updateToday();
- setTimeIndicator();
- setAxisFormat();
- setStartOfBusiness();
- setEndOfBusiness();
- setWeekendDays();
- setBindingMode();
- setSelectable();
- }
-
- function updateToday()
- {
- var i;
- var bodyCell;
- var date;
- var today = clearTime(new Date());
- for (i=0; i<colCnt; i++) {
- date = colDate(i);
- bodyCell = dayBodyCells.eq(i);
- if (+date == +today) {
- bodyCell.addClass(tm + '-state-highlight fc-today');
- addTodayClass(bodyCell);
- }else{
- bodyCell.removeClass(tm + '-state-highlight fc-today');
- removeTodayClass(bodyCell);
- }
- }
- }
-
- function setAxisFormat()
- {
- var slotNormal = opt('slotMinutes') % 15 == 0;
- var d = zeroDate();
- addMinutes(d, minMinute);
-
- slotTable.find('th').each(function(index, element){
- var minutes = d.getMinutes();
- $(element).html((!slotNormal || !minutes) ? formatDate(d, opt('axisFormat')) : '&nbsp;');
- addMinutes(d, opt('slotMinutes'));
- });
- }
-
- function setStartOfBusiness()
- {
- updateBusinessHours();
- }
-
- function setEndOfBusiness()
- {
- updateBusinessHours();
- }
-
- function updateBusinessHours()
- {
- var startOfBusiness = opt("startOfBusiness") * (60/opt("slotMinutes"));
- var endOfBusiness = (opt("endOfBusiness") - (opt("slotMinutes")/60)) * (60/opt("slotMinutes"));
- slotTable.find('tr').each(function(index, element){
- if(index < startOfBusiness || index > endOfBusiness)
- $(element).addClass('fc-non-business-hours');
- else
- $(element).removeClass('fc-non-business-hours');
- });
- }
-
- function setWeekendDays()
- {
- dayHeadCells.each(function(i, _cell) {
- setDayID($(_cell), colDate(i), opt);
- });
-
- dayBodyCells.each(function(i, _cell) {
- setDayID($(_cell), colDate(i), opt);
- });
- }
-
- function setBindingMode()
- {
- dayBind(allDayRow.find('td'));
- slotBind(slotTable.find('td'));
- }
-
- function setSelectable()
- {
- dayBind(allDayRow.find('td'));
- slotBind(slotTable.find('td'));
- }
-
- function setHeight(height, dateChanged) {
- if (height === undefined) {
- height = viewHeight;
- }
- viewHeight = height;
- slotTopCache = {};
-
- var headHeight = dayBody.position().top;
- var allDayHeight = opt('allDaySlot') ? 4 : 0; //if divider is present
- var bodyHeight = Math.min( // total body height, including borders
- height - headHeight, // when scrollbars
- slotTable.height() + allDayHeight + 1 // when no scrollbars. +1 for bottom border
- );
-
- var maxAllDayHeight = Math.floor((bodyHeight - allDayHeight - 1) / 3);
- dayScroller.css('max-height', maxAllDayHeight + 3);
- allDayRow.find('div:first').children().css('max-height', maxAllDayHeight);
-
- allDayHeight = allDayTable.height();
- if(opt('allDaySlot')) {
- divider.css('position', 'relative');
- divider.css('top', allDayHeight);
- slotScroller.css('top', allDayHeight + 4);
- }
-
- //allDayHeight = slotScroller.position().top; // including divider
- bodyHeight = Math.min( // total body height, including borders
- height - headHeight, // when scrollbars
- slotTable.height() + allDayHeight + 1 // when no scrollbars. +1 for bottom border
- );
-
- dayBodyFirstCellStretcher
- .height(bodyHeight - vsides(dayBodyFirstCell));
-
- var slotScrollerHeight = bodyHeight - allDayHeight - 1 - (opt('allDaySlot') ? 4 : 0);
- slotLayer.css('top', headHeight);
- slotScroller.height(slotScrollerHeight);
- slotHeight = slotTableFirstInner.height() + 1; // +1 for border
-
- slotJumpersTopContainer.css('top', allDayHeight+1);
- slotJumpersBottomContainer.css('top', slotScrollerHeight + allDayHeight + 1 - slotJumpersBottom.first().height());
-
- if (dateChanged) {
- resetScroll();
- }
-
- if(t.addedView) {
- t.addedView.setHeight(height, dateChanged);
- }
- }
-
- function setWidth(width) {
- if (width === undefined) {
- width = viewWidth;
- }
- viewWidth = width;
- if(t.addedView) {
- var outerWidth = Math.floor(element.parent().width() / 2);
- element.css({'width' : outerWidth});
- viewWidth = outerWidth;
- }
- colContentPositions.clear();
-
- axisWidth = 0;
- setOuterWidth(
- axisFirstCells
- .width('')
- .each(function(i, _cell) {
- axisWidth = Math.max(axisWidth, $(_cell).outerWidth());
- }),
- axisWidth
- );
-
- var slotTableWidth = slotScroller[0].clientWidth; // needs to be done after axisWidth (for IE7)
- //slotTable.width(slotTableWidth);
-
- //var oldGutterWidth = gutterWidth;
- gutterWidth = slotScroller.width() - slotTableWidth || dayScroller.width() - dayContent.width();
- if (gutterWidth) {
- /*if(!gutterAck) {
- viewWidth -= gutterWidth;
- gutterAck = true;
- }*/
- setOuterWidth(gutterCells, gutterWidth);
- gutterCells
- .show()
- .prev()
- .removeClass('fc-last');
- }else{
- /*if(gutterAck) {
- viewWidth += oldGutterWidth;
- gutterAck = false;
- }*/
- gutterCells
- .hide()
- .prev()
- .addClass('fc-last');
- }
-
- colWidth = Math.floor((slotTableWidth - axisWidth) / colCnt);
- setOuterWidth(dayHeadCells.slice(0, -1), colWidth);
-
- slotJumpersTop.each(function(i,e){
- var jumper=$(e);
- jumper.css('left',axisWidth + (colWidth*(i+1)) - 1 - jumper.width());
- });
- slotJumpersBottom.each(function(i,e){
- var jumper=$(e);
- jumper.css('left',axisWidth + (colWidth*(i+1)) - 1 - jumper.width());
- });
-
- if(t.addedView) {
- t.addedView.setWidth(outerWidth);
- }
- }
-
- function resetScroll() {
- var d0 = zeroDate();
- var scrollDate = cloneDate(d0);
- scrollDate.setHours(opt('firstHour'));
- var top = timePosition(d0, scrollDate) + 1; // +1 for the border
- function scroll() {
- slotScroller.scrollTop(top);
- }
- scroll();
- setTimeout(scroll, 0); // overrides any previous scroll state made by the browser
- }
-
- function beforeHide() {
- savedScrollTop = slotScroller.scrollTop();
- }
-
- function afterShow() {
- slotScroller.scrollTop(savedScrollTop);
- }
-
- /* Slot/Day clicking and binding
- -----------------------------------------------------------------------*/
-
- function dayBind(cells) {
- cells.unbind('click dblclick');
- if(opt('bindingMode') == 'double')
- cells.dblclick(daySlotClick).mousedown(daySelectionMousedown);
- else
- cells.click(daySlotClick).mousedown(daySelectionMousedown);
- }
-
- function slotBind(cells) {
- cells.unbind('click dblclick');
- if(opt('bindingMode') == 'double')
- cells.dblclick(slotClick).mousedown(slotSelectionMousedown);
- else
- cells.click(slotClick).mousedown(slotSelectionMousedown);
- }
-
- function daySlotClick(ev) {
- var col = Math.min(colCnt-1, Math.floor((ev.pageX - dayTable.offset().left - axisWidth) / colWidth));
- var date = colDate(col);
- trigger('dayClick', dayBodyCells[col], date, true, ev);
- }
-
- function slotClick(ev) {
- //if (!opt('selectable')) { // if selectable, SelectionManager will worry about dayClick
- var col = Math.min(colCnt-1, Math.floor((ev.pageX - dayTable.offset().left - axisWidth) / colWidth));
- var date = colDate(col);
- var rowMatch = this.parentNode.className.match(/fc-slot(\d+)/); // TODO: maybe use data
- if (rowMatch) {
- var mins = parseInt(rowMatch[1]) * opt('slotMinutes');
- var hours = Math.floor(mins/60);
- date.setHours(hours);
- date.setMinutes(mins%60 + minMinute);
- trigger('dayClick', dayBodyCells[col], date, false, ev);
- }else{
- trigger('dayClick', dayBodyCells[col], date, true, ev);
- }
- //}
- }
-
- /* Semi-transparent Overlay Helpers
- -----------------------------------------------------*/
-
- function renderDayOverlay(startDate, endDate, refreshCoordinateGrid) { // endDate is exclusive
- if (refreshCoordinateGrid) {
- coordinateGrid.build();
- }
- var visStart = cloneDate(t.visStart);
- var startCol, endCol;
- if (rtl) {
- startCol = dayDiff(endDate, visStart)*dis+dit+1;
- endCol = dayDiff(startDate, visStart)*dis+dit+1;
- }else{
- startCol = dayDiff(startDate, visStart);
- endCol = dayDiff(endDate, visStart);
- }
- startCol = Math.max(0, startCol);
- endCol = Math.min(colCnt, endCol);
- if (startCol < endCol) {
- dayBind(
- renderCellOverlay(0, startCol, 0, endCol-1)
- );
- }
- }
-
- function renderCellOverlay(row0, col0, row1, col1) { // only for all-day?
- var rect = coordinateGrid.rect(row0, col0, row1, col1, slotLayer);
- return renderOverlay(rect, slotLayer);
- }
-
- function renderSlotOverlay(overlayStart, overlayEnd) {
- var dayStart = cloneDate(t.visStart);
- var dayEnd = addDays(cloneDate(dayStart), 1);
- for (var i=0; i<colCnt; i++) {
- var stretchStart = new Date(Math.max(dayStart, overlayStart));
- var stretchEnd = new Date(Math.min(dayEnd, overlayEnd));
- if (stretchStart < stretchEnd) {
- var col = i*dis+dit;
- var rect = coordinateGrid.rect(0, col, 0, col, slotContent); // only use it for horizontal coords
- var top = timePosition(dayStart, stretchStart);
- var bottom = timePosition(dayStart, stretchEnd);
- rect.top = top;
- rect.height = bottom - top;
- slotBind(
- renderOverlay(rect, slotContent)
- );
- }
- addDays(dayStart, 1);
- addDays(dayEnd, 1);
- }
- }
-
- /* Coordinate Utilities
- -----------------------------------------------------------------------------*/
-
- coordinateGrid = new CoordinateGrid(function(rows, cols) {
- var e, n, p;
- dayHeadCells.each(function(i, _e) {
- e = $(_e);
- n = e.offset().left;
- if (i) {
- p[1] = n;
- }
- p = [n];
- cols[i] = p;
- });
- p[1] = n + e.outerWidth();
- if (opt('allDaySlot')) {
- e = allDayRow;
- n = e.offset().top;
- rows[0] = [n, n+e.outerHeight()];
- }
- var slotTableTop = slotContent.offset().top;
- var slotScrollerTop = slotScroller.offset().top;
- var slotScrollerBottom = slotScrollerTop + slotScroller.outerHeight();
- function constrain(n) {
- return Math.max(slotScrollerTop, Math.min(slotScrollerBottom, n));
- }
- for (var i=0; i<slotCnt; i++) {
- rows.push([
- constrain(slotTableTop + slotHeight*i),
- constrain(slotTableTop + slotHeight*(i+1))
- ]);
- }
- });
-
- hoverListener = new HoverListener(coordinateGrid);
-
- colContentPositions = new HorizontalPositionCache(function(col) {
- return dayBodyCellInners.eq(col);
- });
-
- function colContentLeft(col) {
- return colContentPositions.left(col);
- }
-
- function colContentRight(col) {
- return colContentPositions.right(col);
- }
-
- function dateCell(date) { // "cell" terminology is now confusing
- return {
- row: Math.floor(dayDiff(date, t.visStart) / 7),
- col: dayOfWeekCol(date.getDay())
- };
- }
-
- function cellDate(cell) {
- var d = colDate(cell.col);
- var slotIndex = cell.row;
- if (opt('allDaySlot')) {
- slotIndex--;
- }
- if (slotIndex >= 0) {
- addMinutes(d, minMinute + slotIndex * opt('slotMinutes'));
- }
- return d;
- }
-
- function colDate(col) { // returns dates with 00:00:00
- return addDays(cloneDate(t.visStart), col*dis+dit);
- }
-
- function cellIsAllDay(cell) {
- return opt('allDaySlot') && !cell.row;
- }
-
- function dayOfWeekCol(dayOfWeek) {
- return ((dayOfWeek - Math.max(firstDay, nwe) + colCnt) % colCnt)*dis+dit;
- }
-
- // get the Y coordinate of the given time on the given day (both Date objects)
- function timePosition(day, time) { // both date objects. day holds 00:00 of current day
- day = cloneDate(day, true);
- if (time < addMinutes(cloneDate(day), minMinute)) {
- return 0;
- }
- if (time >= addMinutes(cloneDate(day), maxMinute)) {
- return slotTable.height();
- }
- var slotMinutes = opt('slotMinutes'),
- minutes = time.getHours()*60 + time.getMinutes() - minMinute,
- slotI = Math.floor(minutes / slotMinutes),
- slotTop = slotTopCache[slotI];
- if (slotTop === undefined) {
- slotTop = slotTopCache[slotI] = slotTable.find('tr:eq(' + slotI + ') td div')[0].offsetTop; //.position().top; // need this optimization???
- }
- return Math.max(0, Math.round(
- slotTop - 1 + slotHeight * ((minutes % slotMinutes) / slotMinutes)
- ));
- }
-
- function allDayBounds() {
- return {
- left: axisWidth,
- right: viewWidth - gutterWidth
- }
- }
-
- function getAllDayRow(index) {
- return allDayRow;
- }
-
- function defaultEventEnd(event) {
- var start = cloneDate(event.start);
- if (event.allDay) {
- return start;
- }
- return addMinutes(start, opt('defaultEventMinutes'));
- }
-
- /* Selection
- ---------------------------------------------------------------------------------*/
-
- function defaultSelectionEnd(startDate, allDay) {
- if (allDay) {
- return cloneDate(startDate);
- }
- return addMinutes(cloneDate(startDate), opt('slotMinutes'));
- }
-
- function renderSelection(startDate, endDate, allDay) { // only for all-day
- if (allDay) {
- if (opt('allDaySlot')) {
- renderDayOverlay(startDate, addDays(cloneDate(endDate), 1), true);
- }
- }else{
- renderSlotSelection(startDate, endDate);
- }
- }
-
- function renderSlotSelection(startDate, endDate) {
- var helperOption = opt('selectHelper');
- coordinateGrid.build();
- if (helperOption) {
- var col = dayDiff(startDate, t.visStart) * dis + dit;
- if (col >= 0 && col < colCnt) { // only works when times are on same day
- var rect = coordinateGrid.rect(0, col, 0, col, slotContent); // only for horizontal coords
- var top = timePosition(startDate, startDate);
- var bottom = timePosition(startDate, endDate);
- if (bottom > top) { // protect against selections that are entirely before or after visible range
- rect.top = top;
- rect.height = bottom - top;
- rect.left += 2;
- rect.width -= 5;
- if ($.isFunction(helperOption)) {
- var helperRes = helperOption(startDate, endDate);
- if (helperRes) {
- rect.position = 'absolute';
- rect.zIndex = 8;
- selectionHelper = $(helperRes)
- .css(rect)
- .appendTo(slotContent);
- }
- }else{
- rect.isStart = true; // conside rect a "seg" now
- rect.isEnd = true; //
- selectionHelper = $(slotSegHtml(
- {
- title: '',
- start: startDate,
- end: endDate,
- className: ['fc-select-helper'],
- editable: false
- },
- rect
- ));
- selectionHelper.css('opacity', opt('dragOpacity'));
- }
- if (selectionHelper) {
- slotBind(selectionHelper);
- slotContent.append(selectionHelper);
- setOuterWidth(selectionHelper, rect.width, true); // needs to be after appended
- setOuterHeight(selectionHelper, rect.height, true);
- }
- }
- }
- }else{
- renderSlotOverlay(startDate, endDate);
- }
- }
-
- function clearSelection() {
- clearOverlays();
- if (selectionHelper) {
- selectionHelper.remove();
- selectionHelper = null;
- }
- }
-
- function slotSelectionMousedown(ev) {
- if (ev.which == 1 && opt('selectable')) { // ev.which==1 means left mouse button
- unselect(ev);
- var dates;
- hoverListener.start(function(cell, origCell) {
- clearSelection();
- if (cell && (cell.col == origCell.col || !opt('selectHelper')) && !cellIsAllDay(cell)) {
- var d1 = cellDate(origCell);
- var d2 = cellDate(cell);
- dates = [
- d1,
- addMinutes(cloneDate(d1), opt('slotMinutes')),
- d2,
- addMinutes(cloneDate(d2), opt('slotMinutes'))
- ].sort(cmp);
- renderSlotSelection(dates[0], dates[3]);
- }else{
- dates = null;
- }
- }, ev);
- $(document).one('mouseup', function(ev) {
- hoverListener.stop();
- if (dates) {
- if (+dates[0] == +dates[1]) {
- //reportDayClick(dates[0], false, ev);
- }
- reportSelection(dates[0], dates[3], false, ev);
- }
- });
- }
- }
-
- function reportDayClick(date, allDay, ev) {
- trigger('dayClick', dayBodyCells[dayOfWeekCol(date.getDay())], date, allDay, ev);
- }
-
- /* External Dragging
- --------------------------------------------------------------------------------*/
-
- function dragStart(_dragElement, ev, ui) {
- hoverListener.start(function(cell) {
- clearOverlays();
- if (cell) {
- if (cellIsAllDay(cell)) {
- renderCellOverlay(cell.row, cell.col, cell.row, cell.col);
- }else{
- var d1 = cellDate(cell);
- var d2 = addMinutes(cloneDate(d1), opt('defaultEventMinutes'));
- renderSlotOverlay(d1, d2);
- }
- }
- }, ev);
- }
-
- function dragStop(_dragElement, ev, ui) {
- var cell = hoverListener.stop();
- clearOverlays();
- if (cell) {
- trigger('drop', _dragElement, cellDate(cell), cellIsAllDay(cell), ev, ui);
- }
- }
-
-}
-
-function AgendaEventRenderer() {
- var t = this;
-
- // exports
- t.renderEvents = renderEvents;
- t.compileDaySegs = compileDaySegs; // for DayEventRenderer
- t.clearEvents = clearEvents;
- t.slotSegHtml = slotSegHtml;
- t.bindDaySeg = bindDaySeg;
- t.setTimeIndicator = setTimeIndicator;
-
- // imports
- DayEventRenderer.call(t);
- var opt = t.opt;
- var trigger = t.trigger;
- //var setOverflowHidden = t.setOverflowHidden;
- var isEventDraggable = t.isEventDraggable;
- var isEventResizable = t.isEventResizable;
- var eventEnd = t.eventEnd;
- var reportEvents = t.reportEvents;
- var reportEventClear = t.reportEventClear;
- var eventElementHandlers = t.eventElementHandlers;
- var setHeight = t.setHeight;
- var setWidth = t.setWidth;
- var getDaySegmentContainer = t.getDaySegmentContainer;
- var getSlotJumpersTop = t.getSlotJumpersTop;
- var getSlotJumpersBottom = t.getSlotJumpersBottom;
- var getslotScroller = t.getslotScroller;
- var getSlotContent = t.getSlotContent;
- var getSlotSegmentContainer = t.getSlotSegmentContainer;
- var getHoverListener = t.getHoverListener;
- var getMaxMinute = t.getMaxMinute;
- var getMinMinute = t.getMinMinute;
- var timePosition = t.timePosition;
- var colContentLeft = t.colContentLeft;
- var colContentRight = t.colContentRight;
- var renderDaySegs = t.renderDaySegs;
- var resizableDayEvent = t.resizableDayEvent; // TODO: streamline binding architecture
- var getColCnt = t.getColCnt;
- var getColWidth = t.getColWidth;
- var getSlotHeight = t.getSlotHeight;
- var getBodyContent = t.getBodyContent;
- var reportEventElement = t.reportEventElement;
- var showEvents = t.showEvents;
- var hideEvents = t.hideEvents;
- var eventDrop = t.eventDrop;
- var eventResize = t.eventResize;
- var renderDayOverlay = t.renderDayOverlay;
- var renderSlotSelection = t.renderSlotSelection;
- var clearOverlays = t.clearOverlays;
- var calendar = t.calendar;
- var formatDate = calendar.formatDate;
- var formatDates = calendar.formatDates;
- var timeLineInterval;
-
- /* Rendering
- ----------------------------------------------------------------------------*/
-
- // draw a horizontal line indicating the current time (#143)
- function setTimeIndicator()
- {
- var container = getBodyContent();
- var timeline = container.children('.fc-timeline');
- var arrow = container.children('.fc-timeline-arrow');
- if (timeline.length == 0 || arrow.length == 0) { // if timeline isn't there, add it
- timeline = $('<hr>').addClass('fc-timeline').appendTo(container);
- arrow = $('<div>').addClass('fc-timeline-arrow').appendTo(container);
- }
-
- var cur_time = new Date();
- var daycol = $('.fc-today', t.element);
- if (daycol.length > 0) {
- timeline.show();
- arrow.show();
- }
- else {
- timeline.hide();
- arrow.hide();
- return;
- }
-
- var secs = (cur_time.getHours() * 60 * 60) + (cur_time.getMinutes() * 60) + cur_time.getSeconds();
- var percents = secs / 86400; // 24 * 60 * 60 = 86400, # of seconds in a day
-
- timeline.css('top', Math.floor(container.height() * percents - 1) + 'px');
- arrow.css('top', Math.floor(container.height() * percents - 1) - 5 + 'px');
-
- var left = daycol.position().left;
- var width = daycol.width();
- timeline.css({ left: left + 'px', width: width + 'px' });
- }
-
- function renderEvents(events, modifiedEventId) {
- reportEvents(events);
- var i, len=events.length,
- dayEvents=[],
- slotEvents=[];
- for (i=0; i<len; i++) {
- if (events[i].allDay) {
- dayEvents.push(events[i]);
- }else{
- slotEvents.push(events[i]);
- }
- }
- if (opt('allDaySlot')) {
- renderDaySegs(compileDaySegs(dayEvents), modifiedEventId, true);
- setHeight(); // no params means set to viewHeight
- setWidth(); // no params means set to viewWidth
- }
- renderSlotSegs(compileSlotSegs(slotEvents), modifiedEventId);
-
- if (opt('currentTimeIndicator')) {
- window.clearInterval(timeLineInterval);
- timeLineInterval = window.setInterval(setTimeIndicator, 30000);
- setTimeIndicator();
- }
-
- if(t.addedView) {
- t.addedView.renderEvents(events, modifiedEventId);
- }
- }
-
- function clearEvents() {
- reportEventClear();
- getDaySegmentContainer().empty();
- getSlotSegmentContainer().empty();
-
- if(t.addedView) {
- t.addedView.clearEvents();
- }
- }
-
- function compileDaySegs(events) {
- var levels = stackSegs(sliceSegs(events, $.map(events, exclEndDay), t.visStart, t.visEnd)),
- i, levelCnt=levels.length, level,
- j, seg,
- segs=[];
- for (i=0; i<levelCnt; i++) {
- level = levels[i];
- for (j=0; j<level.length; j++) {
- seg = level[j];
- seg.row = 0;
- seg.level = i; // not needed anymore
- segs.push(seg);
- }
- }
- return segs;
- }
-
- function compileSlotSegs(events) {
- var colCnt = getColCnt(),
- minMinute = getMinMinute(),
- maxMinute = getMaxMinute(),
- d = addMinutes(cloneDate(t.visStart), minMinute),
- visEventEnds = $.map(events, slotEventEnd),
- i, col,
- j, level,
- k, seg,
- segs=[];
- for (i=0; i<colCnt; i++) {
- col = stackSegs(sliceSegs(events, visEventEnds, d, addMinutes(cloneDate(d), maxMinute-minMinute)));
- countForwardSegs(col);
- for (j=0; j<col.length; j++) {
- level = col[j];
- for (k=0; k<level.length; k++) {
- seg = level[k];
- seg.col = i;
- seg.level = j;
- segs.push(seg);
- }
- }
- addDays(d, 1, true);
- }
- return segs;
- }
-
- function slotEventEnd(event) {
- if (event.end) {
- return cloneDate(event.end);
- }else{
- return addMinutes(cloneDate(event.start), opt('defaultEventMinutes'));
- }
- }
-
- // renders events in the 'time slots' at the bottom
-
- function renderSlotSegs(segs, modifiedEventId) {
- var i, segCnt=segs.length, seg,
- event,
- classes,
- top, bottom,
- colI, levelI, forward,
- leftmost,
- availWidth,
- outerWidth,
- left,
- html='',
- eventElements,
- eventElement,
- triggerRes,
- vsideCache={},
- hsideCache={},
- key, val,
- contentElement,
- height,
- slotJumpersTop = getSlotJumpersTop(),
- slotJumpersBottom = getSlotJumpersBottom(),
- slotSegmentContainer = getSlotSegmentContainer(),
- slotScroller = getslotScroller(),
- rtl, dis, dit,
- colCnt = getColCnt(),
- colBoundaries = new Array(colCnt),
- jumperReserve = 10;
-
- if (rtl = opt('isRTL')) {
- dis = -1;
- dit = colCnt - 1;
- }else{
- dis = 1;
- dit = 0;
- }
-
- // init column tops array
- for(i=0;i<colCnt;i++) {
- colBoundaries[i]={positions:new Array()};
- }
-
- // calculate position/dimensions, create html
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- event = seg.event;
- top = timePosition(seg.start, seg.start);
- bottom = timePosition(seg.start, seg.end);
- colI = seg.col;
- levelI = seg.level;
- forward = seg.forward || 0;
- leftmost = colContentLeft(colI*dis + dit);
- availWidth = colContentRight(colI*dis + dit) - leftmost;
- availWidth = Math.min(availWidth-6, availWidth*.95); // TODO: move this to CSS
- if (levelI) {
- // indented and thin
- outerWidth = availWidth / (levelI + forward + 1);
- }else{
- if (forward) {
- // moderately wide, aligned left still
- outerWidth = ((availWidth / (forward + 1)) - (12/2)) * 2; // 12 is the predicted width of resizer =
- }else{
- // can be entire width, aligned left
- outerWidth = availWidth;
- }
- }
- left = leftmost + // leftmost possible
- (availWidth / (levelI + forward + 1) * levelI) // indentation
- * dis + (rtl ? availWidth - outerWidth : 0); // rtl
- seg.top = top;
- seg.left = left;
- seg.outerWidth = outerWidth;
- seg.outerHeight = bottom - top;
- html += slotSegHtml(event, seg);
- }
- slotSegmentContainer[0].innerHTML = html; // faster than html()
- eventElements = slotSegmentContainer.children();
-
- // retrieve elements, run through eventRender callback, bind event handlers
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- event = seg.event;
- eventElement = $(eventElements[i]); // faster than eq()
- triggerRes = trigger('eventRender', event, event, eventElement);
- if (triggerRes === false) {
- eventElement.remove();
- }else{
- if (triggerRes && triggerRes !== true) {
- eventElement.remove();
- eventElement = $(triggerRes)
- .css({
- position: 'absolute',
- top: seg.top,
- left: seg.left
- })
- .appendTo(slotSegmentContainer);
- }
- seg.element = eventElement;
- if (event._id === modifiedEventId) {
- bindSlotSeg(event, eventElement, seg);
- }else{
- eventElement[0]._fci = i; // for lazySegBind
- }
- reportEventElement(event, eventElement);
- }
- }
-
- lazySegBind(slotSegmentContainer, segs, bindSlotSeg);
-
- // record event sides and title positions
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- if (eventElement = seg.element) {
- val = vsideCache[key = seg.key = cssKey(eventElement[0])];
- seg.vsides = val === undefined ? (vsideCache[key] = vsides(eventElement, true)) : val;
- val = hsideCache[key];
- seg.hsides = val === undefined ? (hsideCache[key] = hsides(eventElement, true)) : val;
- contentElement = eventElement.find('div.fc-event-content');
- if (contentElement.length) {
- seg.contentTop = contentElement[0].offsetTop;
- }
- }
- }
-
- // set all positions/dimensions at once
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- if (eventElement = seg.element) {
- eventElement[0].style.width = Math.max(0, seg.outerWidth - seg.hsides) + 'px';
- height = Math.max(t.getSlotHeight() - seg.vsides, seg.outerHeight - seg.vsides);
- eventElement[0].style.height = height + 'px';
- event = seg.event;
- if (seg.contentTop !== undefined && height - seg.contentTop < 10) {
- // not enough room for title, put it in the time header
- eventElement.find('div.fc-event-time')
- .text(formatDate(event.start, opt('timeFormat')) + ' - ' + event.title);
- //.text(formatDates(event.start, event.end, opt('timeFormat')) + ' - ' + event.title);
- eventElement.find('div.fc-event-title')
- .remove();
- }
- colBoundaries[seg.col].positions.push({top:seg.top, bottom:seg.top+height+seg.vsides});
- trigger('eventAfterRender', event, event, eventElement);
- }
- }
-
- // sort column boundaries on top values and set min and max values
- for(i=0;i<colCnt;i++) {
- var min = null;
- var currentCol = colBoundaries[i];
- var currentColPositions = currentCol.positions;
- currentColPositions = currentColPositions.sort(function(a,b){return a.top-b.top;});
- $.each(currentColPositions,function(ei,ee){
- if(min==null)
- min=ee.bottom;
- else
- min=Math.min(min,ee.bottom);
- });
- currentCol.min=min;
- currentCol.max=currentColPositions.length?currentColPositions[currentColPositions.length-1].top:null;
- }
-
- slotScroller.unbind('scroll').scroll(function(){
- var currentPosition = $(this).scrollTop();
- for(i=0;i<colCnt;i++) {
- var currentCol = colBoundaries[i];
- if(currentCol.min!=null && currentCol.min<=currentPosition+jumperReserve)
- $(slotJumpersTop[i]).css('display','');
- else
- $(slotJumpersTop[i]).css('display','none');
- if(currentCol.max!=null && currentCol.max>=currentPosition+slotScroller.height()-jumperReserve)
- $(slotJumpersBottom[i]).css('display','');
- else
- $(slotJumpersBottom[i]).css('display','none');
- }
- }).trigger('scroll');
- slotJumpersTop.each(function(i, jumper){
- $(jumper).unbind('click').click(function(){
- var targetTop=0;
- var currentPosition = slotScroller.scrollTop();
- $.each(colBoundaries[i].positions,function(ei,ee){
- if(ee.bottom<=currentPosition+jumperReserve)
- targetTop=ee.top;
- return ee.top<currentPosition;
- });
- slotScroller.scrollTop(targetTop-t.getSlotHeight());
- });
- });
- slotJumpersBottom.each(function(i, jumper){
- $(jumper).unbind('click').click(function(){
- var targetPosition=0;
- var currentPosition = slotScroller.scrollTop();
- $.each(colBoundaries[i].positions,function(ei,ee){
- if(ee.top>=currentPosition+slotScroller.height()-jumperReserve)
- {
- targetPosition = ee;
- return false;
- }
- });
- slotScroller.scrollTop(
- targetPosition.bottom-targetPosition.top+t.getSlotHeight()>slotScroller.height()?
- targetPosition.top-t.getSlotHeight():
- targetPosition.bottom-slotScroller.height()+t.getSlotHeight()+1 // +1 is a magic independent constant, used just to make the default scroll position look better
- );
- });
- });
-
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- if(seg.event.source && seg.event.source.background) {
- $('td.fc-col' + seg.col, t.element).addClass('fc-source-bg');
- }
- }
- }
-
- function slotSegHtml(event, seg) {
- var html = "<";
- var url = event.url;
- var skinCss = getSkinCss(event, opt);
- var skinCssAttr = (skinCss ? " style='" + skinCss + "'" : '');
- var classes = ['fc-event', 'fc-event-skin', 'fc-event-vert'];
- if (isEventDraggable(event)) {
- classes.push('fc-event-draggable');
- }
- if (seg.isStart) {
- classes.push('fc-corner-top');
- }
- if (seg.isEnd) {
- classes.push('fc-corner-bottom');
- }
- classes = classes.concat(event.className);
- if (event.source) {
- classes = classes.concat(event.source.className || []);
- }
- if (url) {
- html += "a href='" + htmlEscape(event.url) + "'";
- }else{
- html += "div";
- }
- html +=
- " class='" + classes.join(' ') + "'" +
- " style='position:absolute;z-index:8;top:" + seg.top + "px;left:" + seg.left + "px;" + skinCss + "'" +
- ">" +
- "<div class='fc-event-inner fc-event-skin'" + skinCssAttr + ">" +
- "<div class='fc-event-head fc-event-skin'" + skinCssAttr + ">" +
- "<div class='fc-event-time'>" +
- htmlEscape(formatDates(event.start, event.end, opt('timeFormat'))) +
- "</div>" +
- "</div>" +
- "<div class='fc-event-content'>" +
- "<div class='fc-event-title'>" +
- htmlEscape(event.title) +
- "</div>" +
- "</div>" +
- "<div class='fc-event-bg'></div>" +
- "</div>"; // close inner
- if (seg.isEnd && isEventResizable(event)) {
- html +=
- "<div class='ui-resizable-handle ui-resizable-s'>=</div>";
- }
- html +=
- "</" + (url ? "a" : "div") + ">";
- return html;
- }
-
- function bindDaySeg(event, eventElement, seg) {
- if (isEventDraggable(event)) {
- draggableDayEvent(event, eventElement, seg.isStart);
- }
- if (seg.isEnd && isEventResizable(event)) {
- resizableDayEvent(event, eventElement, seg);
- }
- eventElementHandlers(event, eventElement);
- // needs to be after, because resizableDayEvent might stopImmediatePropagation on click
- }
-
- function bindSlotSeg(event, eventElement, seg) {
- var timeElement = eventElement.find('div.fc-event-time');
- if (isEventDraggable(event)) {
- draggableSlotEvent(event, eventElement, timeElement);
- }
- if (seg.isEnd && isEventResizable(event)) {
- resizableSlotEvent(event, eventElement, timeElement);
- }
- eventElementHandlers(event, eventElement);
- }
-
- /* Dragging
- -----------------------------------------------------------------------------------*/
-
- // when event starts out FULL-DAY
-
- function draggableDayEvent(event, eventElement, isStart) {
- var origWidth;
- var revert;
- var allDay=true;
- var dayDelta;
- var dis = opt('isRTL') ? -1 : 1;
- var hoverListener = getHoverListener();
- var colWidth = getColWidth();
- var slotHeight = getSlotHeight();
- var minMinute = getMinMinute();
- eventElement.draggable({
- zIndex: 9,
- scroll: false,
- opacity: opt('dragOpacity', 'month'), // use whatever the month view was using
- revertDuration: opt('dragRevertDuration'),
- start: function(ev, ui) {
- trigger('eventDragStart', eventElement, event, ev, ui);
- //hideEvents(event, eventElement);
- origWidth = eventElement.width();
- hoverListener.start(function(cell, origCell, rowDelta, colDelta) {
- clearOverlays();
- if (cell) {
- //setOverflowHidden(true);
- revert = false;
- dayDelta = colDelta * dis;
- if (!cell.row) {
- // on full-days
- renderDayOverlay(
- addDays(cloneDate(event.start), dayDelta),
- addDays(exclEndDay(event), dayDelta)
- );
- resetElement();
- }else{
- // mouse is over bottom slots
- if (isStart) {
- if (allDay) {
- // convert event to temporary slot-event
- eventElement.width(colWidth - 10); // don't use entire width
- setOuterHeight(
- eventElement,
- slotHeight * Math.round(
- (event.end ? ((event.end - event.start) / MINUTE_MS) : opt('defaultEventMinutes'))
- / opt('slotMinutes')
- )
- );
- eventElement.draggable('option', 'grid', [colWidth, 1]);
- allDay = false;
- }
- else{
- var cellDate = t.cellDate;
- if (cell && (cell.col == origCell.col || !opt('selectHelper'))) {
- var d1 = cellDate(cell);
- var duration = event.end ? minDiff(event.end, event.start) : opt('defaultEventMinutes');
- var d2 = addMinutes(cloneDate(d1, false), duration);
- dates = [d1, d2].sort(cmp);
- renderSlotSelection(dates[0], dates[1]);
- }
- }
-
- }else{
- revert = true;
- }
- }
- revert = revert || (allDay && !dayDelta);
- }else{
- resetElement();
- //setOverflowHidden(false);
- revert = true;
- }
- eventElement.draggable('option', 'revert', revert);
- }, ev, 'drag');
- },
- stop: function(ev, ui) {
- hoverListener.stop();
- clearOverlays();
- trigger('eventDragStop', eventElement, event, ev, ui);
- if (revert) {
- // hasn't moved or is out of bounds (draggable has already reverted)
- resetElement();
- eventElement.css('filter', ''); // clear IE opacity side-effects
- //showEvents(event, eventElement);
- }else{
- // changed!
- var minuteDelta = 0;
- if (!allDay) {
- minuteDelta = Math.round((eventElement.offset().top - getBodyContent().offset().top) / slotHeight)
- * opt('slotMinutes')
- + minMinute
- - (event.start.getHours() * 60 + event.start.getMinutes());
- }
- eventDrop(this, event, dayDelta, minuteDelta, allDay, ev, ui);
- }
- //setOverflowHidden(false);
- }
- });
- function resetElement() {
- if (!allDay) {
- eventElement
- .width(origWidth)
- .height('')
- .draggable('option', 'grid', null);
- allDay = true;
- }
- }
- }
-
- // when event starts out IN TIMESLOTS
-
- function draggableSlotEvent(event, eventElement, timeElement) {
- var origPosition;
- var allDay=false;
- var dayDelta;
- var minuteDelta;
- var prevMinuteDelta;
- var dis = opt('isRTL') ? -1 : 1;
- var hoverListener = getHoverListener();
- var colCnt = getColCnt();
- var colWidth = getColWidth();
- var slotHeight = getSlotHeight();
- eventElement.draggable({
- zIndex: 9,
- scroll: false,
- grid: [colWidth, slotHeight],
- axis: colCnt==1 ? 'y' : false,
- opacity: opt('dragOpacity'),
- revertDuration: opt('dragRevertDuration'),
- start: function(ev, ui) {
- trigger('eventDragStart', eventElement, event, ev, ui);
- //hideEvents(event, eventElement);
- origPosition = eventElement.position();
- minuteDelta = prevMinuteDelta = 0;
- hoverListener.start(function(cell, origCell, rowDelta, colDelta) {
- eventElement.draggable('option', 'revert', !cell);
- clearOverlays();
- if (cell) {
- dayDelta = colDelta * dis;
- if (opt('allDaySlot') && !cell.row) {
- // over full days
- if (!allDay) {
- // convert to temporary all-day event
- allDay = true;
- timeElement.hide();
- eventElement.draggable('option', 'grid', null);
- }
- renderDayOverlay(
- addDays(cloneDate(event.start), dayDelta),
- addDays(exclEndDay(event), dayDelta)
- );
- }else{
- // on slots
- resetElement();
- }
- }
- }, ev, 'drag');
- },
- drag: function(ev, ui) {
- ui.position.left = origPosition.left + (dayDelta * dis) * colWidth;
- minuteDelta = Math.round((ui.position.top - origPosition.top) / slotHeight) * opt('slotMinutes');
- if (minuteDelta != prevMinuteDelta) {
- if (!allDay) {
- updateTimeText(minuteDelta);
- }
- prevMinuteDelta = minuteDelta;
- }
- },
- stop: function(ev, ui) {
- var cell = hoverListener.stop();
- clearOverlays();
- trigger('eventDragStop', eventElement, event, ev, ui);
- if (cell && (dayDelta || minuteDelta || allDay)) {
- // changed!
- eventDrop(this, event, dayDelta, allDay ? 0 : minuteDelta, allDay, ev, ui);
- }else{
- // either no change or out-of-bounds (draggable has already reverted)
- resetElement();
- eventElement.css('filter', ''); // clear IE opacity side-effects
- eventElement.css(origPosition); // sometimes fast drags make event revert to wrong position
- updateTimeText(0);
- //showEvents(event, eventElement);
- }
- }
- });
- function updateTimeText(minuteDelta) {
- var newStart = addMinutes(cloneDate(event.start), minuteDelta);
- var newEnd;
- if (event.end) {
- newEnd = addMinutes(cloneDate(event.end), minuteDelta);
- }
- timeElement.text(formatDates(newStart, newEnd, opt('timeFormat')));
- }
- function resetElement() {
- // convert back to original slot-event
- if (allDay) {
- timeElement.css('display', ''); // show() was causing display=inline
- eventElement.draggable('option', 'grid', [colWidth, slotHeight]);
- allDay = false;
- }
- }
- }
-
- /* Resizing
- --------------------------------------------------------------------------------------*/
-
- function resizableSlotEvent(event, eventElement, timeElement) {
- var slotDelta, prevSlotDelta;
- var slotHeight = getSlotHeight();
- eventElement.resizable({
- handles: {
- s: 'div.ui-resizable-s'
- },
- grid: slotHeight,
- start: function(ev, ui) {
- slotDelta = prevSlotDelta = 0;
- //hideEvents(event, eventElement);
- eventElement.css('z-index', 9);
- trigger('eventResizeStart', this, event, ev, ui);
- },
- resize: function(ev, ui) {
- // don't rely on ui.size.height, doesn't take grid into account
- slotDelta = Math.round((Math.max(slotHeight, eventElement.height()) - ui.originalSize.height) / slotHeight);
- if (slotDelta != prevSlotDelta) {
- timeElement.text(
- formatDates(
- event.start,
- (!slotDelta && !event.end) ? null : // no change, so don't display time range
- addMinutes(eventEnd(event), opt('slotMinutes')*slotDelta),
- opt('timeFormat')
- )
- );
- prevSlotDelta = slotDelta;
- }
- },
- stop: function(ev, ui) {
- trigger('eventResizeStop', this, event, ev, ui);
-
- var minutesDelta = opt('slotMinutes')*slotDelta;
- if(event.end===null) {
- minutesDelta+=opt('defaultEventMinutes');
- }
-
- if (slotDelta) {
- eventResize(this, event, 0, minutesDelta, ev, ui);
- }else{
- eventElement.css('z-index', 8);
- //showEvents(event, eventElement);
- // BUG: if event was really short, need to put title back in span
- }
- }
- });
- }
-}
-
-function countForwardSegs(levels) {
- var i, j, k, level, segForward, segBack;
- for (i=levels.length-1; i>0; i--) {
- level = levels[i];
- for (j=0; j<level.length; j++) {
- segForward = level[j];
- for (k=0; k<levels[i-1].length; k++) {
- segBack = levels[i-1][k];
- if (segsCollide(segForward, segBack)) {
- segBack.forward = Math.max(segBack.forward||0, (segForward.forward||0)+1);
- }
- }
- }
- }
-}
-
-function View(element, calendar, viewName) {
- var t = this;
-
- // exports
- t.element = element;
- t.calendar = calendar;
- t.name = viewName;
- t.opt = opt;
- t.trigger = trigger;
- //t.setOverflowHidden = setOverflowHidden;
- t.isEventDraggable = isEventDraggable;
- t.isEventResizable = isEventResizable;
- t.reportEvents = reportEvents;
- t.eventEnd = eventEnd;
- t.reportEventElement = reportEventElement;
- t.reportEventClear = reportEventClear;
- t.eventElementHandlers = eventElementHandlers;
- t.showEvents = showEvents;
- t.hideEvents = hideEvents;
- t.eventDrop = eventDrop;
- t.eventResize = eventResize;
- t.selectedElement = null;
- t.selectEvent = selectEvent;
- // t.title
- // t.start, t.end
- // t.visStart, t.visEnd
-
- // imports
- var defaultEventEnd = t.defaultEventEnd;
- var normalizeEvent = calendar.normalizeEvent; // in EventManager
- var reportEventChange = calendar.reportEventChange;
-
- // locals
- var eventsByID = {};
- var eventElements = [];
- var eventElementsByID = {};
- var options = calendar.options;
-
- function opt(name, viewNameOverride) {
- var v = options[name];
- if (typeof v == 'object' && !v.length && !$.isArray(v)) {
- return smartProperty(v, viewNameOverride || viewName);
- }
- return v;
- }
-
- function trigger(name, thisObj) {
- return calendar.trigger.apply(
- calendar,
- [name, thisObj || t].concat(Array.prototype.slice.call(arguments, 2), [t])
- );
- }
-
- function isEventDraggable(event) {
- return isEventEditable(event) && !opt('disableDragging');
- }
-
- function isEventResizable(event) { // but also need to make sure the seg.isEnd == true
- return isEventEditable(event) && !opt('disableResizing');
- }
-
- function isEventEditable(event) {
- return firstDefined(event.editable, (event.source || {}).editable, opt('editable'));
- }
-
- /* Event Data
- ------------------------------------------------------------------------------*/
-
- // report when view receives new events
- function reportEvents(events) { // events are already normalized at this point
- eventsByID = {};
- var i, len=events.length, event;
- for (i=0; i<len; i++) {
- event = events[i];
- if (eventsByID[event._id]) {
- eventsByID[event._id].push(event);
- }else{
- eventsByID[event._id] = [event];
- }
- }
- }
-
- // returns a Date object for an event's end
- function eventEnd(event) {
- return event.end ? cloneDate(event.end) : defaultEventEnd(event);
- }
-
- /* Event Elements
- ------------------------------------------------------------------------------*/
-
- // report when view creates an element for an event
- function reportEventElement(event, element) {
- eventElements.push(element);
- if (eventElementsByID[event._id]) {
- eventElementsByID[event._id].push(element);
- }else{
- eventElementsByID[event._id] = [element];
- }
- }
-
- function reportEventClear() {
- eventElements = [];
- eventElementsByID = {};
- }
-
- // attaches eventClick, eventMouseover, eventMouseout
- function eventElementHandlers(event, eventElement) {
- eventElement
- .click(function(ev) {
- if (!eventElement.hasClass('ui-draggable-dragging') &&
- !eventElement.hasClass('ui-resizable-resizing')) {
- selectEvent(eventElement, true);
- return trigger('eventClick', this, event, ev);
- }
- })
- .hover(
- function(ev) {
- trigger('eventMouseover', this, event, ev);
- },
- function(ev) {
- trigger('eventMouseout', this, event, ev);
- }
- );
-
- eventElement.find('.fc-event-checkbox').click(function(ev) {
- trigger('eventCheckClicked', this, $(this), event, ev);
- });
- // TODO: don't fire eventMouseover/eventMouseout *while* dragging is occuring (on subject element)
- // TODO: same for resizing
- }
-
- function selectEvent(eventElement, noClick) {
- if(t.name!='todo' || t.eventSelectLock<0) {
- return false;
- }
-
- if(typeof eventElement=='undefined' || eventElement==null || eventElement.length==0) {
- eventElement=t.getDaySegmentContainer().find($('.fc-event[data-repeat-hash="'+t.selectedElement+'"]:visible'));
- }
-
- if(eventElement.length==0) {
- eventElement=t.element.find('.fc-event:visible:first');
- }
-
- if(eventElement.length==0) {
- trigger('selectEmpty');
- return false;
- }
-
- t.selectedElement=eventElement.attr('data-repeat-hash');
- t.element.find('.fc-event-selected').removeClass('fc-event-selected');
- eventElement.addClass('fc-event-selected');
-
- var offset=eventElement.position().top;
- if(offset<eventElement.outerHeight() || offset>t.getDaySegmentContainer().parent().height())
- {
- var top=t.getDaySegmentContainer().parent().scrollTop();
- t.getDaySegmentContainer().parent().scrollTop(top+offset-(t.getDaySegmentContainer().parent().height()*0.2));
- }
-
- // Force event click callback, although its not pretty
- if(!noClick) {
- eventElement.trigger('mouseover').trigger('click');
- }
- }
-
- function showEvents(event, exceptElement) {
- eachEventElement(event, exceptElement, 'show');
- }
-
- function hideEvents(event, exceptElement) {
- eachEventElement(event, exceptElement, 'hide');
- }
-
- function eachEventElement(event, exceptElement, funcName) {
- event[funcName]();
-// var elements = eventElementsByID[event._id],
-// i, len = elements.length;
-// for (i=0; i<len; i++) {
-// if (!exceptElement || elements[i][0] != exceptElement[0]) {
-// elements[i][funcName]();
-// }
-// }
- }
-
- /* Event Modification Reporting
- ---------------------------------------------------------------------------------*/
-
- function eventDrop(e, event, dayDelta, minuteDelta, allDay, ev, ui) {
- var oldAllDay = event.allDay;
- var eventId = event._id;
- //moveEvents(eventsByID[eventId], dayDelta, minuteDelta, allDay);
- moveEvents([event], dayDelta, minuteDelta, allDay);
- trigger(
- 'eventDrop',
- e,
- event,
- dayDelta,
- minuteDelta,
- allDay,
- function() {
- // TODO: investigate cases where this inverse technique might not work
- //moveEvents(eventsByID[eventId], -dayDelta, -minuteDelta, oldAllDay);
- moveEvents([event], -dayDelta, -minuteDelta, oldAllDay);
- reportEventChange(eventId);
- },
- ev,
- ui
- );
- reportEventChange(eventId);
- }
-
- function eventResize(e, event, dayDelta, minuteDelta, ev, ui) {
- var eventId = event._id;
- //elongateEvents(eventsByID[eventId], dayDelta, minuteDelta);
- elongateEvents([event], dayDelta, minuteDelta);
- trigger(
- 'eventResize',
- e,
- event,
- dayDelta,
- minuteDelta,
- function() {
- // TODO: investigate cases where this inverse technique might not work
- //elongateEvents(eventsByID[eventId], -dayDelta, -minuteDelta);
- elongateEvents([event], -dayDelta, -minuteDelta);
- reportEventChange(eventId);
- },
- ev,
- ui
- );
- reportEventChange(eventId);
- }
-
- /* Event Modification Math
- ---------------------------------------------------------------------------------*/
-
- function moveEvents(events, dayDelta, minuteDelta, allDay) {
- minuteDelta = minuteDelta || 0;
- for (var e, len=events.length, i=0; i<len; i++) {
- e = events[i];
- if (allDay !== undefined) {
- e.allDay = allDay;
- }
- addMinutes(addDays(e.start, dayDelta, true), minuteDelta);
- if (e.end) {
- e.end = addMinutes(addDays(e.end, dayDelta, true), minuteDelta);
- }
- normalizeEvent(e, options);
- }
- }
-
- function elongateEvents(events, dayDelta, minuteDelta) {
- minuteDelta = minuteDelta || 0;
- for (var e, len=events.length, i=0; i<len; i++) {
- e = events[i];
- e.end = addMinutes(addDays(eventEnd(e), dayDelta, true), minuteDelta);
- normalizeEvent(e, options);
- }
- }
-
-}
-
-function DayEventRenderer() {
- var t = this;
-
- // exports
- t.renderDaySegs = renderDaySegs;
- t.resizableDayEvent = resizableDayEvent;
-
- // imports
- var opt = t.opt;
- var trigger = t.trigger;
- var isEventDraggable = t.isEventDraggable;
- var isEventResizable = t.isEventResizable;
- var eventEnd = t.eventEnd;
- var reportEventElement = t.reportEventElement;
- var showEvents = t.showEvents;
- var hideEvents = t.hideEvents;
- var eventResize = t.eventResize;
- var getRowCnt = t.getRowCnt;
- var getColCnt = t.getColCnt;
- var getColWidth = t.getColWidth;
- var allDayRow = t.allDayRow;
- var allDayBounds = t.allDayBounds;
- var colContentLeft = t.colContentLeft;
- var colContentRight = t.colContentRight;
- var dayOfWeekCol = t.dayOfWeekCol;
- var dateCell = t.dateCell;
- var compileDaySegs = t.compileDaySegs;
- var getDaySegmentContainer = t.getDaySegmentContainer;
- var bindDaySeg = t.bindDaySeg; //TODO: streamline this
- var formatDates = t.calendar.formatDates;
- var renderDayOverlay = t.renderDayOverlay;
- var clearOverlays = t.clearOverlays;
- var clearSelection = t.clearSelection;
-
- /* Rendering
- -----------------------------------------------------------------------------*/
-
- function renderDaySegs(segs, modifiedEventId, isAllDay) {
- var segmentContainer = getDaySegmentContainer();
- var rowDivs;
- var rowCnt = getRowCnt();
- var colCnt = getColCnt();
- var i = 0;
- var rowI;
- var levelI;
- var colHeights;
- var j;
- var segCnt = segs.length;
- var seg;
- var top;
- var k;
- segmentContainer[0].innerHTML = daySegHTML(segs); // faster than .html()
- daySegElementResolve(segs, segmentContainer.children());
- daySegElementReport(segs);
- daySegHandlers(segs, segmentContainer, modifiedEventId);
- daySegCalcHSides(segs);
- daySegSetWidths(segs);
- daySegCalcHeights(segs);
- rowDivs = getRowDivs();
- // set row heights, calculate event tops (in relation to row top)
- for (rowI=0; rowI<rowCnt; rowI++) {
- levelI = 0;
- colHeights = [];
- for (j=0; j<colCnt; j++) {
- colHeights[j] = 0;
- }
- while (i<segCnt && (seg = segs[i]).row == rowI) {
- // loop through segs in a row
- top = arrayMax(colHeights.slice(seg.startCol, seg.endCol));
- seg.top = top;
- if (typeof seg.outerHeight != "undefined") top += seg.outerHeight;
- for (k=seg.startCol; k<seg.endCol; k++) {
- colHeights[k] = top;
- }
- i++;
- }
- if(isAllDay) {
- segmentContainer.parent().height(arrayMax(colHeights) ? arrayMax(colHeights) + 3 : 0);
- }
- rowDivs[rowI].height(arrayMax(colHeights));
- }
- daySegSetTops(segs, getRowTops(rowDivs));
-
- $('.fc-source-bg', t.element).removeClass('fc-source-bg');
- if(!isAllDay) { // month or multiweek view
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- if(seg.event.source && seg.event.source.background) {
- for(c=seg.startCol; c<seg.endCol; c++) {
- $('td.fc-day' + (seg.row*7+c), t.element).addClass('fc-source-bg');
- }
- }
- }
- }
- else { // agenda views
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- if(seg.event.source && seg.event.source.background) {
- for(c=seg.startCol; c<seg.endCol; c++) {
- $('td.fc-col' + c, t.element).addClass('fc-source-bg');
- }
- }
- }
- }
- }
-
- function renderTempDaySegs(segs, adjustRow, adjustTop) {
- var tempContainer = $("<div/>");
- var elements;
- var segmentContainer = getDaySegmentContainer();
- var i;
- var segCnt = segs.length;
- var element;
- tempContainer[0].innerHTML = daySegHTML(segs); // faster than .html()
- elements = tempContainer.children();
- segmentContainer.append(elements);
- daySegElementResolve(segs, elements);
- daySegCalcHSides(segs);
- daySegSetWidths(segs);
- daySegCalcHeights(segs);
- daySegSetTops(segs, getRowTops(getRowDivs()));
- elements = [];
- for (i=0; i<segCnt; i++) {
- element = segs[i].element;
- if (element) {
- if (segs[i].row === adjustRow) {
- element.css('top', adjustTop);
- }
- elements.push(element[0]);
- }
- }
- return $(elements);
- }
-
- function daySegHTML(segs) { // also sets seg.left and seg.outerWidth
- var rtl = opt('isRTL');
- var i;
- var segCnt=segs.length;
- var seg;
- var event;
- var url;
- var classes;
- var bounds = allDayBounds();
- var minLeft = bounds.left;
- var maxLeft = bounds.right;
- var leftCol;
- var rightCol;
- var left;
- var right;
- var titleWidth;
- var skinCss;
- var html = '';
- // calculate desired position/dimensions, create html
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- event = seg.event;
- classes = ['fc-event', 'fc-event-skin', 'fc-event-hori'];
- if (isEventDraggable(event)) {
- classes.push('fc-event-draggable');
- }
- if (rtl) {
- if (seg.isStart) {
- classes.push('fc-corner-right');
- }
- if (seg.isEnd) {
- classes.push('fc-corner-left');
- }
- leftCol = dayOfWeekCol(seg.end.getDay()-1);
- rightCol = dayOfWeekCol(seg.start.getDay());
- left = seg.isEnd ? colContentLeft(leftCol) : minLeft;
- right = seg.isStart ? colContentRight(rightCol) : maxLeft;
- }else{
- if (seg.isStart) {
- classes.push('fc-corner-left');
- }
- if (seg.isEnd) {
- classes.push('fc-corner-right');
- }
- leftCol = dayOfWeekCol(seg.start.getDay());
- rightCol = dayOfWeekCol(seg.end.getDay()-1);
- left = seg.isStart ? colContentLeft(leftCol) : minLeft;
- right = seg.isEnd ? colContentRight(rightCol) : maxLeft;
- }
- titleWidth = right - left - 2 - 2 - 2;
- classes = classes.concat(event.className);
- if (event.source) {
- classes = classes.concat(event.source.className || []);
- }
- url = event.url;
- skinCss = getSkinCss(event, opt);
- if (url) {
- html += "<a href='" + htmlEscape(url) + "'";
- }else{
- html += "<div";
- }
- html +=
- " class='" + classes.join(' ') + "'" +
- " style='position:absolute;z-index:8;left:"+left+"px;" + skinCss + "'" +
- ">" +
- "<div" +
- " class='fc-event-inner fc-event-skin'" +
- " style='width:" + titleWidth + "px;z-index:inherit;" +
- (skinCss ? skinCss : '') +
- "'" +
- //(skinCss ? " style='" + skinCss + "'" : '') +
- ">";
- if (opt('dayEventSizeStrict')) {
- html += "<div class='fc-event-title-strict'>";
- }
- if (!event.allDay && seg.isStart && opt('timeFormat')) {
- html +=
- "<span class='fc-event-time'>" +
- htmlEscape(formatDates(event.start, event.end, opt('timeFormat'))) +
- "</span>";
- }
- html += "<span class='fc-event-title'>" + htmlEscape(event.title.replace(/(\r\n|\n|\r)+/gm," ")) + "</span>";
- if (opt('dayEventSizeStrict')) {
- html += "</div>";
- }
- html += "</div>";
- if (seg.isEnd && isEventResizable(event)) {
- html +=
- "<div class='ui-resizable-handle ui-resizable-" + (rtl ? 'w' : 'e') + "'>" +
- "&nbsp;&nbsp;&nbsp;" + // makes hit area a lot better for IE6/7
- "</div>";
- }
- html +=
- "<div class='fc-event-bg'></div>" +
- "</" + (url ? "a" : "div" ) + ">";
- seg.left = left;
- seg.outerWidth = right - left;
- seg.startCol = leftCol;
- seg.endCol = rightCol + 1; // needs to be exclusive
- }
- return html;
- }
-
- function daySegElementResolve(segs, elements) { // sets seg.element
- var i;
- var segCnt = segs.length;
- var seg;
- var event;
- var element;
- var triggerRes;
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- event = seg.event;
- element = $(elements[i]); // faster than .eq()
- triggerRes = trigger('eventRender', event, event, element);
- if (triggerRes === false) {
- element.remove();
- }else{
- if (triggerRes && triggerRes !== true) {
- triggerRes = $(triggerRes)
- .css({
- position: 'absolute',
- left: seg.left
- });
- element.replaceWith(triggerRes);
- element = triggerRes;
- }
- seg.element = element;
- }
- }
- }
-
-
- function daySegElementReport(segs) {
- var i;
- var segCnt = segs.length;
- var seg;
- var element;
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- element = seg.element;
- if (element) {
- reportEventElement(seg.event, element);
- }
- }
- }
-
-
- function daySegHandlers(segs, segmentContainer, modifiedEventId) {
- var i;
- var segCnt = segs.length;
- var seg;
- var element;
- var event;
- // retrieve elements, run through eventRender callback, bind handlers
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- element = seg.element;
- if (element) {
- event = seg.event;
- if (event._id === modifiedEventId) {
- bindDaySeg(event, element, seg);
- }else{
- element[0]._fci = i; // for lazySegBind
- }
- }
- }
- lazySegBind(segmentContainer, segs, bindDaySeg);
- }
-
-
- function daySegCalcHSides(segs) { // also sets seg.key
- var i;
- var segCnt = segs.length;
- var seg;
- var element;
- var key, val;
- var hsideCache = {};
- // record event horizontal sides
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- element = seg.element;
- if (element) {
- key = seg.key = cssKey(element[0]);
- val = hsideCache[key];
- if (val === undefined) {
- val = hsideCache[key] = hsides(element, true);
- }
- seg.hsides = val;
- }
- }
- }
-
-
- function daySegSetWidths(segs) {
- var i;
- var segCnt = segs.length;
- var seg;
- var element;
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- element = seg.element;
- if (element) {
- element[0].style.width = Math.max(0, seg.outerWidth - seg.hsides) + 'px';
- }
- }
- }
-
-
- function daySegCalcHeights(segs) {
- var i;
- var segCnt = segs.length;
- var seg;
- var element;
- var key, val;
- var vmarginCache = {};
- // record event heights
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- element = seg.element;
- if (element) {
- key = seg.key; // created in daySegCalcHSides
- val = vmarginCache[key];
- if (val === undefined) {
- val = vmarginCache[key] = vmargins(element);
- }
- seg.outerHeight = element[0].offsetHeight + val;
- }
- else // always set a value (issue #1108 )
- seg.outerHeight = 0;
- }
- }
-
-
- function getRowDivs() {
- var i;
- var rowCnt = getRowCnt();
- var rowDivs = [];
- for (i=0; i<rowCnt; i++) {
- rowDivs[i] = allDayRow(i)
- .find('td:first div.fc-day-content > div'); // optimal selector?
- }
- return rowDivs;
- }
-
-
- function getRowTops(rowDivs) {
- var i;
- var rowCnt = rowDivs.length;
- var tops = [];
- for (i=0; i<rowCnt; i++) {
- tops[i] = rowDivs[i][0].offsetTop; // !!?? but this means the element needs position:relative if in a table cell!!!!
- }
- return tops;
- }
-
-
- function daySegSetTops(segs, rowTops) { // also triggers eventAfterRender
- var i;
- var segCnt = segs.length;
- var seg;
- var element;
- var event;
- for (i=0; i<segCnt; i++) {
- seg = segs[i];
- element = seg.element;
- if (element) {
- element[0].style.top = rowTops[seg.row] + (seg.top||0) + 'px';
- event = seg.event;
- trigger('eventAfterRender', event, event, element);
- }
- }
- }
-
- /* Resizing
- -----------------------------------------------------------------------------------*/
-
- function resizableDayEvent(event, element, seg) {
- var rtl = opt('isRTL');
- var direction = rtl ? 'w' : 'e';
- var handle = element.find('div.ui-resizable-' + direction);
- var isResizing = false;
-
- // TODO: look into using jquery-ui mouse widget for this stuff
- disableTextSelection(element); // prevent native <a> selection for IE
- element
- .mousedown(function(ev) { // prevent native <a> selection for others
- ev.preventDefault();
- })
- .click(function(ev) {
- if (isResizing) {
- ev.preventDefault(); // prevent link from being visited (only method that worked in IE6)
- ev.stopImmediatePropagation(); // prevent fullcalendar eventClick handler from being called
- // (eventElementHandlers needs to be bound after resizableDayEvent)
- }
- });
-
- handle.mousedown(function(ev) {
- if (ev.which != 1) {
- return; // needs to be left mouse button
- }
- isResizing = true;
- var hoverListener = t.getHoverListener();
- var rowCnt = getRowCnt();
- var colCnt = getColCnt();
- var dis = rtl ? -1 : 1;
- var dit = rtl ? colCnt-1 : 0;
- var elementTop = element.css('top');
- var dayDelta;
- var helpers;
- var eventCopy = $.extend({}, event);
- var minCell = dateCell(event.start);
- clearSelection();
- $('body')
- .css('cursor', direction + '-resize')
- .one('mouseup', mouseup);
- trigger('eventResizeStart', this, event, ev);
- hoverListener.start(function(cell, origCell) {
- if (cell) {
- var r = Math.max(minCell.row, cell.row);
- var c = cell.col;
- if (rowCnt == 1) {
- r = 0; // hack for all-day area in agenda views
- }
- if (r == minCell.row) {
- if (rtl) {
- c = Math.min(minCell.col, c);
- }else{
- c = Math.max(minCell.col, c);
- }
- }
- dayDelta = (r*7 + c*dis+dit) - (origCell.row*7 + origCell.col*dis+dit);
- var newEnd = addDays(eventEnd(event), dayDelta, true);
- if (dayDelta) {
- eventCopy.end = newEnd;
- var oldHelpers = helpers;
- helpers = renderTempDaySegs(compileDaySegs([eventCopy]), seg.row, elementTop);
- helpers.find('*').css('cursor', direction + '-resize');
- trigger('eventResizeHelperCreated', this, event, ev, element, helpers);
- if (oldHelpers) {
- oldHelpers.remove();
- }
- //hideEvents(event);
- hideEvents(element);
- }else{
- if (helpers) {
- //showEvents(event);
- showEvents(element);
- helpers.remove();
- helpers = null;
- }
- }
- clearOverlays();
- renderDayOverlay(event.start, addDays(cloneDate(newEnd), 1)); // coordinate grid already rebuild at hoverListener.start
- }
- }, ev);
-
- function mouseup(ev) {
- trigger('eventResizeStop', this, event, ev);
- $('body').css('cursor', '');
- hoverListener.stop();
- clearOverlays();
- if (dayDelta) {
- eventResize(this, event, dayDelta, 0, ev);
- // event redraw will clear helpers
- }
- // otherwise, the drag handler already restored the old events
-
- setTimeout(function() { // make this happen after the element's click event
- isResizing = false;
- },0);
- }
-
- });
- }
-
-
-}
-
-//BUG: unselect needs to be triggered when events are dragged+dropped
-
-function SelectionManager() {
- var t = this;
-
-
- // exports
- t.select = select;
- t.unselect = unselect;
- t.reportSelection = reportSelection;
- t.daySelectionMousedown = daySelectionMousedown;
-
-
- // imports
- var opt = t.opt;
- var trigger = t.trigger;
- var defaultSelectionEnd = t.defaultSelectionEnd;
- var renderSelection = t.renderSelection;
- var clearSelection = t.clearSelection;
-
-
- // locals
- var selected = false;
-
-
-
- // unselectAuto
- if (opt('selectable') && opt('unselectAuto')) {
- $(document).mousedown(function(ev) {
- var ignore = opt('unselectCancel');
- if (ignore) {
- if ($(ev.target).parents(ignore).length) { // could be optimized to stop after first match
- return;
- }
- }
- unselect(ev);
- });
- }
-
-
- function select(startDate, endDate, allDay) {
- unselect();
- if (!endDate) {
- endDate = defaultSelectionEnd(startDate, allDay);
- }
- renderSelection(startDate, endDate, allDay);
- reportSelection(startDate, endDate, allDay);
- }
-
-
- function unselect(ev) {
- if (selected) {
- selected = false;
- clearSelection();
- trigger('unselect', null, ev);
- }
- }
-
-
- function reportSelection(startDate, endDate, allDay, ev) {
- selected = true;
- trigger('select', null, startDate, endDate, allDay, ev);
- }
-
-
- function daySelectionMousedown(ev) { // not really a generic manager method, oh well
- var cellDate = t.cellDate;
- var cellIsAllDay = t.cellIsAllDay;
- var hoverListener = t.getHoverListener();
- var reportDayClick = t.reportDayClick; // this is hacky and sort of weird
- if (ev.which == 1 && opt('selectable')) { // which==1 means left mouse button
- unselect(ev);
- var _mousedownElement = this;
- var dates;
- hoverListener.start(function(cell, origCell) { // TODO: maybe put cellDate/cellIsAllDay info in cell
- clearSelection();
- if (cell && cellIsAllDay(cell)) {
- dates = [ cellDate(origCell), cellDate(cell) ].sort(cmp);
- renderSelection(dates[0], dates[1], true);
- }else{
- dates = null;
- }
- }, ev);
- $(document).one('mouseup', function(ev) {
- hoverListener.stop();
- if (dates) {
- if (+dates[0] == +dates[1]) {
- //reportDayClick(dates[0], true, ev);
- }
- reportSelection(dates[0], dates[1], true, ev);
- }
- });
- }
- }
-
-
-}
-
-function OverlayManager() {
- var t = this;
-
-
- // exports
- t.renderOverlay = renderOverlay;
- t.clearOverlays = clearOverlays;
-
-
- // locals
- var usedOverlays = [];
- var unusedOverlays = [];
-
-
- function renderOverlay(rect, parent) {
- var e = unusedOverlays.shift();
- if (!e) {
- e = $("<div class='fc-cell-overlay' style='position:absolute;z-index:3'/>");
- }
- if (e[0].parentNode != parent[0]) {
- e.appendTo(parent);
- }
- usedOverlays.push(e.css(rect).show());
- return e;
- }
-
-
- function clearOverlays() {
- var e;
- while (e = usedOverlays.shift()) {
- unusedOverlays.push(e.hide().unbind());
- }
- }
-
-
-}
-
-function CoordinateGrid(buildFunc) {
- var t = this;
- var rows;
- var cols;
-
- t.build = function() {
- rows = [];
- cols = [];
- buildFunc(rows, cols);
- };
-
- t.cell = function(x, y) {
- var rowCnt = rows.length;
- var colCnt = cols.length;
- var i, r=-1, c=-1;
- for (i=0; i<rowCnt; i++) {
- if (y >= rows[i][0] && y < rows[i][1]) {
- r = i;
- break;
- }
- }
- for (i=0; i<colCnt; i++) {
- if (x >= cols[i][0] && x < cols[i][1]) {
- c = i;
- break;
- }
- }
- return (r>=0 && c>=0) ? { row:r, col:c } : null;
- };
-
- t.rect = function(row0, col0, row1, col1, originElement) { // row1,col1 is inclusive
- var origin = originElement.offset();
- return {
- top: rows[row0][0] - origin.top,
- left: cols[col0][0] - origin.left,
- width: cols[col1][1] - cols[col0][0],
- height: rows[row1][1] - rows[row0][0]
- };
- };
-}
-
-function HoverListener(coordinateGrid) {
-
- var t = this;
- var bindType;
- var change;
- var firstCell;
- var cell;
- var origEvent;
-
- t.start = function(_change, ev, _bindType) {
- origEvent = ev;
- change = _change;
- firstCell = cell = null;
- coordinateGrid.build();
- mouse(ev);
- bindType = _bindType || 'mousemove';
- $(document).bind(bindType, mouse);
- };
-
- function mouse(ev) {
- _fixUIEvent(ev); // see below
- if(origEvent.pageX - ev.pageX == 0 && origEvent.pageY - ev.pageY == 0) {
- return false;
- }
- var newCell = coordinateGrid.cell(ev.pageX, ev.pageY);
- if (!newCell != !cell || newCell && (newCell.row != cell.row || newCell.col != cell.col)) {
- if (newCell) {
- if (!firstCell) {
- firstCell = newCell;
- }
- change(newCell, firstCell, newCell.row-firstCell.row, newCell.col-firstCell.col);
- }else{
- change(newCell, firstCell);
- }
- cell = newCell;
- }
- }
-
- t.stop = function() {
- $(document).unbind(bindType, mouse);
- return cell;
- };
-}
-
-// this fix was only necessary for jQuery UI 1.8.16 (and jQuery 1.7 or 1.7.1)
-// upgrading to jQuery UI 1.8.17 (and using either jQuery 1.7 or 1.7.1) fixed the problem
-// but keep this in here for 1.8.16 users
-// and maybe remove it down the line
-
-function _fixUIEvent(event) { // for issue 1168
- if (event.pageX === undefined) {
- event.pageX = event.originalEvent.pageX;
- event.pageY = event.originalEvent.pageY;
- }
-}
-function HorizontalPositionCache(getElement) {
-
- var t = this,
- elements = {},
- lefts = {},
- rights = {};
-
- function e(i) {
- return elements[i] = elements[i] || getElement(i);
- }
-
- t.left = function(i) {
- return lefts[i] = lefts[i] === undefined ? e(i).position().left : lefts[i];
- };
-
- t.right = function(i) {
- return rights[i] = rights[i] === undefined ? t.left(i) + e(i).width() : rights[i];
- };
-
- t.clear = function() {
- elements = {};
- lefts = {};
- rights = {};
- };
-}
-
-function addTodayText(cell, todayText)
-{
- target = cell.find(".fc-day-text");
- target.html(todayText);
-}
-
-function removeTodayText(cell, todayText)
-{
- target = cell.find(".fc-day-text");
- target.html('');
-}
-
-function addWeekNumber(cell, date)
-{
- target = cell.find(".fc-week-number");
- target.html(getWeekNumber(date));
-}
-
-function removeWeekNumber(cell, date)
-{
- target = cell.find(".fc-week-number");
- target.html('');
-}
-
-function addTodayClass(cell)
-{
- var classes = cell.attr('class').split(' ');
- var filter = ['fc-state-highlight', 'fc-today', 'fc-widget-content', 'fc-source-bg'];
- classes = $.grep(classes, function(el) {
- if ($.inArray(el, filter) > -1) {
- return false;
- }
-
- return true;
- });
- classes.push('fc-widget-header');
- var target = $('.' + classes.join('.'));
- target.addClass('fc-today');
-}
-
-function removeTodayClass(cell)
-{
- var classes = cell.attr('class').split(' ');
- var filter = ['fc-state-highlight', 'fc-today', 'fc-widget-content', 'fc-source-bg'];
- classes = $.grep(classes, function(el) {
- if ($.inArray(el, filter) > -1) {
- return false;
- }
- return true;
- });
- classes.push('fc-widget-header');
- var target = $('.' + classes.join('.'));
- target.removeClass('fc-today');
-}
-
-function getWeekNumber(date) {
- //By tanguy.pruvot at gmail.com (2010)
-
- //first week of year always contains 4th Jan, or 28 Dec (ISO)
-
- var jan4 = new Date(date.getFullYear(),0,4 ,date.getHours());
-
- //ISO weeks numbers begins on monday, so rotate monday:sunday to 0:6
- var jan4Day = (jan4.getDay() - 1 + 7) % 7;
-
- var days = Math.round((date - jan4) / 86400000);
- var week = Math.floor((days + jan4Day ) / 7)+1;
-
- //special cases
- var thisDay = (date.getDay() - 1 + 7) % 7;
- if (date.getMonth()==11 && date.getDate() >= 28) {
-
- jan4 = new Date(date.getFullYear()+1,0,4 ,date.getHours());
- jan4Day = (jan4.getDay() - 1 + 7) % 7;
-
- if (thisDay < jan4Day) return 1;
-
- var prevWeek = new Date(date.valueOf()-(86400000*7));
- return getWeekNumber(prevWeek) + 1;
- }
-
- if (week == 0 && thisDay > 3 && date.getMonth()==0) {
- var prevWeek = new Date(date.valueOf()-(86400000*7));
- return getWeekNumber(prevWeek) + 1;
- }
-
- return week;
-}
-
-/* Additional view: list (by bruederli@kolabsys.com)
----------------------------------------------------------------------------------*/
-
-function ListEventRenderer() {
- var t = this;
-
- // exports
- t.renderEvents = renderEvents;
- t.renderEventTime = renderEventTime;
- t.compileDaySegs = compileSegs; // for DayEventRenderer
- t.clearEvents = clearEvents;
- t.lazySegBind = lazySegBind;
- t.sortCmp = sortCmp;
-
- // imports
- DayEventRenderer.call(t);
- var opt = t.opt;
- var trigger = t.trigger;
- var reportEvents = t.reportEvents;
- var reportEventClear = t.reportEventClear;
- var reportEventElement = t.reportEventElement;
- var eventElementHandlers = t.eventElementHandlers;
- var showEvents = t.showEvents;
- var hideEvents = t.hideEvents;
- var getListContainer = t.getDaySegmentContainer;
- var calendar = t.calendar;
- var formatDate = calendar.formatDate;
- var formatDates = calendar.formatDates;
-
-
- /* Rendering
- --------------------------------------------------------------------*/
-
- function clearEvents() {
- reportEventClear();
- getListContainer().empty();
- }
-
- function renderEvents(events, modifiedEventId) {
- events.sort(sortCmp);
- reportEvents(events);
- renderSegs(compileSegs(events), modifiedEventId);
- }
-
- /*function compileSegs(events) {
- var segs = [];
- var colFormat = opt('titleFormat', 'day');
- var firstDay = opt('firstDay');
- var segmode = opt('listSections');
- var event, i, dd, wd, md, seg, segHash, curSegHash, segDate, curSeg = -1;
- var today = clearTime(new Date());
- var weekstart = addDays(cloneDate(today), -((today.getDay() - firstDay + 7) % 7));
-
- for (i=0; i < events.length; i++) {
- event = events[i];
- var eventEnd = event.end ? cloneDate(event.end) : cloneDate(event.start);
-
- // skip events out of range
- if (eventEnd < t.start || event.start > t.visEnd)
- continue;
-
- // define sections of this event
- // create smart sections such as today, tomorrow, this week, next week, next month, ect.
- segDate = cloneDate(event.start < t.start && eventEnd > t.start ? t.start : event.start, true);
- dd = dayDiff(segDate, today);
- wd = Math.floor(dayDiff(segDate, weekstart) / 7);
- md = segDate.getMonth() + ((segDate.getYear() - today.getYear()) * 12) - today.getMonth();
-
- // build section title
- if (segmode == 'smart') {
- if (dd < 0) {
- segHash = opt('listTexts', 'past');
- } else if (dd == 0) {
- segHash = opt('listTexts', 'today');
- } else if (dd == 1) {
- segHash = opt('listTexts', 'tomorrow');
- } else if (wd == 0) {
- segHash = opt('listTexts', 'thisWeek');
- } else if (wd == 1) {
- segHash = opt('listTexts', 'nextWeek');
- } else if (md == 0) {
- segHash = opt('listTexts', 'thisMonth');
- } else if (md == 1) {
- segHash = opt('listTexts', 'nextMonth');
- } else if (md > 1) {
- segHash = opt('listTexts', 'future');
- }
- } else if (segmode == 'month') {
- segHash = formatDate(segDate, 'MMMM yyyy');
- } else if (segmode == 'week') {
- segHash = opt('listTexts', 'week') + formatDate(segDate, ' W');
- } else if (segmode == 'day') {
- segHash = formatDate(segDate, colFormat);
- } else {
- segHash = '';
- }
-
- // start new segment
- if (segHash != curSegHash) {
- segs[++curSeg] = { events: [], start: segDate, title: segHash, daydiff: dd, weekdiff: wd, monthdiff: md };
- curSegHash = segHash;
- }
-
- segs[curSeg].events.push(event);
- }
-
- return segs;
- }*/
-
-function compileSegs(events) {
- var segs = {};
- var colFormat = opt('columnFormat', t.name);
- var firstDay = opt('firstDay');
- var segmode = opt('listSections');
- var event, i, j, dd, wd, md, seg, segHash, segDate;
- var today = clearTime(new Date());
- var weekstart = addDays(cloneDate(today), -((today.getDay() - firstDay + 7) % 7));
-
- for (i=0; i < events.length; i++) {
- event = events[i];
- var eventEnd = event.end ? cloneDate(event.end) : cloneDate(event.start);
-
- // skip events out of range
- if (eventEnd < t.start || event.start > t.visEnd)
- continue;
-
- var boundEventStart = cloneDate(event.start < t.start ? t.start : event.start, true);
- var boundEventEnd = cloneDate(eventEnd > t.visEnd ? t.visEnd : eventEnd, true);
- var dayDuration = dayDiff(boundEventEnd, boundEventStart);
-
- for(j = 0; j <= dayDuration; j++) {
- segDate = cloneDate(boundEventStart);
- segDate.setDate(segDate.getDate() + j);
-
- // define sections of this event
- // create smart sections such as today, tomorrow, this week, next week, next month, ect.
- //segDate = cloneDate(event.start < t.start && eventEnd > t.start ? t.start : event.start, true);
- dd = dayDiff(segDate, today);
- wd = Math.floor(dayDiff(segDate, weekstart) / 7);
- md = segDate.getMonth() + ((segDate.getYear() - today.getYear()) * 12) - today.getMonth();
-
- // build section title
- if (segmode == 'smart') {
- if (dd < 0) {
- segHash = opt('listTexts', 'past');
- } else if (dd == 0) {
- segHash = opt('listTexts', 'today');
- } else if (dd == 1) {
- segHash = opt('listTexts', 'tomorrow');
- } else if (wd == 0) {
- segHash = opt('listTexts', 'thisWeek');
- } else if (wd == 1) {
- segHash = opt('listTexts', 'nextWeek');
- } else if (md == 0) {
- segHash = opt('listTexts', 'thisMonth');
- } else if (md == 1) {
- segHash = opt('listTexts', 'nextMonth');
- } else if (md > 1) {
- segHash = opt('listTexts', 'future');
- }
- } else if (segmode == 'month') {
- segHash = formatDate(segDate, 'MMMM yyyy');
- } else if (segmode == 'week') {
- segHash = opt('listTexts', 'week') + formatDate(segDate, ' W');
- } else if (segmode == 'day') {
- segHash = formatDate(segDate, colFormat);
- } else {
- segHash = '';
- }
-
- // start new segment
- if (!(segHash in segs)) {
- segs[segHash] = { events: [], start: segDate, title: segHash, daydiff: dd, weekdiff: wd, monthdiff: md };
- }
-
- segs[segHash].events.push(event);
- }
- }
-
- return segs;
- }
-
- function sortCmp(a, b) {
- /*var datediff = 0;
- if(a.start != null && b.start != null) {
- datediff = a.start.getTime() - b.start.getTime();
- }
- if(datediff == 0 && a.end != null && b.end != null) {
- datediff = a.end.getTime() - b.end.getTime();
- }
- return datediff;*/
- var retVal = a.start.getTime() - b.start.getTime();
-
- if(retVal == 0) {
- var aEnd = a.end ? a.end : a.start;
- var bEnd = b.end ? b.end : b.start;
- retVal = aEnd.getTime() - bEnd.getTime();
- }
-
- if(retVal == 0) {
- if(a.compareString < b.compareString) {
- retVal = -1;
- }
- else if(b.compareString < a.compareString) {
- retVal = 1;
- }
- }
- return retVal;
- }
-
- function renderSegs(segs, modifiedEventId) {
- var tm = opt('theme') ? 'ui' : 'fc';
- var headerClass = tm + "-widget-header";
- var contentClass = tm + "-widget-content";
- var i, j, seg, event, times, s, skinCss, skinCssAttr, classes, segContainer, eventElement, eventElements, triggerRes;
-
- for (j=0; j < segs.length; j++) {
- seg = segs[j];
-
- if (seg.title) {
- $('<div class="fc-list-header ' + headerClass + '">' + htmlEscape(seg.title) + '</div>').appendTo(getListContainer());
- }
- segContainer = $('<div>').addClass('fc-list-section ' + contentClass).appendTo(getListContainer());
- s = '';
-
- for (i=0; i < seg.events.length; i++) {
- event = seg.events[i];
- times = renderEventTime(event, seg);
- skinCss = getSkinCss(event, opt);
- skinCssAttr = (skinCss ? " style='" + skinCss + "'" : '');
- classes = ['fc-event', 'fc-event-skin', 'fc-event-vert', 'fc-corner-top', 'fc-corner-bottom'].concat(event.className);
- if (event.source && event.source.className) {
- classes = classes.concat(event.source.className);
- }
-
- s +=
- "<div class='" + classes.join(' ') + "'" + skinCssAttr + ">" +
- "<div class='fc-event-inner fc-event-skin'" + skinCssAttr + ">" +
- "<div class='fc-event-head fc-event-skin'" + skinCssAttr + ">" +
- "<div class='fc-event-time'>" +
- (times[0] ? '<span class="fc-col-date">' + times[0] + '</span> ' : '') +
- (times[1] ? '<span class="fc-col-time">' + times[1] + '</span>' : '') +
- "</div>" +
- "</div>" +
- "<div class='fc-event-content'>" +
- "<div class='fc-event-title'>" +
- htmlEscape(event.title.replace(/(\r\n|\n|\r)+/gm," ")) +
- "</div>" +
- "</div>" +
- "<div class='fc-event-bg'></div>" +
- "</div>" + // close inner
- "</div>"; // close outer
- }
-
- segContainer[0].innerHTML = s;
- eventElements = segContainer.children();
-
- // retrieve elements, run through eventRender callback, bind event handlers
- for (i=0; i < seg.events.length; i++) {
- event = seg.events[i];
- eventElement = $(eventElements[i]); // faster than eq()
- triggerRes = trigger('eventRender', event, event, eventElement);
- if (triggerRes === false) {
- eventElement.remove();
- } else {
- if (triggerRes && triggerRes !== true) {
- eventElement.remove();
- eventElement = $(triggerRes).appendTo(segContainer);
- }
- if (event._id === modifiedEventId) {
- eventElementHandlers(event, eventElement, seg);
- } else {
- eventElement[0]._fci = i; // for lazySegBind
- }
- reportEventElement(event, eventElement);
- }
- }
-
- lazySegBind(segContainer, seg, eventElementHandlers);
- }
-
- markFirstLast(getListContainer());
- }
-
- // event time/date range to display
- function renderEventTime(event, seg) {
- var timeFormat = opt('timeFormat', 'list');
- var timeFormatFull = opt('timeFormat', 'listFull');
- var timeFormatFullAllDay = opt('timeFormat', 'listFullAllDay');
- var dateFormat = opt('columnFormat');
- var segmode = opt('listSections');
- var eventEnd = event.end ? cloneDate(event.end) : cloneDate(event.start);
- var duration = eventEnd.getTime() - event.start.getTime();
- var datestr = '', timestr = '';
-
- if (segmode == 'smart') {
- if (event.start < seg.start) {
- datestr = opt('listTexts', 'until') + ' ' + formatDate(eventEnd, (event.allDay || eventEnd.getDate() != seg.start.getDate()) ? dateFormat : timeFormat);
- } else if (duration > DAY_MS) {
- datestr = formatDates(event.start, eventEnd, dateFormat + '{ – ' + dateFormat + '}');
- } else if (seg.daydiff == 0) {
- datestr = opt('listTexts', 'today');
- } else if (seg.daydiff == 1) {
- datestr = opt('listTexts', 'tomorrow');
- } else if (seg.weekdiff == 0 || seg.weekdiff == 1) {
- datestr = formatDate(event.start, 'dddd');
- } else if (seg.daydiff > 1 || seg.daydiff < 0) {
- datestr = formatDate(event.start, dateFormat);
- }
- } else if (segmode != 'day') {
- datestr = formatDates(event.start, eventEnd, dateFormat + (duration > DAY_MS ? '{ – ' + dateFormat + '}' : ''));
- }
-
- if (!datestr && event.allDay) {
- if(dayDiff(eventEnd, event.start)) { //spans multiple days
- timestr = formatDates(event.start, eventEnd, timeFormatFullAllDay);
- }
- else {
- timestr = opt('allDayText');
- }
- } else if ((!datestr || !dayDiff(eventEnd, event.start)) && !event.allDay) {
- if(dayDiff(eventEnd, event.start)) //spans multiple days
- timestr = formatDates(event.start, eventEnd, timeFormatFull);
- else if(duration)
- timestr = formatDates(event.start, eventEnd, timeFormat);
- else
- timestr = formatDates(event.start, null, timeFormat);
- }
-
- return [datestr, timestr];
- }
-
- function lazySegBind(container, seg, bindHandlers) {
- container.unbind('mouseover').mouseover(function(ev) {
- var parent = ev.target, e = parent, i, event;
- while (parent != this) {
- e = parent;
- parent = parent.parentNode;
- }
- if ((i = e._fci) !== undefined) {
- e._fci = undefined;
- event = seg.events[i];
- bindHandlers(event, container.children().eq(i), seg);
- $(ev.target).trigger(ev);
- }
- ev.stopPropagation();
- });
- }
-}
-
-fcViews.list = ListView;
-
-function ListView(element, calendar) {
- var t = this;
-
- // exports
- t.render = render;
- t.select = dummy;
- t.unselect = dummy;
- t.getDaySegmentContainer = function(){ return body; };
-
- // imports
- View.call(t, element, calendar, 'list');
- ListEventRenderer.call(t);
- var opt = t.opt;
- var trigger = t.trigger;
- var clearEvents = t.clearEvents;
- var reportEventClear = t.reportEventClear;
- var formatDates = calendar.formatDates;
- var formatDate = calendar.formatDate;
-
- // overrides
- t.setWidth = setWidth;
- t.setHeight = setHeight;
-
- // locals
- var body;
- var firstDay;
- var nwe;
- var tm;
- var colFormat;
-
-
- function render(date, delta) {
- if (delta) {
- addDays(date, opt('listPage') * delta);
- }
- t.start = t.visStart = cloneDate(date, true);
- t.end = addDays(cloneDate(t.start), opt('listPage'));
- t.visEnd = addDays(cloneDate(t.start), opt('listRange'));
- addMinutes(t.visEnd, -1); // set end to 23:59
- t.title = formatDates(date, t.visEnd, opt('titleFormat'));
-
- updateOptions();
-
- if (!body) {
- buildSkeleton();
- } else {
- clearEvents();
- }
- }
-
-
- function updateOptions() {
- firstDay = opt('firstDay');
- nwe = opt('weekends') ? 0 : 1;
- tm = opt('theme') ? 'ui' : 'fc';
- colFormat = opt('columnFormat', 'day');
- }
-
-
- function buildSkeleton() {
- body = $('<div>').addClass('fc-list-content').appendTo(element);
- }
-
- function setHeight(height, dateChanged) {
- body.css('height', (height-1)+'px').css('overflow', 'auto');
- }
-
- function setWidth(width) {
- // nothing to be done here
- }
-
- function dummy() {
- // Stub.
- }
-
-}
-
-/* Additional view: table (by bruederli@kolabsys.com)
----------------------------------------------------------------------------------*/
-
-function TableEventRenderer() {
- var t = this;
-
- // imports
- ListEventRenderer.call(t);
- var opt = t.opt;
- var sortCmp = t.sortCmp;
- var trigger = t.trigger;
- var getOrigDate = t.getOrigDate;
- var compileSegs = t.compileDaySegs;
- var reportEvents = t.reportEvents;
- var reportEventClear = t.reportEventClear;
- var reportEventElement = t.reportEventElement;
- var eventElementHandlers = t.eventElementHandlers;
- var renderEventTime = t.renderEventTime;
- var showEvents = t.showEvents;
- var hideEvents = t.hideEvents;
- var getListContainer = t.getDaySegmentContainer;
- var lazySegBind = t.lazySegBind;
- var calendar = t.calendar;
- var formatDate = calendar.formatDate;
- var formatDates = calendar.formatDates;
- var prevMonth;
- var nextMonth;
-
- // exports
- t.renderEvents = renderEvents;
- t.scrollToDate = scrollToDate;
- t.clearEvents = clearEvents;
- t.prevMonthNav = prevMonth;
- t.nextMonthNav = nextMonth;
-
-
- /* Rendering
- --------------------------------------------------------------------*/
-
- function scrollToDate(date) {
- var colFormat = opt('columnFormat', t.name);
- var currentDate = cloneDate(date, false);
- var nextDate;
- var segHash;
- var currSegHash;
- var segFound = false;
-
- if(currentDate.getDate() == 1) {
- getListContainer().parent().scrollTop(0);
- }
- else {
- while(!segFound) {
- segHash = formatDate(currentDate, colFormat);
- getListContainer().find('td.fc-list-header.fc-widget-header').each(function(){
- currSegHash = $(this).html();
- if(currSegHash == segHash) {
- segFound = true;
- var offset = $(this).position().top;
- var top = getListContainer().parent().scrollTop();
- getListContainer().parent().scrollTop(top + offset);
- }
- });
-
- if(!segFound) {
- nextDate = cloneDate(currentDate, false);
- nextDate.setDate(nextDate.getDate()+1);
-
- if(nextDate.getDate() > currentDate.getDate()) {
- currentDate = cloneDate(nextDate, false);
- }
- else {
- segFound = true;
- getListContainer().parent().scrollTop(getListContainer().height());
- }
- }
- }
- }
- }
-
- function clearEvents() {
- reportEventClear();
- getListContainer().children('tbody').remove();
- }
-
- function renderEvents(events, modifiedEventId) {
- events.sort(sortCmp);
- reportEvents(events);
- renderSegs(compileSegs(events), modifiedEventId);
- getListContainer().removeClass('fc-list-smart fc-list-day fc-list-month fc-list-week').addClass('fc-list-' + opt('listSections'));
- scrollToDate(getOrigDate());
- }
-
- function renderSegs(segs, modifiedEventId) {
- var tm = opt('theme') ? 'ui' : 'fc';
- var table = getListContainer();
- var headerClass = tm + "-widget-header";
- var contentClass = tm + "-widget-content";
- var segHeader = null;
- var tableCols = opt('tableCols');
- var timecol = $.inArray('time', tableCols) >= 0;
- var i, j, seg, event, times, s, bg, skinCss, skinCssAttr, skinClasses, rowClasses, segContainer, eventElements, eventElement, triggerRes;
-
- prevMonth = $('<tbody class="fc-list-header"><tr><td class="fc-list-header fc-month-nav fc-month-prev ' + headerClass + '" colspan="' + tableCols.length + '">' + opt('buttonText', 'prevMonth') + '</td></tr></tbody>').appendTo(table);
- prevMonth.click(function(){
- var prevMonthDate = cloneDate(t.getOrigDate(), true);
- prevMonthDate.setDate(0);
- calendar.gotoDate(prevMonthDate);
- trigger('prevClick');
- });
-
- for (j in segs) {
- seg = segs[j];
- bg = false;
-
- if (seg.title) {
- var segHeader = $('<tbody class="fc-list-header"><tr><td class="fc-list-header ' + headerClass + '" colspan="' + tableCols.length + '">' + htmlEscape(seg.title) + '</td></tr></tbody>').appendTo(table);
- }
- segContainer = $('<tbody>').addClass('fc-list-section ' + contentClass).appendTo(table);
- s = '';
-
- for (i=0; i < seg.events.length; i++) {
- event = seg.events[i];
- times = renderEventTime(event, seg);
- skinCss = getSkinCss(event, opt);
- skinCssAttr = (skinCss ? " style='" + skinCss + "'" : '');
- skinClasses = ['fc-event-skin', 'fc-corner-left', 'fc-corner-right', 'fc-corner-top', 'fc-corner-bottom'].concat(event.className);
- if (event.source && event.source.className) {
- skinClasses = skinClasses.concat(event.source.className);
- }
- if(event.source && event.source.background) {
- bg = true;
- }
- rowClasses = ['fc-'+dayIDs[event.start.getDay()], 'fc-event', 'fc-event-row'];
- if(opt('weekendDays').length>0 && opt('weekendDays').indexOf(segs[j].start.getDay())!=-1)
- rowClasses.splice(1, 0, 'fc-weekend-day');
-
- if (seg.daydiff == 0) {
- if(segHeader)
- segHeader.addClass('fc-today');
- rowClasses.push('fc-today');
- rowClasses.push('fc-state-highlight');
- }
-
- s += "<tr class='" + rowClasses.join(' ') + "'>";
- for (var col, c=0; c < tableCols.length; c++) {
- col = tableCols[c];
- if (col == 'handle') {
- s += "<td class='fc-event-handle'" + skinCssAttr + "></td>";
- } else if (col == 'title') {
- s += "<td class='fc-event-title'>" + (event.title ? htmlEscape(event.title.replace(/(\r\n|\n|\r)+/gm," ")) : '&nbsp;') + "</td>";
- } else if (col == 'date') {
- s += "<td class='fc-event-date' colspan='" + (times[1] || !timecol ? 1 : 2) + "'>" + htmlEscape(times[0]) + "</td>";
- } else if (col == 'time') {
- if (times[1]) {
- s += "<td class='fc-event-time' style='text-overflow: ellipsis; overflow: hidden;'>" + htmlEscape(times[1]) + "</td>";
- }
- } else {
- s += "<td class='fc-event-" + col + "'>" + (event[col] ? htmlEscape(event[col]) : '&nbsp;') + "</td>";
- }
- }
- s += "</tr>";
-
- // IE doesn't like innerHTML on tbody elements so we insert every row individually
- if (document.all) {
- $(s).appendTo(segContainer);
- s = '';
- }
- }
-
- if (!document.all)
- segContainer[0].innerHTML = s;
-
- eventElements = segContainer.children();
-
- // retrieve elements, run through eventRender callback, bind event handlers
- for (i=0; i < seg.events.length; i++) {
- event = seg.events[i];
- eventElement = $(eventElements[i]); // faster than eq()
- if(bg) {
- eventElement.addClass('fc-source-bg');
- }
- triggerRes = trigger('eventRender', event, event, eventElement);
- if (triggerRes === false) {
- eventElement.remove();
- } else {
- if (triggerRes && triggerRes !== true) {
- eventElement.remove();
- eventElement = $(triggerRes).appendTo(segContainer);
- }
- if (event._id === modifiedEventId) {
- eventElementHandlers(event, eventElement, seg);
- } else {
- eventElement[0]._fci = i; // for lazySegBind
- }
- reportEventElement(event, eventElement);
- }
- trigger('eventAfterRender', event, event, eventElement);
- }
-
- lazySegBind(segContainer, seg, eventElementHandlers);
- markFirstLast(segContainer);
- segContainer.addClass('fc-day-'+seg.start.getDay());
- }
-
- nextMonth = $('<tbody class="fc-list-header"><tr><td class="fc-list-header fc-month-nav fc-month-next ' + headerClass + '" colspan="' + tableCols.length + '">' + opt('buttonText', 'nextMonth') + '</td></tr></tbody>').appendTo(table);
- nextMonth.click(function(){
- var nextMonthDate = cloneDate(t.getOrigDate(), true);
- nextMonthDate.setDate(1);
- nextMonthDate.setMonth(nextMonthDate.getMonth() + 1);
- calendar.gotoDate(nextMonthDate);
- trigger('nextClick');
- });
-
- //markFirstLast(table);
- }
-
-}
-
-
-fcViews.table = TableView;
-
-
-function TableView(element, calendar) {
- var t = this;
-
- // exports
- t.render = render;
- t.select = dummy;
- t.unselect = dummy;
- t.getDaySegmentContainer = function(){return table;};
- t.getOrigDate = function() {return origDate;};
- t.updateGrid = updateGrid;
- t.updateToday = updateToday;
- t.setAxisFormat = setAxisFormat;
- t.setStartOfBusiness = setStartOfBusiness;
- t.setEndOfBusiness = setEndOfBusiness;
- t.setWeekendDays = setWeekendDays;
- t.setBindingMode = setBindingMode;
- t.setSelectable = setSelectable;
-
- // imports
- View.call(t, element, calendar, 'table');
- TableEventRenderer.call(t);
- var opt = t.opt;
- var trigger = t.trigger;
- var clearEvents = t.clearEvents;
- var reportEventClear = t.reportEventClear;
- var formatDates = calendar.formatDates;
- var formatDate = calendar.formatDate;
-
- // overrides
- t.setWidth = setWidth;
- t.setHeight = setHeight;
-
- // locals
- var div;
- var table;
- var firstDay;
- var nwe;
- var tm;
- var colFormat;
- var datepicker;
- var dateInfo;
- var dateInfoNumber;
- var dateInfoNumberDiv;
- var dateInfoText;
- var origDate;
-
- function render(date, delta) {
- /*if (delta) {
- addDays(date, opt('listPage') * delta);
- }
- t.start = t.visStart = cloneDate(date, true);
- t.end = addDays(cloneDate(t.start), opt('listPage'));
- t.visEnd = addDays(cloneDate(t.start), opt('listRange'));*/
-
- origDate = date;
- if (delta) {
- addMonths(date, delta);
- date.setDate(1);
- }
- t.start = cloneDate(date, true);
- t.start.setDate(1);
- t.end = addMonths(cloneDate(t.start), 1);
- t.visStart = cloneDate(t.start);
- t.visEnd = cloneDate(t.end);
-
- addMinutes(t.visEnd, -1); // set end to 23:59
- t.title = formatDates(
- t.visStart,
- t.visEnd,
- opt('titleFormat')
- );
- //t.title = (t.visEnd.getTime() - t.visStart.getTime() < DAY_MS) ? formatDate(date, opt('titleFormat')) : formatDates(date, t.visEnd, opt('titleFormat'));
-
- updateOptions();
- if (!table) {
- buildSkeleton(origDate);
- } else {
- clearEvents();
- if(opt('showDatepicker')) {
- dateInfoNumberDiv.html(origDate.getDate());
- dateInfoText.html(formatDates(origDate, null, opt('titleFormat', 'table')));
- datepicker.datepicker('option','firstDay',firstDay);
- datepicker.datepicker('setDate', origDate);
- }
- }
- }
-
-
- function updateOptions() {
- firstDay = opt('firstDay');
- nwe = opt('weekends') ? 0 : 1;
- tm = opt('theme') ? 'ui' : 'fc';
- colFormat = opt('columnFormat');
- }
-
- function buildSkeleton(date) {
- var tableCols = opt('tableCols');
- var s =
- "<table class='fc-border-separate' style='width:100%' cellspacing='0'>" +
- "<colgroup>";
- for (var c=0; c < tableCols.length; c++) {
- s += "<col class='fc-event-" + tableCols[c] + "' />";
- }
- s += "</colgroup>" +
- "</table>";
- if(opt('showDatepicker')) {
- dateInfo = $('<div>').addClass('fc-table-dateinfo').appendTo(element);
- dateInfoNumber = $('<div>').addClass('fc-table-dateinfo-number').appendTo(dateInfo);
- dateInfoNumberDiv = $('<div>').appendTo(dateInfoNumber);
- dateInfoNumberDiv.html(date.getDate());
- dateInfoText = $('<div>').addClass('fc-table-dateinfo-text').appendTo(dateInfo);
- dateInfoText.html(formatDates(origDate, null, opt('titleFormat', 'table')));
- datepicker = $('<div>').addClass('fc-table-datepicker').appendTo(element);
- datepicker.datepicker({
- firstDay: opt('firstDay'),
- weekendDays: opt('weekendDays'),
- defaultDate: date,
- showWeek: true,
- weekHeader: '',
-
- onSelect: function(dateText, inst) {
- var date = new Date(dateText);
- calendar.gotoDate(date);
- trigger('datepickerClick', this, date);
- },
- });
- }
- div = $('<div>').addClass('fc-list-content').appendTo(element);
- table = $(s).appendTo(div);
- }
-
- function updateGrid()
- {
- updateToday();
- setAxisFormat();
- setStartOfBusiness();
- setEndOfBusiness();
- setWeekendDays();
- setBindingMode();
- setSelectable();
- }
-
- function updateToday()
- {
- var today = clearTime(new Date());
- var segHash = formatDate(today, colFormat);
-
- $(table).find('.fc-list-header').each(function() {
- $(this).removeClass('fc-today');
- $(this).next().children().removeClass('fc-state-highlight');
-
- if(segHash == $(this).find('td').html()) {
- $(this).addClass('fc-today');
- $(this).next().children().addClass('fc-state-highlight');
- }
- });
-
- datepicker.datepicker('refresh');
- }
-
- function setAxisFormat()
- {
- // dummy
- }
-
- function setStartOfBusiness()
- {
- // dummy
- }
-
- function setEndOfBusiness()
- {
- // dummy
- }
-
- function setWeekendDays()
- {
- var weekendDays = opt('weekendDays');
-
- $(table).find('.fc-list-section').each(function() {
- var day=parseInt(this.className.match(/fc-day-(\d)/)[1],10);
- if(weekendDays.indexOf(day)==-1)
- $(this).children().removeClass('fc-weekend-day');
- else
- $(this).children().addClass('fc-weekend-day');
- });
-
- if(opt('showDatepicker'))
- datepicker.datepicker('option','weekendDays',weekendDays);
- }
-
- function setBindingMode()
- {
- // dummy
- }
-
- function setSelectable()
- {
- // dummy
- }
-
- function setHeight(height, dateChanged) {
- if(opt('showDatepicker')) {
- var datepickerHeight = datepicker.height();
- dateInfoText.css('padding-bottom', datepickerHeight - datepicker.children().outerHeight() + 3); //+3 for paddings
- var textHeight = dateInfoText.outerHeight();
- dateInfoNumber.css({'height': datepickerHeight - textHeight,
- 'font-size': 145 - textHeight});
- dateInfoNumberDiv.height(145 - textHeight);
- }
-
- div.css('height', (height-div.position().top-2)+'px').css('overflow', 'auto');
- }
-
- function setWidth(width) {
- var outerWidth = Math.floor(element.parent().width() / 2) - 8;
- element.css({'left' : width, 'width' : outerWidth});
- }
-
- function dummy() {
- // Stub.
- }
-
-}
-
-function TodoEventRenderer() {
- var t = this;
-
- // exports
- t.renderEvents = renderEvents;
- t.clearEvents = clearEvents;
- t.renderEventTime = renderEventTime;
- t.compileDaySegs = compileSegs; // for DayEventRenderer
- t.lazySegBind = lazySegBind;
- t.sortCmp = sortCmp;
-
- // imports
- DayEventRenderer.call(t);
- var opt = t.opt;
- var sortCmp = t.sortCmp;
- var trigger = t.trigger;
- var compileSegs = t.compileDaySegs;
- var reportEvents = t.reportEvents;
- var reportEventClear = t.reportEventClear;
- var reportEventElement = t.reportEventElement;
- var eventElementHandlers = t.eventElementHandlers;
- var renderEventTime = t.renderEventTime;
- var showEvents = t.showEvents;
- var hideEvents = t.hideEvents;
- var getListContainer = t.getDaySegmentContainer;
- var lazySegBind = t.lazySegBind;
- var calendar = t.calendar;
- var formatDate = calendar.formatDate;
- var formatDates = calendar.formatDates;
- var prevMonth;
- var nextMonth;
-
- function compileSegs(events) {
- var segs = {};
- var event, i;
-
- //for (i=0; i < events.length; i++) {
- for (i=events.length-1; i > -1; i--) {
- event = events[i];
- var segHash = event.repeatHash;
- var eventEnd = event.end ? cloneDate(event.end) : cloneDate(event.start);
-
- // skip events out of range
- if ((event.completedOn && event.completedOn < t.start && (opt('showUnstartedEvents') || !event.start || event.completedOn > event.start)) ||
- (!opt('showUnstartedEvents') && event.start && event.start > t.visEnd)) {
- continue;
- }
-
- // start new segment
- if (!(segHash in segs)) {
- segs[segHash] = { events: [], id: segHash};
- }
-
- segs[segHash].events.push(event);
- }
-
- return segs;
- }
-
- function reverseSegs(oldSegs) {
- var newSegs = {};
- var keys = $.map(oldSegs, function (value, key) { return key; });
- var values = $.map(oldSegs, function (value, key) { return value; });
-
- for (i=keys.length-1; i > -1; i--) {
- newSegs[keys[i]] = values[i];
- }
-
- return newSegs;
- }
-
- function sortCmp(a, b) {
- /*var sd = a.start.getTime() - b.start.getTime();
- var aEnd = a.end ? a.end : a.start;
- var bEnd = b.end ? b.end : b.start;
- return sd + (sd ? 0 : aEnd.getTime() - bEnd.getTime());*/
- var aEnd = a.end ? a.end.getTime() : Infinity;
- var bEnd = b.end ? b.end.getTime() : Infinity;
- var aStart = a.start ? a.start.getTime() : Infinity;
- var bStart = b.start ? b.start.getTime() : Infinity;
- var aPriority = parseInt(a.priority, 10) || 10;
- var bPriority = parseInt(b.priority, 10) || 10;
-
- var statusSort = {
- "NEEDS-ACTION": 1,
- "IN-PROCESS": 2,
- "COMPLETED": 3,
- "CANCELLED": 4
- };
-
- if(aEnd < bEnd) {
- return -1;
- }
- else if(bEnd < aEnd) {
- return 1;
- }
- else if(aStart < bStart){
- return -1;
- }
- else if(bStart < aStart) {
- return 1;
- }
- else if(aPriority < bPriority) {
- return -1;
- }
- else if(bPriority < aPriority) {
- return 1;
- }
- else if(statusSort[a.status] < statusSort[b.status]) {
- return -1;
- }
- else if(statusSort[b.status] < statusSort[a.status]) {
- return 1;
- }
- else if(a.percent < b.percent) {
- return -1;
- }
- else if(b.percent < a.percent) {
- return 1;
- }
- else if(a.compareString < b.compareString) {
- return -1;
- }
- else if(b.compareString < a.compareString) {
- return 1;
- }
- else {
- return 0;
- }
- }
-
- // event time/date range to display
- function renderEventTime(event) {
- var timeFormat = opt('timeFormat', 'list');
- return event.end? formatDate(event.end, timeFormat) : '';
- }
-
- function lazySegBind(container, seg, bindHandlers) {
- container.unbind('mouseover').mouseover(function(ev) {
- var parent = ev.target, e = parent, i, event;
- while (parent != this) {
- e = parent;
- parent = parent.parentNode;
- }
- if ((i = e._fci) !== undefined) {
- e._fci = undefined;
- event = seg.events[i];
- bindHandlers(event, container.children().eq(0), seg);
- $(ev.target).trigger(ev);
- }
- ev.stopPropagation();
- });
- }
-
- function clearEvents() {
- reportEventClear();
- getListContainer().children('tbody').remove();
- }
-
- function renderEvents(events, modifiedEventId) {
- events.sort(sortCmp);
- reportEvents(events);
- renderSegs(reverseSegs(compileSegs(events)), modifiedEventId);
- getListContainer().removeClass('fc-list-smart fc-list-day fc-list-month fc-list-week').addClass('fc-list-' + opt('listSections'));
- //t.selectEvent();
- t.applyFilters();
- }
-
- function renderSegs(segs, modifiedEventId) {
- var tm = opt('theme') ? 'ui' : 'fc';
- var table = getListContainer();
- var headerClass = tm + "-widget-header";
- var contentClass = tm + "-widget-content";
- var segHeader = null;
- var tableCols = opt('todoCols');
- var timecol = $.inArray('time', tableCols) >= 0;
- var i, j, iter, seg, event, times, s, skinCss, skinCssAttr, skinClasses, rowClasses, segContainer, eventElements, eventElement, triggerRes;
-
- for (j in segs) {
- seg = segs[j];
-
- segContainer = $('<tbody>').addClass('fc-list-section ' + contentClass).appendTo(table);
- s = '';
-
- event = seg.events[0];
- iter=0;
- if(opt('showUnstartedEvents') && seg.events.length>1) {
- for(;iter<seg.events.length; iter++) {
- if(seg.events[iter].start<t.end) {
- event = seg.events[iter];
- break;
- }
- }
- if(iter==seg.events.length) {
- continue;
- }
- }
-
- dueTime = renderEventTime(event);
- skinCss = getSkinCss(event, opt);
- skinCssAttr = (skinCss ? " style='" + skinCss + "'" : '');
- skinClasses = ['fc-event-skin', 'fc-corner-left', 'fc-corner-right', 'fc-corner-top', 'fc-corner-bottom'].concat(event.className);
- if (event.source && event.source.className) {
- skinClasses = skinClasses.concat(event.source.className);
- }
-
- rowClasses = ['fc-event', 'fc-event-row'];
- if(event.end && event.end.getTime() < cloneDate(t.start, true)) {
- rowClasses.push('fc-event-pastdue');
- }
- else if(event.end && event.end.getTime() < addDays(cloneDate(t.start), 2, false).getTime()) {
- rowClasses.push('fc-event-urgent');
- }
- if(event.filterStatus) {
- rowClasses.push('fc-event-'+event.filterStatus);
- }
-
- s += "<tr class='" + rowClasses.join(' ') + "'>";
- for (var col, c=0; c < tableCols.length; c++) {
- col = tableCols[c];
- if (col == 'handle') {
- s += "<td class='fc-event-handle'" + skinCssAttr + "></td>";
- } else if (col == 'check') {
- s += "<td class='fc-event-check'>" + '<input type="checkbox" class="fc-event-checkbox" data-ind="false"/>' + "</td>";
- } else if (col == 'priority') {
- s += "<td class='fc-event-priority fc-event-priority-" + event.renderPriority + "'>" + (event.renderPriority ? '&nbsp;' : '') + "</td>";
- } else if (col == 'time') {
- s += "<td class='fc-event-time'>" + htmlEscape(dueTime) + "</td>";
- } else if (col == 'title') {
- s += "<td class='fc-event-title'>" + htmlEscape(event.title.replace(/(\r\n|\n|\r)+/gm, " ")) + "</td>";
- } else if (col == 'location') {
- s += "<td class='fc-event-location'>" + htmlEscape(event.location.replace(/(\r\n|\n|\r)+/gm, " ")) + "</td>";
- } else if (col == 'status') {
- s += "<td class='fc-event-status'></td>";
- } else if (col == 'percent') {
- s += "<td class='fc-event-percent'>" + event.percent + '%' + "</td>";
- }
- else {
- s += "<td class='fc-event-" + col + "'>" + (event[col] ? htmlEscape(event[col]) : '&nbsp;') + "</td>";
- }
- }
- s += "</tr>";
-
- // IE doesn't like innerHTML on tbody elements so we insert every row individually
- if (document.all) {
- $(s).appendTo(segContainer);
- s = '';
- }
-
- if (!document.all)
- segContainer[0].innerHTML = s;
-
- eventElements = segContainer.children();
-
- // retrieve elements, run through eventRender callback, bind event handlers
- eventElement = $(eventElements[0]); // faster than eq()
- triggerRes = trigger('eventRender', event, event, eventElement);
- if (triggerRes === false) {
- eventElement.remove();
- } else {
- if (triggerRes && triggerRes !== true) {
- eventElement.remove();
- eventElement = $(triggerRes).appendTo(segContainer);
- }
- if (event._id === modifiedEventId) {
- eventElementHandlers(event, eventElement, seg);
- } else {
- eventElement[0]._fci = iter; // for lazySegBind
- }
- reportEventElement(event, eventElement);
- }
- trigger('eventCheckDefault', event, event, eventElement.find('.fc-event-checkbox'));
- trigger('eventAfterRender', event, event, eventElement);
-
- lazySegBind(segContainer, seg, eventElementHandlers);
- markFirstLast(segContainer);
- }
-
- //markFirstLast(table);
- }
-
-}
-
-fcViews.todo = TodoView;
-
-function TodoView(element, calendar) {
- var t = this;
-
- // exports
- t.render = render;
- t.select = dummy;
- t.unselect = dummy;
- t.getDaySegmentContainer = function(){ return table; };
- t.applyFilters = applyFilters;
- t.allowSelectEvent = allowSelectEvent;
- t.eventSelectLock = 0;
- t.updateGrid = updateGrid;
- t.updateToday = updateToday;
- t.setAxisFormat = setAxisFormat;
- t.setStartOfBusiness = setStartOfBusiness;
- t.setEndOfBusiness = setEndOfBusiness;
- t.setWeekendDays = setWeekendDays;
- t.setBindingMode = setBindingMode;
- t.setSelectable = setSelectable;
-
- // imports
- View.call(t, element, calendar, 'todo');
- TodoEventRenderer.call(t);
- var opt = t.opt;
- var trigger = t.trigger;
- var clearEvents = t.clearEvents;
- var reportEventClear = t.reportEventClear;
- var formatDates = calendar.formatDates;
- var formatDate = calendar.formatDate;
-
- // overrides
- t.setWidth = setWidth;
- t.setHeight = setHeight;
-
- // locals
- var div;
- var table;
- var filter;
- var filterTable;
- var firstDay;
- var nwe;
- var tm;
- var colFormat;
- var currentDate;
- var datepickers;
- var dateInfo;
- var dateInfoNumber;
- var dateInfoNumberDiv;
- var dateInfoText;
-
- function render(date, delta) {
- if (delta) {
- addMonths(date, delta);
- date.setDate(1);
- }
- currentDate = date;
- var start = cloneDate(date, true);
- var end = addDays(cloneDate(start), 1);
- t.title = formatDate(date, opt('titleFormat'));
- t.start = t.visStart = start;
- t.end = t.visEnd = end;
-
- updateOptions();
- if (!table) {
- buildSkeleton(date);
- initFilters();
- } else {
- clearEvents();
- filterTable.find('.fc-filter-table-footer').text(opt('buttonText', 'filtersFooter').replace('%date%', formatDates(date, null, opt('columnFormat', 'todo'))));
- if(opt('showDatepicker')) {
- dateInfoNumberDiv.html(date.getDate());
- dateInfoText.html(formatDates(date, null, opt('titleFormat', 'todo')));
-
- var defaultDate = cloneDate(date, true);
- defaultDate.setHours(12);
- defaultDate.setDate(1);
- defaultDate.setMonth(currentDate.getMonth() - datepickers.length + 1);
-
- datepickers.forEach(function(e, i){
- defaultDate.setMonth(defaultDate.getMonth() + 1);
- e.datepicker('option','firstDay',firstDay);
- if((i===0 && datepickers.length<3) || (i===datepickers.length-2 && datepickers.length>2))
- e.datepicker('setDate', date);
- else
- e.datepicker('setDate', defaultDate);
- });
- }
- }
- }
-
- function updateOptions() {
- firstDay = opt('firstDay');
- nwe = opt('weekends') ? 0 : 1;
- tm = opt('theme') ? 'ui' : 'fc';
- colFormat = opt('columnFormat');
- }
-
- function buildSkeleton(date) {
- var tableCols = opt('todoCols');
- var s =
- "<table class='fc-border-separate' style='width:100%' cellspacing='0'>" +
- "<colgroup>";
- for (var c=0; c < tableCols.length; c++) {
- s += "<col class='fc-event-" + tableCols[c] + "' />";
- }
- s += "</colgroup>" +
- "</table>";
- if(opt('showDatepicker')) {
- dateInfo = $('<div>').addClass('fc-table-dateinfo').appendTo(element);
- dateInfoNumber = $('<div>').addClass('fc-table-dateinfo-number').appendTo(dateInfo);
- dateInfoNumberDiv = $('<div>').appendTo(dateInfoNumber);
- dateInfoNumberDiv.html(date.getDate());
- dateInfoText = $('<div>').addClass('fc-table-dateinfo-text').appendTo(dateInfo);
- dateInfoText.html(formatDates(date, null, opt('titleFormat', 'todo')));
-
- datepickers = [$('<div>').addClass('fc-table-datepicker fc-table-datepicker-current').appendTo(element)];
- datepickers[0].datepicker({
- firstDay: opt('firstDay'),
- weekendDays: opt('weekendDays'),
- defaultDate: date,
- showWeek: true,
- weekHeader: '',
-
- onSelect: function(dateText, inst) {
- var date = new Date(dateText);
- calendar.gotoDate(date);
- trigger('datepickerClick', this, date);
- }
- });
- }
- filter = $('<div>').addClass('fc-filter').appendTo(element);
- var ft = '<table class="fc-filter-table">' +
- '<tr>' +
- '<td class="fc-filter-table-header" colspan="2">'+opt('buttonText', 'filtersHeader')+'</td>' +
- '</tr>';
-
- if(opt('simpleFilters')) {
- ft += '<tr>' +
- '<td class="fc-filter-option fc-filter-action" data-type="filterAction">'+ opt('buttonText', 'filterAction') +'</td>' +
- '<td class="fc-filter-option fc-filter-completed fc-filter-option-last" data-type="filterCompleted">'+ opt('buttonText', 'filterCompleted') +' *</td>' +
- '</tr>';
- }
- else {
- ft += '<tr>' +
- '<td class="fc-filter-option fc-filter-action" data-type="filterAction">'+ opt('buttonText', 'filterAction') +'</td>' +
- '<td class="fc-filter-option fc-filter-progress" data-type="filterProgress">'+ opt('buttonText', 'filterProgress') +'</td>' +
- '</tr>' +
- '<tr>' +
- '<td class="fc-filter-option fc-filter-completed" data-type="filterCompleted">'+ opt('buttonText', 'filterCompleted') +' *</td>' +
- '<td class="fc-filter-option fc-filter-canceled fc-filter-option-last" data-type="filterCanceled">'+ opt('buttonText', 'filterCanceled') +'</td>' +
- '</tr>';
- }
-
- ft += '<tr>' +
- '<td class="fc-filter-table-footer" colspan="2">'+opt('buttonText', 'filtersFooter').replace('%date%', formatDates(date, null, opt('columnFormat', 'todo')))+'</td>' +
- '</tr>' +
- '</table>';
- filterTable = $(ft).appendTo(filter);
- div = $('<div>').addClass('fc-list-content').appendTo(element);
- table = $(s).appendTo(div);
- }
-
- function updateGrid()
- {
- updateToday();
- setAxisFormat();
- setStartOfBusiness();
- setEndOfBusiness();
- setWeekendDays();
- setBindingMode();
- setSelectable();
- }
-
- function updateToday()
- {
- if(opt('showDatepicker'))
- datepickers.forEach(function(e){
- e.datepicker('refresh');
- });
- }
-
- function setAxisFormat()
- {
- // dummy
- }
-
- function setStartOfBusiness()
- {
- // dummy
- }
-
- function setEndOfBusiness()
- {
- // dummy
- }
-
- function setWeekendDays()
- {
- if(opt('showDatepicker'))
- datepickers.forEach(function(e){
- e.datepicker('option','weekendDays',opt('weekendDays'));
- });
- }
-
- function setBindingMode()
- {
- // dummy
- }
-
- function setSelectable()
- {
- // dummy
- }
-
- function initFilters() {
- filterTable.find('.fc-filter-option').each(function() {
- if(opt('defaultFilters').indexOf($(this).attr('data-type')) != -1) {
- filterToggle($(this));
- }
- $(this).click(function(){
- filterToggle($(this));
- });
- });
- }
-
- function filterToggle(button) {
- if(button.hasClass('fc-filter-option-selected')) {
- button.removeClass('fc-filter-option-selected');
- }
- else {
- button.addClass('fc-filter-option-selected');
- }
- applyFilters();
- }
-
- function applyFilters() {
- filterTable.find('.fc-filter-option').each(function(){
- if($(this).hasClass('fc-filter-option-selected')) {
- t.getDaySegmentContainer().find('.fc-event-' + $(this).attr('data-type')).removeClass('fc-filter-hide');
- }
- else {
- t.getDaySegmentContainer().find('.fc-event-' + $(this).attr('data-type')).addClass('fc-filter-hide');
- }
- });
-
- opt('todoOptionalCols').forEach(function(item){
- var itemsFilled = $('.fc-event-'+item.col+':visible').filter(function(){
- return this.innerHTML!=='';
- });
-
- $('col.fc-event-'+item.col).toggleClass('fc-hidden-empty', !itemsFilled.length);
- });
-
- //if(!t.getDaySegmentContainer().find('.fc-event-selected:visible').length) {
- t.selectEvent();
- //}
- }
-
- function setHeight(height, dateChanged) {
- if(opt('showDatepicker')) {
- var datepickerHeight = datepickers[0].height();
- dateInfoText.css('padding-bottom', datepickerHeight - datepickers[0].children().outerHeight() + 3); //+3 for paddings
- var textHeight = dateInfoText.outerHeight();
- dateInfoNumber.css({'height': datepickerHeight - textHeight,
- 'font-size': 145 - textHeight});
- dateInfoNumberDiv.height(145 - textHeight);
- }
-
- div.css({'height': height-div.position().top-2, 'overflow': 'auto'});
- }
-
- function setWidth(width) {
- element.width(width);
- var slots = Math.floor((width - dateInfo.outerWidth() - 1) / datepickers[0].outerWidth());
-
- if(slots > datepickers.length) {
- var defaultDate = cloneDate(currentDate, true);
- defaultDate.setHours(12);
- defaultDate.setDate(1);
- defaultDate.setMonth(currentDate.getMonth() + 1);
-
- if(datepickers.length==1) {
- datepickers.push($('<div>').addClass('fc-table-datepicker fc-table-datepicker-no-default').prependTo(element).datepicker({
- firstDay: opt('firstDay'),
- weekendDays: opt('weekendDays'),
- defaultDate: cloneDate(defaultDate),
- showWeek: true,
- weekHeader: '',
- hideIfNoPrevNext: true,
-
- onSelect: function(dateText, inst) {
- var date = new Date(dateText);
- calendar.gotoDate(date);
- trigger('datepickerClick', this, date);
- }
- }));
- }
-
- defaultDate.setMonth(defaultDate.getMonth() - datepickers.length + 1);
- for(var i=datepickers.length; i<slots; i++) {
- defaultDate.setMonth(defaultDate.getMonth() - 1);
- datepickers.unshift($('<div>').addClass('fc-table-datepicker fc-table-datepicker-no-default').insertBefore(filter).datepicker({
- firstDay: opt('firstDay'),
- weekendDays: opt('weekendDays'),
- defaultDate: cloneDate(defaultDate),
- showWeek: true,
- weekHeader: '',
- hideIfNoPrevNext: true,
-
- onSelect: function(dateText, inst) {
- var date = new Date(dateText);
- calendar.gotoDate(date);
- trigger('datepickerClick', this, date);
- }
- }));
- }
- }
- else {
- while(datepickers.length>slots && datepickers.length>1) {
- if(datepickers.length==2)
- datepickers.pop().remove();
- else
- datepickers.shift().remove();
- }
- }
-
- var hiddenWidth = 0;
- opt('todoOptionalCols').forEach(function(e){
- hiddenWidth += $('col.fc-event-'+e.col).hasClass('fc-hidden-empty') ? e.width : 0;
- });
- opt('todoColThresholds').forEach(function(e){
- $('col.fc-event-'+e.col).toggleClass('fc-hidden-width', width<e.width-hiddenWidth);
- });
- }
-
- function allowSelectEvent(value) {
- if(value)
- t.eventSelectLock++;
- else
- t.eventSelectLock--;
- }
-
- function dummy() {
- // Stub.
- }
-
-}
-
-})(jQuery);
diff --git a/radicale_web/web/infcloud/lib/ie_base64.js b/radicale_web/web/infcloud/lib/ie_base64.js
deleted file mode 100644
index 5baba0d..0000000
--- a/radicale_web/web/infcloud/lib/ie_base64.js
+++ /dev/null
@@ -1,176 +0,0 @@
-/*
- * Copyright (c) 2010 Nick Galbreath
- * http://code.google.com/p/stringencoders/source/browse/#svn/trunk/javascript
- *
- * Permission is hereby granted, free of charge, to any person
- * obtaining a copy of this software and associated documentation
- * files (the "Software"), to deal in the Software without
- * restriction, including without limitation the rights to use,
- * copy, modify, merge, publish, distribute, sublicense, and/or sell
- * copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following
- * conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
- * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
- * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
- * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-/* base64 encode/decode compatible with window.btoa/atob
- *
- * window.atob/btoa is a Firefox extension to convert binary data (the "b")
- * to base64 (ascii, the "a").
- *
- * It is also found in Safari and Chrome. It is not available in IE.
- *
- * if (!window.btoa) window.btoa = base64.encode
- * if (!window.atob) window.atob = base64.decode
- *
- * The original spec's for atob/btoa are a bit lacking
- * https://developer.mozilla.org/en/DOM/window.atob
- * https://developer.mozilla.org/en/DOM/window.btoa
- *
- * window.btoa and base64.encode takes a string where charCodeAt is [0,255]
- * If any character is not [0,255], then an DOMException(5) is thrown.
- *
- * window.atob and base64.decode take a base64-encoded string
- * If the input length is not a multiple of 4, or contains invalid characters
- * then an DOMException(5) is thrown.
- */
-var base64 = {};
-base64.PADCHAR = '=';
-base64.ALPHA = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/';
-
-base64.makeDOMException = function() {
- // sadly in FF,Safari,Chrome you can't make a DOMException
- var e, tmp;
-
- try {
- return new DOMException(DOMException.INVALID_CHARACTER_ERR);
- } catch (tmp) {
- // not available, just passback a duck-typed equiv
- // https://developer.mozilla.org/en/Core_JavaScript_1.5_Reference/Global_Objects/Error
- // https://developer.mozilla.org/en/Core_JavaScript_1.5_Reference/Global_Objects/Error/prototype
- var ex = new Error("DOM Exception 5");
-
- // ex.number and ex.description is IE-specific.
- ex.code = ex.number = 5;
- ex.name = ex.description = "INVALID_CHARACTER_ERR";
-
- // Safari/Chrome output format
- ex.toString = function() { return 'Error: ' + ex.name + ': ' + ex.message; };
- return ex;
- }
-}
-
-base64.getbyte64 = function(s,i) {
- // This is oddly fast, except on Chrome/V8.
- // Minimal or no improvement in performance by using a
- // object with properties mapping chars to value (eg. 'A': 0)
- var idx = base64.ALPHA.indexOf(s.charAt(i));
- if (idx === -1) {
- throw base64.makeDOMException();
- }
- return idx;
-}
-
-base64.decode = function(s) {
- // convert to string
- s = '' + s;
- var getbyte64 = base64.getbyte64;
- var pads, i, b10;
- var imax = s.length
- if (imax === 0) {
- return s;
- }
-
- if (imax % 4 !== 0) {
- throw base64.makeDOMException();
- }
-
- pads = 0
- if (s.charAt(imax - 1) === base64.PADCHAR) {
- pads = 1;
- if (s.charAt(imax - 2) === base64.PADCHAR) {
- pads = 2;
- }
- // either way, we want to ignore this last block
- imax -= 4;
- }
-
- var x = [];
- for (i = 0; i < imax; i += 4) {
- b10 = (getbyte64(s,i) << 18) | (getbyte64(s,i+1) << 12) |
- (getbyte64(s,i+2) << 6) | getbyte64(s,i+3);
- x.push(String.fromCharCode(b10 >> 16, (b10 >> 8) & 0xff, b10 & 0xff));
- }
-
- switch (pads) {
- case 1:
- b10 = (getbyte64(s,i) << 18) | (getbyte64(s,i+1) << 12) | (getbyte64(s,i+2) << 6);
- x.push(String.fromCharCode(b10 >> 16, (b10 >> 8) & 0xff));
- break;
- case 2:
- b10 = (getbyte64(s,i) << 18) | (getbyte64(s,i+1) << 12);
- x.push(String.fromCharCode(b10 >> 16));
- break;
- }
- return x.join('');
-}
-
-base64.getbyte = function(s,i) {
- var x = s.charCodeAt(i);
- if (x > 255) {
- throw base64.makeDOMException();
- }
- return x;
-}
-
-base64.encode = function(s) {
- if (arguments.length !== 1) {
- throw new SyntaxError("Not enough arguments");
- }
- var padchar = base64.PADCHAR;
- var alpha = base64.ALPHA;
- var getbyte = base64.getbyte;
-
- var i, b10;
- var x = [];
-
- // convert to string
- s = '' + s;
-
- var imax = s.length - s.length % 3;
-
- if (s.length === 0) {
- return s;
- }
- for (i = 0; i < imax; i += 3) {
- b10 = (getbyte(s,i) << 16) | (getbyte(s,i+1) << 8) | getbyte(s,i+2);
- x.push(alpha.charAt(b10 >> 18));
- x.push(alpha.charAt((b10 >> 12) & 0x3F));
- x.push(alpha.charAt((b10 >> 6) & 0x3f));
- x.push(alpha.charAt(b10 & 0x3f));
- }
- switch (s.length - imax) {
- case 1:
- b10 = getbyte(s,i) << 16;
- x.push(alpha.charAt(b10 >> 18) + alpha.charAt((b10 >> 12) & 0x3F) +
- padchar + padchar);
- break;
- case 2:
- b10 = (getbyte(s,i) << 16) | (getbyte(s,i+1) << 8);
- x.push(alpha.charAt(b10 >> 18) + alpha.charAt((b10 >> 12) & 0x3F) +
- alpha.charAt((b10 >> 6) & 0x3f) + padchar);
- break;
- }
- return x.join('');
-}
diff --git a/radicale_web/web/infcloud/lib/jquery-2.1.4.min.js b/radicale_web/web/infcloud/lib/jquery-2.1.4.min.js
deleted file mode 100644
index 49990d6..0000000
--- a/radicale_web/web/infcloud/lib/jquery-2.1.4.min.js
+++ /dev/null
@@ -1,4 +0,0 @@
-/*! jQuery v2.1.4 | (c) 2005, 2015 jQuery Foundation, Inc. | jquery.org/license */
-!function(a,b){"object"==typeof module&&"object"==typeof module.exports?module.exports=a.document?b(a,!0):function(a){if(!a.document)throw new Error("jQuery requires a window with a document");return b(a)}:b(a)}("undefined"!=typeof window?window:this,function(a,b){var c=[],d=c.slice,e=c.concat,f=c.push,g=c.indexOf,h={},i=h.toString,j=h.hasOwnProperty,k={},l=a.document,m="2.1.4",n=function(a,b){return new n.fn.init(a,b)},o=/^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g,p=/^-ms-/,q=/-([\da-z])/gi,r=function(a,b){return b.toUpperCase()};n.fn=n.prototype={jquery:m,constructor:n,selector:"",length:0,toArray:function(){return d.call(this)},get:function(a){return null!=a?0>a?this[a+this.length]:this[a]:d.call(this)},pushStack:function(a){var b=n.merge(this.constructor(),a);return b.prevObject=this,b.context=this.context,b},each:function(a,b){return n.each(this,a,b)},map:function(a){return this.pushStack(n.map(this,function(b,c){return a.call(b,c,b)}))},slice:function(){return this.pushStack(d.apply(this,arguments))},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},eq:function(a){var b=this.length,c=+a+(0>a?b:0);return this.pushStack(c>=0&&b>c?[this[c]]:[])},end:function(){return this.prevObject||this.constructor(null)},push:f,sort:c.sort,splice:c.splice},n.extend=n.fn.extend=function(){var a,b,c,d,e,f,g=arguments[0]||{},h=1,i=arguments.length,j=!1;for("boolean"==typeof g&&(j=g,g=arguments[h]||{},h++),"object"==typeof g||n.isFunction(g)||(g={}),h===i&&(g=this,h--);i>h;h++)if(null!=(a=arguments[h]))for(b in a)c=g[b],d=a[b],g!==d&&(j&&d&&(n.isPlainObject(d)||(e=n.isArray(d)))?(e?(e=!1,f=c&&n.isArray(c)?c:[]):f=c&&n.isPlainObject(c)?c:{},g[b]=n.extend(j,f,d)):void 0!==d&&(g[b]=d));return g},n.extend({expando:"jQuery"+(m+Math.random()).replace(/\D/g,""),isReady:!0,error:function(a){throw new Error(a)},noop:function(){},isFunction:function(a){return"function"===n.type(a)},isArray:Array.isArray,isWindow:function(a){return null!=a&&a===a.window},isNumeric:function(a){return!n.isArray(a)&&a-parseFloat(a)+1>=0},isPlainObject:function(a){return"object"!==n.type(a)||a.nodeType||n.isWindow(a)?!1:a.constructor&&!j.call(a.constructor.prototype,"isPrototypeOf")?!1:!0},isEmptyObject:function(a){var b;for(b in a)return!1;return!0},type:function(a){return null==a?a+"":"object"==typeof a||"function"==typeof a?h[i.call(a)]||"object":typeof a},globalEval:function(a){var b,c=eval;a=n.trim(a),a&&(1===a.indexOf("use strict")?(b=l.createElement("script"),b.text=a,l.head.appendChild(b).parentNode.removeChild(b)):c(a))},camelCase:function(a){return a.replace(p,"ms-").replace(q,r)},nodeName:function(a,b){return a.nodeName&&a.nodeName.toLowerCase()===b.toLowerCase()},each:function(a,b,c){var d,e=0,f=a.length,g=s(a);if(c){if(g){for(;f>e;e++)if(d=b.apply(a[e],c),d===!1)break}else for(e in a)if(d=b.apply(a[e],c),d===!1)break}else if(g){for(;f>e;e++)if(d=b.call(a[e],e,a[e]),d===!1)break}else for(e in a)if(d=b.call(a[e],e,a[e]),d===!1)break;return a},trim:function(a){return null==a?"":(a+"").replace(o,"")},makeArray:function(a,b){var c=b||[];return null!=a&&(s(Object(a))?n.merge(c,"string"==typeof a?[a]:a):f.call(c,a)),c},inArray:function(a,b,c){return null==b?-1:g.call(b,a,c)},merge:function(a,b){for(var c=+b.length,d=0,e=a.length;c>d;d++)a[e++]=b[d];return a.length=e,a},grep:function(a,b,c){for(var d,e=[],f=0,g=a.length,h=!c;g>f;f++)d=!b(a[f],f),d!==h&&e.push(a[f]);return e},map:function(a,b,c){var d,f=0,g=a.length,h=s(a),i=[];if(h)for(;g>f;f++)d=b(a[f],f,c),null!=d&&i.push(d);else for(f in a)d=b(a[f],f,c),null!=d&&i.push(d);return e.apply([],i)},guid:1,proxy:function(a,b){var c,e,f;return"string"==typeof b&&(c=a[b],b=a,a=c),n.isFunction(a)?(e=d.call(arguments,2),f=function(){return a.apply(b||this,e.concat(d.call(arguments)))},f.guid=a.guid=a.guid||n.guid++,f):void 0},now:Date.now,support:k}),n.each("Boolean Number String Function Array Date RegExp Object Error".split(" "),function(a,b){h["[object "+b+"]"]=b.toLowerCase()});function s(a){var b="length"in a&&a.length,c=n.type(a);return"function"===c||n.isWindow(a)?!1:1===a.nodeType&&b?!0:"array"===c||0===b||"number"==typeof b&&b>0&&b-1 in a}var t=function(a){var b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u="sizzle"+1*new Date,v=a.document,w=0,x=0,y=ha(),z=ha(),A=ha(),B=function(a,b){return a===b&&(l=!0),0},C=1<<31,D={}.hasOwnProperty,E=[],F=E.pop,G=E.push,H=E.push,I=E.slice,J=function(a,b){for(var c=0,d=a.length;d>c;c++)if(a[c]===b)return c;return-1},K="checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped",L="[\\x20\\t\\r\\n\\f]",M="(?:\\\\.|[\\w-]|[^\\x00-\\xa0])+",N=M.replace("w","w#"),O="\\["+L+"*("+M+")(?:"+L+"*([*^$|!~]?=)"+L+"*(?:'((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\"|("+N+"))|)"+L+"*\\]",P=":("+M+")(?:\\((('((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\")|((?:\\\\.|[^\\\\()[\\]]|"+O+")*)|.*)\\)|)",Q=new RegExp(L+"+","g"),R=new RegExp("^"+L+"+|((?:^|[^\\\\])(?:\\\\.)*)"+L+"+$","g"),S=new RegExp("^"+L+"*,"+L+"*"),T=new RegExp("^"+L+"*([>+~]|"+L+")"+L+"*"),U=new RegExp("="+L+"*([^\\]'\"]*?)"+L+"*\\]","g"),V=new RegExp(P),W=new RegExp("^"+N+"$"),X={ID:new RegExp("^#("+M+")"),CLASS:new RegExp("^\\.("+M+")"),TAG:new RegExp("^("+M.replace("w","w*")+")"),ATTR:new RegExp("^"+O),PSEUDO:new RegExp("^"+P),CHILD:new RegExp("^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\("+L+"*(even|odd|(([+-]|)(\\d*)n|)"+L+"*(?:([+-]|)"+L+"*(\\d+)|))"+L+"*\\)|)","i"),bool:new RegExp("^(?:"+K+")$","i"),needsContext:new RegExp("^"+L+"*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\("+L+"*((?:-\\d)?\\d*)"+L+"*\\)|)(?=[^-]|$)","i")},Y=/^(?:input|select|textarea|button)$/i,Z=/^h\d$/i,$=/^[^{]+\{\s*\[native \w/,_=/^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/,aa=/[+~]/,ba=/'|\\/g,ca=new RegExp("\\\\([\\da-f]{1,6}"+L+"?|("+L+")|.)","ig"),da=function(a,b,c){var d="0x"+b-65536;return d!==d||c?b:0>d?String.fromCharCode(d+65536):String.fromCharCode(d>>10|55296,1023&d|56320)},ea=function(){m()};try{H.apply(E=I.call(v.childNodes),v.childNodes),E[v.childNodes.length].nodeType}catch(fa){H={apply:E.length?function(a,b){G.apply(a,I.call(b))}:function(a,b){var c=a.length,d=0;while(a[c++]=b[d++]);a.length=c-1}}}function ga(a,b,d,e){var f,h,j,k,l,o,r,s,w,x;if((b?b.ownerDocument||b:v)!==n&&m(b),b=b||n,d=d||[],k=b.nodeType,"string"!=typeof a||!a||1!==k&&9!==k&&11!==k)return d;if(!e&&p){if(11!==k&&(f=_.exec(a)))if(j=f[1]){if(9===k){if(h=b.getElementById(j),!h||!h.parentNode)return d;if(h.id===j)return d.push(h),d}else if(b.ownerDocument&&(h=b.ownerDocument.getElementById(j))&&t(b,h)&&h.id===j)return d.push(h),d}else{if(f[2])return H.apply(d,b.getElementsByTagName(a)),d;if((j=f[3])&&c.getElementsByClassName)return H.apply(d,b.getElementsByClassName(j)),d}if(c.qsa&&(!q||!q.test(a))){if(s=r=u,w=b,x=1!==k&&a,1===k&&"object"!==b.nodeName.toLowerCase()){o=g(a),(r=b.getAttribute("id"))?s=r.replace(ba,"\\$&"):b.setAttribute("id",s),s="[id='"+s+"'] ",l=o.length;while(l--)o[l]=s+ra(o[l]);w=aa.test(a)&&pa(b.parentNode)||b,x=o.join(",")}if(x)try{return H.apply(d,w.querySelectorAll(x)),d}catch(y){}finally{r||b.removeAttribute("id")}}}return i(a.replace(R,"$1"),b,d,e)}function ha(){var a=[];function b(c,e){return a.push(c+" ")>d.cacheLength&&delete b[a.shift()],b[c+" "]=e}return b}function ia(a){return a[u]=!0,a}function ja(a){var b=n.createElement("div");try{return!!a(b)}catch(c){return!1}finally{b.parentNode&&b.parentNode.removeChild(b),b=null}}function ka(a,b){var c=a.split("|"),e=a.length;while(e--)d.attrHandle[c[e]]=b}function la(a,b){var c=b&&a,d=c&&1===a.nodeType&&1===b.nodeType&&(~b.sourceIndex||C)-(~a.sourceIndex||C);if(d)return d;if(c)while(c=c.nextSibling)if(c===b)return-1;return a?1:-1}function ma(a){return function(b){var c=b.nodeName.toLowerCase();return"input"===c&&b.type===a}}function na(a){return function(b){var c=b.nodeName.toLowerCase();return("input"===c||"button"===c)&&b.type===a}}function oa(a){return ia(function(b){return b=+b,ia(function(c,d){var e,f=a([],c.length,b),g=f.length;while(g--)c[e=f[g]]&&(c[e]=!(d[e]=c[e]))})})}function pa(a){return a&&"undefined"!=typeof a.getElementsByTagName&&a}c=ga.support={},f=ga.isXML=function(a){var b=a&&(a.ownerDocument||a).documentElement;return b?"HTML"!==b.nodeName:!1},m=ga.setDocument=function(a){var b,e,g=a?a.ownerDocument||a:v;return g!==n&&9===g.nodeType&&g.documentElement?(n=g,o=g.documentElement,e=g.defaultView,e&&e!==e.top&&(e.addEventListener?e.addEventListener("unload",ea,!1):e.attachEvent&&e.attachEvent("onunload",ea)),p=!f(g),c.attributes=ja(function(a){return a.className="i",!a.getAttribute("className")}),c.getElementsByTagName=ja(function(a){return a.appendChild(g.createComment("")),!a.getElementsByTagName("*").length}),c.getElementsByClassName=$.test(g.getElementsByClassName),c.getById=ja(function(a){return o.appendChild(a).id=u,!g.getElementsByName||!g.getElementsByName(u).length}),c.getById?(d.find.ID=function(a,b){if("undefined"!=typeof b.getElementById&&p){var c=b.getElementById(a);return c&&c.parentNode?[c]:[]}},d.filter.ID=function(a){var b=a.replace(ca,da);return function(a){return a.getAttribute("id")===b}}):(delete d.find.ID,d.filter.ID=function(a){var b=a.replace(ca,da);return function(a){var c="undefined"!=typeof a.getAttributeNode&&a.getAttributeNode("id");return c&&c.value===b}}),d.find.TAG=c.getElementsByTagName?function(a,b){return"undefined"!=typeof b.getElementsByTagName?b.getElementsByTagName(a):c.qsa?b.querySelectorAll(a):void 0}:function(a,b){var c,d=[],e=0,f=b.getElementsByTagName(a);if("*"===a){while(c=f[e++])1===c.nodeType&&d.push(c);return d}return f},d.find.CLASS=c.getElementsByClassName&&function(a,b){return p?b.getElementsByClassName(a):void 0},r=[],q=[],(c.qsa=$.test(g.querySelectorAll))&&(ja(function(a){o.appendChild(a).innerHTML="<a id='"+u+"'></a><select id='"+u+"-\f]' msallowcapture=''><option selected=''></option></select>",a.querySelectorAll("[msallowcapture^='']").length&&q.push("[*^$]="+L+"*(?:''|\"\")"),a.querySelectorAll("[selected]").length||q.push("\\["+L+"*(?:value|"+K+")"),a.querySelectorAll("[id~="+u+"-]").length||q.push("~="),a.querySelectorAll(":checked").length||q.push(":checked"),a.querySelectorAll("a#"+u+"+*").length||q.push(".#.+[+~]")}),ja(function(a){var b=g.createElement("input");b.setAttribute("type","hidden"),a.appendChild(b).setAttribute("name","D"),a.querySelectorAll("[name=d]").length&&q.push("name"+L+"*[*^$|!~]?="),a.querySelectorAll(":enabled").length||q.push(":enabled",":disabled"),a.querySelectorAll("*,:x"),q.push(",.*:")})),(c.matchesSelector=$.test(s=o.matches||o.webkitMatchesSelector||o.mozMatchesSelector||o.oMatchesSelector||o.msMatchesSelector))&&ja(function(a){c.disconnectedMatch=s.call(a,"div"),s.call(a,"[s!='']:x"),r.push("!=",P)}),q=q.length&&new RegExp(q.join("|")),r=r.length&&new RegExp(r.join("|")),b=$.test(o.compareDocumentPosition),t=b||$.test(o.contains)?function(a,b){var c=9===a.nodeType?a.documentElement:a,d=b&&b.parentNode;return a===d||!(!d||1!==d.nodeType||!(c.contains?c.contains(d):a.compareDocumentPosition&&16&a.compareDocumentPosition(d)))}:function(a,b){if(b)while(b=b.parentNode)if(b===a)return!0;return!1},B=b?function(a,b){if(a===b)return l=!0,0;var d=!a.compareDocumentPosition-!b.compareDocumentPosition;return d?d:(d=(a.ownerDocument||a)===(b.ownerDocument||b)?a.compareDocumentPosition(b):1,1&d||!c.sortDetached&&b.compareDocumentPosition(a)===d?a===g||a.ownerDocument===v&&t(v,a)?-1:b===g||b.ownerDocument===v&&t(v,b)?1:k?J(k,a)-J(k,b):0:4&d?-1:1)}:function(a,b){if(a===b)return l=!0,0;var c,d=0,e=a.parentNode,f=b.parentNode,h=[a],i=[b];if(!e||!f)return a===g?-1:b===g?1:e?-1:f?1:k?J(k,a)-J(k,b):0;if(e===f)return la(a,b);c=a;while(c=c.parentNode)h.unshift(c);c=b;while(c=c.parentNode)i.unshift(c);while(h[d]===i[d])d++;return d?la(h[d],i[d]):h[d]===v?-1:i[d]===v?1:0},g):n},ga.matches=function(a,b){return ga(a,null,null,b)},ga.matchesSelector=function(a,b){if((a.ownerDocument||a)!==n&&m(a),b=b.replace(U,"='$1']"),!(!c.matchesSelector||!p||r&&r.test(b)||q&&q.test(b)))try{var d=s.call(a,b);if(d||c.disconnectedMatch||a.document&&11!==a.document.nodeType)return d}catch(e){}return ga(b,n,null,[a]).length>0},ga.contains=function(a,b){return(a.ownerDocument||a)!==n&&m(a),t(a,b)},ga.attr=function(a,b){(a.ownerDocument||a)!==n&&m(a);var e=d.attrHandle[b.toLowerCase()],f=e&&D.call(d.attrHandle,b.toLowerCase())?e(a,b,!p):void 0;return void 0!==f?f:c.attributes||!p?a.getAttribute(b):(f=a.getAttributeNode(b))&&f.specified?f.value:null},ga.error=function(a){throw new Error("Syntax error, unrecognized expression: "+a)},ga.uniqueSort=function(a){var b,d=[],e=0,f=0;if(l=!c.detectDuplicates,k=!c.sortStable&&a.slice(0),a.sort(B),l){while(b=a[f++])b===a[f]&&(e=d.push(f));while(e--)a.splice(d[e],1)}return k=null,a},e=ga.getText=function(a){var b,c="",d=0,f=a.nodeType;if(f){if(1===f||9===f||11===f){if("string"==typeof a.textContent)return a.textContent;for(a=a.firstChild;a;a=a.nextSibling)c+=e(a)}else if(3===f||4===f)return a.nodeValue}else while(b=a[d++])c+=e(b);return c},d=ga.selectors={cacheLength:50,createPseudo:ia,match:X,attrHandle:{},find:{},relative:{">":{dir:"parentNode",first:!0}," ":{dir:"parentNode"},"+":{dir:"previousSibling",first:!0},"~":{dir:"previousSibling"}},preFilter:{ATTR:function(a){return a[1]=a[1].replace(ca,da),a[3]=(a[3]||a[4]||a[5]||"").replace(ca,da),"~="===a[2]&&(a[3]=" "+a[3]+" "),a.slice(0,4)},CHILD:function(a){return a[1]=a[1].toLowerCase(),"nth"===a[1].slice(0,3)?(a[3]||ga.error(a[0]),a[4]=+(a[4]?a[5]+(a[6]||1):2*("even"===a[3]||"odd"===a[3])),a[5]=+(a[7]+a[8]||"odd"===a[3])):a[3]&&ga.error(a[0]),a},PSEUDO:function(a){var b,c=!a[6]&&a[2];return X.CHILD.test(a[0])?null:(a[3]?a[2]=a[4]||a[5]||"":c&&V.test(c)&&(b=g(c,!0))&&(b=c.indexOf(")",c.length-b)-c.length)&&(a[0]=a[0].slice(0,b),a[2]=c.slice(0,b)),a.slice(0,3))}},filter:{TAG:function(a){var b=a.replace(ca,da).toLowerCase();return"*"===a?function(){return!0}:function(a){return a.nodeName&&a.nodeName.toLowerCase()===b}},CLASS:function(a){var b=y[a+" "];return b||(b=new RegExp("(^|"+L+")"+a+"("+L+"|$)"))&&y(a,function(a){return b.test("string"==typeof a.className&&a.className||"undefined"!=typeof a.getAttribute&&a.getAttribute("class")||"")})},ATTR:function(a,b,c){return function(d){var e=ga.attr(d,a);return null==e?"!="===b:b?(e+="","="===b?e===c:"!="===b?e!==c:"^="===b?c&&0===e.indexOf(c):"*="===b?c&&e.indexOf(c)>-1:"$="===b?c&&e.slice(-c.length)===c:"~="===b?(" "+e.replace(Q," ")+" ").indexOf(c)>-1:"|="===b?e===c||e.slice(0,c.length+1)===c+"-":!1):!0}},CHILD:function(a,b,c,d,e){var f="nth"!==a.slice(0,3),g="last"!==a.slice(-4),h="of-type"===b;return 1===d&&0===e?function(a){return!!a.parentNode}:function(b,c,i){var j,k,l,m,n,o,p=f!==g?"nextSibling":"previousSibling",q=b.parentNode,r=h&&b.nodeName.toLowerCase(),s=!i&&!h;if(q){if(f){while(p){l=b;while(l=l[p])if(h?l.nodeName.toLowerCase()===r:1===l.nodeType)return!1;o=p="only"===a&&!o&&"nextSibling"}return!0}if(o=[g?q.firstChild:q.lastChild],g&&s){k=q[u]||(q[u]={}),j=k[a]||[],n=j[0]===w&&j[1],m=j[0]===w&&j[2],l=n&&q.childNodes[n];while(l=++n&&l&&l[p]||(m=n=0)||o.pop())if(1===l.nodeType&&++m&&l===b){k[a]=[w,n,m];break}}else if(s&&(j=(b[u]||(b[u]={}))[a])&&j[0]===w)m=j[1];else while(l=++n&&l&&l[p]||(m=n=0)||o.pop())if((h?l.nodeName.toLowerCase()===r:1===l.nodeType)&&++m&&(s&&((l[u]||(l[u]={}))[a]=[w,m]),l===b))break;return m-=e,m===d||m%d===0&&m/d>=0}}},PSEUDO:function(a,b){var c,e=d.pseudos[a]||d.setFilters[a.toLowerCase()]||ga.error("unsupported pseudo: "+a);return e[u]?e(b):e.length>1?(c=[a,a,"",b],d.setFilters.hasOwnProperty(a.toLowerCase())?ia(function(a,c){var d,f=e(a,b),g=f.length;while(g--)d=J(a,f[g]),a[d]=!(c[d]=f[g])}):function(a){return e(a,0,c)}):e}},pseudos:{not:ia(function(a){var b=[],c=[],d=h(a.replace(R,"$1"));return d[u]?ia(function(a,b,c,e){var f,g=d(a,null,e,[]),h=a.length;while(h--)(f=g[h])&&(a[h]=!(b[h]=f))}):function(a,e,f){return b[0]=a,d(b,null,f,c),b[0]=null,!c.pop()}}),has:ia(function(a){return function(b){return ga(a,b).length>0}}),contains:ia(function(a){return a=a.replace(ca,da),function(b){return(b.textContent||b.innerText||e(b)).indexOf(a)>-1}}),lang:ia(function(a){return W.test(a||"")||ga.error("unsupported lang: "+a),a=a.replace(ca,da).toLowerCase(),function(b){var c;do if(c=p?b.lang:b.getAttribute("xml:lang")||b.getAttribute("lang"))return c=c.toLowerCase(),c===a||0===c.indexOf(a+"-");while((b=b.parentNode)&&1===b.nodeType);return!1}}),target:function(b){var c=a.location&&a.location.hash;return c&&c.slice(1)===b.id},root:function(a){return a===o},focus:function(a){return a===n.activeElement&&(!n.hasFocus||n.hasFocus())&&!!(a.type||a.href||~a.tabIndex)},enabled:function(a){return a.disabled===!1},disabled:function(a){return a.disabled===!0},checked:function(a){var b=a.nodeName.toLowerCase();return"input"===b&&!!a.checked||"option"===b&&!!a.selected},selected:function(a){return a.parentNode&&a.parentNode.selectedIndex,a.selected===!0},empty:function(a){for(a=a.firstChild;a;a=a.nextSibling)if(a.nodeType<6)return!1;return!0},parent:function(a){return!d.pseudos.empty(a)},header:function(a){return Z.test(a.nodeName)},input:function(a){return Y.test(a.nodeName)},button:function(a){var b=a.nodeName.toLowerCase();return"input"===b&&"button"===a.type||"button"===b},text:function(a){var b;return"input"===a.nodeName.toLowerCase()&&"text"===a.type&&(null==(b=a.getAttribute("type"))||"text"===b.toLowerCase())},first:oa(function(){return[0]}),last:oa(function(a,b){return[b-1]}),eq:oa(function(a,b,c){return[0>c?c+b:c]}),even:oa(function(a,b){for(var c=0;b>c;c+=2)a.push(c);return a}),odd:oa(function(a,b){for(var c=1;b>c;c+=2)a.push(c);return a}),lt:oa(function(a,b,c){for(var d=0>c?c+b:c;--d>=0;)a.push(d);return a}),gt:oa(function(a,b,c){for(var d=0>c?c+b:c;++d<b;)a.push(d);return a})}},d.pseudos.nth=d.pseudos.eq;for(b in{radio:!0,checkbox:!0,file:!0,password:!0,image:!0})d.pseudos[b]=ma(b);for(b in{submit:!0,reset:!0})d.pseudos[b]=na(b);function qa(){}qa.prototype=d.filters=d.pseudos,d.setFilters=new qa,g=ga.tokenize=function(a,b){var c,e,f,g,h,i,j,k=z[a+" "];if(k)return b?0:k.slice(0);h=a,i=[],j=d.preFilter;while(h){(!c||(e=S.exec(h)))&&(e&&(h=h.slice(e[0].length)||h),i.push(f=[])),c=!1,(e=T.exec(h))&&(c=e.shift(),f.push({value:c,type:e[0].replace(R," ")}),h=h.slice(c.length));for(g in d.filter)!(e=X[g].exec(h))||j[g]&&!(e=j[g](e))||(c=e.shift(),f.push({value:c,type:g,matches:e}),h=h.slice(c.length));if(!c)break}return b?h.length:h?ga.error(a):z(a,i).slice(0)};function ra(a){for(var b=0,c=a.length,d="";c>b;b++)d+=a[b].value;return d}function sa(a,b,c){var d=b.dir,e=c&&"parentNode"===d,f=x++;return b.first?function(b,c,f){while(b=b[d])if(1===b.nodeType||e)return a(b,c,f)}:function(b,c,g){var h,i,j=[w,f];if(g){while(b=b[d])if((1===b.nodeType||e)&&a(b,c,g))return!0}else while(b=b[d])if(1===b.nodeType||e){if(i=b[u]||(b[u]={}),(h=i[d])&&h[0]===w&&h[1]===f)return j[2]=h[2];if(i[d]=j,j[2]=a(b,c,g))return!0}}}function ta(a){return a.length>1?function(b,c,d){var e=a.length;while(e--)if(!a[e](b,c,d))return!1;return!0}:a[0]}function ua(a,b,c){for(var d=0,e=b.length;e>d;d++)ga(a,b[d],c);return c}function va(a,b,c,d,e){for(var f,g=[],h=0,i=a.length,j=null!=b;i>h;h++)(f=a[h])&&(!c||c(f,d,e))&&(g.push(f),j&&b.push(h));return g}function wa(a,b,c,d,e,f){return d&&!d[u]&&(d=wa(d)),e&&!e[u]&&(e=wa(e,f)),ia(function(f,g,h,i){var j,k,l,m=[],n=[],o=g.length,p=f||ua(b||"*",h.nodeType?[h]:h,[]),q=!a||!f&&b?p:va(p,m,a,h,i),r=c?e||(f?a:o||d)?[]:g:q;if(c&&c(q,r,h,i),d){j=va(r,n),d(j,[],h,i),k=j.length;while(k--)(l=j[k])&&(r[n[k]]=!(q[n[k]]=l))}if(f){if(e||a){if(e){j=[],k=r.length;while(k--)(l=r[k])&&j.push(q[k]=l);e(null,r=[],j,i)}k=r.length;while(k--)(l=r[k])&&(j=e?J(f,l):m[k])>-1&&(f[j]=!(g[j]=l))}}else r=va(r===g?r.splice(o,r.length):r),e?e(null,g,r,i):H.apply(g,r)})}function xa(a){for(var b,c,e,f=a.length,g=d.relative[a[0].type],h=g||d.relative[" "],i=g?1:0,k=sa(function(a){return a===b},h,!0),l=sa(function(a){return J(b,a)>-1},h,!0),m=[function(a,c,d){var e=!g&&(d||c!==j)||((b=c).nodeType?k(a,c,d):l(a,c,d));return b=null,e}];f>i;i++)if(c=d.relative[a[i].type])m=[sa(ta(m),c)];else{if(c=d.filter[a[i].type].apply(null,a[i].matches),c[u]){for(e=++i;f>e;e++)if(d.relative[a[e].type])break;return wa(i>1&&ta(m),i>1&&ra(a.slice(0,i-1).concat({value:" "===a[i-2].type?"*":""})).replace(R,"$1"),c,e>i&&xa(a.slice(i,e)),f>e&&xa(a=a.slice(e)),f>e&&ra(a))}m.push(c)}return ta(m)}function ya(a,b){var c=b.length>0,e=a.length>0,f=function(f,g,h,i,k){var l,m,o,p=0,q="0",r=f&&[],s=[],t=j,u=f||e&&d.find.TAG("*",k),v=w+=null==t?1:Math.random()||.1,x=u.length;for(k&&(j=g!==n&&g);q!==x&&null!=(l=u[q]);q++){if(e&&l){m=0;while(o=a[m++])if(o(l,g,h)){i.push(l);break}k&&(w=v)}c&&((l=!o&&l)&&p--,f&&r.push(l))}if(p+=q,c&&q!==p){m=0;while(o=b[m++])o(r,s,g,h);if(f){if(p>0)while(q--)r[q]||s[q]||(s[q]=F.call(i));s=va(s)}H.apply(i,s),k&&!f&&s.length>0&&p+b.length>1&&ga.uniqueSort(i)}return k&&(w=v,j=t),r};return c?ia(f):f}return h=ga.compile=function(a,b){var c,d=[],e=[],f=A[a+" "];if(!f){b||(b=g(a)),c=b.length;while(c--)f=xa(b[c]),f[u]?d.push(f):e.push(f);f=A(a,ya(e,d)),f.selector=a}return f},i=ga.select=function(a,b,e,f){var i,j,k,l,m,n="function"==typeof a&&a,o=!f&&g(a=n.selector||a);if(e=e||[],1===o.length){if(j=o[0]=o[0].slice(0),j.length>2&&"ID"===(k=j[0]).type&&c.getById&&9===b.nodeType&&p&&d.relative[j[1].type]){if(b=(d.find.ID(k.matches[0].replace(ca,da),b)||[])[0],!b)return e;n&&(b=b.parentNode),a=a.slice(j.shift().value.length)}i=X.needsContext.test(a)?0:j.length;while(i--){if(k=j[i],d.relative[l=k.type])break;if((m=d.find[l])&&(f=m(k.matches[0].replace(ca,da),aa.test(j[0].type)&&pa(b.parentNode)||b))){if(j.splice(i,1),a=f.length&&ra(j),!a)return H.apply(e,f),e;break}}}return(n||h(a,o))(f,b,!p,e,aa.test(a)&&pa(b.parentNode)||b),e},c.sortStable=u.split("").sort(B).join("")===u,c.detectDuplicates=!!l,m(),c.sortDetached=ja(function(a){return 1&a.compareDocumentPosition(n.createElement("div"))}),ja(function(a){return a.innerHTML="<a href='#'></a>","#"===a.firstChild.getAttribute("href")})||ka("type|href|height|width",function(a,b,c){return c?void 0:a.getAttribute(b,"type"===b.toLowerCase()?1:2)}),c.attributes&&ja(function(a){return a.innerHTML="<input/>",a.firstChild.setAttribute("value",""),""===a.firstChild.getAttribute("value")})||ka("value",function(a,b,c){return c||"input"!==a.nodeName.toLowerCase()?void 0:a.defaultValue}),ja(function(a){return null==a.getAttribute("disabled")})||ka(K,function(a,b,c){var d;return c?void 0:a[b]===!0?b.toLowerCase():(d=a.getAttributeNode(b))&&d.specified?d.value:null}),ga}(a);n.find=t,n.expr=t.selectors,n.expr[":"]=n.expr.pseudos,n.unique=t.uniqueSort,n.text=t.getText,n.isXMLDoc=t.isXML,n.contains=t.contains;var u=n.expr.match.needsContext,v=/^<(\w+)\s*\/?>(?:<\/\1>|)$/,w=/^.[^:#\[\.,]*$/;function x(a,b,c){if(n.isFunction(b))return n.grep(a,function(a,d){return!!b.call(a,d,a)!==c});if(b.nodeType)return n.grep(a,function(a){return a===b!==c});if("string"==typeof b){if(w.test(b))return n.filter(b,a,c);b=n.filter(b,a)}return n.grep(a,function(a){return g.call(b,a)>=0!==c})}n.filter=function(a,b,c){var d=b[0];return c&&(a=":not("+a+")"),1===b.length&&1===d.nodeType?n.find.matchesSelector(d,a)?[d]:[]:n.find.matches(a,n.grep(b,function(a){return 1===a.nodeType}))},n.fn.extend({find:function(a){var b,c=this.length,d=[],e=this;if("string"!=typeof a)return this.pushStack(n(a).filter(function(){for(b=0;c>b;b++)if(n.contains(e[b],this))return!0}));for(b=0;c>b;b++)n.find(a,e[b],d);return d=this.pushStack(c>1?n.unique(d):d),d.selector=this.selector?this.selector+" "+a:a,d},filter:function(a){return this.pushStack(x(this,a||[],!1))},not:function(a){return this.pushStack(x(this,a||[],!0))},is:function(a){return!!x(this,"string"==typeof a&&u.test(a)?n(a):a||[],!1).length}});var y,z=/^(?:\s*(<[\w\W]+>)[^>]*|#([\w-]*))$/,A=n.fn.init=function(a,b){var c,d;if(!a)return this;if("string"==typeof a){if(c="<"===a[0]&&">"===a[a.length-1]&&a.length>=3?[null,a,null]:z.exec(a),!c||!c[1]&&b)return!b||b.jquery?(b||y).find(a):this.constructor(b).find(a);if(c[1]){if(b=b instanceof n?b[0]:b,n.merge(this,n.parseHTML(c[1],b&&b.nodeType?b.ownerDocument||b:l,!0)),v.test(c[1])&&n.isPlainObject(b))for(c in b)n.isFunction(this[c])?this[c](b[c]):this.attr(c,b[c]);return this}return d=l.getElementById(c[2]),d&&d.parentNode&&(this.length=1,this[0]=d),this.context=l,this.selector=a,this}return a.nodeType?(this.context=this[0]=a,this.length=1,this):n.isFunction(a)?"undefined"!=typeof y.ready?y.ready(a):a(n):(void 0!==a.selector&&(this.selector=a.selector,this.context=a.context),n.makeArray(a,this))};A.prototype=n.fn,y=n(l);var B=/^(?:parents|prev(?:Until|All))/,C={children:!0,contents:!0,next:!0,prev:!0};n.extend({dir:function(a,b,c){var d=[],e=void 0!==c;while((a=a[b])&&9!==a.nodeType)if(1===a.nodeType){if(e&&n(a).is(c))break;d.push(a)}return d},sibling:function(a,b){for(var c=[];a;a=a.nextSibling)1===a.nodeType&&a!==b&&c.push(a);return c}}),n.fn.extend({has:function(a){var b=n(a,this),c=b.length;return this.filter(function(){for(var a=0;c>a;a++)if(n.contains(this,b[a]))return!0})},closest:function(a,b){for(var c,d=0,e=this.length,f=[],g=u.test(a)||"string"!=typeof a?n(a,b||this.context):0;e>d;d++)for(c=this[d];c&&c!==b;c=c.parentNode)if(c.nodeType<11&&(g?g.index(c)>-1:1===c.nodeType&&n.find.matchesSelector(c,a))){f.push(c);break}return this.pushStack(f.length>1?n.unique(f):f)},index:function(a){return a?"string"==typeof a?g.call(n(a),this[0]):g.call(this,a.jquery?a[0]:a):this[0]&&this[0].parentNode?this.first().prevAll().length:-1},add:function(a,b){return this.pushStack(n.unique(n.merge(this.get(),n(a,b))))},addBack:function(a){return this.add(null==a?this.prevObject:this.prevObject.filter(a))}});function D(a,b){while((a=a[b])&&1!==a.nodeType);return a}n.each({parent:function(a){var b=a.parentNode;return b&&11!==b.nodeType?b:null},parents:function(a){return n.dir(a,"parentNode")},parentsUntil:function(a,b,c){return n.dir(a,"parentNode",c)},next:function(a){return D(a,"nextSibling")},prev:function(a){return D(a,"previousSibling")},nextAll:function(a){return n.dir(a,"nextSibling")},prevAll:function(a){return n.dir(a,"previousSibling")},nextUntil:function(a,b,c){return n.dir(a,"nextSibling",c)},prevUntil:function(a,b,c){return n.dir(a,"previousSibling",c)},siblings:function(a){return n.sibling((a.parentNode||{}).firstChild,a)},children:function(a){return n.sibling(a.firstChild)},contents:function(a){return a.contentDocument||n.merge([],a.childNodes)}},function(a,b){n.fn[a]=function(c,d){var e=n.map(this,b,c);return"Until"!==a.slice(-5)&&(d=c),d&&"string"==typeof d&&(e=n.filter(d,e)),this.length>1&&(C[a]||n.unique(e),B.test(a)&&e.reverse()),this.pushStack(e)}});var E=/\S+/g,F={};function G(a){var b=F[a]={};return n.each(a.match(E)||[],function(a,c){b[c]=!0}),b}n.Callbacks=function(a){a="string"==typeof a?F[a]||G(a):n.extend({},a);var b,c,d,e,f,g,h=[],i=!a.once&&[],j=function(l){for(b=a.memory&&l,c=!0,g=e||0,e=0,f=h.length,d=!0;h&&f>g;g++)if(h[g].apply(l[0],l[1])===!1&&a.stopOnFalse){b=!1;break}d=!1,h&&(i?i.length&&j(i.shift()):b?h=[]:k.disable())},k={add:function(){if(h){var c=h.length;!function g(b){n.each(b,function(b,c){var d=n.type(c);"function"===d?a.unique&&k.has(c)||h.push(c):c&&c.length&&"string"!==d&&g(c)})}(arguments),d?f=h.length:b&&(e=c,j(b))}return this},remove:function(){return h&&n.each(arguments,function(a,b){var c;while((c=n.inArray(b,h,c))>-1)h.splice(c,1),d&&(f>=c&&f--,g>=c&&g--)}),this},has:function(a){return a?n.inArray(a,h)>-1:!(!h||!h.length)},empty:function(){return h=[],f=0,this},disable:function(){return h=i=b=void 0,this},disabled:function(){return!h},lock:function(){return i=void 0,b||k.disable(),this},locked:function(){return!i},fireWith:function(a,b){return!h||c&&!i||(b=b||[],b=[a,b.slice?b.slice():b],d?i.push(b):j(b)),this},fire:function(){return k.fireWith(this,arguments),this},fired:function(){return!!c}};return k},n.extend({Deferred:function(a){var b=[["resolve","done",n.Callbacks("once memory"),"resolved"],["reject","fail",n.Callbacks("once memory"),"rejected"],["notify","progress",n.Callbacks("memory")]],c="pending",d={state:function(){return c},always:function(){return e.done(arguments).fail(arguments),this},then:function(){var a=arguments;return n.Deferred(function(c){n.each(b,function(b,f){var g=n.isFunction(a[b])&&a[b];e[f[1]](function(){var a=g&&g.apply(this,arguments);a&&n.isFunction(a.promise)?a.promise().done(c.resolve).fail(c.reject).progress(c.notify):c[f[0]+"With"](this===d?c.promise():this,g?[a]:arguments)})}),a=null}).promise()},promise:function(a){return null!=a?n.extend(a,d):d}},e={};return d.pipe=d.then,n.each(b,function(a,f){var g=f[2],h=f[3];d[f[1]]=g.add,h&&g.add(function(){c=h},b[1^a][2].disable,b[2][2].lock),e[f[0]]=function(){return e[f[0]+"With"](this===e?d:this,arguments),this},e[f[0]+"With"]=g.fireWith}),d.promise(e),a&&a.call(e,e),e},when:function(a){var b=0,c=d.call(arguments),e=c.length,f=1!==e||a&&n.isFunction(a.promise)?e:0,g=1===f?a:n.Deferred(),h=function(a,b,c){return function(e){b[a]=this,c[a]=arguments.length>1?d.call(arguments):e,c===i?g.notifyWith(b,c):--f||g.resolveWith(b,c)}},i,j,k;if(e>1)for(i=new Array(e),j=new Array(e),k=new Array(e);e>b;b++)c[b]&&n.isFunction(c[b].promise)?c[b].promise().done(h(b,k,c)).fail(g.reject).progress(h(b,j,i)):--f;return f||g.resolveWith(k,c),g.promise()}});var H;n.fn.ready=function(a){return n.ready.promise().done(a),this},n.extend({isReady:!1,readyWait:1,holdReady:function(a){a?n.readyWait++:n.ready(!0)},ready:function(a){(a===!0?--n.readyWait:n.isReady)||(n.isReady=!0,a!==!0&&--n.readyWait>0||(H.resolveWith(l,[n]),n.fn.triggerHandler&&(n(l).triggerHandler("ready"),n(l).off("ready"))))}});function I(){l.removeEventListener("DOMContentLoaded",I,!1),a.removeEventListener("load",I,!1),n.ready()}n.ready.promise=function(b){return H||(H=n.Deferred(),"complete"===l.readyState?setTimeout(n.ready):(l.addEventListener("DOMContentLoaded",I,!1),a.addEventListener("load",I,!1))),H.promise(b)},n.ready.promise();var J=n.access=function(a,b,c,d,e,f,g){var h=0,i=a.length,j=null==c;if("object"===n.type(c)){e=!0;for(h in c)n.access(a,b,h,c[h],!0,f,g)}else if(void 0!==d&&(e=!0,n.isFunction(d)||(g=!0),j&&(g?(b.call(a,d),b=null):(j=b,b=function(a,b,c){return j.call(n(a),c)})),b))for(;i>h;h++)b(a[h],c,g?d:d.call(a[h],h,b(a[h],c)));return e?a:j?b.call(a):i?b(a[0],c):f};n.acceptData=function(a){return 1===a.nodeType||9===a.nodeType||!+a.nodeType};function K(){Object.defineProperty(this.cache={},0,{get:function(){return{}}}),this.expando=n.expando+K.uid++}K.uid=1,K.accepts=n.acceptData,K.prototype={key:function(a){if(!K.accepts(a))return 0;var b={},c=a[this.expando];if(!c){c=K.uid++;try{b[this.expando]={value:c},Object.defineProperties(a,b)}catch(d){b[this.expando]=c,n.extend(a,b)}}return this.cache[c]||(this.cache[c]={}),c},set:function(a,b,c){var d,e=this.key(a),f=this.cache[e];if("string"==typeof b)f[b]=c;else if(n.isEmptyObject(f))n.extend(this.cache[e],b);else for(d in b)f[d]=b[d];return f},get:function(a,b){var c=this.cache[this.key(a)];return void 0===b?c:c[b]},access:function(a,b,c){var d;return void 0===b||b&&"string"==typeof b&&void 0===c?(d=this.get(a,b),void 0!==d?d:this.get(a,n.camelCase(b))):(this.set(a,b,c),void 0!==c?c:b)},remove:function(a,b){var c,d,e,f=this.key(a),g=this.cache[f];if(void 0===b)this.cache[f]={};else{n.isArray(b)?d=b.concat(b.map(n.camelCase)):(e=n.camelCase(b),b in g?d=[b,e]:(d=e,d=d in g?[d]:d.match(E)||[])),c=d.length;while(c--)delete g[d[c]]}},hasData:function(a){return!n.isEmptyObject(this.cache[a[this.expando]]||{})},discard:function(a){a[this.expando]&&delete this.cache[a[this.expando]]}};var L=new K,M=new K,N=/^(?:\{[\w\W]*\}|\[[\w\W]*\])$/,O=/([A-Z])/g;function P(a,b,c){var d;if(void 0===c&&1===a.nodeType)if(d="data-"+b.replace(O,"-$1").toLowerCase(),c=a.getAttribute(d),"string"==typeof c){try{c="true"===c?!0:"false"===c?!1:"null"===c?null:+c+""===c?+c:N.test(c)?n.parseJSON(c):c}catch(e){}M.set(a,b,c)}else c=void 0;return c}n.extend({hasData:function(a){return M.hasData(a)||L.hasData(a)},data:function(a,b,c){
-return M.access(a,b,c)},removeData:function(a,b){M.remove(a,b)},_data:function(a,b,c){return L.access(a,b,c)},_removeData:function(a,b){L.remove(a,b)}}),n.fn.extend({data:function(a,b){var c,d,e,f=this[0],g=f&&f.attributes;if(void 0===a){if(this.length&&(e=M.get(f),1===f.nodeType&&!L.get(f,"hasDataAttrs"))){c=g.length;while(c--)g[c]&&(d=g[c].name,0===d.indexOf("data-")&&(d=n.camelCase(d.slice(5)),P(f,d,e[d])));L.set(f,"hasDataAttrs",!0)}return e}return"object"==typeof a?this.each(function(){M.set(this,a)}):J(this,function(b){var c,d=n.camelCase(a);if(f&&void 0===b){if(c=M.get(f,a),void 0!==c)return c;if(c=M.get(f,d),void 0!==c)return c;if(c=P(f,d,void 0),void 0!==c)return c}else this.each(function(){var c=M.get(this,d);M.set(this,d,b),-1!==a.indexOf("-")&&void 0!==c&&M.set(this,a,b)})},null,b,arguments.length>1,null,!0)},removeData:function(a){return this.each(function(){M.remove(this,a)})}}),n.extend({queue:function(a,b,c){var d;return a?(b=(b||"fx")+"queue",d=L.get(a,b),c&&(!d||n.isArray(c)?d=L.access(a,b,n.makeArray(c)):d.push(c)),d||[]):void 0},dequeue:function(a,b){b=b||"fx";var c=n.queue(a,b),d=c.length,e=c.shift(),f=n._queueHooks(a,b),g=function(){n.dequeue(a,b)};"inprogress"===e&&(e=c.shift(),d--),e&&("fx"===b&&c.unshift("inprogress"),delete f.stop,e.call(a,g,f)),!d&&f&&f.empty.fire()},_queueHooks:function(a,b){var c=b+"queueHooks";return L.get(a,c)||L.access(a,c,{empty:n.Callbacks("once memory").add(function(){L.remove(a,[b+"queue",c])})})}}),n.fn.extend({queue:function(a,b){var c=2;return"string"!=typeof a&&(b=a,a="fx",c--),arguments.length<c?n.queue(this[0],a):void 0===b?this:this.each(function(){var c=n.queue(this,a,b);n._queueHooks(this,a),"fx"===a&&"inprogress"!==c[0]&&n.dequeue(this,a)})},dequeue:function(a){return this.each(function(){n.dequeue(this,a)})},clearQueue:function(a){return this.queue(a||"fx",[])},promise:function(a,b){var c,d=1,e=n.Deferred(),f=this,g=this.length,h=function(){--d||e.resolveWith(f,[f])};"string"!=typeof a&&(b=a,a=void 0),a=a||"fx";while(g--)c=L.get(f[g],a+"queueHooks"),c&&c.empty&&(d++,c.empty.add(h));return h(),e.promise(b)}});var Q=/[+-]?(?:\d*\.|)\d+(?:[eE][+-]?\d+|)/.source,R=["Top","Right","Bottom","Left"],S=function(a,b){return a=b||a,"none"===n.css(a,"display")||!n.contains(a.ownerDocument,a)},T=/^(?:checkbox|radio)$/i;!function(){var a=l.createDocumentFragment(),b=a.appendChild(l.createElement("div")),c=l.createElement("input");c.setAttribute("type","radio"),c.setAttribute("checked","checked"),c.setAttribute("name","t"),b.appendChild(c),k.checkClone=b.cloneNode(!0).cloneNode(!0).lastChild.checked,b.innerHTML="<textarea>x</textarea>",k.noCloneChecked=!!b.cloneNode(!0).lastChild.defaultValue}();var U="undefined";k.focusinBubbles="onfocusin"in a;var V=/^key/,W=/^(?:mouse|pointer|contextmenu)|click/,X=/^(?:focusinfocus|focusoutblur)$/,Y=/^([^.]*)(?:\.(.+)|)$/;function Z(){return!0}function $(){return!1}function _(){try{return l.activeElement}catch(a){}}n.event={global:{},add:function(a,b,c,d,e){var f,g,h,i,j,k,l,m,o,p,q,r=L.get(a);if(r){c.handler&&(f=c,c=f.handler,e=f.selector),c.guid||(c.guid=n.guid++),(i=r.events)||(i=r.events={}),(g=r.handle)||(g=r.handle=function(b){return typeof n!==U&&n.event.triggered!==b.type?n.event.dispatch.apply(a,arguments):void 0}),b=(b||"").match(E)||[""],j=b.length;while(j--)h=Y.exec(b[j])||[],o=q=h[1],p=(h[2]||"").split(".").sort(),o&&(l=n.event.special[o]||{},o=(e?l.delegateType:l.bindType)||o,l=n.event.special[o]||{},k=n.extend({type:o,origType:q,data:d,handler:c,guid:c.guid,selector:e,needsContext:e&&n.expr.match.needsContext.test(e),namespace:p.join(".")},f),(m=i[o])||(m=i[o]=[],m.delegateCount=0,l.setup&&l.setup.call(a,d,p,g)!==!1||a.addEventListener&&a.addEventListener(o,g,!1)),l.add&&(l.add.call(a,k),k.handler.guid||(k.handler.guid=c.guid)),e?m.splice(m.delegateCount++,0,k):m.push(k),n.event.global[o]=!0)}},remove:function(a,b,c,d,e){var f,g,h,i,j,k,l,m,o,p,q,r=L.hasData(a)&&L.get(a);if(r&&(i=r.events)){b=(b||"").match(E)||[""],j=b.length;while(j--)if(h=Y.exec(b[j])||[],o=q=h[1],p=(h[2]||"").split(".").sort(),o){l=n.event.special[o]||{},o=(d?l.delegateType:l.bindType)||o,m=i[o]||[],h=h[2]&&new RegExp("(^|\\.)"+p.join("\\.(?:.*\\.|)")+"(\\.|$)"),g=f=m.length;while(f--)k=m[f],!e&&q!==k.origType||c&&c.guid!==k.guid||h&&!h.test(k.namespace)||d&&d!==k.selector&&("**"!==d||!k.selector)||(m.splice(f,1),k.selector&&m.delegateCount--,l.remove&&l.remove.call(a,k));g&&!m.length&&(l.teardown&&l.teardown.call(a,p,r.handle)!==!1||n.removeEvent(a,o,r.handle),delete i[o])}else for(o in i)n.event.remove(a,o+b[j],c,d,!0);n.isEmptyObject(i)&&(delete r.handle,L.remove(a,"events"))}},trigger:function(b,c,d,e){var f,g,h,i,k,m,o,p=[d||l],q=j.call(b,"type")?b.type:b,r=j.call(b,"namespace")?b.namespace.split("."):[];if(g=h=d=d||l,3!==d.nodeType&&8!==d.nodeType&&!X.test(q+n.event.triggered)&&(q.indexOf(".")>=0&&(r=q.split("."),q=r.shift(),r.sort()),k=q.indexOf(":")<0&&"on"+q,b=b[n.expando]?b:new n.Event(q,"object"==typeof b&&b),b.isTrigger=e?2:3,b.namespace=r.join("."),b.namespace_re=b.namespace?new RegExp("(^|\\.)"+r.join("\\.(?:.*\\.|)")+"(\\.|$)"):null,b.result=void 0,b.target||(b.target=d),c=null==c?[b]:n.makeArray(c,[b]),o=n.event.special[q]||{},e||!o.trigger||o.trigger.apply(d,c)!==!1)){if(!e&&!o.noBubble&&!n.isWindow(d)){for(i=o.delegateType||q,X.test(i+q)||(g=g.parentNode);g;g=g.parentNode)p.push(g),h=g;h===(d.ownerDocument||l)&&p.push(h.defaultView||h.parentWindow||a)}f=0;while((g=p[f++])&&!b.isPropagationStopped())b.type=f>1?i:o.bindType||q,m=(L.get(g,"events")||{})[b.type]&&L.get(g,"handle"),m&&m.apply(g,c),m=k&&g[k],m&&m.apply&&n.acceptData(g)&&(b.result=m.apply(g,c),b.result===!1&&b.preventDefault());return b.type=q,e||b.isDefaultPrevented()||o._default&&o._default.apply(p.pop(),c)!==!1||!n.acceptData(d)||k&&n.isFunction(d[q])&&!n.isWindow(d)&&(h=d[k],h&&(d[k]=null),n.event.triggered=q,d[q](),n.event.triggered=void 0,h&&(d[k]=h)),b.result}},dispatch:function(a){a=n.event.fix(a);var b,c,e,f,g,h=[],i=d.call(arguments),j=(L.get(this,"events")||{})[a.type]||[],k=n.event.special[a.type]||{};if(i[0]=a,a.delegateTarget=this,!k.preDispatch||k.preDispatch.call(this,a)!==!1){h=n.event.handlers.call(this,a,j),b=0;while((f=h[b++])&&!a.isPropagationStopped()){a.currentTarget=f.elem,c=0;while((g=f.handlers[c++])&&!a.isImmediatePropagationStopped())(!a.namespace_re||a.namespace_re.test(g.namespace))&&(a.handleObj=g,a.data=g.data,e=((n.event.special[g.origType]||{}).handle||g.handler).apply(f.elem,i),void 0!==e&&(a.result=e)===!1&&(a.preventDefault(),a.stopPropagation()))}return k.postDispatch&&k.postDispatch.call(this,a),a.result}},handlers:function(a,b){var c,d,e,f,g=[],h=b.delegateCount,i=a.target;if(h&&i.nodeType&&(!a.button||"click"!==a.type))for(;i!==this;i=i.parentNode||this)if(i.disabled!==!0||"click"!==a.type){for(d=[],c=0;h>c;c++)f=b[c],e=f.selector+" ",void 0===d[e]&&(d[e]=f.needsContext?n(e,this).index(i)>=0:n.find(e,this,null,[i]).length),d[e]&&d.push(f);d.length&&g.push({elem:i,handlers:d})}return h<b.length&&g.push({elem:this,handlers:b.slice(h)}),g},props:"altKey bubbles cancelable ctrlKey currentTarget eventPhase metaKey relatedTarget shiftKey target timeStamp view which".split(" "),fixHooks:{},keyHooks:{props:"char charCode key keyCode".split(" "),filter:function(a,b){return null==a.which&&(a.which=null!=b.charCode?b.charCode:b.keyCode),a}},mouseHooks:{props:"button buttons clientX clientY offsetX offsetY pageX pageY screenX screenY toElement".split(" "),filter:function(a,b){var c,d,e,f=b.button;return null==a.pageX&&null!=b.clientX&&(c=a.target.ownerDocument||l,d=c.documentElement,e=c.body,a.pageX=b.clientX+(d&&d.scrollLeft||e&&e.scrollLeft||0)-(d&&d.clientLeft||e&&e.clientLeft||0),a.pageY=b.clientY+(d&&d.scrollTop||e&&e.scrollTop||0)-(d&&d.clientTop||e&&e.clientTop||0)),a.which||void 0===f||(a.which=1&f?1:2&f?3:4&f?2:0),a}},fix:function(a){if(a[n.expando])return a;var b,c,d,e=a.type,f=a,g=this.fixHooks[e];g||(this.fixHooks[e]=g=W.test(e)?this.mouseHooks:V.test(e)?this.keyHooks:{}),d=g.props?this.props.concat(g.props):this.props,a=new n.Event(f),b=d.length;while(b--)c=d[b],a[c]=f[c];return a.target||(a.target=l),3===a.target.nodeType&&(a.target=a.target.parentNode),g.filter?g.filter(a,f):a},special:{load:{noBubble:!0},focus:{trigger:function(){return this!==_()&&this.focus?(this.focus(),!1):void 0},delegateType:"focusin"},blur:{trigger:function(){return this===_()&&this.blur?(this.blur(),!1):void 0},delegateType:"focusout"},click:{trigger:function(){return"checkbox"===this.type&&this.click&&n.nodeName(this,"input")?(this.click(),!1):void 0},_default:function(a){return n.nodeName(a.target,"a")}},beforeunload:{postDispatch:function(a){void 0!==a.result&&a.originalEvent&&(a.originalEvent.returnValue=a.result)}}},simulate:function(a,b,c,d){var e=n.extend(new n.Event,c,{type:a,isSimulated:!0,originalEvent:{}});d?n.event.trigger(e,null,b):n.event.dispatch.call(b,e),e.isDefaultPrevented()&&c.preventDefault()}},n.removeEvent=function(a,b,c){a.removeEventListener&&a.removeEventListener(b,c,!1)},n.Event=function(a,b){return this instanceof n.Event?(a&&a.type?(this.originalEvent=a,this.type=a.type,this.isDefaultPrevented=a.defaultPrevented||void 0===a.defaultPrevented&&a.returnValue===!1?Z:$):this.type=a,b&&n.extend(this,b),this.timeStamp=a&&a.timeStamp||n.now(),void(this[n.expando]=!0)):new n.Event(a,b)},n.Event.prototype={isDefaultPrevented:$,isPropagationStopped:$,isImmediatePropagationStopped:$,preventDefault:function(){var a=this.originalEvent;this.isDefaultPrevented=Z,a&&a.preventDefault&&a.preventDefault()},stopPropagation:function(){var a=this.originalEvent;this.isPropagationStopped=Z,a&&a.stopPropagation&&a.stopPropagation()},stopImmediatePropagation:function(){var a=this.originalEvent;this.isImmediatePropagationStopped=Z,a&&a.stopImmediatePropagation&&a.stopImmediatePropagation(),this.stopPropagation()}},n.each({mouseenter:"mouseover",mouseleave:"mouseout",pointerenter:"pointerover",pointerleave:"pointerout"},function(a,b){n.event.special[a]={delegateType:b,bindType:b,handle:function(a){var c,d=this,e=a.relatedTarget,f=a.handleObj;return(!e||e!==d&&!n.contains(d,e))&&(a.type=f.origType,c=f.handler.apply(this,arguments),a.type=b),c}}}),k.focusinBubbles||n.each({focus:"focusin",blur:"focusout"},function(a,b){var c=function(a){n.event.simulate(b,a.target,n.event.fix(a),!0)};n.event.special[b]={setup:function(){var d=this.ownerDocument||this,e=L.access(d,b);e||d.addEventListener(a,c,!0),L.access(d,b,(e||0)+1)},teardown:function(){var d=this.ownerDocument||this,e=L.access(d,b)-1;e?L.access(d,b,e):(d.removeEventListener(a,c,!0),L.remove(d,b))}}}),n.fn.extend({on:function(a,b,c,d,e){var f,g;if("object"==typeof a){"string"!=typeof b&&(c=c||b,b=void 0);for(g in a)this.on(g,b,c,a[g],e);return this}if(null==c&&null==d?(d=b,c=b=void 0):null==d&&("string"==typeof b?(d=c,c=void 0):(d=c,c=b,b=void 0)),d===!1)d=$;else if(!d)return this;return 1===e&&(f=d,d=function(a){return n().off(a),f.apply(this,arguments)},d.guid=f.guid||(f.guid=n.guid++)),this.each(function(){n.event.add(this,a,d,c,b)})},one:function(a,b,c,d){return this.on(a,b,c,d,1)},off:function(a,b,c){var d,e;if(a&&a.preventDefault&&a.handleObj)return d=a.handleObj,n(a.delegateTarget).off(d.namespace?d.origType+"."+d.namespace:d.origType,d.selector,d.handler),this;if("object"==typeof a){for(e in a)this.off(e,b,a[e]);return this}return(b===!1||"function"==typeof b)&&(c=b,b=void 0),c===!1&&(c=$),this.each(function(){n.event.remove(this,a,c,b)})},trigger:function(a,b){return this.each(function(){n.event.trigger(a,b,this)})},triggerHandler:function(a,b){var c=this[0];return c?n.event.trigger(a,b,c,!0):void 0}});var aa=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/gi,ba=/<([\w:]+)/,ca=/<|&#?\w+;/,da=/<(?:script|style|link)/i,ea=/checked\s*(?:[^=]|=\s*.checked.)/i,fa=/^$|\/(?:java|ecma)script/i,ga=/^true\/(.*)/,ha=/^\s*<!(?:\[CDATA\[|--)|(?:\]\]|--)>\s*$/g,ia={option:[1,"<select multiple='multiple'>","</select>"],thead:[1,"<table>","</table>"],col:[2,"<table><colgroup>","</colgroup></table>"],tr:[2,"<table><tbody>","</tbody></table>"],td:[3,"<table><tbody><tr>","</tr></tbody></table>"],_default:[0,"",""]};ia.optgroup=ia.option,ia.tbody=ia.tfoot=ia.colgroup=ia.caption=ia.thead,ia.th=ia.td;function ja(a,b){return n.nodeName(a,"table")&&n.nodeName(11!==b.nodeType?b:b.firstChild,"tr")?a.getElementsByTagName("tbody")[0]||a.appendChild(a.ownerDocument.createElement("tbody")):a}function ka(a){return a.type=(null!==a.getAttribute("type"))+"/"+a.type,a}function la(a){var b=ga.exec(a.type);return b?a.type=b[1]:a.removeAttribute("type"),a}function ma(a,b){for(var c=0,d=a.length;d>c;c++)L.set(a[c],"globalEval",!b||L.get(b[c],"globalEval"))}function na(a,b){var c,d,e,f,g,h,i,j;if(1===b.nodeType){if(L.hasData(a)&&(f=L.access(a),g=L.set(b,f),j=f.events)){delete g.handle,g.events={};for(e in j)for(c=0,d=j[e].length;d>c;c++)n.event.add(b,e,j[e][c])}M.hasData(a)&&(h=M.access(a),i=n.extend({},h),M.set(b,i))}}function oa(a,b){var c=a.getElementsByTagName?a.getElementsByTagName(b||"*"):a.querySelectorAll?a.querySelectorAll(b||"*"):[];return void 0===b||b&&n.nodeName(a,b)?n.merge([a],c):c}function pa(a,b){var c=b.nodeName.toLowerCase();"input"===c&&T.test(a.type)?b.checked=a.checked:("input"===c||"textarea"===c)&&(b.defaultValue=a.defaultValue)}n.extend({clone:function(a,b,c){var d,e,f,g,h=a.cloneNode(!0),i=n.contains(a.ownerDocument,a);if(!(k.noCloneChecked||1!==a.nodeType&&11!==a.nodeType||n.isXMLDoc(a)))for(g=oa(h),f=oa(a),d=0,e=f.length;e>d;d++)pa(f[d],g[d]);if(b)if(c)for(f=f||oa(a),g=g||oa(h),d=0,e=f.length;e>d;d++)na(f[d],g[d]);else na(a,h);return g=oa(h,"script"),g.length>0&&ma(g,!i&&oa(a,"script")),h},buildFragment:function(a,b,c,d){for(var e,f,g,h,i,j,k=b.createDocumentFragment(),l=[],m=0,o=a.length;o>m;m++)if(e=a[m],e||0===e)if("object"===n.type(e))n.merge(l,e.nodeType?[e]:e);else if(ca.test(e)){f=f||k.appendChild(b.createElement("div")),g=(ba.exec(e)||["",""])[1].toLowerCase(),h=ia[g]||ia._default,f.innerHTML=h[1]+e.replace(aa,"<$1></$2>")+h[2],j=h[0];while(j--)f=f.lastChild;n.merge(l,f.childNodes),f=k.firstChild,f.textContent=""}else l.push(b.createTextNode(e));k.textContent="",m=0;while(e=l[m++])if((!d||-1===n.inArray(e,d))&&(i=n.contains(e.ownerDocument,e),f=oa(k.appendChild(e),"script"),i&&ma(f),c)){j=0;while(e=f[j++])fa.test(e.type||"")&&c.push(e)}return k},cleanData:function(a){for(var b,c,d,e,f=n.event.special,g=0;void 0!==(c=a[g]);g++){if(n.acceptData(c)&&(e=c[L.expando],e&&(b=L.cache[e]))){if(b.events)for(d in b.events)f[d]?n.event.remove(c,d):n.removeEvent(c,d,b.handle);L.cache[e]&&delete L.cache[e]}delete M.cache[c[M.expando]]}}}),n.fn.extend({text:function(a){return J(this,function(a){return void 0===a?n.text(this):this.empty().each(function(){(1===this.nodeType||11===this.nodeType||9===this.nodeType)&&(this.textContent=a)})},null,a,arguments.length)},append:function(){return this.domManip(arguments,function(a){if(1===this.nodeType||11===this.nodeType||9===this.nodeType){var b=ja(this,a);b.appendChild(a)}})},prepend:function(){return this.domManip(arguments,function(a){if(1===this.nodeType||11===this.nodeType||9===this.nodeType){var b=ja(this,a);b.insertBefore(a,b.firstChild)}})},before:function(){return this.domManip(arguments,function(a){this.parentNode&&this.parentNode.insertBefore(a,this)})},after:function(){return this.domManip(arguments,function(a){this.parentNode&&this.parentNode.insertBefore(a,this.nextSibling)})},remove:function(a,b){for(var c,d=a?n.filter(a,this):this,e=0;null!=(c=d[e]);e++)b||1!==c.nodeType||n.cleanData(oa(c)),c.parentNode&&(b&&n.contains(c.ownerDocument,c)&&ma(oa(c,"script")),c.parentNode.removeChild(c));return this},empty:function(){for(var a,b=0;null!=(a=this[b]);b++)1===a.nodeType&&(n.cleanData(oa(a,!1)),a.textContent="");return this},clone:function(a,b){return a=null==a?!1:a,b=null==b?a:b,this.map(function(){return n.clone(this,a,b)})},html:function(a){return J(this,function(a){var b=this[0]||{},c=0,d=this.length;if(void 0===a&&1===b.nodeType)return b.innerHTML;if("string"==typeof a&&!da.test(a)&&!ia[(ba.exec(a)||["",""])[1].toLowerCase()]){a=a.replace(aa,"<$1></$2>");try{for(;d>c;c++)b=this[c]||{},1===b.nodeType&&(n.cleanData(oa(b,!1)),b.innerHTML=a);b=0}catch(e){}}b&&this.empty().append(a)},null,a,arguments.length)},replaceWith:function(){var a=arguments[0];return this.domManip(arguments,function(b){a=this.parentNode,n.cleanData(oa(this)),a&&a.replaceChild(b,this)}),a&&(a.length||a.nodeType)?this:this.remove()},detach:function(a){return this.remove(a,!0)},domManip:function(a,b){a=e.apply([],a);var c,d,f,g,h,i,j=0,l=this.length,m=this,o=l-1,p=a[0],q=n.isFunction(p);if(q||l>1&&"string"==typeof p&&!k.checkClone&&ea.test(p))return this.each(function(c){var d=m.eq(c);q&&(a[0]=p.call(this,c,d.html())),d.domManip(a,b)});if(l&&(c=n.buildFragment(a,this[0].ownerDocument,!1,this),d=c.firstChild,1===c.childNodes.length&&(c=d),d)){for(f=n.map(oa(c,"script"),ka),g=f.length;l>j;j++)h=c,j!==o&&(h=n.clone(h,!0,!0),g&&n.merge(f,oa(h,"script"))),b.call(this[j],h,j);if(g)for(i=f[f.length-1].ownerDocument,n.map(f,la),j=0;g>j;j++)h=f[j],fa.test(h.type||"")&&!L.access(h,"globalEval")&&n.contains(i,h)&&(h.src?n._evalUrl&&n._evalUrl(h.src):n.globalEval(h.textContent.replace(ha,"")))}return this}}),n.each({appendTo:"append",prependTo:"prepend",insertBefore:"before",insertAfter:"after",replaceAll:"replaceWith"},function(a,b){n.fn[a]=function(a){for(var c,d=[],e=n(a),g=e.length-1,h=0;g>=h;h++)c=h===g?this:this.clone(!0),n(e[h])[b](c),f.apply(d,c.get());return this.pushStack(d)}});var qa,ra={};function sa(b,c){var d,e=n(c.createElement(b)).appendTo(c.body),f=a.getDefaultComputedStyle&&(d=a.getDefaultComputedStyle(e[0]))?d.display:n.css(e[0],"display");return e.detach(),f}function ta(a){var b=l,c=ra[a];return c||(c=sa(a,b),"none"!==c&&c||(qa=(qa||n("<iframe frameborder='0' width='0' height='0'/>")).appendTo(b.documentElement),b=qa[0].contentDocument,b.write(),b.close(),c=sa(a,b),qa.detach()),ra[a]=c),c}var ua=/^margin/,va=new RegExp("^("+Q+")(?!px)[a-z%]+$","i"),wa=function(b){return b.ownerDocument.defaultView.opener?b.ownerDocument.defaultView.getComputedStyle(b,null):a.getComputedStyle(b,null)};function xa(a,b,c){var d,e,f,g,h=a.style;return c=c||wa(a),c&&(g=c.getPropertyValue(b)||c[b]),c&&(""!==g||n.contains(a.ownerDocument,a)||(g=n.style(a,b)),va.test(g)&&ua.test(b)&&(d=h.width,e=h.minWidth,f=h.maxWidth,h.minWidth=h.maxWidth=h.width=g,g=c.width,h.width=d,h.minWidth=e,h.maxWidth=f)),void 0!==g?g+"":g}function ya(a,b){return{get:function(){return a()?void delete this.get:(this.get=b).apply(this,arguments)}}}!function(){var b,c,d=l.documentElement,e=l.createElement("div"),f=l.createElement("div");if(f.style){f.style.backgroundClip="content-box",f.cloneNode(!0).style.backgroundClip="",k.clearCloneStyle="content-box"===f.style.backgroundClip,e.style.cssText="border:0;width:0;height:0;top:0;left:-9999px;margin-top:1px;position:absolute",e.appendChild(f);function g(){f.style.cssText="-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box;display:block;margin-top:1%;top:1%;border:1px;padding:1px;width:4px;position:absolute",f.innerHTML="",d.appendChild(e);var g=a.getComputedStyle(f,null);b="1%"!==g.top,c="4px"===g.width,d.removeChild(e)}a.getComputedStyle&&n.extend(k,{pixelPosition:function(){return g(),b},boxSizingReliable:function(){return null==c&&g(),c},reliableMarginRight:function(){var b,c=f.appendChild(l.createElement("div"));return c.style.cssText=f.style.cssText="-webkit-box-sizing:content-box;-moz-box-sizing:content-box;box-sizing:content-box;display:block;margin:0;border:0;padding:0",c.style.marginRight=c.style.width="0",f.style.width="1px",d.appendChild(e),b=!parseFloat(a.getComputedStyle(c,null).marginRight),d.removeChild(e),f.removeChild(c),b}})}}(),n.swap=function(a,b,c,d){var e,f,g={};for(f in b)g[f]=a.style[f],a.style[f]=b[f];e=c.apply(a,d||[]);for(f in b)a.style[f]=g[f];return e};var za=/^(none|table(?!-c[ea]).+)/,Aa=new RegExp("^("+Q+")(.*)$","i"),Ba=new RegExp("^([+-])=("+Q+")","i"),Ca={position:"absolute",visibility:"hidden",display:"block"},Da={letterSpacing:"0",fontWeight:"400"},Ea=["Webkit","O","Moz","ms"];function Fa(a,b){if(b in a)return b;var c=b[0].toUpperCase()+b.slice(1),d=b,e=Ea.length;while(e--)if(b=Ea[e]+c,b in a)return b;return d}function Ga(a,b,c){var d=Aa.exec(b);return d?Math.max(0,d[1]-(c||0))+(d[2]||"px"):b}function Ha(a,b,c,d,e){for(var f=c===(d?"border":"content")?4:"width"===b?1:0,g=0;4>f;f+=2)"margin"===c&&(g+=n.css(a,c+R[f],!0,e)),d?("content"===c&&(g-=n.css(a,"padding"+R[f],!0,e)),"margin"!==c&&(g-=n.css(a,"border"+R[f]+"Width",!0,e))):(g+=n.css(a,"padding"+R[f],!0,e),"padding"!==c&&(g+=n.css(a,"border"+R[f]+"Width",!0,e)));return g}function Ia(a,b,c){var d=!0,e="width"===b?a.offsetWidth:a.offsetHeight,f=wa(a),g="border-box"===n.css(a,"boxSizing",!1,f);if(0>=e||null==e){if(e=xa(a,b,f),(0>e||null==e)&&(e=a.style[b]),va.test(e))return e;d=g&&(k.boxSizingReliable()||e===a.style[b]),e=parseFloat(e)||0}return e+Ha(a,b,c||(g?"border":"content"),d,f)+"px"}function Ja(a,b){for(var c,d,e,f=[],g=0,h=a.length;h>g;g++)d=a[g],d.style&&(f[g]=L.get(d,"olddisplay"),c=d.style.display,b?(f[g]||"none"!==c||(d.style.display=""),""===d.style.display&&S(d)&&(f[g]=L.access(d,"olddisplay",ta(d.nodeName)))):(e=S(d),"none"===c&&e||L.set(d,"olddisplay",e?c:n.css(d,"display"))));for(g=0;h>g;g++)d=a[g],d.style&&(b&&"none"!==d.style.display&&""!==d.style.display||(d.style.display=b?f[g]||"":"none"));return a}n.extend({cssHooks:{opacity:{get:function(a,b){if(b){var c=xa(a,"opacity");return""===c?"1":c}}}},cssNumber:{columnCount:!0,fillOpacity:!0,flexGrow:!0,flexShrink:!0,fontWeight:!0,lineHeight:!0,opacity:!0,order:!0,orphans:!0,widows:!0,zIndex:!0,zoom:!0},cssProps:{"float":"cssFloat"},style:function(a,b,c,d){if(a&&3!==a.nodeType&&8!==a.nodeType&&a.style){var e,f,g,h=n.camelCase(b),i=a.style;return b=n.cssProps[h]||(n.cssProps[h]=Fa(i,h)),g=n.cssHooks[b]||n.cssHooks[h],void 0===c?g&&"get"in g&&void 0!==(e=g.get(a,!1,d))?e:i[b]:(f=typeof c,"string"===f&&(e=Ba.exec(c))&&(c=(e[1]+1)*e[2]+parseFloat(n.css(a,b)),f="number"),null!=c&&c===c&&("number"!==f||n.cssNumber[h]||(c+="px"),k.clearCloneStyle||""!==c||0!==b.indexOf("background")||(i[b]="inherit"),g&&"set"in g&&void 0===(c=g.set(a,c,d))||(i[b]=c)),void 0)}},css:function(a,b,c,d){var e,f,g,h=n.camelCase(b);return b=n.cssProps[h]||(n.cssProps[h]=Fa(a.style,h)),g=n.cssHooks[b]||n.cssHooks[h],g&&"get"in g&&(e=g.get(a,!0,c)),void 0===e&&(e=xa(a,b,d)),"normal"===e&&b in Da&&(e=Da[b]),""===c||c?(f=parseFloat(e),c===!0||n.isNumeric(f)?f||0:e):e}}),n.each(["height","width"],function(a,b){n.cssHooks[b]={get:function(a,c,d){return c?za.test(n.css(a,"display"))&&0===a.offsetWidth?n.swap(a,Ca,function(){return Ia(a,b,d)}):Ia(a,b,d):void 0},set:function(a,c,d){var e=d&&wa(a);return Ga(a,c,d?Ha(a,b,d,"border-box"===n.css(a,"boxSizing",!1,e),e):0)}}}),n.cssHooks.marginRight=ya(k.reliableMarginRight,function(a,b){return b?n.swap(a,{display:"inline-block"},xa,[a,"marginRight"]):void 0}),n.each({margin:"",padding:"",border:"Width"},function(a,b){n.cssHooks[a+b]={expand:function(c){for(var d=0,e={},f="string"==typeof c?c.split(" "):[c];4>d;d++)e[a+R[d]+b]=f[d]||f[d-2]||f[0];return e}},ua.test(a)||(n.cssHooks[a+b].set=Ga)}),n.fn.extend({css:function(a,b){return J(this,function(a,b,c){var d,e,f={},g=0;if(n.isArray(b)){for(d=wa(a),e=b.length;e>g;g++)f[b[g]]=n.css(a,b[g],!1,d);return f}return void 0!==c?n.style(a,b,c):n.css(a,b)},a,b,arguments.length>1)},show:function(){return Ja(this,!0)},hide:function(){return Ja(this)},toggle:function(a){return"boolean"==typeof a?a?this.show():this.hide():this.each(function(){S(this)?n(this).show():n(this).hide()})}});function Ka(a,b,c,d,e){return new Ka.prototype.init(a,b,c,d,e)}n.Tween=Ka,Ka.prototype={constructor:Ka,init:function(a,b,c,d,e,f){this.elem=a,this.prop=c,this.easing=e||"swing",this.options=b,this.start=this.now=this.cur(),this.end=d,this.unit=f||(n.cssNumber[c]?"":"px")},cur:function(){var a=Ka.propHooks[this.prop];return a&&a.get?a.get(this):Ka.propHooks._default.get(this)},run:function(a){var b,c=Ka.propHooks[this.prop];return this.options.duration?this.pos=b=n.easing[this.easing](a,this.options.duration*a,0,1,this.options.duration):this.pos=b=a,this.now=(this.end-this.start)*b+this.start,this.options.step&&this.options.step.call(this.elem,this.now,this),c&&c.set?c.set(this):Ka.propHooks._default.set(this),this}},Ka.prototype.init.prototype=Ka.prototype,Ka.propHooks={_default:{get:function(a){var b;return null==a.elem[a.prop]||a.elem.style&&null!=a.elem.style[a.prop]?(b=n.css(a.elem,a.prop,""),b&&"auto"!==b?b:0):a.elem[a.prop]},set:function(a){n.fx.step[a.prop]?n.fx.step[a.prop](a):a.elem.style&&(null!=a.elem.style[n.cssProps[a.prop]]||n.cssHooks[a.prop])?n.style(a.elem,a.prop,a.now+a.unit):a.elem[a.prop]=a.now}}},Ka.propHooks.scrollTop=Ka.propHooks.scrollLeft={set:function(a){a.elem.nodeType&&a.elem.parentNode&&(a.elem[a.prop]=a.now)}},n.easing={linear:function(a){return a},swing:function(a){return.5-Math.cos(a*Math.PI)/2}},n.fx=Ka.prototype.init,n.fx.step={};var La,Ma,Na=/^(?:toggle|show|hide)$/,Oa=new RegExp("^(?:([+-])=|)("+Q+")([a-z%]*)$","i"),Pa=/queueHooks$/,Qa=[Va],Ra={"*":[function(a,b){var c=this.createTween(a,b),d=c.cur(),e=Oa.exec(b),f=e&&e[3]||(n.cssNumber[a]?"":"px"),g=(n.cssNumber[a]||"px"!==f&&+d)&&Oa.exec(n.css(c.elem,a)),h=1,i=20;if(g&&g[3]!==f){f=f||g[3],e=e||[],g=+d||1;do h=h||".5",g/=h,n.style(c.elem,a,g+f);while(h!==(h=c.cur()/d)&&1!==h&&--i)}return e&&(g=c.start=+g||+d||0,c.unit=f,c.end=e[1]?g+(e[1]+1)*e[2]:+e[2]),c}]};function Sa(){return setTimeout(function(){La=void 0}),La=n.now()}function Ta(a,b){var c,d=0,e={height:a};for(b=b?1:0;4>d;d+=2-b)c=R[d],e["margin"+c]=e["padding"+c]=a;return b&&(e.opacity=e.width=a),e}function Ua(a,b,c){for(var d,e=(Ra[b]||[]).concat(Ra["*"]),f=0,g=e.length;g>f;f++)if(d=e[f].call(c,b,a))return d}function Va(a,b,c){var d,e,f,g,h,i,j,k,l=this,m={},o=a.style,p=a.nodeType&&S(a),q=L.get(a,"fxshow");c.queue||(h=n._queueHooks(a,"fx"),null==h.unqueued&&(h.unqueued=0,i=h.empty.fire,h.empty.fire=function(){h.unqueued||i()}),h.unqueued++,l.always(function(){l.always(function(){h.unqueued--,n.queue(a,"fx").length||h.empty.fire()})})),1===a.nodeType&&("height"in b||"width"in b)&&(c.overflow=[o.overflow,o.overflowX,o.overflowY],j=n.css(a,"display"),k="none"===j?L.get(a,"olddisplay")||ta(a.nodeName):j,"inline"===k&&"none"===n.css(a,"float")&&(o.display="inline-block")),c.overflow&&(o.overflow="hidden",l.always(function(){o.overflow=c.overflow[0],o.overflowX=c.overflow[1],o.overflowY=c.overflow[2]}));for(d in b)if(e=b[d],Na.exec(e)){if(delete b[d],f=f||"toggle"===e,e===(p?"hide":"show")){if("show"!==e||!q||void 0===q[d])continue;p=!0}m[d]=q&&q[d]||n.style(a,d)}else j=void 0;if(n.isEmptyObject(m))"inline"===("none"===j?ta(a.nodeName):j)&&(o.display=j);else{q?"hidden"in q&&(p=q.hidden):q=L.access(a,"fxshow",{}),f&&(q.hidden=!p),p?n(a).show():l.done(function(){n(a).hide()}),l.done(function(){var b;L.remove(a,"fxshow");for(b in m)n.style(a,b,m[b])});for(d in m)g=Ua(p?q[d]:0,d,l),d in q||(q[d]=g.start,p&&(g.end=g.start,g.start="width"===d||"height"===d?1:0))}}function Wa(a,b){var c,d,e,f,g;for(c in a)if(d=n.camelCase(c),e=b[d],f=a[c],n.isArray(f)&&(e=f[1],f=a[c]=f[0]),c!==d&&(a[d]=f,delete a[c]),g=n.cssHooks[d],g&&"expand"in g){f=g.expand(f),delete a[d];for(c in f)c in a||(a[c]=f[c],b[c]=e)}else b[d]=e}function Xa(a,b,c){var d,e,f=0,g=Qa.length,h=n.Deferred().always(function(){delete i.elem}),i=function(){if(e)return!1;for(var b=La||Sa(),c=Math.max(0,j.startTime+j.duration-b),d=c/j.duration||0,f=1-d,g=0,i=j.tweens.length;i>g;g++)j.tweens[g].run(f);return h.notifyWith(a,[j,f,c]),1>f&&i?c:(h.resolveWith(a,[j]),!1)},j=h.promise({elem:a,props:n.extend({},b),opts:n.extend(!0,{specialEasing:{}},c),originalProperties:b,originalOptions:c,startTime:La||Sa(),duration:c.duration,tweens:[],createTween:function(b,c){var d=n.Tween(a,j.opts,b,c,j.opts.specialEasing[b]||j.opts.easing);return j.tweens.push(d),d},stop:function(b){var c=0,d=b?j.tweens.length:0;if(e)return this;for(e=!0;d>c;c++)j.tweens[c].run(1);return b?h.resolveWith(a,[j,b]):h.rejectWith(a,[j,b]),this}}),k=j.props;for(Wa(k,j.opts.specialEasing);g>f;f++)if(d=Qa[f].call(j,a,k,j.opts))return d;return n.map(k,Ua,j),n.isFunction(j.opts.start)&&j.opts.start.call(a,j),n.fx.timer(n.extend(i,{elem:a,anim:j,queue:j.opts.queue})),j.progress(j.opts.progress).done(j.opts.done,j.opts.complete).fail(j.opts.fail).always(j.opts.always)}n.Animation=n.extend(Xa,{tweener:function(a,b){n.isFunction(a)?(b=a,a=["*"]):a=a.split(" ");for(var c,d=0,e=a.length;e>d;d++)c=a[d],Ra[c]=Ra[c]||[],Ra[c].unshift(b)},prefilter:function(a,b){b?Qa.unshift(a):Qa.push(a)}}),n.speed=function(a,b,c){var d=a&&"object"==typeof a?n.extend({},a):{complete:c||!c&&b||n.isFunction(a)&&a,duration:a,easing:c&&b||b&&!n.isFunction(b)&&b};return d.duration=n.fx.off?0:"number"==typeof d.duration?d.duration:d.duration in n.fx.speeds?n.fx.speeds[d.duration]:n.fx.speeds._default,(null==d.queue||d.queue===!0)&&(d.queue="fx"),d.old=d.complete,d.complete=function(){n.isFunction(d.old)&&d.old.call(this),d.queue&&n.dequeue(this,d.queue)},d},n.fn.extend({fadeTo:function(a,b,c,d){return this.filter(S).css("opacity",0).show().end().animate({opacity:b},a,c,d)},animate:function(a,b,c,d){var e=n.isEmptyObject(a),f=n.speed(b,c,d),g=function(){var b=Xa(this,n.extend({},a),f);(e||L.get(this,"finish"))&&b.stop(!0)};return g.finish=g,e||f.queue===!1?this.each(g):this.queue(f.queue,g)},stop:function(a,b,c){var d=function(a){var b=a.stop;delete a.stop,b(c)};return"string"!=typeof a&&(c=b,b=a,a=void 0),b&&a!==!1&&this.queue(a||"fx",[]),this.each(function(){var b=!0,e=null!=a&&a+"queueHooks",f=n.timers,g=L.get(this);if(e)g[e]&&g[e].stop&&d(g[e]);else for(e in g)g[e]&&g[e].stop&&Pa.test(e)&&d(g[e]);for(e=f.length;e--;)f[e].elem!==this||null!=a&&f[e].queue!==a||(f[e].anim.stop(c),b=!1,f.splice(e,1));(b||!c)&&n.dequeue(this,a)})},finish:function(a){return a!==!1&&(a=a||"fx"),this.each(function(){var b,c=L.get(this),d=c[a+"queue"],e=c[a+"queueHooks"],f=n.timers,g=d?d.length:0;for(c.finish=!0,n.queue(this,a,[]),e&&e.stop&&e.stop.call(this,!0),b=f.length;b--;)f[b].elem===this&&f[b].queue===a&&(f[b].anim.stop(!0),f.splice(b,1));for(b=0;g>b;b++)d[b]&&d[b].finish&&d[b].finish.call(this);delete c.finish})}}),n.each(["toggle","show","hide"],function(a,b){var c=n.fn[b];n.fn[b]=function(a,d,e){return null==a||"boolean"==typeof a?c.apply(this,arguments):this.animate(Ta(b,!0),a,d,e)}}),n.each({slideDown:Ta("show"),slideUp:Ta("hide"),slideToggle:Ta("toggle"),fadeIn:{opacity:"show"},fadeOut:{opacity:"hide"},fadeToggle:{opacity:"toggle"}},function(a,b){n.fn[a]=function(a,c,d){return this.animate(b,a,c,d)}}),n.timers=[],n.fx.tick=function(){var a,b=0,c=n.timers;for(La=n.now();b<c.length;b++)a=c[b],a()||c[b]!==a||c.splice(b--,1);c.length||n.fx.stop(),La=void 0},n.fx.timer=function(a){n.timers.push(a),a()?n.fx.start():n.timers.pop()},n.fx.interval=13,n.fx.start=function(){Ma||(Ma=setInterval(n.fx.tick,n.fx.interval))},n.fx.stop=function(){clearInterval(Ma),Ma=null},n.fx.speeds={slow:600,fast:200,_default:400},n.fn.delay=function(a,b){return a=n.fx?n.fx.speeds[a]||a:a,b=b||"fx",this.queue(b,function(b,c){var d=setTimeout(b,a);c.stop=function(){clearTimeout(d)}})},function(){var a=l.createElement("input"),b=l.createElement("select"),c=b.appendChild(l.createElement("option"));a.type="checkbox",k.checkOn=""!==a.value,k.optSelected=c.selected,b.disabled=!0,k.optDisabled=!c.disabled,a=l.createElement("input"),a.value="t",a.type="radio",k.radioValue="t"===a.value}();var Ya,Za,$a=n.expr.attrHandle;n.fn.extend({attr:function(a,b){return J(this,n.attr,a,b,arguments.length>1)},removeAttr:function(a){return this.each(function(){n.removeAttr(this,a)})}}),n.extend({attr:function(a,b,c){var d,e,f=a.nodeType;if(a&&3!==f&&8!==f&&2!==f)return typeof a.getAttribute===U?n.prop(a,b,c):(1===f&&n.isXMLDoc(a)||(b=b.toLowerCase(),d=n.attrHooks[b]||(n.expr.match.bool.test(b)?Za:Ya)),
-void 0===c?d&&"get"in d&&null!==(e=d.get(a,b))?e:(e=n.find.attr(a,b),null==e?void 0:e):null!==c?d&&"set"in d&&void 0!==(e=d.set(a,c,b))?e:(a.setAttribute(b,c+""),c):void n.removeAttr(a,b))},removeAttr:function(a,b){var c,d,e=0,f=b&&b.match(E);if(f&&1===a.nodeType)while(c=f[e++])d=n.propFix[c]||c,n.expr.match.bool.test(c)&&(a[d]=!1),a.removeAttribute(c)},attrHooks:{type:{set:function(a,b){if(!k.radioValue&&"radio"===b&&n.nodeName(a,"input")){var c=a.value;return a.setAttribute("type",b),c&&(a.value=c),b}}}}}),Za={set:function(a,b,c){return b===!1?n.removeAttr(a,c):a.setAttribute(c,c),c}},n.each(n.expr.match.bool.source.match(/\w+/g),function(a,b){var c=$a[b]||n.find.attr;$a[b]=function(a,b,d){var e,f;return d||(f=$a[b],$a[b]=e,e=null!=c(a,b,d)?b.toLowerCase():null,$a[b]=f),e}});var _a=/^(?:input|select|textarea|button)$/i;n.fn.extend({prop:function(a,b){return J(this,n.prop,a,b,arguments.length>1)},removeProp:function(a){return this.each(function(){delete this[n.propFix[a]||a]})}}),n.extend({propFix:{"for":"htmlFor","class":"className"},prop:function(a,b,c){var d,e,f,g=a.nodeType;if(a&&3!==g&&8!==g&&2!==g)return f=1!==g||!n.isXMLDoc(a),f&&(b=n.propFix[b]||b,e=n.propHooks[b]),void 0!==c?e&&"set"in e&&void 0!==(d=e.set(a,c,b))?d:a[b]=c:e&&"get"in e&&null!==(d=e.get(a,b))?d:a[b]},propHooks:{tabIndex:{get:function(a){return a.hasAttribute("tabindex")||_a.test(a.nodeName)||a.href?a.tabIndex:-1}}}}),k.optSelected||(n.propHooks.selected={get:function(a){var b=a.parentNode;return b&&b.parentNode&&b.parentNode.selectedIndex,null}}),n.each(["tabIndex","readOnly","maxLength","cellSpacing","cellPadding","rowSpan","colSpan","useMap","frameBorder","contentEditable"],function(){n.propFix[this.toLowerCase()]=this});var ab=/[\t\r\n\f]/g;n.fn.extend({addClass:function(a){var b,c,d,e,f,g,h="string"==typeof a&&a,i=0,j=this.length;if(n.isFunction(a))return this.each(function(b){n(this).addClass(a.call(this,b,this.className))});if(h)for(b=(a||"").match(E)||[];j>i;i++)if(c=this[i],d=1===c.nodeType&&(c.className?(" "+c.className+" ").replace(ab," "):" ")){f=0;while(e=b[f++])d.indexOf(" "+e+" ")<0&&(d+=e+" ");g=n.trim(d),c.className!==g&&(c.className=g)}return this},removeClass:function(a){var b,c,d,e,f,g,h=0===arguments.length||"string"==typeof a&&a,i=0,j=this.length;if(n.isFunction(a))return this.each(function(b){n(this).removeClass(a.call(this,b,this.className))});if(h)for(b=(a||"").match(E)||[];j>i;i++)if(c=this[i],d=1===c.nodeType&&(c.className?(" "+c.className+" ").replace(ab," "):"")){f=0;while(e=b[f++])while(d.indexOf(" "+e+" ")>=0)d=d.replace(" "+e+" "," ");g=a?n.trim(d):"",c.className!==g&&(c.className=g)}return this},toggleClass:function(a,b){var c=typeof a;return"boolean"==typeof b&&"string"===c?b?this.addClass(a):this.removeClass(a):this.each(n.isFunction(a)?function(c){n(this).toggleClass(a.call(this,c,this.className,b),b)}:function(){if("string"===c){var b,d=0,e=n(this),f=a.match(E)||[];while(b=f[d++])e.hasClass(b)?e.removeClass(b):e.addClass(b)}else(c===U||"boolean"===c)&&(this.className&&L.set(this,"__className__",this.className),this.className=this.className||a===!1?"":L.get(this,"__className__")||"")})},hasClass:function(a){for(var b=" "+a+" ",c=0,d=this.length;d>c;c++)if(1===this[c].nodeType&&(" "+this[c].className+" ").replace(ab," ").indexOf(b)>=0)return!0;return!1}});var bb=/\r/g;n.fn.extend({val:function(a){var b,c,d,e=this[0];{if(arguments.length)return d=n.isFunction(a),this.each(function(c){var e;1===this.nodeType&&(e=d?a.call(this,c,n(this).val()):a,null==e?e="":"number"==typeof e?e+="":n.isArray(e)&&(e=n.map(e,function(a){return null==a?"":a+""})),b=n.valHooks[this.type]||n.valHooks[this.nodeName.toLowerCase()],b&&"set"in b&&void 0!==b.set(this,e,"value")||(this.value=e))});if(e)return b=n.valHooks[e.type]||n.valHooks[e.nodeName.toLowerCase()],b&&"get"in b&&void 0!==(c=b.get(e,"value"))?c:(c=e.value,"string"==typeof c?c.replace(bb,""):null==c?"":c)}}}),n.extend({valHooks:{option:{get:function(a){var b=n.find.attr(a,"value");return null!=b?b:n.trim(n.text(a))}},select:{get:function(a){for(var b,c,d=a.options,e=a.selectedIndex,f="select-one"===a.type||0>e,g=f?null:[],h=f?e+1:d.length,i=0>e?h:f?e:0;h>i;i++)if(c=d[i],!(!c.selected&&i!==e||(k.optDisabled?c.disabled:null!==c.getAttribute("disabled"))||c.parentNode.disabled&&n.nodeName(c.parentNode,"optgroup"))){if(b=n(c).val(),f)return b;g.push(b)}return g},set:function(a,b){var c,d,e=a.options,f=n.makeArray(b),g=e.length;while(g--)d=e[g],(d.selected=n.inArray(d.value,f)>=0)&&(c=!0);return c||(a.selectedIndex=-1),f}}}}),n.each(["radio","checkbox"],function(){n.valHooks[this]={set:function(a,b){return n.isArray(b)?a.checked=n.inArray(n(a).val(),b)>=0:void 0}},k.checkOn||(n.valHooks[this].get=function(a){return null===a.getAttribute("value")?"on":a.value})}),n.each("blur focus focusin focusout load resize scroll unload click dblclick mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave change select submit keydown keypress keyup error contextmenu".split(" "),function(a,b){n.fn[b]=function(a,c){return arguments.length>0?this.on(b,null,a,c):this.trigger(b)}}),n.fn.extend({hover:function(a,b){return this.mouseenter(a).mouseleave(b||a)},bind:function(a,b,c){return this.on(a,null,b,c)},unbind:function(a,b){return this.off(a,null,b)},delegate:function(a,b,c,d){return this.on(b,a,c,d)},undelegate:function(a,b,c){return 1===arguments.length?this.off(a,"**"):this.off(b,a||"**",c)}});var cb=n.now(),db=/\?/;n.parseJSON=function(a){return JSON.parse(a+"")},n.parseXML=function(a){var b,c;if(!a||"string"!=typeof a)return null;try{c=new DOMParser,b=c.parseFromString(a,"text/xml")}catch(d){b=void 0}return(!b||b.getElementsByTagName("parsererror").length)&&n.error("Invalid XML: "+a),b};var eb=/#.*$/,fb=/([?&])_=[^&]*/,gb=/^(.*?):[ \t]*([^\r\n]*)$/gm,hb=/^(?:about|app|app-storage|.+-extension|file|res|widget):$/,ib=/^(?:GET|HEAD)$/,jb=/^\/\//,kb=/^([\w.+-]+:)(?:\/\/(?:[^\/?#]*@|)([^\/?#:]*)(?::(\d+)|)|)/,lb={},mb={},nb="*/".concat("*"),ob=a.location.href,pb=kb.exec(ob.toLowerCase())||[];function qb(a){return function(b,c){"string"!=typeof b&&(c=b,b="*");var d,e=0,f=b.toLowerCase().match(E)||[];if(n.isFunction(c))while(d=f[e++])"+"===d[0]?(d=d.slice(1)||"*",(a[d]=a[d]||[]).unshift(c)):(a[d]=a[d]||[]).push(c)}}function rb(a,b,c,d){var e={},f=a===mb;function g(h){var i;return e[h]=!0,n.each(a[h]||[],function(a,h){var j=h(b,c,d);return"string"!=typeof j||f||e[j]?f?!(i=j):void 0:(b.dataTypes.unshift(j),g(j),!1)}),i}return g(b.dataTypes[0])||!e["*"]&&g("*")}function sb(a,b){var c,d,e=n.ajaxSettings.flatOptions||{};for(c in b)void 0!==b[c]&&((e[c]?a:d||(d={}))[c]=b[c]);return d&&n.extend(!0,a,d),a}function tb(a,b,c){var d,e,f,g,h=a.contents,i=a.dataTypes;while("*"===i[0])i.shift(),void 0===d&&(d=a.mimeType||b.getResponseHeader("Content-Type"));if(d)for(e in h)if(h[e]&&h[e].test(d)){i.unshift(e);break}if(i[0]in c)f=i[0];else{for(e in c){if(!i[0]||a.converters[e+" "+i[0]]){f=e;break}g||(g=e)}f=f||g}return f?(f!==i[0]&&i.unshift(f),c[f]):void 0}function ub(a,b,c,d){var e,f,g,h,i,j={},k=a.dataTypes.slice();if(k[1])for(g in a.converters)j[g.toLowerCase()]=a.converters[g];f=k.shift();while(f)if(a.responseFields[f]&&(c[a.responseFields[f]]=b),!i&&d&&a.dataFilter&&(b=a.dataFilter(b,a.dataType)),i=f,f=k.shift())if("*"===f)f=i;else if("*"!==i&&i!==f){if(g=j[i+" "+f]||j["* "+f],!g)for(e in j)if(h=e.split(" "),h[1]===f&&(g=j[i+" "+h[0]]||j["* "+h[0]])){g===!0?g=j[e]:j[e]!==!0&&(f=h[0],k.unshift(h[1]));break}if(g!==!0)if(g&&a["throws"])b=g(b);else try{b=g(b)}catch(l){return{state:"parsererror",error:g?l:"No conversion from "+i+" to "+f}}}return{state:"success",data:b}}n.extend({active:0,lastModified:{},etag:{},ajaxSettings:{url:ob,type:"GET",isLocal:hb.test(pb[1]),global:!0,processData:!0,async:!0,contentType:"application/x-www-form-urlencoded; charset=UTF-8",accepts:{"*":nb,text:"text/plain",html:"text/html",xml:"application/xml, text/xml",json:"application/json, text/javascript"},contents:{xml:/xml/,html:/html/,json:/json/},responseFields:{xml:"responseXML",text:"responseText",json:"responseJSON"},converters:{"* text":String,"text html":!0,"text json":n.parseJSON,"text xml":n.parseXML},flatOptions:{url:!0,context:!0}},ajaxSetup:function(a,b){return b?sb(sb(a,n.ajaxSettings),b):sb(n.ajaxSettings,a)},ajaxPrefilter:qb(lb),ajaxTransport:qb(mb),ajax:function(a,b){"object"==typeof a&&(b=a,a=void 0),b=b||{};var c,d,e,f,g,h,i,j,k=n.ajaxSetup({},b),l=k.context||k,m=k.context&&(l.nodeType||l.jquery)?n(l):n.event,o=n.Deferred(),p=n.Callbacks("once memory"),q=k.statusCode||{},r={},s={},t=0,u="canceled",v={readyState:0,getResponseHeader:function(a){var b;if(2===t){if(!f){f={};while(b=gb.exec(e))f[b[1].toLowerCase()]=b[2]}b=f[a.toLowerCase()]}return null==b?null:b},getAllResponseHeaders:function(){return 2===t?e:null},setRequestHeader:function(a,b){var c=a.toLowerCase();return t||(a=s[c]=s[c]||a,r[a]=b),this},overrideMimeType:function(a){return t||(k.mimeType=a),this},statusCode:function(a){var b;if(a)if(2>t)for(b in a)q[b]=[q[b],a[b]];else v.always(a[v.status]);return this},abort:function(a){var b=a||u;return c&&c.abort(b),x(0,b),this}};if(o.promise(v).complete=p.add,v.success=v.done,v.error=v.fail,k.url=((a||k.url||ob)+"").replace(eb,"").replace(jb,pb[1]+"//"),k.type=b.method||b.type||k.method||k.type,k.dataTypes=n.trim(k.dataType||"*").toLowerCase().match(E)||[""],null==k.crossDomain&&(h=kb.exec(k.url.toLowerCase()),k.crossDomain=!(!h||h[1]===pb[1]&&h[2]===pb[2]&&(h[3]||("http:"===h[1]?"80":"443"))===(pb[3]||("http:"===pb[1]?"80":"443")))),k.data&&k.processData&&"string"!=typeof k.data&&(k.data=n.param(k.data,k.traditional)),rb(lb,k,b,v),2===t)return v;i=n.event&&k.global,i&&0===n.active++&&n.event.trigger("ajaxStart"),k.type=k.type.toUpperCase(),k.hasContent=!ib.test(k.type),d=k.url,k.hasContent||(k.data&&(d=k.url+=(db.test(d)?"&":"?")+k.data,delete k.data),k.cache===!1&&(k.url=fb.test(d)?d.replace(fb,"$1_="+cb++):d+(db.test(d)?"&":"?")+"_="+cb++)),k.ifModified&&(n.lastModified[d]&&v.setRequestHeader("If-Modified-Since",n.lastModified[d]),n.etag[d]&&v.setRequestHeader("If-None-Match",n.etag[d])),(k.data&&k.hasContent&&k.contentType!==!1||b.contentType)&&v.setRequestHeader("Content-Type",k.contentType),v.setRequestHeader("Accept",k.dataTypes[0]&&k.accepts[k.dataTypes[0]]?k.accepts[k.dataTypes[0]]+("*"!==k.dataTypes[0]?", "+nb+"; q=0.01":""):k.accepts["*"]);for(j in k.headers)v.setRequestHeader(j,k.headers[j]);if(k.beforeSend&&(k.beforeSend.call(l,v,k)===!1||2===t))return v.abort();u="abort";for(j in{success:1,error:1,complete:1})v[j](k[j]);if(c=rb(mb,k,b,v)){v.readyState=1,i&&m.trigger("ajaxSend",[v,k]),k.async&&k.timeout>0&&(g=setTimeout(function(){v.abort("timeout")},k.timeout));try{t=1,c.send(r,x)}catch(w){if(!(2>t))throw w;x(-1,w)}}else x(-1,"No Transport");function x(a,b,f,h){var j,r,s,u,w,x=b;2!==t&&(t=2,g&&clearTimeout(g),c=void 0,e=h||"",v.readyState=a>0?4:0,j=a>=200&&300>a||304===a,f&&(u=tb(k,v,f)),u=ub(k,u,v,j),j?(k.ifModified&&(w=v.getResponseHeader("Last-Modified"),w&&(n.lastModified[d]=w),w=v.getResponseHeader("etag"),w&&(n.etag[d]=w)),204===a||"HEAD"===k.type?x="nocontent":304===a?x="notmodified":(x=u.state,r=u.data,s=u.error,j=!s)):(s=x,(a||!x)&&(x="error",0>a&&(a=0))),v.status=a,v.statusText=(b||x)+"",j?o.resolveWith(l,[r,x,v]):o.rejectWith(l,[v,x,s]),v.statusCode(q),q=void 0,i&&m.trigger(j?"ajaxSuccess":"ajaxError",[v,k,j?r:s]),p.fireWith(l,[v,x]),i&&(m.trigger("ajaxComplete",[v,k]),--n.active||n.event.trigger("ajaxStop")))}return v},getJSON:function(a,b,c){return n.get(a,b,c,"json")},getScript:function(a,b){return n.get(a,void 0,b,"script")}}),n.each(["get","post"],function(a,b){n[b]=function(a,c,d,e){return n.isFunction(c)&&(e=e||d,d=c,c=void 0),n.ajax({url:a,type:b,dataType:e,data:c,success:d})}}),n._evalUrl=function(a){return n.ajax({url:a,type:"GET",dataType:"script",async:!1,global:!1,"throws":!0})},n.fn.extend({wrapAll:function(a){var b;return n.isFunction(a)?this.each(function(b){n(this).wrapAll(a.call(this,b))}):(this[0]&&(b=n(a,this[0].ownerDocument).eq(0).clone(!0),this[0].parentNode&&b.insertBefore(this[0]),b.map(function(){var a=this;while(a.firstElementChild)a=a.firstElementChild;return a}).append(this)),this)},wrapInner:function(a){return this.each(n.isFunction(a)?function(b){n(this).wrapInner(a.call(this,b))}:function(){var b=n(this),c=b.contents();c.length?c.wrapAll(a):b.append(a)})},wrap:function(a){var b=n.isFunction(a);return this.each(function(c){n(this).wrapAll(b?a.call(this,c):a)})},unwrap:function(){return this.parent().each(function(){n.nodeName(this,"body")||n(this).replaceWith(this.childNodes)}).end()}}),n.expr.filters.hidden=function(a){return a.offsetWidth<=0&&a.offsetHeight<=0},n.expr.filters.visible=function(a){return!n.expr.filters.hidden(a)};var vb=/%20/g,wb=/\[\]$/,xb=/\r?\n/g,yb=/^(?:submit|button|image|reset|file)$/i,zb=/^(?:input|select|textarea|keygen)/i;function Ab(a,b,c,d){var e;if(n.isArray(b))n.each(b,function(b,e){c||wb.test(a)?d(a,e):Ab(a+"["+("object"==typeof e?b:"")+"]",e,c,d)});else if(c||"object"!==n.type(b))d(a,b);else for(e in b)Ab(a+"["+e+"]",b[e],c,d)}n.param=function(a,b){var c,d=[],e=function(a,b){b=n.isFunction(b)?b():null==b?"":b,d[d.length]=encodeURIComponent(a)+"="+encodeURIComponent(b)};if(void 0===b&&(b=n.ajaxSettings&&n.ajaxSettings.traditional),n.isArray(a)||a.jquery&&!n.isPlainObject(a))n.each(a,function(){e(this.name,this.value)});else for(c in a)Ab(c,a[c],b,e);return d.join("&").replace(vb,"+")},n.fn.extend({serialize:function(){return n.param(this.serializeArray())},serializeArray:function(){return this.map(function(){var a=n.prop(this,"elements");return a?n.makeArray(a):this}).filter(function(){var a=this.type;return this.name&&!n(this).is(":disabled")&&zb.test(this.nodeName)&&!yb.test(a)&&(this.checked||!T.test(a))}).map(function(a,b){var c=n(this).val();return null==c?null:n.isArray(c)?n.map(c,function(a){return{name:b.name,value:a.replace(xb,"\r\n")}}):{name:b.name,value:c.replace(xb,"\r\n")}}).get()}}),n.ajaxSettings.xhr=function(){try{return new XMLHttpRequest}catch(a){}};var Bb=0,Cb={},Db={0:200,1223:204},Eb=n.ajaxSettings.xhr();a.attachEvent&&a.attachEvent("onunload",function(){for(var a in Cb)Cb[a]()}),k.cors=!!Eb&&"withCredentials"in Eb,k.ajax=Eb=!!Eb,n.ajaxTransport(function(a){var b;return k.cors||Eb&&!a.crossDomain?{send:function(c,d){var e,f=a.xhr(),g=++Bb;if(f.open(a.type,a.url,a.async,a.username,a.password),a.xhrFields)for(e in a.xhrFields)f[e]=a.xhrFields[e];a.mimeType&&f.overrideMimeType&&f.overrideMimeType(a.mimeType),a.crossDomain||c["X-Requested-With"]||(c["X-Requested-With"]="XMLHttpRequest");for(e in c)f.setRequestHeader(e,c[e]);b=function(a){return function(){b&&(delete Cb[g],b=f.onload=f.onerror=null,"abort"===a?f.abort():"error"===a?d(f.status,f.statusText):d(Db[f.status]||f.status,f.statusText,"string"==typeof f.responseText?{text:f.responseText}:void 0,f.getAllResponseHeaders()))}},f.onload=b(),f.onerror=b("error"),b=Cb[g]=b("abort");try{f.send(a.hasContent&&a.data||null)}catch(h){if(b)throw h}},abort:function(){b&&b()}}:void 0}),n.ajaxSetup({accepts:{script:"text/javascript, application/javascript, application/ecmascript, application/x-ecmascript"},contents:{script:/(?:java|ecma)script/},converters:{"text script":function(a){return n.globalEval(a),a}}}),n.ajaxPrefilter("script",function(a){void 0===a.cache&&(a.cache=!1),a.crossDomain&&(a.type="GET")}),n.ajaxTransport("script",function(a){if(a.crossDomain){var b,c;return{send:function(d,e){b=n("<script>").prop({async:!0,charset:a.scriptCharset,src:a.url}).on("load error",c=function(a){b.remove(),c=null,a&&e("error"===a.type?404:200,a.type)}),l.head.appendChild(b[0])},abort:function(){c&&c()}}}});var Fb=[],Gb=/(=)\?(?=&|$)|\?\?/;n.ajaxSetup({jsonp:"callback",jsonpCallback:function(){var a=Fb.pop()||n.expando+"_"+cb++;return this[a]=!0,a}}),n.ajaxPrefilter("json jsonp",function(b,c,d){var e,f,g,h=b.jsonp!==!1&&(Gb.test(b.url)?"url":"string"==typeof b.data&&!(b.contentType||"").indexOf("application/x-www-form-urlencoded")&&Gb.test(b.data)&&"data");return h||"jsonp"===b.dataTypes[0]?(e=b.jsonpCallback=n.isFunction(b.jsonpCallback)?b.jsonpCallback():b.jsonpCallback,h?b[h]=b[h].replace(Gb,"$1"+e):b.jsonp!==!1&&(b.url+=(db.test(b.url)?"&":"?")+b.jsonp+"="+e),b.converters["script json"]=function(){return g||n.error(e+" was not called"),g[0]},b.dataTypes[0]="json",f=a[e],a[e]=function(){g=arguments},d.always(function(){a[e]=f,b[e]&&(b.jsonpCallback=c.jsonpCallback,Fb.push(e)),g&&n.isFunction(f)&&f(g[0]),g=f=void 0}),"script"):void 0}),n.parseHTML=function(a,b,c){if(!a||"string"!=typeof a)return null;"boolean"==typeof b&&(c=b,b=!1),b=b||l;var d=v.exec(a),e=!c&&[];return d?[b.createElement(d[1])]:(d=n.buildFragment([a],b,e),e&&e.length&&n(e).remove(),n.merge([],d.childNodes))};var Hb=n.fn.load;n.fn.load=function(a,b,c){if("string"!=typeof a&&Hb)return Hb.apply(this,arguments);var d,e,f,g=this,h=a.indexOf(" ");return h>=0&&(d=n.trim(a.slice(h)),a=a.slice(0,h)),n.isFunction(b)?(c=b,b=void 0):b&&"object"==typeof b&&(e="POST"),g.length>0&&n.ajax({url:a,type:e,dataType:"html",data:b}).done(function(a){f=arguments,g.html(d?n("<div>").append(n.parseHTML(a)).find(d):a)}).complete(c&&function(a,b){g.each(c,f||[a.responseText,b,a])}),this},n.each(["ajaxStart","ajaxStop","ajaxComplete","ajaxError","ajaxSuccess","ajaxSend"],function(a,b){n.fn[b]=function(a){return this.on(b,a)}}),n.expr.filters.animated=function(a){return n.grep(n.timers,function(b){return a===b.elem}).length};var Ib=a.document.documentElement;function Jb(a){return n.isWindow(a)?a:9===a.nodeType&&a.defaultView}n.offset={setOffset:function(a,b,c){var d,e,f,g,h,i,j,k=n.css(a,"position"),l=n(a),m={};"static"===k&&(a.style.position="relative"),h=l.offset(),f=n.css(a,"top"),i=n.css(a,"left"),j=("absolute"===k||"fixed"===k)&&(f+i).indexOf("auto")>-1,j?(d=l.position(),g=d.top,e=d.left):(g=parseFloat(f)||0,e=parseFloat(i)||0),n.isFunction(b)&&(b=b.call(a,c,h)),null!=b.top&&(m.top=b.top-h.top+g),null!=b.left&&(m.left=b.left-h.left+e),"using"in b?b.using.call(a,m):l.css(m)}},n.fn.extend({offset:function(a){if(arguments.length)return void 0===a?this:this.each(function(b){n.offset.setOffset(this,a,b)});var b,c,d=this[0],e={top:0,left:0},f=d&&d.ownerDocument;if(f)return b=f.documentElement,n.contains(b,d)?(typeof d.getBoundingClientRect!==U&&(e=d.getBoundingClientRect()),c=Jb(f),{top:e.top+c.pageYOffset-b.clientTop,left:e.left+c.pageXOffset-b.clientLeft}):e},position:function(){if(this[0]){var a,b,c=this[0],d={top:0,left:0};return"fixed"===n.css(c,"position")?b=c.getBoundingClientRect():(a=this.offsetParent(),b=this.offset(),n.nodeName(a[0],"html")||(d=a.offset()),d.top+=n.css(a[0],"borderTopWidth",!0),d.left+=n.css(a[0],"borderLeftWidth",!0)),{top:b.top-d.top-n.css(c,"marginTop",!0),left:b.left-d.left-n.css(c,"marginLeft",!0)}}},offsetParent:function(){return this.map(function(){var a=this.offsetParent||Ib;while(a&&!n.nodeName(a,"html")&&"static"===n.css(a,"position"))a=a.offsetParent;return a||Ib})}}),n.each({scrollLeft:"pageXOffset",scrollTop:"pageYOffset"},function(b,c){var d="pageYOffset"===c;n.fn[b]=function(e){return J(this,function(b,e,f){var g=Jb(b);return void 0===f?g?g[c]:b[e]:void(g?g.scrollTo(d?a.pageXOffset:f,d?f:a.pageYOffset):b[e]=f)},b,e,arguments.length,null)}}),n.each(["top","left"],function(a,b){n.cssHooks[b]=ya(k.pixelPosition,function(a,c){return c?(c=xa(a,b),va.test(c)?n(a).position()[b]+"px":c):void 0})}),n.each({Height:"height",Width:"width"},function(a,b){n.each({padding:"inner"+a,content:b,"":"outer"+a},function(c,d){n.fn[d]=function(d,e){var f=arguments.length&&(c||"boolean"!=typeof d),g=c||(d===!0||e===!0?"margin":"border");return J(this,function(b,c,d){var e;return n.isWindow(b)?b.document.documentElement["client"+a]:9===b.nodeType?(e=b.documentElement,Math.max(b.body["scroll"+a],e["scroll"+a],b.body["offset"+a],e["offset"+a],e["client"+a])):void 0===d?n.css(b,c,g):n.style(b,c,d,g)},b,f?d:void 0,f,null)}})}),n.fn.size=function(){return this.length},n.fn.andSelf=n.fn.addBack,"function"==typeof define&&define.amd&&define("jquery",[],function(){return n});var Kb=a.jQuery,Lb=a.$;return n.noConflict=function(b){return a.$===n&&(a.$=Lb),b&&a.jQuery===n&&(a.jQuery=Kb),n},typeof b===U&&(a.jQuery=a.$=n),n});
diff --git a/radicale_web/web/infcloud/lib/jquery-ui-1.11.4.custom.js b/radicale_web/web/infcloud/lib/jquery-ui-1.11.4.custom.js
deleted file mode 100644
index fa650d7..0000000
--- a/radicale_web/web/infcloud/lib/jquery-ui-1.11.4.custom.js
+++ /dev/null
@@ -1,8226 +0,0 @@
-/*! jQuery UI - v1.11.4 - 2015-03-15
-* http://jqueryui.com
-* Includes: core.js, widget.js, mouse.js, position.js, draggable.js, droppable.js, resizable.js, autocomplete.js, datepicker.js, menu.js, slider.js
-* Copyright 2015 jQuery Foundation and other contributors; Licensed MIT */
-
-(function( factory ) {
- if ( typeof define === "function" && define.amd ) {
-
- // AMD. Register as an anonymous module.
- define([ "jquery" ], factory );
- } else {
-
- // Browser globals
- factory( jQuery );
- }
-}(function( $ ) {
-/*!
- * jQuery UI Core 1.11.4
- * http://jqueryui.com
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- *
- * http://api.jqueryui.com/category/ui-core/
- */
-
-
-// $.ui might exist from components with no dependencies, e.g., $.ui.position
-$.ui = $.ui || {};
-
-$.extend( $.ui, {
- version: "1.11.4",
-
- keyCode: {
- BACKSPACE: 8,
- COMMA: 188,
- DELETE: 46,
- DOWN: 40,
- END: 35,
- ENTER: 13,
- ESCAPE: 27,
- HOME: 36,
- LEFT: 37,
- PAGE_DOWN: 34,
- PAGE_UP: 33,
- PERIOD: 190,
- RIGHT: 39,
- SPACE: 32,
- TAB: 9,
- UP: 38
- }
-});
-
-// plugins
-$.fn.extend({
- scrollParent: function( includeHidden ) {
- var position = this.css( "position" ),
- excludeStaticParent = position === "absolute",
- overflowRegex = includeHidden ? /(auto|scroll|hidden)/ : /(auto|scroll)/,
- scrollParent = this.parents().filter( function() {
- var parent = $( this );
- if ( excludeStaticParent && parent.css( "position" ) === "static" ) {
- return false;
- }
- return overflowRegex.test( parent.css( "overflow" ) + parent.css( "overflow-y" ) + parent.css( "overflow-x" ) );
- }).eq( 0 );
-
- return position === "fixed" || !scrollParent.length ? $( this[ 0 ].ownerDocument || document ) : scrollParent;
- },
-
- uniqueId: (function() {
- var uuid = 0;
-
- return function() {
- return this.each(function() {
- if ( !this.id ) {
- this.id = "ui-id-" + ( ++uuid );
- }
- });
- };
- })(),
-
- removeUniqueId: function() {
- return this.each(function() {
- if ( /^ui-id-\d+$/.test( this.id ) ) {
- $( this ).removeAttr( "id" );
- }
- });
- }
-});
-
-// selectors
-function focusable( element, isTabIndexNotNaN ) {
- var map, mapName, img,
- nodeName = element.nodeName.toLowerCase();
- if ( "area" === nodeName ) {
- map = element.parentNode;
- mapName = map.name;
- if ( !element.href || !mapName || map.nodeName.toLowerCase() !== "map" ) {
- return false;
- }
- img = $( "img[usemap='#" + mapName + "']" )[ 0 ];
- return !!img && visible( img );
- }
- return ( /^(input|select|textarea|button|object)$/.test( nodeName ) ?
- !element.disabled :
- "a" === nodeName ?
- element.href || isTabIndexNotNaN :
- isTabIndexNotNaN) &&
- // the element and all of its ancestors must be visible
- visible( element );
-}
-
-function visible( element ) {
- return $.expr.filters.visible( element ) &&
- !$( element ).parents().addBack().filter(function() {
- return $.css( this, "visibility" ) === "hidden";
- }).length;
-}
-
-$.extend( $.expr[ ":" ], {
- data: $.expr.createPseudo ?
- $.expr.createPseudo(function( dataName ) {
- return function( elem ) {
- return !!$.data( elem, dataName );
- };
- }) :
- // support: jQuery <1.8
- function( elem, i, match ) {
- return !!$.data( elem, match[ 3 ] );
- },
-
- focusable: function( element ) {
- return focusable( element, !isNaN( $.attr( element, "tabindex" ) ) );
- },
-
- tabbable: function( element ) {
- var tabIndex = $.attr( element, "tabindex" ),
- isTabIndexNaN = isNaN( tabIndex );
- return ( isTabIndexNaN || tabIndex >= 0 ) && focusable( element, !isTabIndexNaN );
- }
-});
-
-// support: jQuery <1.8
-if ( !$( "<a>" ).outerWidth( 1 ).jquery ) {
- $.each( [ "Width", "Height" ], function( i, name ) {
- var side = name === "Width" ? [ "Left", "Right" ] : [ "Top", "Bottom" ],
- type = name.toLowerCase(),
- orig = {
- innerWidth: $.fn.innerWidth,
- innerHeight: $.fn.innerHeight,
- outerWidth: $.fn.outerWidth,
- outerHeight: $.fn.outerHeight
- };
-
- function reduce( elem, size, border, margin ) {
- $.each( side, function() {
- size -= parseFloat( $.css( elem, "padding" + this ) ) || 0;
- if ( border ) {
- size -= parseFloat( $.css( elem, "border" + this + "Width" ) ) || 0;
- }
- if ( margin ) {
- size -= parseFloat( $.css( elem, "margin" + this ) ) || 0;
- }
- });
- return size;
- }
-
- $.fn[ "inner" + name ] = function( size ) {
- if ( size === undefined ) {
- return orig[ "inner" + name ].call( this );
- }
-
- return this.each(function() {
- $( this ).css( type, reduce( this, size ) + "px" );
- });
- };
-
- $.fn[ "outer" + name] = function( size, margin ) {
- if ( typeof size !== "number" ) {
- return orig[ "outer" + name ].call( this, size );
- }
-
- return this.each(function() {
- $( this).css( type, reduce( this, size, true, margin ) + "px" );
- });
- };
- });
-}
-
-// support: jQuery <1.8
-if ( !$.fn.addBack ) {
- $.fn.addBack = function( selector ) {
- return this.add( selector == null ?
- this.prevObject : this.prevObject.filter( selector )
- );
- };
-}
-
-// support: jQuery 1.6.1, 1.6.2 (http://bugs.jquery.com/ticket/9413)
-if ( $( "<a>" ).data( "a-b", "a" ).removeData( "a-b" ).data( "a-b" ) ) {
- $.fn.removeData = (function( removeData ) {
- return function( key ) {
- if ( arguments.length ) {
- return removeData.call( this, $.camelCase( key ) );
- } else {
- return removeData.call( this );
- }
- };
- })( $.fn.removeData );
-}
-
-// deprecated
-$.ui.ie = !!/msie [\w.]+/.exec( navigator.userAgent.toLowerCase() );
-
-$.fn.extend({
- focus: (function( orig ) {
- return function( delay, fn ) {
- return typeof delay === "number" ?
- this.each(function() {
- var elem = this;
- setTimeout(function() {
- $( elem ).focus();
- if ( fn ) {
- fn.call( elem );
- }
- }, delay );
- }) :
- orig.apply( this, arguments );
- };
- })( $.fn.focus ),
-
- disableSelection: (function() {
- var eventType = "onselectstart" in document.createElement( "div" ) ?
- "selectstart" :
- "mousedown";
-
- return function() {
- return this.bind( eventType + ".ui-disableSelection", function( event ) {
- event.preventDefault();
- });
- };
- })(),
-
- enableSelection: function() {
- return this.unbind( ".ui-disableSelection" );
- },
-
- zIndex: function( zIndex ) {
- if ( zIndex !== undefined ) {
- return this.css( "zIndex", zIndex );
- }
-
- if ( this.length ) {
- var elem = $( this[ 0 ] ), position, value;
- while ( elem.length && elem[ 0 ] !== document ) {
- // Ignore z-index if position is set to a value where z-index is ignored by the browser
- // This makes behavior of this function consistent across browsers
- // WebKit always returns auto if the element is positioned
- position = elem.css( "position" );
- if ( position === "absolute" || position === "relative" || position === "fixed" ) {
- // IE returns 0 when zIndex is not specified
- // other browsers return a string
- // we ignore the case of nested elements with an explicit value of 0
- // <div style="z-index: -10;"><div style="z-index: 0;"></div></div>
- value = parseInt( elem.css( "zIndex" ), 10 );
- if ( !isNaN( value ) && value !== 0 ) {
- return value;
- }
- }
- elem = elem.parent();
- }
- }
-
- return 0;
- }
-});
-
-// $.ui.plugin is deprecated. Use $.widget() extensions instead.
-$.ui.plugin = {
- add: function( module, option, set ) {
- var i,
- proto = $.ui[ module ].prototype;
- for ( i in set ) {
- proto.plugins[ i ] = proto.plugins[ i ] || [];
- proto.plugins[ i ].push( [ option, set[ i ] ] );
- }
- },
- call: function( instance, name, args, allowDisconnected ) {
- var i,
- set = instance.plugins[ name ];
-
- if ( !set ) {
- return;
- }
-
- if ( !allowDisconnected && ( !instance.element[ 0 ].parentNode || instance.element[ 0 ].parentNode.nodeType === 11 ) ) {
- return;
- }
-
- for ( i = 0; i < set.length; i++ ) {
- if ( instance.options[ set[ i ][ 0 ] ] ) {
- set[ i ][ 1 ].apply( instance.element, args );
- }
- }
- }
-};
-
-
-/*!
- * jQuery UI Widget 1.11.4
- * http://jqueryui.com
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- *
- * http://api.jqueryui.com/jQuery.widget/
- */
-
-
-var widget_uuid = 0,
- widget_slice = Array.prototype.slice;
-
-$.cleanData = (function( orig ) {
- return function( elems ) {
- var events, elem, i;
- for ( i = 0; (elem = elems[i]) != null; i++ ) {
- try {
-
- // Only trigger remove when necessary to save time
- events = $._data( elem, "events" );
- if ( events && events.remove ) {
- $( elem ).triggerHandler( "remove" );
- }
-
- // http://bugs.jquery.com/ticket/8235
- } catch ( e ) {}
- }
- orig( elems );
- };
-})( $.cleanData );
-
-$.widget = function( name, base, prototype ) {
- var fullName, existingConstructor, constructor, basePrototype,
- // proxiedPrototype allows the provided prototype to remain unmodified
- // so that it can be used as a mixin for multiple widgets (#8876)
- proxiedPrototype = {},
- namespace = name.split( "." )[ 0 ];
-
- name = name.split( "." )[ 1 ];
- fullName = namespace + "-" + name;
-
- if ( !prototype ) {
- prototype = base;
- base = $.Widget;
- }
-
- // create selector for plugin
- $.expr[ ":" ][ fullName.toLowerCase() ] = function( elem ) {
- return !!$.data( elem, fullName );
- };
-
- $[ namespace ] = $[ namespace ] || {};
- existingConstructor = $[ namespace ][ name ];
- constructor = $[ namespace ][ name ] = function( options, element ) {
- // allow instantiation without "new" keyword
- if ( !this._createWidget ) {
- return new constructor( options, element );
- }
-
- // allow instantiation without initializing for simple inheritance
- // must use "new" keyword (the code above always passes args)
- if ( arguments.length ) {
- this._createWidget( options, element );
- }
- };
- // extend with the existing constructor to carry over any static properties
- $.extend( constructor, existingConstructor, {
- version: prototype.version,
- // copy the object used to create the prototype in case we need to
- // redefine the widget later
- _proto: $.extend( {}, prototype ),
- // track widgets that inherit from this widget in case this widget is
- // redefined after a widget inherits from it
- _childConstructors: []
- });
-
- basePrototype = new base();
- // we need to make the options hash a property directly on the new instance
- // otherwise we'll modify the options hash on the prototype that we're
- // inheriting from
- basePrototype.options = $.widget.extend( {}, basePrototype.options );
- $.each( prototype, function( prop, value ) {
- if ( !$.isFunction( value ) ) {
- proxiedPrototype[ prop ] = value;
- return;
- }
- proxiedPrototype[ prop ] = (function() {
- var _super = function() {
- return base.prototype[ prop ].apply( this, arguments );
- },
- _superApply = function( args ) {
- return base.prototype[ prop ].apply( this, args );
- };
- return function() {
- var __super = this._super,
- __superApply = this._superApply,
- returnValue;
-
- this._super = _super;
- this._superApply = _superApply;
-
- returnValue = value.apply( this, arguments );
-
- this._super = __super;
- this._superApply = __superApply;
-
- return returnValue;
- };
- })();
- });
- constructor.prototype = $.widget.extend( basePrototype, {
- // TODO: remove support for widgetEventPrefix
- // always use the name + a colon as the prefix, e.g., draggable:start
- // don't prefix for widgets that aren't DOM-based
- widgetEventPrefix: existingConstructor ? (basePrototype.widgetEventPrefix || name) : name
- }, proxiedPrototype, {
- constructor: constructor,
- namespace: namespace,
- widgetName: name,
- widgetFullName: fullName
- });
-
- // If this widget is being redefined then we need to find all widgets that
- // are inheriting from it and redefine all of them so that they inherit from
- // the new version of this widget. We're essentially trying to replace one
- // level in the prototype chain.
- if ( existingConstructor ) {
- $.each( existingConstructor._childConstructors, function( i, child ) {
- var childPrototype = child.prototype;
-
- // redefine the child widget using the same prototype that was
- // originally used, but inherit from the new version of the base
- $.widget( childPrototype.namespace + "." + childPrototype.widgetName, constructor, child._proto );
- });
- // remove the list of existing child constructors from the old constructor
- // so the old child constructors can be garbage collected
- delete existingConstructor._childConstructors;
- } else {
- base._childConstructors.push( constructor );
- }
-
- $.widget.bridge( name, constructor );
-
- return constructor;
-};
-
-$.widget.extend = function( target ) {
- var input = widget_slice.call( arguments, 1 ),
- inputIndex = 0,
- inputLength = input.length,
- key,
- value;
- for ( ; inputIndex < inputLength; inputIndex++ ) {
- for ( key in input[ inputIndex ] ) {
- value = input[ inputIndex ][ key ];
- if ( input[ inputIndex ].hasOwnProperty( key ) && value !== undefined ) {
- // Clone objects
- if ( $.isPlainObject( value ) ) {
- target[ key ] = $.isPlainObject( target[ key ] ) ?
- $.widget.extend( {}, target[ key ], value ) :
- // Don't extend strings, arrays, etc. with objects
- $.widget.extend( {}, value );
- // Copy everything else by reference
- } else {
- target[ key ] = value;
- }
- }
- }
- }
- return target;
-};
-
-$.widget.bridge = function( name, object ) {
- var fullName = object.prototype.widgetFullName || name;
- $.fn[ name ] = function( options ) {
- var isMethodCall = typeof options === "string",
- args = widget_slice.call( arguments, 1 ),
- returnValue = this;
-
- if ( isMethodCall ) {
- this.each(function() {
- var methodValue,
- instance = $.data( this, fullName );
- if ( options === "instance" ) {
- returnValue = instance;
- return false;
- }
- if ( !instance ) {
- return $.error( "cannot call methods on " + name + " prior to initialization; " +
- "attempted to call method '" + options + "'" );
- }
- if ( !$.isFunction( instance[options] ) || options.charAt( 0 ) === "_" ) {
- return $.error( "no such method '" + options + "' for " + name + " widget instance" );
- }
- methodValue = instance[ options ].apply( instance, args );
- if ( methodValue !== instance && methodValue !== undefined ) {
- returnValue = methodValue && methodValue.jquery ?
- returnValue.pushStack( methodValue.get() ) :
- methodValue;
- return false;
- }
- });
- } else {
-
- // Allow multiple hashes to be passed on init
- if ( args.length ) {
- options = $.widget.extend.apply( null, [ options ].concat(args) );
- }
-
- this.each(function() {
- var instance = $.data( this, fullName );
- if ( instance ) {
- instance.option( options || {} );
- if ( instance._init ) {
- instance._init();
- }
- } else {
- $.data( this, fullName, new object( options, this ) );
- }
- });
- }
-
- return returnValue;
- };
-};
-
-$.Widget = function( /* options, element */ ) {};
-$.Widget._childConstructors = [];
-
-$.Widget.prototype = {
- widgetName: "widget",
- widgetEventPrefix: "",
- defaultElement: "<div>",
- options: {
- disabled: false,
-
- // callbacks
- create: null
- },
- _createWidget: function( options, element ) {
- element = $( element || this.defaultElement || this )[ 0 ];
- this.element = $( element );
- this.uuid = widget_uuid++;
- this.eventNamespace = "." + this.widgetName + this.uuid;
-
- this.bindings = $();
- this.hoverable = $();
- this.focusable = $();
-
- if ( element !== this ) {
- $.data( element, this.widgetFullName, this );
- this._on( true, this.element, {
- remove: function( event ) {
- if ( event.target === element ) {
- this.destroy();
- }
- }
- });
- this.document = $( element.style ?
- // element within the document
- element.ownerDocument :
- // element is window or document
- element.document || element );
- this.window = $( this.document[0].defaultView || this.document[0].parentWindow );
- }
-
- this.options = $.widget.extend( {},
- this.options,
- this._getCreateOptions(),
- options );
-
- this._create();
- this._trigger( "create", null, this._getCreateEventData() );
- this._init();
- },
- _getCreateOptions: $.noop,
- _getCreateEventData: $.noop,
- _create: $.noop,
- _init: $.noop,
-
- destroy: function() {
- this._destroy();
- // we can probably remove the unbind calls in 2.0
- // all event bindings should go through this._on()
- this.element
- .unbind( this.eventNamespace )
- .removeData( this.widgetFullName )
- // support: jquery <1.6.3
- // http://bugs.jquery.com/ticket/9413
- .removeData( $.camelCase( this.widgetFullName ) );
- this.widget()
- .unbind( this.eventNamespace )
- .removeAttr( "aria-disabled" )
- .removeClass(
- this.widgetFullName + "-disabled " +
- "ui-state-disabled" );
-
- // clean up events and states
- this.bindings.unbind( this.eventNamespace );
- this.hoverable.removeClass( "ui-state-hover" );
- this.focusable.removeClass( "ui-state-focus" );
- },
- _destroy: $.noop,
-
- widget: function() {
- return this.element;
- },
-
- option: function( key, value ) {
- var options = key,
- parts,
- curOption,
- i;
-
- if ( arguments.length === 0 ) {
- // don't return a reference to the internal hash
- return $.widget.extend( {}, this.options );
- }
-
- if ( typeof key === "string" ) {
- // handle nested keys, e.g., "foo.bar" => { foo: { bar: ___ } }
- options = {};
- parts = key.split( "." );
- key = parts.shift();
- if ( parts.length ) {
- curOption = options[ key ] = $.widget.extend( {}, this.options[ key ] );
- for ( i = 0; i < parts.length - 1; i++ ) {
- curOption[ parts[ i ] ] = curOption[ parts[ i ] ] || {};
- curOption = curOption[ parts[ i ] ];
- }
- key = parts.pop();
- if ( arguments.length === 1 ) {
- return curOption[ key ] === undefined ? null : curOption[ key ];
- }
- curOption[ key ] = value;
- } else {
- if ( arguments.length === 1 ) {
- return this.options[ key ] === undefined ? null : this.options[ key ];
- }
- options[ key ] = value;
- }
- }
-
- this._setOptions( options );
-
- return this;
- },
- _setOptions: function( options ) {
- var key;
-
- for ( key in options ) {
- this._setOption( key, options[ key ] );
- }
-
- return this;
- },
- _setOption: function( key, value ) {
- this.options[ key ] = value;
-
- if ( key === "disabled" ) {
- this.widget()
- .toggleClass( this.widgetFullName + "-disabled", !!value );
-
- // If the widget is becoming disabled, then nothing is interactive
- if ( value ) {
- this.hoverable.removeClass( "ui-state-hover" );
- this.focusable.removeClass( "ui-state-focus" );
- }
- }
-
- return this;
- },
-
- enable: function() {
- return this._setOptions({ disabled: false });
- },
- disable: function() {
- return this._setOptions({ disabled: true });
- },
-
- _on: function( suppressDisabledCheck, element, handlers ) {
- var delegateElement,
- instance = this;
-
- // no suppressDisabledCheck flag, shuffle arguments
- if ( typeof suppressDisabledCheck !== "boolean" ) {
- handlers = element;
- element = suppressDisabledCheck;
- suppressDisabledCheck = false;
- }
-
- // no element argument, shuffle and use this.element
- if ( !handlers ) {
- handlers = element;
- element = this.element;
- delegateElement = this.widget();
- } else {
- element = delegateElement = $( element );
- this.bindings = this.bindings.add( element );
- }
-
- $.each( handlers, function( event, handler ) {
- function handlerProxy() {
- // allow widgets to customize the disabled handling
- // - disabled as an array instead of boolean
- // - disabled class as method for disabling individual parts
- if ( !suppressDisabledCheck &&
- ( instance.options.disabled === true ||
- $( this ).hasClass( "ui-state-disabled" ) ) ) {
- return;
- }
- return ( typeof handler === "string" ? instance[ handler ] : handler )
- .apply( instance, arguments );
- }
-
- // copy the guid so direct unbinding works
- if ( typeof handler !== "string" ) {
- handlerProxy.guid = handler.guid =
- handler.guid || handlerProxy.guid || $.guid++;
- }
-
- var match = event.match( /^([\w:-]*)\s*(.*)$/ ),
- eventName = match[1] + instance.eventNamespace,
- selector = match[2];
- if ( selector ) {
- delegateElement.delegate( selector, eventName, handlerProxy );
- } else {
- element.bind( eventName, handlerProxy );
- }
- });
- },
-
- _off: function( element, eventName ) {
- eventName = (eventName || "").split( " " ).join( this.eventNamespace + " " ) +
- this.eventNamespace;
- element.unbind( eventName ).undelegate( eventName );
-
- // Clear the stack to avoid memory leaks (#10056)
- this.bindings = $( this.bindings.not( element ).get() );
- this.focusable = $( this.focusable.not( element ).get() );
- this.hoverable = $( this.hoverable.not( element ).get() );
- },
-
- _delay: function( handler, delay ) {
- function handlerProxy() {
- return ( typeof handler === "string" ? instance[ handler ] : handler )
- .apply( instance, arguments );
- }
- var instance = this;
- return setTimeout( handlerProxy, delay || 0 );
- },
-
- _hoverable: function( element ) {
- this.hoverable = this.hoverable.add( element );
- this._on( element, {
- mouseenter: function( event ) {
- $( event.currentTarget ).addClass( "ui-state-hover" );
- },
- mouseleave: function( event ) {
- $( event.currentTarget ).removeClass( "ui-state-hover" );
- }
- });
- },
-
- _focusable: function( element ) {
- this.focusable = this.focusable.add( element );
- this._on( element, {
- focusin: function( event ) {
- $( event.currentTarget ).addClass( "ui-state-focus" );
- },
- focusout: function( event ) {
- $( event.currentTarget ).removeClass( "ui-state-focus" );
- }
- });
- },
-
- _trigger: function( type, event, data ) {
- var prop, orig,
- callback = this.options[ type ];
-
- data = data || {};
- event = $.Event( event );
- event.type = ( type === this.widgetEventPrefix ?
- type :
- this.widgetEventPrefix + type ).toLowerCase();
- // the original event may come from any element
- // so we need to reset the target on the new event
- event.target = this.element[ 0 ];
-
- // copy original event properties over to the new event
- orig = event.originalEvent;
- if ( orig ) {
- for ( prop in orig ) {
- if ( !( prop in event ) ) {
- event[ prop ] = orig[ prop ];
- }
- }
- }
-
- this.element.trigger( event, data );
- return !( $.isFunction( callback ) &&
- callback.apply( this.element[0], [ event ].concat( data ) ) === false ||
- event.isDefaultPrevented() );
- }
-};
-
-$.each( { show: "fadeIn", hide: "fadeOut" }, function( method, defaultEffect ) {
- $.Widget.prototype[ "_" + method ] = function( element, options, callback ) {
- if ( typeof options === "string" ) {
- options = { effect: options };
- }
- var hasOptions,
- effectName = !options ?
- method :
- options === true || typeof options === "number" ?
- defaultEffect :
- options.effect || defaultEffect;
- options = options || {};
- if ( typeof options === "number" ) {
- options = { duration: options };
- }
- hasOptions = !$.isEmptyObject( options );
- options.complete = callback;
- if ( options.delay ) {
- element.delay( options.delay );
- }
- if ( hasOptions && $.effects && $.effects.effect[ effectName ] ) {
- element[ method ]( options );
- } else if ( effectName !== method && element[ effectName ] ) {
- element[ effectName ]( options.duration, options.easing, callback );
- } else {
- element.queue(function( next ) {
- $( this )[ method ]();
- if ( callback ) {
- callback.call( element[ 0 ] );
- }
- next();
- });
- }
- };
-});
-
-var widget = $.widget;
-
-
-/*!
- * jQuery UI Mouse 1.11.4
- * http://jqueryui.com
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- *
- * http://api.jqueryui.com/mouse/
- */
-
-
-var mouseHandled = false;
-$( document ).mouseup( function() {
- mouseHandled = false;
-});
-
-var mouse = $.widget("ui.mouse", {
- version: "1.11.4",
- options: {
- cancel: "input,textarea,button,select,option",
- distance: 1,
- delay: 0
- },
- _mouseInit: function() {
- var that = this;
-
- this.element
- .bind("mousedown." + this.widgetName, function(event) {
- return that._mouseDown(event);
- })
- .bind("click." + this.widgetName, function(event) {
- if (true === $.data(event.target, that.widgetName + ".preventClickEvent")) {
- $.removeData(event.target, that.widgetName + ".preventClickEvent");
- event.stopImmediatePropagation();
- return false;
- }
- });
-
- this.started = false;
- },
-
- // TODO: make sure destroying one instance of mouse doesn't mess with
- // other instances of mouse
- _mouseDestroy: function() {
- this.element.unbind("." + this.widgetName);
- if ( this._mouseMoveDelegate ) {
- this.document
- .unbind("mousemove." + this.widgetName, this._mouseMoveDelegate)
- .unbind("mouseup." + this.widgetName, this._mouseUpDelegate);
- }
- },
-
- _mouseDown: function(event) {
- // don't let more than one widget handle mouseStart
- if ( mouseHandled ) {
- return;
- }
-
- this._mouseMoved = false;
-
- // we may have missed mouseup (out of window)
- (this._mouseStarted && this._mouseUp(event));
-
- this._mouseDownEvent = event;
-
- var that = this,
- btnIsLeft = (event.which === 1),
- // event.target.nodeName works around a bug in IE 8 with
- // disabled inputs (#7620)
- elIsCancel = (typeof this.options.cancel === "string" && event.target.nodeName ? $(event.target).closest(this.options.cancel).length : false);
- if (!btnIsLeft || elIsCancel || !this._mouseCapture(event)) {
- return true;
- }
-
- this.mouseDelayMet = !this.options.delay;
- if (!this.mouseDelayMet) {
- this._mouseDelayTimer = setTimeout(function() {
- that.mouseDelayMet = true;
- }, this.options.delay);
- }
-
- if (this._mouseDistanceMet(event) && this._mouseDelayMet(event)) {
- this._mouseStarted = (this._mouseStart(event) !== false);
- if (!this._mouseStarted) {
- event.preventDefault();
- return true;
- }
- }
-
- // Click event may never have fired (Gecko & Opera)
- if (true === $.data(event.target, this.widgetName + ".preventClickEvent")) {
- $.removeData(event.target, this.widgetName + ".preventClickEvent");
- }
-
- // these delegates are required to keep context
- this._mouseMoveDelegate = function(event) {
- return that._mouseMove(event);
- };
- this._mouseUpDelegate = function(event) {
- return that._mouseUp(event);
- };
-
- this.document
- .bind( "mousemove." + this.widgetName, this._mouseMoveDelegate )
- .bind( "mouseup." + this.widgetName, this._mouseUpDelegate );
-
- event.preventDefault();
-
- mouseHandled = true;
- return true;
- },
-
- _mouseMove: function(event) {
- // Only check for mouseups outside the document if you've moved inside the document
- // at least once. This prevents the firing of mouseup in the case of IE<9, which will
- // fire a mousemove event if content is placed under the cursor. See #7778
- // Support: IE <9
- if ( this._mouseMoved ) {
- // IE mouseup check - mouseup happened when mouse was out of window
- if ($.ui.ie && ( !document.documentMode || document.documentMode < 9 ) && !event.button) {
- return this._mouseUp(event);
-
- // Iframe mouseup check - mouseup occurred in another document
- } else if ( !event.which ) {
- return this._mouseUp( event );
- }
- }
-
- if ( event.which || event.button ) {
- this._mouseMoved = true;
- }
-
- if (this._mouseStarted) {
- this._mouseDrag(event);
- return event.preventDefault();
- }
-
- if (this._mouseDistanceMet(event) && this._mouseDelayMet(event)) {
- this._mouseStarted =
- (this._mouseStart(this._mouseDownEvent, event) !== false);
- (this._mouseStarted ? this._mouseDrag(event) : this._mouseUp(event));
- }
-
- return !this._mouseStarted;
- },
-
- _mouseUp: function(event) {
- this.document
- .unbind( "mousemove." + this.widgetName, this._mouseMoveDelegate )
- .unbind( "mouseup." + this.widgetName, this._mouseUpDelegate );
-
- if (this._mouseStarted) {
- this._mouseStarted = false;
-
- if (event.target === this._mouseDownEvent.target) {
- $.data(event.target, this.widgetName + ".preventClickEvent", true);
- }
-
- this._mouseStop(event);
- }
-
- mouseHandled = false;
- return false;
- },
-
- _mouseDistanceMet: function(event) {
- return (Math.max(
- Math.abs(this._mouseDownEvent.pageX - event.pageX),
- Math.abs(this._mouseDownEvent.pageY - event.pageY)
- ) >= this.options.distance
- );
- },
-
- _mouseDelayMet: function(/* event */) {
- return this.mouseDelayMet;
- },
-
- // These are placeholder methods, to be overriden by extending plugin
- _mouseStart: function(/* event */) {},
- _mouseDrag: function(/* event */) {},
- _mouseStop: function(/* event */) {},
- _mouseCapture: function(/* event */) { return true; }
-});
-
-
-/*!
- * jQuery UI Position 1.11.4
- * http://jqueryui.com
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- *
- * http://api.jqueryui.com/position/
- */
-
-(function() {
-
-$.ui = $.ui || {};
-
-var cachedScrollbarWidth, supportsOffsetFractions,
- max = Math.max,
- abs = Math.abs,
- round = Math.round,
- rhorizontal = /left|center|right/,
- rvertical = /top|center|bottom/,
- roffset = /[\+\-]\d+(\.[\d]+)?%?/,
- rposition = /^\w+/,
- rpercent = /%$/,
- _position = $.fn.position;
-
-function getOffsets( offsets, width, height ) {
- return [
- parseFloat( offsets[ 0 ] ) * ( rpercent.test( offsets[ 0 ] ) ? width / 100 : 1 ),
- parseFloat( offsets[ 1 ] ) * ( rpercent.test( offsets[ 1 ] ) ? height / 100 : 1 )
- ];
-}
-
-function parseCss( element, property ) {
- return parseInt( $.css( element, property ), 10 ) || 0;
-}
-
-function getDimensions( elem ) {
- var raw = elem[0];
- if ( raw.nodeType === 9 ) {
- return {
- width: elem.width(),
- height: elem.height(),
- offset: { top: 0, left: 0 }
- };
- }
- if ( $.isWindow( raw ) ) {
- return {
- width: elem.width(),
- height: elem.height(),
- offset: { top: elem.scrollTop(), left: elem.scrollLeft() }
- };
- }
- if ( raw.preventDefault ) {
- return {
- width: 0,
- height: 0,
- offset: { top: raw.pageY, left: raw.pageX }
- };
- }
- return {
- width: elem.outerWidth(),
- height: elem.outerHeight(),
- offset: elem.offset()
- };
-}
-
-$.position = {
- scrollbarWidth: function() {
- if ( cachedScrollbarWidth !== undefined ) {
- return cachedScrollbarWidth;
- }
- var w1, w2,
- div = $( "<div style='display:block;position:absolute;width:50px;height:50px;overflow:hidden;'><div style='height:100px;width:auto;'></div></div>" ),
- innerDiv = div.children()[0];
-
- $( "body" ).append( div );
- w1 = innerDiv.offsetWidth;
- div.css( "overflow", "scroll" );
-
- w2 = innerDiv.offsetWidth;
-
- if ( w1 === w2 ) {
- w2 = div[0].clientWidth;
- }
-
- div.remove();
-
- return (cachedScrollbarWidth = w1 - w2);
- },
- getScrollInfo: function( within ) {
- var overflowX = within.isWindow || within.isDocument ? "" :
- within.element.css( "overflow-x" ),
- overflowY = within.isWindow || within.isDocument ? "" :
- within.element.css( "overflow-y" ),
- hasOverflowX = overflowX === "scroll" ||
- ( overflowX === "auto" && within.width < within.element[0].scrollWidth ),
- hasOverflowY = overflowY === "scroll" ||
- ( overflowY === "auto" && within.height < within.element[0].scrollHeight );
- return {
- width: hasOverflowY ? $.position.scrollbarWidth() : 0,
- height: hasOverflowX ? $.position.scrollbarWidth() : 0
- };
- },
- getWithinInfo: function( element ) {
- var withinElement = $( element || window ),
- isWindow = $.isWindow( withinElement[0] ),
- isDocument = !!withinElement[ 0 ] && withinElement[ 0 ].nodeType === 9;
- return {
- element: withinElement,
- isWindow: isWindow,
- isDocument: isDocument,
- offset: withinElement.offset() || { left: 0, top: 0 },
- scrollLeft: withinElement.scrollLeft(),
- scrollTop: withinElement.scrollTop(),
-
- // support: jQuery 1.6.x
- // jQuery 1.6 doesn't support .outerWidth/Height() on documents or windows
- width: isWindow || isDocument ? withinElement.width() : withinElement.outerWidth(),
- height: isWindow || isDocument ? withinElement.height() : withinElement.outerHeight()
- };
- }
-};
-
-$.fn.position = function( options ) {
- if ( !options || !options.of ) {
- return _position.apply( this, arguments );
- }
-
- // make a copy, we don't want to modify arguments
- options = $.extend( {}, options );
-
- var atOffset, targetWidth, targetHeight, targetOffset, basePosition, dimensions,
- target = $( options.of ),
- within = $.position.getWithinInfo( options.within ),
- scrollInfo = $.position.getScrollInfo( within ),
- collision = ( options.collision || "flip" ).split( " " ),
- offsets = {};
-
- dimensions = getDimensions( target );
- if ( target[0].preventDefault ) {
- // force left top to allow flipping
- options.at = "left top";
- }
- targetWidth = dimensions.width;
- targetHeight = dimensions.height;
- targetOffset = dimensions.offset;
- // clone to reuse original targetOffset later
- basePosition = $.extend( {}, targetOffset );
-
- // force my and at to have valid horizontal and vertical positions
- // if a value is missing or invalid, it will be converted to center
- $.each( [ "my", "at" ], function() {
- var pos = ( options[ this ] || "" ).split( " " ),
- horizontalOffset,
- verticalOffset;
-
- if ( pos.length === 1) {
- pos = rhorizontal.test( pos[ 0 ] ) ?
- pos.concat( [ "center" ] ) :
- rvertical.test( pos[ 0 ] ) ?
- [ "center" ].concat( pos ) :
- [ "center", "center" ];
- }
- pos[ 0 ] = rhorizontal.test( pos[ 0 ] ) ? pos[ 0 ] : "center";
- pos[ 1 ] = rvertical.test( pos[ 1 ] ) ? pos[ 1 ] : "center";
-
- // calculate offsets
- horizontalOffset = roffset.exec( pos[ 0 ] );
- verticalOffset = roffset.exec( pos[ 1 ] );
- offsets[ this ] = [
- horizontalOffset ? horizontalOffset[ 0 ] : 0,
- verticalOffset ? verticalOffset[ 0 ] : 0
- ];
-
- // reduce to just the positions without the offsets
- options[ this ] = [
- rposition.exec( pos[ 0 ] )[ 0 ],
- rposition.exec( pos[ 1 ] )[ 0 ]
- ];
- });
-
- // normalize collision option
- if ( collision.length === 1 ) {
- collision[ 1 ] = collision[ 0 ];
- }
-
- if ( options.at[ 0 ] === "right" ) {
- basePosition.left += targetWidth;
- } else if ( options.at[ 0 ] === "center" ) {
- basePosition.left += targetWidth / 2;
- }
-
- if ( options.at[ 1 ] === "bottom" ) {
- basePosition.top += targetHeight;
- } else if ( options.at[ 1 ] === "center" ) {
- basePosition.top += targetHeight / 2;
- }
-
- atOffset = getOffsets( offsets.at, targetWidth, targetHeight );
- basePosition.left += atOffset[ 0 ];
- basePosition.top += atOffset[ 1 ];
-
- return this.each(function() {
- var collisionPosition, using,
- elem = $( this ),
- elemWidth = elem.outerWidth(),
- elemHeight = elem.outerHeight(),
- marginLeft = parseCss( this, "marginLeft" ),
- marginTop = parseCss( this, "marginTop" ),
- collisionWidth = elemWidth + marginLeft + parseCss( this, "marginRight" ) + scrollInfo.width,
- collisionHeight = elemHeight + marginTop + parseCss( this, "marginBottom" ) + scrollInfo.height,
- position = $.extend( {}, basePosition ),
- myOffset = getOffsets( offsets.my, elem.outerWidth(), elem.outerHeight() );
-
- if ( options.my[ 0 ] === "right" ) {
- position.left -= elemWidth;
- } else if ( options.my[ 0 ] === "center" ) {
- position.left -= elemWidth / 2;
- }
-
- if ( options.my[ 1 ] === "bottom" ) {
- position.top -= elemHeight;
- } else if ( options.my[ 1 ] === "center" ) {
- position.top -= elemHeight / 2;
- }
-
- position.left += myOffset[ 0 ];
- position.top += myOffset[ 1 ];
-
- // if the browser doesn't support fractions, then round for consistent results
- if ( !supportsOffsetFractions ) {
- position.left = round( position.left );
- position.top = round( position.top );
- }
-
- collisionPosition = {
- marginLeft: marginLeft,
- marginTop: marginTop
- };
-
- $.each( [ "left", "top" ], function( i, dir ) {
- if ( $.ui.position[ collision[ i ] ] ) {
- $.ui.position[ collision[ i ] ][ dir ]( position, {
- targetWidth: targetWidth,
- targetHeight: targetHeight,
- elemWidth: elemWidth,
- elemHeight: elemHeight,
- collisionPosition: collisionPosition,
- collisionWidth: collisionWidth,
- collisionHeight: collisionHeight,
- offset: [ atOffset[ 0 ] + myOffset[ 0 ], atOffset [ 1 ] + myOffset[ 1 ] ],
- my: options.my,
- at: options.at,
- within: within,
- elem: elem
- });
- }
- });
-
- if ( options.using ) {
- // adds feedback as second argument to using callback, if present
- using = function( props ) {
- var left = targetOffset.left - position.left,
- right = left + targetWidth - elemWidth,
- top = targetOffset.top - position.top,
- bottom = top + targetHeight - elemHeight,
- feedback = {
- target: {
- element: target,
- left: targetOffset.left,
- top: targetOffset.top,
- width: targetWidth,
- height: targetHeight
- },
- element: {
- element: elem,
- left: position.left,
- top: position.top,
- width: elemWidth,
- height: elemHeight
- },
- horizontal: right < 0 ? "left" : left > 0 ? "right" : "center",
- vertical: bottom < 0 ? "top" : top > 0 ? "bottom" : "middle"
- };
- if ( targetWidth < elemWidth && abs( left + right ) < targetWidth ) {
- feedback.horizontal = "center";
- }
- if ( targetHeight < elemHeight && abs( top + bottom ) < targetHeight ) {
- feedback.vertical = "middle";
- }
- if ( max( abs( left ), abs( right ) ) > max( abs( top ), abs( bottom ) ) ) {
- feedback.important = "horizontal";
- } else {
- feedback.important = "vertical";
- }
- options.using.call( this, props, feedback );
- };
- }
-
- elem.offset( $.extend( position, { using: using } ) );
- });
-};
-
-$.ui.position = {
- fit: {
- left: function( position, data ) {
- var within = data.within,
- withinOffset = within.isWindow ? within.scrollLeft : within.offset.left,
- outerWidth = within.width,
- collisionPosLeft = position.left - data.collisionPosition.marginLeft,
- overLeft = withinOffset - collisionPosLeft,
- overRight = collisionPosLeft + data.collisionWidth - outerWidth - withinOffset,
- newOverRight;
-
- // element is wider than within
- if ( data.collisionWidth > outerWidth ) {
- // element is initially over the left side of within
- if ( overLeft > 0 && overRight <= 0 ) {
- newOverRight = position.left + overLeft + data.collisionWidth - outerWidth - withinOffset;
- position.left += overLeft - newOverRight;
- // element is initially over right side of within
- } else if ( overRight > 0 && overLeft <= 0 ) {
- position.left = withinOffset;
- // element is initially over both left and right sides of within
- } else {
- if ( overLeft > overRight ) {
- position.left = withinOffset + outerWidth - data.collisionWidth;
- } else {
- position.left = withinOffset;
- }
- }
- // too far left -> align with left edge
- } else if ( overLeft > 0 ) {
- position.left += overLeft;
- // too far right -> align with right edge
- } else if ( overRight > 0 ) {
- position.left -= overRight;
- // adjust based on position and margin
- } else {
- position.left = max( position.left - collisionPosLeft, position.left );
- }
- },
- top: function( position, data ) {
- var within = data.within,
- withinOffset = within.isWindow ? within.scrollTop : within.offset.top,
- outerHeight = data.within.height,
- collisionPosTop = position.top - data.collisionPosition.marginTop,
- overTop = withinOffset - collisionPosTop,
- overBottom = collisionPosTop + data.collisionHeight - outerHeight - withinOffset,
- newOverBottom;
-
- // element is taller than within
- if ( data.collisionHeight > outerHeight ) {
- // element is initially over the top of within
- if ( overTop > 0 && overBottom <= 0 ) {
- newOverBottom = position.top + overTop + data.collisionHeight - outerHeight - withinOffset;
- position.top += overTop - newOverBottom;
- // element is initially over bottom of within
- } else if ( overBottom > 0 && overTop <= 0 ) {
- position.top = withinOffset;
- // element is initially over both top and bottom of within
- } else {
- if ( overTop > overBottom ) {
- position.top = withinOffset + outerHeight - data.collisionHeight;
- } else {
- position.top = withinOffset;
- }
- }
- // too far up -> align with top
- } else if ( overTop > 0 ) {
- position.top += overTop;
- // too far down -> align with bottom edge
- } else if ( overBottom > 0 ) {
- position.top -= overBottom;
- // adjust based on position and margin
- } else {
- position.top = max( position.top - collisionPosTop, position.top );
- }
- }
- },
- flip: {
- left: function( position, data ) {
- var within = data.within,
- withinOffset = within.offset.left + within.scrollLeft,
- outerWidth = within.width,
- offsetLeft = within.isWindow ? within.scrollLeft : within.offset.left,
- collisionPosLeft = position.left - data.collisionPosition.marginLeft,
- overLeft = collisionPosLeft - offsetLeft,
- overRight = collisionPosLeft + data.collisionWidth - outerWidth - offsetLeft,
- myOffset = data.my[ 0 ] === "left" ?
- -data.elemWidth :
- data.my[ 0 ] === "right" ?
- data.elemWidth :
- 0,
- atOffset = data.at[ 0 ] === "left" ?
- data.targetWidth :
- data.at[ 0 ] === "right" ?
- -data.targetWidth :
- 0,
- offset = -2 * data.offset[ 0 ],
- newOverRight,
- newOverLeft;
-
- if ( overLeft < 0 ) {
- newOverRight = position.left + myOffset + atOffset + offset + data.collisionWidth - outerWidth - withinOffset;
- if ( newOverRight < 0 || newOverRight < abs( overLeft ) ) {
- position.left += myOffset + atOffset + offset;
- }
- } else if ( overRight > 0 ) {
- newOverLeft = position.left - data.collisionPosition.marginLeft + myOffset + atOffset + offset - offsetLeft;
- if ( newOverLeft > 0 || abs( newOverLeft ) < overRight ) {
- position.left += myOffset + atOffset + offset;
- }
- }
- },
- top: function( position, data ) {
- var within = data.within,
- withinOffset = within.offset.top + within.scrollTop,
- outerHeight = within.height,
- offsetTop = within.isWindow ? within.scrollTop : within.offset.top,
- collisionPosTop = position.top - data.collisionPosition.marginTop,
- overTop = collisionPosTop - offsetTop,
- overBottom = collisionPosTop + data.collisionHeight - outerHeight - offsetTop,
- top = data.my[ 1 ] === "top",
- myOffset = top ?
- -data.elemHeight :
- data.my[ 1 ] === "bottom" ?
- data.elemHeight :
- 0,
- atOffset = data.at[ 1 ] === "top" ?
- data.targetHeight :
- data.at[ 1 ] === "bottom" ?
- -data.targetHeight :
- 0,
- offset = -2 * data.offset[ 1 ],
- newOverTop,
- newOverBottom;
- if ( overTop < 0 ) {
- newOverBottom = position.top + myOffset + atOffset + offset + data.collisionHeight - outerHeight - withinOffset;
- if ( newOverBottom < 0 || newOverBottom < abs( overTop ) ) {
- position.top += myOffset + atOffset + offset;
- }
- } else if ( overBottom > 0 ) {
- newOverTop = position.top - data.collisionPosition.marginTop + myOffset + atOffset + offset - offsetTop;
- if ( newOverTop > 0 || abs( newOverTop ) < overBottom ) {
- position.top += myOffset + atOffset + offset;
- }
- }
- }
- },
- flipfit: {
- left: function() {
- $.ui.position.flip.left.apply( this, arguments );
- $.ui.position.fit.left.apply( this, arguments );
- },
- top: function() {
- $.ui.position.flip.top.apply( this, arguments );
- $.ui.position.fit.top.apply( this, arguments );
- }
- }
-};
-
-// fraction support test
-(function() {
- var testElement, testElementParent, testElementStyle, offsetLeft, i,
- body = document.getElementsByTagName( "body" )[ 0 ],
- div = document.createElement( "div" );
-
- //Create a "fake body" for testing based on method used in jQuery.support
- testElement = document.createElement( body ? "div" : "body" );
- testElementStyle = {
- visibility: "hidden",
- width: 0,
- height: 0,
- border: 0,
- margin: 0,
- background: "none"
- };
- if ( body ) {
- $.extend( testElementStyle, {
- position: "absolute",
- left: "-1000px",
- top: "-1000px"
- });
- }
- for ( i in testElementStyle ) {
- testElement.style[ i ] = testElementStyle[ i ];
- }
- testElement.appendChild( div );
- testElementParent = body || document.documentElement;
- testElementParent.insertBefore( testElement, testElementParent.firstChild );
-
- div.style.cssText = "position: absolute; left: 10.7432222px;";
-
- offsetLeft = $( div ).offset().left;
- supportsOffsetFractions = offsetLeft > 10 && offsetLeft < 11;
-
- testElement.innerHTML = "";
- testElementParent.removeChild( testElement );
-})();
-
-})();
-
-var position = $.ui.position;
-
-
-/*!
- * jQuery UI Draggable 1.11.4
- * http://jqueryui.com
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- *
- * http://api.jqueryui.com/draggable/
- */
-
-
-$.widget("ui.draggable", $.ui.mouse, {
- version: "1.11.4",
- widgetEventPrefix: "drag",
- options: {
- addClasses: true,
- appendTo: "parent",
- axis: false,
- connectToSortable: false,
- containment: false,
- cursor: "auto",
- cursorAt: false,
- grid: false,
- handle: false,
- helper: "original",
- iframeFix: false,
- opacity: false,
- refreshPositions: false,
- revert: false,
- revertDuration: 500,
- scope: "default",
- scroll: true,
- scrollSensitivity: 20,
- scrollSpeed: 20,
- snap: false,
- snapMode: "both",
- snapTolerance: 20,
- stack: false,
- zIndex: false,
-
- // callbacks
- drag: null,
- start: null,
- stop: null
- },
- _create: function() {
-
- if ( this.options.helper === "original" ) {
- this._setPositionRelative();
- }
- if (this.options.addClasses){
- this.element.addClass("ui-draggable");
- }
- if (this.options.disabled){
- this.element.addClass("ui-draggable-disabled");
- }
- this._setHandleClassName();
-
- this._mouseInit();
- },
-
- _setOption: function( key, value ) {
- this._super( key, value );
- if ( key === "handle" ) {
- this._removeHandleClassName();
- this._setHandleClassName();
- }
- },
-
- _destroy: function() {
- if ( ( this.helper || this.element ).is( ".ui-draggable-dragging" ) ) {
- this.destroyOnClear = true;
- return;
- }
- this.element.removeClass( "ui-draggable ui-draggable-dragging ui-draggable-disabled" );
- this._removeHandleClassName();
- this._mouseDestroy();
- },
-
- _mouseCapture: function(event) {
- var o = this.options;
-
- this._blurActiveElement( event );
-
- // among others, prevent a drag on a resizable-handle
- if (this.helper || o.disabled || $(event.target).closest(".ui-resizable-handle").length > 0) {
- return false;
- }
-
- //Quit if we're not on a valid handle
- this.handle = this._getHandle(event);
- if (!this.handle) {
- return false;
- }
-
- this._blockFrames( o.iframeFix === true ? "iframe" : o.iframeFix );
-
- return true;
-
- },
-
- _blockFrames: function( selector ) {
- this.iframeBlocks = this.document.find( selector ).map(function() {
- var iframe = $( this );
-
- return $( "<div>" )
- .css( "position", "absolute" )
- .appendTo( iframe.parent() )
- .outerWidth( iframe.outerWidth() )
- .outerHeight( iframe.outerHeight() )
- .offset( iframe.offset() )[ 0 ];
- });
- },
-
- _unblockFrames: function() {
- if ( this.iframeBlocks ) {
- this.iframeBlocks.remove();
- delete this.iframeBlocks;
- }
- },
-
- _blurActiveElement: function( event ) {
- var document = this.document[ 0 ];
-
- // Only need to blur if the event occurred on the draggable itself, see #10527
- if ( !this.handleElement.is( event.target ) ) {
- return;
- }
-
- // support: IE9
- // IE9 throws an "Unspecified error" accessing document.activeElement from an <iframe>
- try {
-
- // Support: IE9, IE10
- // If the <body> is blurred, IE will switch windows, see #9520
- if ( document.activeElement && document.activeElement.nodeName.toLowerCase() !== "body" ) {
-
- // Blur any element that currently has focus, see #4261
- $( document.activeElement ).blur();
- }
- } catch ( error ) {}
- },
-
- _mouseStart: function(event) {
-
- var o = this.options;
-
- //Create and append the visible helper
- this.helper = this._createHelper(event);
-
- this.helper.addClass("ui-draggable-dragging");
-
- //Cache the helper size
- this._cacheHelperProportions();
-
- //If ddmanager is used for droppables, set the global draggable
- if ($.ui.ddmanager) {
- $.ui.ddmanager.current = this;
- }
-
- /*
- * - Position generation -
- * This block generates everything position related - it's the core of draggables.
- */
-
- //Cache the margins of the original element
- this._cacheMargins();
-
- //Store the helper's css position
- this.cssPosition = this.helper.css( "position" );
- this.scrollParent = this.helper.scrollParent( true );
- this.offsetParent = this.helper.offsetParent();
- this.hasFixedAncestor = this.helper.parents().filter(function() {
- return $( this ).css( "position" ) === "fixed";
- }).length > 0;
-
- //The element's absolute position on the page minus margins
- this.positionAbs = this.element.offset();
- this._refreshOffsets( event );
-
- //Generate the original position
- this.originalPosition = this.position = this._generatePosition( event, false );
- this.originalPageX = event.pageX;
- this.originalPageY = event.pageY;
-
- //Adjust the mouse offset relative to the helper if "cursorAt" is supplied
- (o.cursorAt && this._adjustOffsetFromHelper(o.cursorAt));
-
- //Set a containment if given in the options
- this._setContainment();
-
- //Trigger event + callbacks
- if (this._trigger("start", event) === false) {
- this._clear();
- return false;
- }
-
- //Recache the helper size
- this._cacheHelperProportions();
-
- //Prepare the droppable offsets
- if ($.ui.ddmanager && !o.dropBehaviour) {
- $.ui.ddmanager.prepareOffsets(this, event);
- }
-
- // Reset helper's right/bottom css if they're set and set explicit width/height instead
- // as this prevents resizing of elements with right/bottom set (see #7772)
- this._normalizeRightBottom();
-
- this._mouseDrag(event, true); //Execute the drag once - this causes the helper not to be visible before getting its correct position
-
- //If the ddmanager is used for droppables, inform the manager that dragging has started (see #5003)
- if ( $.ui.ddmanager ) {
- $.ui.ddmanager.dragStart(this, event);
- }
-
- return true;
- },
-
- _refreshOffsets: function( event ) {
- this.offset = {
- top: this.positionAbs.top - this.margins.top,
- left: this.positionAbs.left - this.margins.left,
- scroll: false,
- parent: this._getParentOffset(),
- relative: this._getRelativeOffset()
- };
-
- this.offset.click = {
- left: event.pageX - this.offset.left,
- top: event.pageY - this.offset.top
- };
- },
-
- _mouseDrag: function(event, noPropagation) {
- // reset any necessary cached properties (see #5009)
- if ( this.hasFixedAncestor ) {
- this.offset.parent = this._getParentOffset();
- }
-
- //Compute the helpers position
- this.position = this._generatePosition( event, true );
- this.positionAbs = this._convertPositionTo("absolute");
-
- //Call plugins and callbacks and use the resulting position if something is returned
- if (!noPropagation) {
- var ui = this._uiHash();
- if (this._trigger("drag", event, ui) === false) {
- this._mouseUp({});
- return false;
- }
- this.position = ui.position;
- }
-
- this.helper[ 0 ].style.left = this.position.left + "px";
- this.helper[ 0 ].style.top = this.position.top + "px";
-
- if ($.ui.ddmanager) {
- $.ui.ddmanager.drag(this, event);
- }
-
- return false;
- },
-
- _mouseStop: function(event) {
-
- //If we are using droppables, inform the manager about the drop
- var that = this,
- dropped = false;
- if ($.ui.ddmanager && !this.options.dropBehaviour) {
- dropped = $.ui.ddmanager.drop(this, event);
- }
-
- //if a drop comes from outside (a sortable)
- if (this.dropped) {
- dropped = this.dropped;
- this.dropped = false;
- }
-
- if ((this.options.revert === "invalid" && !dropped) || (this.options.revert === "valid" && dropped) || this.options.revert === true || ($.isFunction(this.options.revert) && this.options.revert.call(this.element, dropped))) {
- $(this.helper).animate(this.originalPosition, parseInt(this.options.revertDuration, 10), function() {
- if (that._trigger("stop", event) !== false) {
- that._clear();
- }
- });
- } else {
- if (this._trigger("stop", event) !== false) {
- this._clear();
- }
- }
-
- return false;
- },
-
- _mouseUp: function( event ) {
- this._unblockFrames();
-
- //If the ddmanager is used for droppables, inform the manager that dragging has stopped (see #5003)
- if ( $.ui.ddmanager ) {
- $.ui.ddmanager.dragStop(this, event);
- }
-
- // Only need to focus if the event occurred on the draggable itself, see #10527
- if ( this.handleElement.is( event.target ) ) {
- // The interaction is over; whether or not the click resulted in a drag, focus the element
- this.element.focus();
- }
-
- return $.ui.mouse.prototype._mouseUp.call(this, event);
- },
-
- cancel: function() {
-
- if (this.helper.is(".ui-draggable-dragging")) {
- this._mouseUp({});
- } else {
- this._clear();
- }
-
- return this;
-
- },
-
- _getHandle: function(event) {
- return this.options.handle ?
- !!$( event.target ).closest( this.element.find( this.options.handle ) ).length :
- true;
- },
-
- _setHandleClassName: function() {
- this.handleElement = this.options.handle ?
- this.element.find( this.options.handle ) : this.element;
- this.handleElement.addClass( "ui-draggable-handle" );
- },
-
- _removeHandleClassName: function() {
- this.handleElement.removeClass( "ui-draggable-handle" );
- },
-
- _createHelper: function(event) {
-
- var o = this.options,
- helperIsFunction = $.isFunction( o.helper ),
- helper = helperIsFunction ?
- $( o.helper.apply( this.element[ 0 ], [ event ] ) ) :
- ( o.helper === "clone" ?
- this.element.clone().removeAttr( "id" ) :
- this.element );
-
- if (!helper.parents("body").length) {
- helper.appendTo((o.appendTo === "parent" ? this.element[0].parentNode : o.appendTo));
- }
-
- // http://bugs.jqueryui.com/ticket/9446
- // a helper function can return the original element
- // which wouldn't have been set to relative in _create
- if ( helperIsFunction && helper[ 0 ] === this.element[ 0 ] ) {
- this._setPositionRelative();
- }
-
- if (helper[0] !== this.element[0] && !(/(fixed|absolute)/).test(helper.css("position"))) {
- helper.css("position", "absolute");
- }
-
- return helper;
-
- },
-
- _setPositionRelative: function() {
- if ( !( /^(?:r|a|f)/ ).test( this.element.css( "position" ) ) ) {
- this.element[ 0 ].style.position = "relative";
- }
- },
-
- _adjustOffsetFromHelper: function(obj) {
- if (typeof obj === "string") {
- obj = obj.split(" ");
- }
- if ($.isArray(obj)) {
- obj = { left: +obj[0], top: +obj[1] || 0 };
- }
- if ("left" in obj) {
- this.offset.click.left = obj.left + this.margins.left;
- }
- if ("right" in obj) {
- this.offset.click.left = this.helperProportions.width - obj.right + this.margins.left;
- }
- if ("top" in obj) {
- this.offset.click.top = obj.top + this.margins.top;
- }
- if ("bottom" in obj) {
- this.offset.click.top = this.helperProportions.height - obj.bottom + this.margins.top;
- }
- },
-
- _isRootNode: function( element ) {
- return ( /(html|body)/i ).test( element.tagName ) || element === this.document[ 0 ];
- },
-
- _getParentOffset: function() {
-
- //Get the offsetParent and cache its position
- var po = this.offsetParent.offset(),
- document = this.document[ 0 ];
-
- // This is a special case where we need to modify a offset calculated on start, since the following happened:
- // 1. The position of the helper is absolute, so it's position is calculated based on the next positioned parent
- // 2. The actual offset parent is a child of the scroll parent, and the scroll parent isn't the document, which means that
- // the scroll is included in the initial calculation of the offset of the parent, and never recalculated upon drag
- if (this.cssPosition === "absolute" && this.scrollParent[0] !== document && $.contains(this.scrollParent[0], this.offsetParent[0])) {
- po.left += this.scrollParent.scrollLeft();
- po.top += this.scrollParent.scrollTop();
- }
-
- if ( this._isRootNode( this.offsetParent[ 0 ] ) ) {
- po = { top: 0, left: 0 };
- }
-
- return {
- top: po.top + (parseInt(this.offsetParent.css("borderTopWidth"), 10) || 0),
- left: po.left + (parseInt(this.offsetParent.css("borderLeftWidth"), 10) || 0)
- };
-
- },
-
- _getRelativeOffset: function() {
- if ( this.cssPosition !== "relative" ) {
- return { top: 0, left: 0 };
- }
-
- var p = this.element.position(),
- scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] );
-
- return {
- top: p.top - ( parseInt(this.helper.css( "top" ), 10) || 0 ) + ( !scrollIsRootNode ? this.scrollParent.scrollTop() : 0 ),
- left: p.left - ( parseInt(this.helper.css( "left" ), 10) || 0 ) + ( !scrollIsRootNode ? this.scrollParent.scrollLeft() : 0 )
- };
-
- },
-
- _cacheMargins: function() {
- this.margins = {
- left: (parseInt(this.element.css("marginLeft"), 10) || 0),
- top: (parseInt(this.element.css("marginTop"), 10) || 0),
- right: (parseInt(this.element.css("marginRight"), 10) || 0),
- bottom: (parseInt(this.element.css("marginBottom"), 10) || 0)
- };
- },
-
- _cacheHelperProportions: function() {
- this.helperProportions = {
- width: this.helper.outerWidth(),
- height: this.helper.outerHeight()
- };
- },
-
- _setContainment: function() {
-
- var isUserScrollable, c, ce,
- o = this.options,
- document = this.document[ 0 ];
-
- this.relativeContainer = null;
-
- if ( !o.containment ) {
- this.containment = null;
- return;
- }
-
- if ( o.containment === "window" ) {
- this.containment = [
- $( window ).scrollLeft() - this.offset.relative.left - this.offset.parent.left,
- $( window ).scrollTop() - this.offset.relative.top - this.offset.parent.top,
- $( window ).scrollLeft() + $( window ).width() - this.helperProportions.width - this.margins.left,
- $( window ).scrollTop() + ( $( window ).height() || document.body.parentNode.scrollHeight ) - this.helperProportions.height - this.margins.top
- ];
- return;
- }
-
- if ( o.containment === "document") {
- this.containment = [
- 0,
- 0,
- $( document ).width() - this.helperProportions.width - this.margins.left,
- ( $( document ).height() || document.body.parentNode.scrollHeight ) - this.helperProportions.height - this.margins.top
- ];
- return;
- }
-
- if ( o.containment.constructor === Array ) {
- this.containment = o.containment;
- return;
- }
-
- if ( o.containment === "parent" ) {
- o.containment = this.helper[ 0 ].parentNode;
- }
-
- c = $( o.containment );
- ce = c[ 0 ];
-
- if ( !ce ) {
- return;
- }
-
- isUserScrollable = /(scroll|auto)/.test( c.css( "overflow" ) );
-
- this.containment = [
- ( parseInt( c.css( "borderLeftWidth" ), 10 ) || 0 ) + ( parseInt( c.css( "paddingLeft" ), 10 ) || 0 ),
- ( parseInt( c.css( "borderTopWidth" ), 10 ) || 0 ) + ( parseInt( c.css( "paddingTop" ), 10 ) || 0 ),
- ( isUserScrollable ? Math.max( ce.scrollWidth, ce.offsetWidth ) : ce.offsetWidth ) -
- ( parseInt( c.css( "borderRightWidth" ), 10 ) || 0 ) -
- ( parseInt( c.css( "paddingRight" ), 10 ) || 0 ) -
- this.helperProportions.width -
- this.margins.left -
- this.margins.right,
- ( isUserScrollable ? Math.max( ce.scrollHeight, ce.offsetHeight ) : ce.offsetHeight ) -
- ( parseInt( c.css( "borderBottomWidth" ), 10 ) || 0 ) -
- ( parseInt( c.css( "paddingBottom" ), 10 ) || 0 ) -
- this.helperProportions.height -
- this.margins.top -
- this.margins.bottom
- ];
- this.relativeContainer = c;
- },
-
- _convertPositionTo: function(d, pos) {
-
- if (!pos) {
- pos = this.position;
- }
-
- var mod = d === "absolute" ? 1 : -1,
- scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] );
-
- return {
- top: (
- pos.top + // The absolute mouse position
- this.offset.relative.top * mod + // Only for relative positioned nodes: Relative offset from element to offset parent
- this.offset.parent.top * mod - // The offsetParent's offset without borders (offset + border)
- ( ( this.cssPosition === "fixed" ? -this.offset.scroll.top : ( scrollIsRootNode ? 0 : this.offset.scroll.top ) ) * mod)
- ),
- left: (
- pos.left + // The absolute mouse position
- this.offset.relative.left * mod + // Only for relative positioned nodes: Relative offset from element to offset parent
- this.offset.parent.left * mod - // The offsetParent's offset without borders (offset + border)
- ( ( this.cssPosition === "fixed" ? -this.offset.scroll.left : ( scrollIsRootNode ? 0 : this.offset.scroll.left ) ) * mod)
- )
- };
-
- },
-
- _generatePosition: function( event, constrainPosition ) {
-
- var containment, co, top, left,
- o = this.options,
- scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] ),
- pageX = event.pageX,
- pageY = event.pageY;
-
- // Cache the scroll
- if ( !scrollIsRootNode || !this.offset.scroll ) {
- this.offset.scroll = {
- top: this.scrollParent.scrollTop(),
- left: this.scrollParent.scrollLeft()
- };
- }
-
- /*
- * - Position constraining -
- * Constrain the position to a mix of grid, containment.
- */
-
- // If we are not dragging yet, we won't check for options
- if ( constrainPosition ) {
- if ( this.containment ) {
- if ( this.relativeContainer ){
- co = this.relativeContainer.offset();
- containment = [
- this.containment[ 0 ] + co.left,
- this.containment[ 1 ] + co.top,
- this.containment[ 2 ] + co.left,
- this.containment[ 3 ] + co.top
- ];
- } else {
- containment = this.containment;
- }
-
- if (event.pageX - this.offset.click.left < containment[0]) {
- pageX = containment[0] + this.offset.click.left;
- }
- if (event.pageY - this.offset.click.top < containment[1]) {
- pageY = containment[1] + this.offset.click.top;
- }
- if (event.pageX - this.offset.click.left > containment[2]) {
- pageX = containment[2] + this.offset.click.left;
- }
- if (event.pageY - this.offset.click.top > containment[3]) {
- pageY = containment[3] + this.offset.click.top;
- }
- }
-
- if (o.grid) {
- //Check for grid elements set to 0 to prevent divide by 0 error causing invalid argument errors in IE (see ticket #6950)
- top = o.grid[1] ? this.originalPageY + Math.round((pageY - this.originalPageY) / o.grid[1]) * o.grid[1] : this.originalPageY;
- pageY = containment ? ((top - this.offset.click.top >= containment[1] || top - this.offset.click.top > containment[3]) ? top : ((top - this.offset.click.top >= containment[1]) ? top - o.grid[1] : top + o.grid[1])) : top;
-
- left = o.grid[0] ? this.originalPageX + Math.round((pageX - this.originalPageX) / o.grid[0]) * o.grid[0] : this.originalPageX;
- pageX = containment ? ((left - this.offset.click.left >= containment[0] || left - this.offset.click.left > containment[2]) ? left : ((left - this.offset.click.left >= containment[0]) ? left - o.grid[0] : left + o.grid[0])) : left;
- }
-
- if ( o.axis === "y" ) {
- pageX = this.originalPageX;
- }
-
- if ( o.axis === "x" ) {
- pageY = this.originalPageY;
- }
- }
-
- return {
- top: (
- pageY - // The absolute mouse position
- this.offset.click.top - // Click offset (relative to the element)
- this.offset.relative.top - // Only for relative positioned nodes: Relative offset from element to offset parent
- this.offset.parent.top + // The offsetParent's offset without borders (offset + border)
- ( this.cssPosition === "fixed" ? -this.offset.scroll.top : ( scrollIsRootNode ? 0 : this.offset.scroll.top ) )
- ),
- left: (
- pageX - // The absolute mouse position
- this.offset.click.left - // Click offset (relative to the element)
- this.offset.relative.left - // Only for relative positioned nodes: Relative offset from element to offset parent
- this.offset.parent.left + // The offsetParent's offset without borders (offset + border)
- ( this.cssPosition === "fixed" ? -this.offset.scroll.left : ( scrollIsRootNode ? 0 : this.offset.scroll.left ) )
- )
- };
-
- },
-
- _clear: function() {
- this.helper.removeClass("ui-draggable-dragging");
- if (this.helper[0] !== this.element[0] && !this.cancelHelperRemoval) {
- this.helper.remove();
- }
- this.helper = null;
- this.cancelHelperRemoval = false;
- if ( this.destroyOnClear ) {
- this.destroy();
- }
- },
-
- _normalizeRightBottom: function() {
- if ( this.options.axis !== "y" && this.helper.css( "right" ) !== "auto" ) {
- this.helper.width( this.helper.width() );
- this.helper.css( "right", "auto" );
- }
- if ( this.options.axis !== "x" && this.helper.css( "bottom" ) !== "auto" ) {
- this.helper.height( this.helper.height() );
- this.helper.css( "bottom", "auto" );
- }
- },
-
- // From now on bulk stuff - mainly helpers
-
- _trigger: function( type, event, ui ) {
- ui = ui || this._uiHash();
- $.ui.plugin.call( this, type, [ event, ui, this ], true );
-
- // Absolute position and offset (see #6884 ) have to be recalculated after plugins
- if ( /^(drag|start|stop)/.test( type ) ) {
- this.positionAbs = this._convertPositionTo( "absolute" );
- ui.offset = this.positionAbs;
- }
- return $.Widget.prototype._trigger.call( this, type, event, ui );
- },
-
- plugins: {},
-
- _uiHash: function() {
- return {
- helper: this.helper,
- position: this.position,
- originalPosition: this.originalPosition,
- offset: this.positionAbs
- };
- }
-
-});
-
-$.ui.plugin.add( "draggable", "connectToSortable", {
- start: function( event, ui, draggable ) {
- var uiSortable = $.extend( {}, ui, {
- item: draggable.element
- });
-
- draggable.sortables = [];
- $( draggable.options.connectToSortable ).each(function() {
- var sortable = $( this ).sortable( "instance" );
-
- if ( sortable && !sortable.options.disabled ) {
- draggable.sortables.push( sortable );
-
- // refreshPositions is called at drag start to refresh the containerCache
- // which is used in drag. This ensures it's initialized and synchronized
- // with any changes that might have happened on the page since initialization.
- sortable.refreshPositions();
- sortable._trigger("activate", event, uiSortable);
- }
- });
- },
- stop: function( event, ui, draggable ) {
- var uiSortable = $.extend( {}, ui, {
- item: draggable.element
- });
-
- draggable.cancelHelperRemoval = false;
-
- $.each( draggable.sortables, function() {
- var sortable = this;
-
- if ( sortable.isOver ) {
- sortable.isOver = 0;
-
- // Allow this sortable to handle removing the helper
- draggable.cancelHelperRemoval = true;
- sortable.cancelHelperRemoval = false;
-
- // Use _storedCSS To restore properties in the sortable,
- // as this also handles revert (#9675) since the draggable
- // may have modified them in unexpected ways (#8809)
- sortable._storedCSS = {
- position: sortable.placeholder.css( "position" ),
- top: sortable.placeholder.css( "top" ),
- left: sortable.placeholder.css( "left" )
- };
-
- sortable._mouseStop(event);
-
- // Once drag has ended, the sortable should return to using
- // its original helper, not the shared helper from draggable
- sortable.options.helper = sortable.options._helper;
- } else {
- // Prevent this Sortable from removing the helper.
- // However, don't set the draggable to remove the helper
- // either as another connected Sortable may yet handle the removal.
- sortable.cancelHelperRemoval = true;
-
- sortable._trigger( "deactivate", event, uiSortable );
- }
- });
- },
- drag: function( event, ui, draggable ) {
- $.each( draggable.sortables, function() {
- var innermostIntersecting = false,
- sortable = this;
-
- // Copy over variables that sortable's _intersectsWith uses
- sortable.positionAbs = draggable.positionAbs;
- sortable.helperProportions = draggable.helperProportions;
- sortable.offset.click = draggable.offset.click;
-
- if ( sortable._intersectsWith( sortable.containerCache ) ) {
- innermostIntersecting = true;
-
- $.each( draggable.sortables, function() {
- // Copy over variables that sortable's _intersectsWith uses
- this.positionAbs = draggable.positionAbs;
- this.helperProportions = draggable.helperProportions;
- this.offset.click = draggable.offset.click;
-
- if ( this !== sortable &&
- this._intersectsWith( this.containerCache ) &&
- $.contains( sortable.element[ 0 ], this.element[ 0 ] ) ) {
- innermostIntersecting = false;
- }
-
- return innermostIntersecting;
- });
- }
-
- if ( innermostIntersecting ) {
- // If it intersects, we use a little isOver variable and set it once,
- // so that the move-in stuff gets fired only once.
- if ( !sortable.isOver ) {
- sortable.isOver = 1;
-
- // Store draggable's parent in case we need to reappend to it later.
- draggable._parent = ui.helper.parent();
-
- sortable.currentItem = ui.helper
- .appendTo( sortable.element )
- .data( "ui-sortable-item", true );
-
- // Store helper option to later restore it
- sortable.options._helper = sortable.options.helper;
-
- sortable.options.helper = function() {
- return ui.helper[ 0 ];
- };
-
- // Fire the start events of the sortable with our passed browser event,
- // and our own helper (so it doesn't create a new one)
- event.target = sortable.currentItem[ 0 ];
- sortable._mouseCapture( event, true );
- sortable._mouseStart( event, true, true );
-
- // Because the browser event is way off the new appended portlet,
- // modify necessary variables to reflect the changes
- sortable.offset.click.top = draggable.offset.click.top;
- sortable.offset.click.left = draggable.offset.click.left;
- sortable.offset.parent.left -= draggable.offset.parent.left -
- sortable.offset.parent.left;
- sortable.offset.parent.top -= draggable.offset.parent.top -
- sortable.offset.parent.top;
-
- draggable._trigger( "toSortable", event );
-
- // Inform draggable that the helper is in a valid drop zone,
- // used solely in the revert option to handle "valid/invalid".
- draggable.dropped = sortable.element;
-
- // Need to refreshPositions of all sortables in the case that
- // adding to one sortable changes the location of the other sortables (#9675)
- $.each( draggable.sortables, function() {
- this.refreshPositions();
- });
-
- // hack so receive/update callbacks work (mostly)
- draggable.currentItem = draggable.element;
- sortable.fromOutside = draggable;
- }
-
- if ( sortable.currentItem ) {
- sortable._mouseDrag( event );
- // Copy the sortable's position because the draggable's can potentially reflect
- // a relative position, while sortable is always absolute, which the dragged
- // element has now become. (#8809)
- ui.position = sortable.position;
- }
- } else {
- // If it doesn't intersect with the sortable, and it intersected before,
- // we fake the drag stop of the sortable, but make sure it doesn't remove
- // the helper by using cancelHelperRemoval.
- if ( sortable.isOver ) {
-
- sortable.isOver = 0;
- sortable.cancelHelperRemoval = true;
-
- // Calling sortable's mouseStop would trigger a revert,
- // so revert must be temporarily false until after mouseStop is called.
- sortable.options._revert = sortable.options.revert;
- sortable.options.revert = false;
-
- sortable._trigger( "out", event, sortable._uiHash( sortable ) );
- sortable._mouseStop( event, true );
-
- // restore sortable behaviors that were modfied
- // when the draggable entered the sortable area (#9481)
- sortable.options.revert = sortable.options._revert;
- sortable.options.helper = sortable.options._helper;
-
- if ( sortable.placeholder ) {
- sortable.placeholder.remove();
- }
-
- // Restore and recalculate the draggable's offset considering the sortable
- // may have modified them in unexpected ways. (#8809, #10669)
- ui.helper.appendTo( draggable._parent );
- draggable._refreshOffsets( event );
- ui.position = draggable._generatePosition( event, true );
-
- draggable._trigger( "fromSortable", event );
-
- // Inform draggable that the helper is no longer in a valid drop zone
- draggable.dropped = false;
-
- // Need to refreshPositions of all sortables just in case removing
- // from one sortable changes the location of other sortables (#9675)
- $.each( draggable.sortables, function() {
- this.refreshPositions();
- });
- }
- }
- });
- }
-});
-
-$.ui.plugin.add("draggable", "cursor", {
- start: function( event, ui, instance ) {
- var t = $( "body" ),
- o = instance.options;
-
- if (t.css("cursor")) {
- o._cursor = t.css("cursor");
- }
- t.css("cursor", o.cursor);
- },
- stop: function( event, ui, instance ) {
- var o = instance.options;
- if (o._cursor) {
- $("body").css("cursor", o._cursor);
- }
- }
-});
-
-$.ui.plugin.add("draggable", "opacity", {
- start: function( event, ui, instance ) {
- var t = $( ui.helper ),
- o = instance.options;
- if (t.css("opacity")) {
- o._opacity = t.css("opacity");
- }
- t.css("opacity", o.opacity);
- },
- stop: function( event, ui, instance ) {
- var o = instance.options;
- if (o._opacity) {
- $(ui.helper).css("opacity", o._opacity);
- }
- }
-});
-
-$.ui.plugin.add("draggable", "scroll", {
- start: function( event, ui, i ) {
- if ( !i.scrollParentNotHidden ) {
- i.scrollParentNotHidden = i.helper.scrollParent( false );
- }
-
- if ( i.scrollParentNotHidden[ 0 ] !== i.document[ 0 ] && i.scrollParentNotHidden[ 0 ].tagName !== "HTML" ) {
- i.overflowOffset = i.scrollParentNotHidden.offset();
- }
- },
- drag: function( event, ui, i ) {
-
- var o = i.options,
- scrolled = false,
- scrollParent = i.scrollParentNotHidden[ 0 ],
- document = i.document[ 0 ];
-
- if ( scrollParent !== document && scrollParent.tagName !== "HTML" ) {
- if ( !o.axis || o.axis !== "x" ) {
- if ( ( i.overflowOffset.top + scrollParent.offsetHeight ) - event.pageY < o.scrollSensitivity ) {
- scrollParent.scrollTop = scrolled = scrollParent.scrollTop + o.scrollSpeed;
- } else if ( event.pageY - i.overflowOffset.top < o.scrollSensitivity ) {
- scrollParent.scrollTop = scrolled = scrollParent.scrollTop - o.scrollSpeed;
- }
- }
-
- if ( !o.axis || o.axis !== "y" ) {
- if ( ( i.overflowOffset.left + scrollParent.offsetWidth ) - event.pageX < o.scrollSensitivity ) {
- scrollParent.scrollLeft = scrolled = scrollParent.scrollLeft + o.scrollSpeed;
- } else if ( event.pageX - i.overflowOffset.left < o.scrollSensitivity ) {
- scrollParent.scrollLeft = scrolled = scrollParent.scrollLeft - o.scrollSpeed;
- }
- }
-
- } else {
-
- if (!o.axis || o.axis !== "x") {
- if (event.pageY - $(document).scrollTop() < o.scrollSensitivity) {
- scrolled = $(document).scrollTop($(document).scrollTop() - o.scrollSpeed);
- } else if ($(window).height() - (event.pageY - $(document).scrollTop()) < o.scrollSensitivity) {
- scrolled = $(document).scrollTop($(document).scrollTop() + o.scrollSpeed);
- }
- }
-
- if (!o.axis || o.axis !== "y") {
- if (event.pageX - $(document).scrollLeft() < o.scrollSensitivity) {
- scrolled = $(document).scrollLeft($(document).scrollLeft() - o.scrollSpeed);
- } else if ($(window).width() - (event.pageX - $(document).scrollLeft()) < o.scrollSensitivity) {
- scrolled = $(document).scrollLeft($(document).scrollLeft() + o.scrollSpeed);
- }
- }
-
- }
-
- if (scrolled !== false && $.ui.ddmanager && !o.dropBehaviour) {
- $.ui.ddmanager.prepareOffsets(i, event);
- }
-
- }
-});
-
-$.ui.plugin.add("draggable", "snap", {
- start: function( event, ui, i ) {
-
- var o = i.options;
-
- i.snapElements = [];
-
- $(o.snap.constructor !== String ? ( o.snap.items || ":data(ui-draggable)" ) : o.snap).each(function() {
- var $t = $(this),
- $o = $t.offset();
- if (this !== i.element[0]) {
- i.snapElements.push({
- item: this,
- width: $t.outerWidth(), height: $t.outerHeight(),
- top: $o.top, left: $o.left
- });
- }
- });
-
- },
- drag: function( event, ui, inst ) {
-
- var ts, bs, ls, rs, l, r, t, b, i, first,
- o = inst.options,
- d = o.snapTolerance,
- x1 = ui.offset.left, x2 = x1 + inst.helperProportions.width,
- y1 = ui.offset.top, y2 = y1 + inst.helperProportions.height;
-
- for (i = inst.snapElements.length - 1; i >= 0; i--){
-
- l = inst.snapElements[i].left - inst.margins.left;
- r = l + inst.snapElements[i].width;
- t = inst.snapElements[i].top - inst.margins.top;
- b = t + inst.snapElements[i].height;
-
- if ( x2 < l - d || x1 > r + d || y2 < t - d || y1 > b + d || !$.contains( inst.snapElements[ i ].item.ownerDocument, inst.snapElements[ i ].item ) ) {
- if (inst.snapElements[i].snapping) {
- (inst.options.snap.release && inst.options.snap.release.call(inst.element, event, $.extend(inst._uiHash(), { snapItem: inst.snapElements[i].item })));
- }
- inst.snapElements[i].snapping = false;
- continue;
- }
-
- if (o.snapMode !== "inner") {
- ts = Math.abs(t - y2) <= d;
- bs = Math.abs(b - y1) <= d;
- ls = Math.abs(l - x2) <= d;
- rs = Math.abs(r - x1) <= d;
- if (ts) {
- ui.position.top = inst._convertPositionTo("relative", { top: t - inst.helperProportions.height, left: 0 }).top;
- }
- if (bs) {
- ui.position.top = inst._convertPositionTo("relative", { top: b, left: 0 }).top;
- }
- if (ls) {
- ui.position.left = inst._convertPositionTo("relative", { top: 0, left: l - inst.helperProportions.width }).left;
- }
- if (rs) {
- ui.position.left = inst._convertPositionTo("relative", { top: 0, left: r }).left;
- }
- }
-
- first = (ts || bs || ls || rs);
-
- if (o.snapMode !== "outer") {
- ts = Math.abs(t - y1) <= d;
- bs = Math.abs(b - y2) <= d;
- ls = Math.abs(l - x1) <= d;
- rs = Math.abs(r - x2) <= d;
- if (ts) {
- ui.position.top = inst._convertPositionTo("relative", { top: t, left: 0 }).top;
- }
- if (bs) {
- ui.position.top = inst._convertPositionTo("relative", { top: b - inst.helperProportions.height, left: 0 }).top;
- }
- if (ls) {
- ui.position.left = inst._convertPositionTo("relative", { top: 0, left: l }).left;
- }
- if (rs) {
- ui.position.left = inst._convertPositionTo("relative", { top: 0, left: r - inst.helperProportions.width }).left;
- }
- }
-
- if (!inst.snapElements[i].snapping && (ts || bs || ls || rs || first)) {
- (inst.options.snap.snap && inst.options.snap.snap.call(inst.element, event, $.extend(inst._uiHash(), { snapItem: inst.snapElements[i].item })));
- }
- inst.snapElements[i].snapping = (ts || bs || ls || rs || first);
-
- }
-
- }
-});
-
-$.ui.plugin.add("draggable", "stack", {
- start: function( event, ui, instance ) {
- var min,
- o = instance.options,
- group = $.makeArray($(o.stack)).sort(function(a, b) {
- return (parseInt($(a).css("zIndex"), 10) || 0) - (parseInt($(b).css("zIndex"), 10) || 0);
- });
-
- if (!group.length) { return; }
-
- min = parseInt($(group[0]).css("zIndex"), 10) || 0;
- $(group).each(function(i) {
- $(this).css("zIndex", min + i);
- });
- this.css("zIndex", (min + group.length));
- }
-});
-
-$.ui.plugin.add("draggable", "zIndex", {
- start: function( event, ui, instance ) {
- var t = $( ui.helper ),
- o = instance.options;
-
- if (t.css("zIndex")) {
- o._zIndex = t.css("zIndex");
- }
- t.css("zIndex", o.zIndex);
- },
- stop: function( event, ui, instance ) {
- var o = instance.options;
-
- if (o._zIndex) {
- $(ui.helper).css("zIndex", o._zIndex);
- }
- }
-});
-
-var draggable = $.ui.draggable;
-
-
-/*!
- * jQuery UI Droppable 1.11.4
- * http://jqueryui.com
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- *
- * http://api.jqueryui.com/droppable/
- */
-
-
-$.widget( "ui.droppable", {
- version: "1.11.4",
- widgetEventPrefix: "drop",
- options: {
- accept: "*",
- activeClass: false,
- addClasses: true,
- greedy: false,
- hoverClass: false,
- scope: "default",
- tolerance: "intersect",
-
- // callbacks
- activate: null,
- deactivate: null,
- drop: null,
- out: null,
- over: null
- },
- _create: function() {
-
- var proportions,
- o = this.options,
- accept = o.accept;
-
- this.isover = false;
- this.isout = true;
-
- this.accept = $.isFunction( accept ) ? accept : function( d ) {
- return d.is( accept );
- };
-
- this.proportions = function( /* valueToWrite */ ) {
- if ( arguments.length ) {
- // Store the droppable's proportions
- proportions = arguments[ 0 ];
- } else {
- // Retrieve or derive the droppable's proportions
- return proportions ?
- proportions :
- proportions = {
- width: this.element[ 0 ].offsetWidth,
- height: this.element[ 0 ].offsetHeight
- };
- }
- };
-
- this._addToManager( o.scope );
-
- o.addClasses && this.element.addClass( "ui-droppable" );
-
- },
-
- _addToManager: function( scope ) {
- // Add the reference and positions to the manager
- $.ui.ddmanager.droppables[ scope ] = $.ui.ddmanager.droppables[ scope ] || [];
- $.ui.ddmanager.droppables[ scope ].push( this );
- },
-
- _splice: function( drop ) {
- var i = 0;
- for ( ; i < drop.length; i++ ) {
- if ( drop[ i ] === this ) {
- drop.splice( i, 1 );
- }
- }
- },
-
- _destroy: function() {
- var drop = $.ui.ddmanager.droppables[ this.options.scope ];
-
- this._splice( drop );
-
- this.element.removeClass( "ui-droppable ui-droppable-disabled" );
- },
-
- _setOption: function( key, value ) {
-
- if ( key === "accept" ) {
- this.accept = $.isFunction( value ) ? value : function( d ) {
- return d.is( value );
- };
- } else if ( key === "scope" ) {
- var drop = $.ui.ddmanager.droppables[ this.options.scope ];
-
- this._splice( drop );
- this._addToManager( value );
- }
-
- this._super( key, value );
- },
-
- _activate: function( event ) {
- var draggable = $.ui.ddmanager.current;
- if ( this.options.activeClass ) {
- this.element.addClass( this.options.activeClass );
- }
- if ( draggable ){
- this._trigger( "activate", event, this.ui( draggable ) );
- }
- },
-
- _deactivate: function( event ) {
- var draggable = $.ui.ddmanager.current;
- if ( this.options.activeClass ) {
- this.element.removeClass( this.options.activeClass );
- }
- if ( draggable ){
- this._trigger( "deactivate", event, this.ui( draggable ) );
- }
- },
-
- _over: function( event ) {
-
- var draggable = $.ui.ddmanager.current;
-
- // Bail if draggable and droppable are same element
- if ( !draggable || ( draggable.currentItem || draggable.element )[ 0 ] === this.element[ 0 ] ) {
- return;
- }
-
- if ( this.accept.call( this.element[ 0 ], ( draggable.currentItem || draggable.element ) ) ) {
- if ( this.options.hoverClass ) {
- this.element.addClass( this.options.hoverClass );
- }
- this._trigger( "over", event, this.ui( draggable ) );
- }
-
- },
-
- _out: function( event ) {
-
- var draggable = $.ui.ddmanager.current;
-
- // Bail if draggable and droppable are same element
- if ( !draggable || ( draggable.currentItem || draggable.element )[ 0 ] === this.element[ 0 ] ) {
- return;
- }
-
- if ( this.accept.call( this.element[ 0 ], ( draggable.currentItem || draggable.element ) ) ) {
- if ( this.options.hoverClass ) {
- this.element.removeClass( this.options.hoverClass );
- }
- this._trigger( "out", event, this.ui( draggable ) );
- }
-
- },
-
- _drop: function( event, custom ) {
-
- var draggable = custom || $.ui.ddmanager.current,
- childrenIntersection = false;
-
- // Bail if draggable and droppable are same element
- if ( !draggable || ( draggable.currentItem || draggable.element )[ 0 ] === this.element[ 0 ] ) {
- return false;
- }
-
- this.element.find( ":data(ui-droppable)" ).not( ".ui-draggable-dragging" ).each(function() {
- var inst = $( this ).droppable( "instance" );
- if (
- inst.options.greedy &&
- !inst.options.disabled &&
- inst.options.scope === draggable.options.scope &&
- inst.accept.call( inst.element[ 0 ], ( draggable.currentItem || draggable.element ) ) &&
- $.ui.intersect( draggable, $.extend( inst, { offset: inst.element.offset() } ), inst.options.tolerance, event )
- ) { childrenIntersection = true; return false; }
- });
- if ( childrenIntersection ) {
- return false;
- }
-
- if ( this.accept.call( this.element[ 0 ], ( draggable.currentItem || draggable.element ) ) ) {
- if ( this.options.activeClass ) {
- this.element.removeClass( this.options.activeClass );
- }
- if ( this.options.hoverClass ) {
- this.element.removeClass( this.options.hoverClass );
- }
- this._trigger( "drop", event, this.ui( draggable ) );
- return this.element;
- }
-
- return false;
-
- },
-
- ui: function( c ) {
- return {
- draggable: ( c.currentItem || c.element ),
- helper: c.helper,
- position: c.position,
- offset: c.positionAbs
- };
- }
-
-});
-
-$.ui.intersect = (function() {
- function isOverAxis( x, reference, size ) {
- return ( x >= reference ) && ( x < ( reference + size ) );
- }
-
- return function( draggable, droppable, toleranceMode, event ) {
-
- if ( !droppable.offset ) {
- return false;
- }
-
- var x1 = ( draggable.positionAbs || draggable.position.absolute ).left + draggable.margins.left,
- y1 = ( draggable.positionAbs || draggable.position.absolute ).top + draggable.margins.top,
- x2 = x1 + draggable.helperProportions.width,
- y2 = y1 + draggable.helperProportions.height,
- l = droppable.offset.left,
- t = droppable.offset.top,
- r = l + droppable.proportions().width,
- b = t + droppable.proportions().height;
-
- switch ( toleranceMode ) {
- case "fit":
- return ( l <= x1 && x2 <= r && t <= y1 && y2 <= b );
- case "intersect":
- return ( l < x1 + ( draggable.helperProportions.width / 2 ) && // Right Half
- x2 - ( draggable.helperProportions.width / 2 ) < r && // Left Half
- t < y1 + ( draggable.helperProportions.height / 2 ) && // Bottom Half
- y2 - ( draggable.helperProportions.height / 2 ) < b ); // Top Half
- case "pointer":
- return isOverAxis( event.pageY, t, droppable.proportions().height ) && isOverAxis( event.pageX, l, droppable.proportions().width );
- case "touch":
- return (
- ( y1 >= t && y1 <= b ) || // Top edge touching
- ( y2 >= t && y2 <= b ) || // Bottom edge touching
- ( y1 < t && y2 > b ) // Surrounded vertically
- ) && (
- ( x1 >= l && x1 <= r ) || // Left edge touching
- ( x2 >= l && x2 <= r ) || // Right edge touching
- ( x1 < l && x2 > r ) // Surrounded horizontally
- );
- default:
- return false;
- }
- };
-})();
-
-/*
- This manager tracks offsets of draggables and droppables
-*/
-$.ui.ddmanager = {
- current: null,
- droppables: { "default": [] },
- prepareOffsets: function( t, event ) {
-
- var i, j,
- m = $.ui.ddmanager.droppables[ t.options.scope ] || [],
- type = event ? event.type : null, // workaround for #2317
- list = ( t.currentItem || t.element ).find( ":data(ui-droppable)" ).addBack();
-
- droppablesLoop: for ( i = 0; i < m.length; i++ ) {
-
- // No disabled and non-accepted
- if ( m[ i ].options.disabled || ( t && !m[ i ].accept.call( m[ i ].element[ 0 ], ( t.currentItem || t.element ) ) ) ) {
- continue;
- }
-
- // Filter out elements in the current dragged item
- for ( j = 0; j < list.length; j++ ) {
- if ( list[ j ] === m[ i ].element[ 0 ] ) {
- m[ i ].proportions().height = 0;
- continue droppablesLoop;
- }
- }
-
- m[ i ].visible = m[ i ].element.css( "display" ) !== "none";
- if ( !m[ i ].visible ) {
- continue;
- }
-
- // Activate the droppable if used directly from draggables
- if ( type === "mousedown" ) {
- m[ i ]._activate.call( m[ i ], event );
- }
-
- m[ i ].offset = m[ i ].element.offset();
- m[ i ].proportions({ width: m[ i ].element[ 0 ].offsetWidth, height: m[ i ].element[ 0 ].offsetHeight });
-
- }
-
- },
- drop: function( draggable, event ) {
-
- var dropped = false;
- // Create a copy of the droppables in case the list changes during the drop (#9116)
- $.each( ( $.ui.ddmanager.droppables[ draggable.options.scope ] || [] ).slice(), function() {
-
- if ( !this.options ) {
- return;
- }
- if ( !this.options.disabled && this.visible && $.ui.intersect( draggable, this, this.options.tolerance, event ) ) {
- dropped = this._drop.call( this, event ) || dropped;
- }
-
- if ( !this.options.disabled && this.visible && this.accept.call( this.element[ 0 ], ( draggable.currentItem || draggable.element ) ) ) {
- this.isout = true;
- this.isover = false;
- this._deactivate.call( this, event );
- }
-
- });
- return dropped;
-
- },
- dragStart: function( draggable, event ) {
- // Listen for scrolling so that if the dragging causes scrolling the position of the droppables can be recalculated (see #5003)
- draggable.element.parentsUntil( "body" ).bind( "scroll.droppable", function() {
- if ( !draggable.options.refreshPositions ) {
- $.ui.ddmanager.prepareOffsets( draggable, event );
- }
- });
- },
- drag: function( draggable, event ) {
-
- // If you have a highly dynamic page, you might try this option. It renders positions every time you move the mouse.
- if ( draggable.options.refreshPositions ) {
- $.ui.ddmanager.prepareOffsets( draggable, event );
- }
-
- // Run through all droppables and check their positions based on specific tolerance options
- $.each( $.ui.ddmanager.droppables[ draggable.options.scope ] || [], function() {
-
- if ( this.options.disabled || this.greedyChild || !this.visible ) {
- return;
- }
-
- var parentInstance, scope, parent,
- intersects = $.ui.intersect( draggable, this, this.options.tolerance, event ),
- c = !intersects && this.isover ? "isout" : ( intersects && !this.isover ? "isover" : null );
- if ( !c ) {
- return;
- }
-
- if ( this.options.greedy ) {
- // find droppable parents with same scope
- scope = this.options.scope;
- parent = this.element.parents( ":data(ui-droppable)" ).filter(function() {
- return $( this ).droppable( "instance" ).options.scope === scope;
- });
-
- if ( parent.length ) {
- parentInstance = $( parent[ 0 ] ).droppable( "instance" );
- parentInstance.greedyChild = ( c === "isover" );
- }
- }
-
- // we just moved into a greedy child
- if ( parentInstance && c === "isover" ) {
- parentInstance.isover = false;
- parentInstance.isout = true;
- parentInstance._out.call( parentInstance, event );
- }
-
- this[ c ] = true;
- this[c === "isout" ? "isover" : "isout"] = false;
- this[c === "isover" ? "_over" : "_out"].call( this, event );
-
- // we just moved out of a greedy child
- if ( parentInstance && c === "isout" ) {
- parentInstance.isout = false;
- parentInstance.isover = true;
- parentInstance._over.call( parentInstance, event );
- }
- });
-
- },
- dragStop: function( draggable, event ) {
- draggable.element.parentsUntil( "body" ).unbind( "scroll.droppable" );
- // Call prepareOffsets one final time since IE does not fire return scroll events when overflow was caused by drag (see #5003)
- if ( !draggable.options.refreshPositions ) {
- $.ui.ddmanager.prepareOffsets( draggable, event );
- }
- }
-};
-
-var droppable = $.ui.droppable;
-
-
-/*!
- * jQuery UI Resizable 1.11.4
- * http://jqueryui.com
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- *
- * http://api.jqueryui.com/resizable/
- */
-
-
-$.widget("ui.resizable", $.ui.mouse, {
- version: "1.11.4",
- widgetEventPrefix: "resize",
- options: {
- alsoResize: false,
- animate: false,
- animateDuration: "slow",
- animateEasing: "swing",
- aspectRatio: false,
- autoHide: false,
- containment: false,
- ghost: false,
- grid: false,
- handles: "e,s,se",
- helper: false,
- maxHeight: null,
- maxWidth: null,
- minHeight: 10,
- minWidth: 10,
- // See #7960
- zIndex: 90,
-
- // callbacks
- resize: null,
- start: null,
- stop: null
- },
-
- _num: function( value ) {
- return parseInt( value, 10 ) || 0;
- },
-
- _isNumber: function( value ) {
- return !isNaN( parseInt( value, 10 ) );
- },
-
- _hasScroll: function( el, a ) {
-
- if ( $( el ).css( "overflow" ) === "hidden") {
- return false;
- }
-
- var scroll = ( a && a === "left" ) ? "scrollLeft" : "scrollTop",
- has = false;
-
- if ( el[ scroll ] > 0 ) {
- return true;
- }
-
- // TODO: determine which cases actually cause this to happen
- // if the element doesn't have the scroll set, see if it's possible to
- // set the scroll
- el[ scroll ] = 1;
- has = ( el[ scroll ] > 0 );
- el[ scroll ] = 0;
- return has;
- },
-
- _create: function() {
-
- var n, i, handle, axis, hname,
- that = this,
- o = this.options;
- this.element.addClass("ui-resizable");
-
- $.extend(this, {
- _aspectRatio: !!(o.aspectRatio),
- aspectRatio: o.aspectRatio,
- originalElement: this.element,
- _proportionallyResizeElements: [],
- _helper: o.helper || o.ghost || o.animate ? o.helper || "ui-resizable-helper" : null
- });
-
- // Wrap the element if it cannot hold child nodes
- if (this.element[0].nodeName.match(/^(canvas|textarea|input|select|button|img)$/i)) {
-
- this.element.wrap(
- $("<div class='ui-wrapper' style='overflow: hidden;'></div>").css({
- position: this.element.css("position"),
- width: this.element.outerWidth(),
- height: this.element.outerHeight(),
- top: this.element.css("top"),
- left: this.element.css("left")
- })
- );
-
- this.element = this.element.parent().data(
- "ui-resizable", this.element.resizable( "instance" )
- );
-
- this.elementIsWrapper = true;
-
- this.element.css({
- marginLeft: this.originalElement.css("marginLeft"),
- marginTop: this.originalElement.css("marginTop"),
- marginRight: this.originalElement.css("marginRight"),
- marginBottom: this.originalElement.css("marginBottom")
- });
- this.originalElement.css({
- marginLeft: 0,
- marginTop: 0,
- marginRight: 0,
- marginBottom: 0
- });
- // support: Safari
- // Prevent Safari textarea resize
- this.originalResizeStyle = this.originalElement.css("resize");
- this.originalElement.css("resize", "none");
-
- this._proportionallyResizeElements.push( this.originalElement.css({
- position: "static",
- zoom: 1,
- display: "block"
- }) );
-
- // support: IE9
- // avoid IE jump (hard set the margin)
- this.originalElement.css({ margin: this.originalElement.css("margin") });
-
- this._proportionallyResize();
- }
-
- this.handles = o.handles ||
- ( !$(".ui-resizable-handle", this.element).length ?
- "e,s,se" : {
- n: ".ui-resizable-n",
- e: ".ui-resizable-e",
- s: ".ui-resizable-s",
- w: ".ui-resizable-w",
- se: ".ui-resizable-se",
- sw: ".ui-resizable-sw",
- ne: ".ui-resizable-ne",
- nw: ".ui-resizable-nw"
- } );
-
- this._handles = $();
- if ( this.handles.constructor === String ) {
-
- if ( this.handles === "all") {
- this.handles = "n,e,s,w,se,sw,ne,nw";
- }
-
- n = this.handles.split(",");
- this.handles = {};
-
- for (i = 0; i < n.length; i++) {
-
- handle = $.trim(n[i]);
- hname = "ui-resizable-" + handle;
- axis = $("<div class='ui-resizable-handle " + hname + "'></div>");
-
- axis.css({ zIndex: o.zIndex });
-
- // TODO : What's going on here?
- if ("se" === handle) {
- axis.addClass("ui-icon ui-icon-gripsmall-diagonal-se");
- }
-
- this.handles[handle] = ".ui-resizable-" + handle;
- this.element.append(axis);
- }
-
- }
-
- this._renderAxis = function(target) {
-
- var i, axis, padPos, padWrapper;
-
- target = target || this.element;
-
- for (i in this.handles) {
-
- if (this.handles[i].constructor === String) {
- this.handles[i] = this.element.children( this.handles[ i ] ).first().show();
- } else if ( this.handles[ i ].jquery || this.handles[ i ].nodeType ) {
- this.handles[ i ] = $( this.handles[ i ] );
- this._on( this.handles[ i ], { "mousedown": that._mouseDown });
- }
-
- if (this.elementIsWrapper && this.originalElement[0].nodeName.match(/^(textarea|input|select|button)$/i)) {
-
- axis = $(this.handles[i], this.element);
-
- padWrapper = /sw|ne|nw|se|n|s/.test(i) ? axis.outerHeight() : axis.outerWidth();
-
- padPos = [ "padding",
- /ne|nw|n/.test(i) ? "Top" :
- /se|sw|s/.test(i) ? "Bottom" :
- /^e$/.test(i) ? "Right" : "Left" ].join("");
-
- target.css(padPos, padWrapper);
-
- this._proportionallyResize();
- }
-
- this._handles = this._handles.add( this.handles[ i ] );
- }
- };
-
- // TODO: make renderAxis a prototype function
- this._renderAxis(this.element);
-
- this._handles = this._handles.add( this.element.find( ".ui-resizable-handle" ) );
- this._handles.disableSelection();
-
- this._handles.mouseover(function() {
- if (!that.resizing) {
- if (this.className) {
- axis = this.className.match(/ui-resizable-(se|sw|ne|nw|n|e|s|w)/i);
- }
- that.axis = axis && axis[1] ? axis[1] : "se";
- }
- });
-
- if (o.autoHide) {
- this._handles.hide();
- $(this.element)
- .addClass("ui-resizable-autohide")
- .mouseenter(function() {
- if (o.disabled) {
- return;
- }
- $(this).removeClass("ui-resizable-autohide");
- that._handles.show();
- })
- .mouseleave(function() {
- if (o.disabled) {
- return;
- }
- if (!that.resizing) {
- $(this).addClass("ui-resizable-autohide");
- that._handles.hide();
- }
- });
- }
-
- this._mouseInit();
- },
-
- _destroy: function() {
-
- this._mouseDestroy();
-
- var wrapper,
- _destroy = function(exp) {
- $(exp)
- .removeClass("ui-resizable ui-resizable-disabled ui-resizable-resizing")
- .removeData("resizable")
- .removeData("ui-resizable")
- .unbind(".resizable")
- .find(".ui-resizable-handle")
- .remove();
- };
-
- // TODO: Unwrap at same DOM position
- if (this.elementIsWrapper) {
- _destroy(this.element);
- wrapper = this.element;
- this.originalElement.css({
- position: wrapper.css("position"),
- width: wrapper.outerWidth(),
- height: wrapper.outerHeight(),
- top: wrapper.css("top"),
- left: wrapper.css("left")
- }).insertAfter( wrapper );
- wrapper.remove();
- }
-
- this.originalElement.css("resize", this.originalResizeStyle);
- _destroy(this.originalElement);
-
- return this;
- },
-
- _mouseCapture: function(event) {
- var i, handle,
- capture = false;
-
- for (i in this.handles) {
- handle = $(this.handles[i])[0];
- if (handle === event.target || $.contains(handle, event.target)) {
- capture = true;
- }
- }
-
- return !this.options.disabled && capture;
- },
-
- _mouseStart: function(event) {
-
- var curleft, curtop, cursor,
- o = this.options,
- el = this.element;
-
- this.resizing = true;
-
- this._renderProxy();
-
- curleft = this._num(this.helper.css("left"));
- curtop = this._num(this.helper.css("top"));
-
- if (o.containment) {
- curleft += $(o.containment).scrollLeft() || 0;
- curtop += $(o.containment).scrollTop() || 0;
- }
-
- this.offset = this.helper.offset();
- this.position = { left: curleft, top: curtop };
-
- this.size = this._helper ? {
- width: this.helper.width(),
- height: this.helper.height()
- } : {
- width: el.width(),
- height: el.height()
- };
-
- this.originalSize = this._helper ? {
- width: el.outerWidth(),
- height: el.outerHeight()
- } : {
- width: el.width(),
- height: el.height()
- };
-
- this.sizeDiff = {
- width: el.outerWidth() - el.width(),
- height: el.outerHeight() - el.height()
- };
-
- this.originalPosition = { left: curleft, top: curtop };
- this.originalMousePosition = { left: event.pageX, top: event.pageY };
-
- this.aspectRatio = (typeof o.aspectRatio === "number") ?
- o.aspectRatio :
- ((this.originalSize.width / this.originalSize.height) || 1);
-
- cursor = $(".ui-resizable-" + this.axis).css("cursor");
- $("body").css("cursor", cursor === "auto" ? this.axis + "-resize" : cursor);
-
- el.addClass("ui-resizable-resizing");
- this._propagate("start", event);
- return true;
- },
-
- _mouseDrag: function(event) {
-
- var data, props,
- smp = this.originalMousePosition,
- a = this.axis,
- dx = (event.pageX - smp.left) || 0,
- dy = (event.pageY - smp.top) || 0,
- trigger = this._change[a];
-
- this._updatePrevProperties();
-
- if (!trigger) {
- return false;
- }
-
- data = trigger.apply(this, [ event, dx, dy ]);
-
- this._updateVirtualBoundaries(event.shiftKey);
- if (this._aspectRatio || event.shiftKey) {
- data = this._updateRatio(data, event);
- }
-
- data = this._respectSize(data, event);
-
- this._updateCache(data);
-
- this._propagate("resize", event);
-
- props = this._applyChanges();
-
- if ( !this._helper && this._proportionallyResizeElements.length ) {
- this._proportionallyResize();
- }
-
- if ( !$.isEmptyObject( props ) ) {
- this._updatePrevProperties();
- this._trigger( "resize", event, this.ui() );
- this._applyChanges();
- }
-
- return false;
- },
-
- _mouseStop: function(event) {
-
- this.resizing = false;
- var pr, ista, soffseth, soffsetw, s, left, top,
- o = this.options, that = this;
-
- if (this._helper) {
-
- pr = this._proportionallyResizeElements;
- ista = pr.length && (/textarea/i).test(pr[0].nodeName);
- soffseth = ista && this._hasScroll(pr[0], "left") ? 0 : that.sizeDiff.height;
- soffsetw = ista ? 0 : that.sizeDiff.width;
-
- s = {
- width: (that.helper.width() - soffsetw),
- height: (that.helper.height() - soffseth)
- };
- left = (parseInt(that.element.css("left"), 10) +
- (that.position.left - that.originalPosition.left)) || null;
- top = (parseInt(that.element.css("top"), 10) +
- (that.position.top - that.originalPosition.top)) || null;
-
- if (!o.animate) {
- this.element.css($.extend(s, { top: top, left: left }));
- }
-
- that.helper.height(that.size.height);
- that.helper.width(that.size.width);
-
- if (this._helper && !o.animate) {
- this._proportionallyResize();
- }
- }
-
- $("body").css("cursor", "auto");
-
- this.element.removeClass("ui-resizable-resizing");
-
- this._propagate("stop", event);
-
- if (this._helper) {
- this.helper.remove();
- }
-
- return false;
-
- },
-
- _updatePrevProperties: function() {
- this.prevPosition = {
- top: this.position.top,
- left: this.position.left
- };
- this.prevSize = {
- width: this.size.width,
- height: this.size.height
- };
- },
-
- _applyChanges: function() {
- var props = {};
-
- if ( this.position.top !== this.prevPosition.top ) {
- props.top = this.position.top + "px";
- }
- if ( this.position.left !== this.prevPosition.left ) {
- props.left = this.position.left + "px";
- }
- if ( this.size.width !== this.prevSize.width ) {
- props.width = this.size.width + "px";
- }
- if ( this.size.height !== this.prevSize.height ) {
- props.height = this.size.height + "px";
- }
-
- this.helper.css( props );
-
- return props;
- },
-
- _updateVirtualBoundaries: function(forceAspectRatio) {
- var pMinWidth, pMaxWidth, pMinHeight, pMaxHeight, b,
- o = this.options;
-
- b = {
- minWidth: this._isNumber(o.minWidth) ? o.minWidth : 0,
- maxWidth: this._isNumber(o.maxWidth) ? o.maxWidth : Infinity,
- minHeight: this._isNumber(o.minHeight) ? o.minHeight : 0,
- maxHeight: this._isNumber(o.maxHeight) ? o.maxHeight : Infinity
- };
-
- if (this._aspectRatio || forceAspectRatio) {
- pMinWidth = b.minHeight * this.aspectRatio;
- pMinHeight = b.minWidth / this.aspectRatio;
- pMaxWidth = b.maxHeight * this.aspectRatio;
- pMaxHeight = b.maxWidth / this.aspectRatio;
-
- if (pMinWidth > b.minWidth) {
- b.minWidth = pMinWidth;
- }
- if (pMinHeight > b.minHeight) {
- b.minHeight = pMinHeight;
- }
- if (pMaxWidth < b.maxWidth) {
- b.maxWidth = pMaxWidth;
- }
- if (pMaxHeight < b.maxHeight) {
- b.maxHeight = pMaxHeight;
- }
- }
- this._vBoundaries = b;
- },
-
- _updateCache: function(data) {
- this.offset = this.helper.offset();
- if (this._isNumber(data.left)) {
- this.position.left = data.left;
- }
- if (this._isNumber(data.top)) {
- this.position.top = data.top;
- }
- if (this._isNumber(data.height)) {
- this.size.height = data.height;
- }
- if (this._isNumber(data.width)) {
- this.size.width = data.width;
- }
- },
-
- _updateRatio: function( data ) {
-
- var cpos = this.position,
- csize = this.size,
- a = this.axis;
-
- if (this._isNumber(data.height)) {
- data.width = (data.height * this.aspectRatio);
- } else if (this._isNumber(data.width)) {
- data.height = (data.width / this.aspectRatio);
- }
-
- if (a === "sw") {
- data.left = cpos.left + (csize.width - data.width);
- data.top = null;
- }
- if (a === "nw") {
- data.top = cpos.top + (csize.height - data.height);
- data.left = cpos.left + (csize.width - data.width);
- }
-
- return data;
- },
-
- _respectSize: function( data ) {
-
- var o = this._vBoundaries,
- a = this.axis,
- ismaxw = this._isNumber(data.width) && o.maxWidth && (o.maxWidth < data.width),
- ismaxh = this._isNumber(data.height) && o.maxHeight && (o.maxHeight < data.height),
- isminw = this._isNumber(data.width) && o.minWidth && (o.minWidth > data.width),
- isminh = this._isNumber(data.height) && o.minHeight && (o.minHeight > data.height),
- dw = this.originalPosition.left + this.originalSize.width,
- dh = this.position.top + this.size.height,
- cw = /sw|nw|w/.test(a), ch = /nw|ne|n/.test(a);
- if (isminw) {
- data.width = o.minWidth;
- }
- if (isminh) {
- data.height = o.minHeight;
- }
- if (ismaxw) {
- data.width = o.maxWidth;
- }
- if (ismaxh) {
- data.height = o.maxHeight;
- }
-
- if (isminw && cw) {
- data.left = dw - o.minWidth;
- }
- if (ismaxw && cw) {
- data.left = dw - o.maxWidth;
- }
- if (isminh && ch) {
- data.top = dh - o.minHeight;
- }
- if (ismaxh && ch) {
- data.top = dh - o.maxHeight;
- }
-
- // Fixing jump error on top/left - bug #2330
- if (!data.width && !data.height && !data.left && data.top) {
- data.top = null;
- } else if (!data.width && !data.height && !data.top && data.left) {
- data.left = null;
- }
-
- return data;
- },
-
- _getPaddingPlusBorderDimensions: function( element ) {
- var i = 0,
- widths = [],
- borders = [
- element.css( "borderTopWidth" ),
- element.css( "borderRightWidth" ),
- element.css( "borderBottomWidth" ),
- element.css( "borderLeftWidth" )
- ],
- paddings = [
- element.css( "paddingTop" ),
- element.css( "paddingRight" ),
- element.css( "paddingBottom" ),
- element.css( "paddingLeft" )
- ];
-
- for ( ; i < 4; i++ ) {
- widths[ i ] = ( parseInt( borders[ i ], 10 ) || 0 );
- widths[ i ] += ( parseInt( paddings[ i ], 10 ) || 0 );
- }
-
- return {
- height: widths[ 0 ] + widths[ 2 ],
- width: widths[ 1 ] + widths[ 3 ]
- };
- },
-
- _proportionallyResize: function() {
-
- if (!this._proportionallyResizeElements.length) {
- return;
- }
-
- var prel,
- i = 0,
- element = this.helper || this.element;
-
- for ( ; i < this._proportionallyResizeElements.length; i++) {
-
- prel = this._proportionallyResizeElements[i];
-
- // TODO: Seems like a bug to cache this.outerDimensions
- // considering that we are in a loop.
- if (!this.outerDimensions) {
- this.outerDimensions = this._getPaddingPlusBorderDimensions( prel );
- }
-
- prel.css({
- height: (element.height() - this.outerDimensions.height) || 0,
- width: (element.width() - this.outerDimensions.width) || 0
- });
-
- }
-
- },
-
- _renderProxy: function() {
-
- var el = this.element, o = this.options;
- this.elementOffset = el.offset();
-
- if (this._helper) {
-
- this.helper = this.helper || $("<div style='overflow:hidden;'></div>");
-
- this.helper.addClass(this._helper).css({
- width: this.element.outerWidth() - 1,
- height: this.element.outerHeight() - 1,
- position: "absolute",
- left: this.elementOffset.left + "px",
- top: this.elementOffset.top + "px",
- zIndex: ++o.zIndex //TODO: Don't modify option
- });
-
- this.helper
- .appendTo("body")
- .disableSelection();
-
- } else {
- this.helper = this.element;
- }
-
- },
-
- _change: {
- e: function(event, dx) {
- return { width: this.originalSize.width + dx };
- },
- w: function(event, dx) {
- var cs = this.originalSize, sp = this.originalPosition;
- return { left: sp.left + dx, width: cs.width - dx };
- },
- n: function(event, dx, dy) {
- var cs = this.originalSize, sp = this.originalPosition;
- return { top: sp.top + dy, height: cs.height - dy };
- },
- s: function(event, dx, dy) {
- return { height: this.originalSize.height + dy };
- },
- se: function(event, dx, dy) {
- return $.extend(this._change.s.apply(this, arguments),
- this._change.e.apply(this, [ event, dx, dy ]));
- },
- sw: function(event, dx, dy) {
- return $.extend(this._change.s.apply(this, arguments),
- this._change.w.apply(this, [ event, dx, dy ]));
- },
- ne: function(event, dx, dy) {
- return $.extend(this._change.n.apply(this, arguments),
- this._change.e.apply(this, [ event, dx, dy ]));
- },
- nw: function(event, dx, dy) {
- return $.extend(this._change.n.apply(this, arguments),
- this._change.w.apply(this, [ event, dx, dy ]));
- }
- },
-
- _propagate: function(n, event) {
- $.ui.plugin.call(this, n, [ event, this.ui() ]);
- (n !== "resize" && this._trigger(n, event, this.ui()));
- },
-
- plugins: {},
-
- ui: function() {
- return {
- originalElement: this.originalElement,
- element: this.element,
- helper: this.helper,
- position: this.position,
- size: this.size,
- originalSize: this.originalSize,
- originalPosition: this.originalPosition
- };
- }
-
-});
-
-/*
- * Resizable Extensions
- */
-
-$.ui.plugin.add("resizable", "animate", {
-
- stop: function( event ) {
- var that = $(this).resizable( "instance" ),
- o = that.options,
- pr = that._proportionallyResizeElements,
- ista = pr.length && (/textarea/i).test(pr[0].nodeName),
- soffseth = ista && that._hasScroll(pr[0], "left") ? 0 : that.sizeDiff.height,
- soffsetw = ista ? 0 : that.sizeDiff.width,
- style = { width: (that.size.width - soffsetw), height: (that.size.height - soffseth) },
- left = (parseInt(that.element.css("left"), 10) +
- (that.position.left - that.originalPosition.left)) || null,
- top = (parseInt(that.element.css("top"), 10) +
- (that.position.top - that.originalPosition.top)) || null;
-
- that.element.animate(
- $.extend(style, top && left ? { top: top, left: left } : {}), {
- duration: o.animateDuration,
- easing: o.animateEasing,
- step: function() {
-
- var data = {
- width: parseInt(that.element.css("width"), 10),
- height: parseInt(that.element.css("height"), 10),
- top: parseInt(that.element.css("top"), 10),
- left: parseInt(that.element.css("left"), 10)
- };
-
- if (pr && pr.length) {
- $(pr[0]).css({ width: data.width, height: data.height });
- }
-
- // propagating resize, and updating values for each animation step
- that._updateCache(data);
- that._propagate("resize", event);
-
- }
- }
- );
- }
-
-});
-
-$.ui.plugin.add( "resizable", "containment", {
-
- start: function() {
- var element, p, co, ch, cw, width, height,
- that = $( this ).resizable( "instance" ),
- o = that.options,
- el = that.element,
- oc = o.containment,
- ce = ( oc instanceof $ ) ? oc.get( 0 ) : ( /parent/.test( oc ) ) ? el.parent().get( 0 ) : oc;
-
- if ( !ce ) {
- return;
- }
-
- that.containerElement = $( ce );
-
- if ( /document/.test( oc ) || oc === document ) {
- that.containerOffset = {
- left: 0,
- top: 0
- };
- that.containerPosition = {
- left: 0,
- top: 0
- };
-
- that.parentData = {
- element: $( document ),
- left: 0,
- top: 0,
- width: $( document ).width(),
- height: $( document ).height() || document.body.parentNode.scrollHeight
- };
- } else {
- element = $( ce );
- p = [];
- $([ "Top", "Right", "Left", "Bottom" ]).each(function( i, name ) {
- p[ i ] = that._num( element.css( "padding" + name ) );
- });
-
- that.containerOffset = element.offset();
- that.containerPosition = element.position();
- that.containerSize = {
- height: ( element.innerHeight() - p[ 3 ] ),
- width: ( element.innerWidth() - p[ 1 ] )
- };
-
- co = that.containerOffset;
- ch = that.containerSize.height;
- cw = that.containerSize.width;
- width = ( that._hasScroll ( ce, "left" ) ? ce.scrollWidth : cw );
- height = ( that._hasScroll ( ce ) ? ce.scrollHeight : ch ) ;
-
- that.parentData = {
- element: ce,
- left: co.left,
- top: co.top,
- width: width,
- height: height
- };
- }
- },
-
- resize: function( event ) {
- var woset, hoset, isParent, isOffsetRelative,
- that = $( this ).resizable( "instance" ),
- o = that.options,
- co = that.containerOffset,
- cp = that.position,
- pRatio = that._aspectRatio || event.shiftKey,
- cop = {
- top: 0,
- left: 0
- },
- ce = that.containerElement,
- continueResize = true;
-
- if ( ce[ 0 ] !== document && ( /static/ ).test( ce.css( "position" ) ) ) {
- cop = co;
- }
-
- if ( cp.left < ( that._helper ? co.left : 0 ) ) {
- that.size.width = that.size.width +
- ( that._helper ?
- ( that.position.left - co.left ) :
- ( that.position.left - cop.left ) );
-
- if ( pRatio ) {
- that.size.height = that.size.width / that.aspectRatio;
- continueResize = false;
- }
- that.position.left = o.helper ? co.left : 0;
- }
-
- if ( cp.top < ( that._helper ? co.top : 0 ) ) {
- that.size.height = that.size.height +
- ( that._helper ?
- ( that.position.top - co.top ) :
- that.position.top );
-
- if ( pRatio ) {
- that.size.width = that.size.height * that.aspectRatio;
- continueResize = false;
- }
- that.position.top = that._helper ? co.top : 0;
- }
-
- isParent = that.containerElement.get( 0 ) === that.element.parent().get( 0 );
- isOffsetRelative = /relative|absolute/.test( that.containerElement.css( "position" ) );
-
- if ( isParent && isOffsetRelative ) {
- that.offset.left = that.parentData.left + that.position.left;
- that.offset.top = that.parentData.top + that.position.top;
- } else {
- that.offset.left = that.element.offset().left;
- that.offset.top = that.element.offset().top;
- }
-
- woset = Math.abs( that.sizeDiff.width +
- (that._helper ?
- that.offset.left - cop.left :
- (that.offset.left - co.left)) );
-
- hoset = Math.abs( that.sizeDiff.height +
- (that._helper ?
- that.offset.top - cop.top :
- (that.offset.top - co.top)) );
-
- if ( woset + that.size.width >= that.parentData.width ) {
- that.size.width = that.parentData.width - woset;
- if ( pRatio ) {
- that.size.height = that.size.width / that.aspectRatio;
- continueResize = false;
- }
- }
-
- if ( hoset + that.size.height >= that.parentData.height ) {
- that.size.height = that.parentData.height - hoset;
- if ( pRatio ) {
- that.size.width = that.size.height * that.aspectRatio;
- continueResize = false;
- }
- }
-
- if ( !continueResize ) {
- that.position.left = that.prevPosition.left;
- that.position.top = that.prevPosition.top;
- that.size.width = that.prevSize.width;
- that.size.height = that.prevSize.height;
- }
- },
-
- stop: function() {
- var that = $( this ).resizable( "instance" ),
- o = that.options,
- co = that.containerOffset,
- cop = that.containerPosition,
- ce = that.containerElement,
- helper = $( that.helper ),
- ho = helper.offset(),
- w = helper.outerWidth() - that.sizeDiff.width,
- h = helper.outerHeight() - that.sizeDiff.height;
-
- if ( that._helper && !o.animate && ( /relative/ ).test( ce.css( "position" ) ) ) {
- $( this ).css({
- left: ho.left - cop.left - co.left,
- width: w,
- height: h
- });
- }
-
- if ( that._helper && !o.animate && ( /static/ ).test( ce.css( "position" ) ) ) {
- $( this ).css({
- left: ho.left - cop.left - co.left,
- width: w,
- height: h
- });
- }
- }
-});
-
-$.ui.plugin.add("resizable", "alsoResize", {
-
- start: function() {
- var that = $(this).resizable( "instance" ),
- o = that.options;
-
- $(o.alsoResize).each(function() {
- var el = $(this);
- el.data("ui-resizable-alsoresize", {
- width: parseInt(el.width(), 10), height: parseInt(el.height(), 10),
- left: parseInt(el.css("left"), 10), top: parseInt(el.css("top"), 10)
- });
- });
- },
-
- resize: function(event, ui) {
- var that = $(this).resizable( "instance" ),
- o = that.options,
- os = that.originalSize,
- op = that.originalPosition,
- delta = {
- height: (that.size.height - os.height) || 0,
- width: (that.size.width - os.width) || 0,
- top: (that.position.top - op.top) || 0,
- left: (that.position.left - op.left) || 0
- };
-
- $(o.alsoResize).each(function() {
- var el = $(this), start = $(this).data("ui-resizable-alsoresize"), style = {},
- css = el.parents(ui.originalElement[0]).length ?
- [ "width", "height" ] :
- [ "width", "height", "top", "left" ];
-
- $.each(css, function(i, prop) {
- var sum = (start[prop] || 0) + (delta[prop] || 0);
- if (sum && sum >= 0) {
- style[prop] = sum || null;
- }
- });
-
- el.css(style);
- });
- },
-
- stop: function() {
- $(this).removeData("resizable-alsoresize");
- }
-});
-
-$.ui.plugin.add("resizable", "ghost", {
-
- start: function() {
-
- var that = $(this).resizable( "instance" ), o = that.options, cs = that.size;
-
- that.ghost = that.originalElement.clone();
- that.ghost
- .css({
- opacity: 0.25,
- display: "block",
- position: "relative",
- height: cs.height,
- width: cs.width,
- margin: 0,
- left: 0,
- top: 0
- })
- .addClass("ui-resizable-ghost")
- .addClass(typeof o.ghost === "string" ? o.ghost : "");
-
- that.ghost.appendTo(that.helper);
-
- },
-
- resize: function() {
- var that = $(this).resizable( "instance" );
- if (that.ghost) {
- that.ghost.css({
- position: "relative",
- height: that.size.height,
- width: that.size.width
- });
- }
- },
-
- stop: function() {
- var that = $(this).resizable( "instance" );
- if (that.ghost && that.helper) {
- that.helper.get(0).removeChild(that.ghost.get(0));
- }
- }
-
-});
-
-$.ui.plugin.add("resizable", "grid", {
-
- resize: function() {
- var outerDimensions,
- that = $(this).resizable( "instance" ),
- o = that.options,
- cs = that.size,
- os = that.originalSize,
- op = that.originalPosition,
- a = that.axis,
- grid = typeof o.grid === "number" ? [ o.grid, o.grid ] : o.grid,
- gridX = (grid[0] || 1),
- gridY = (grid[1] || 1),
- ox = Math.round((cs.width - os.width) / gridX) * gridX,
- oy = Math.round((cs.height - os.height) / gridY) * gridY,
- newWidth = os.width + ox,
- newHeight = os.height + oy,
- isMaxWidth = o.maxWidth && (o.maxWidth < newWidth),
- isMaxHeight = o.maxHeight && (o.maxHeight < newHeight),
- isMinWidth = o.minWidth && (o.minWidth > newWidth),
- isMinHeight = o.minHeight && (o.minHeight > newHeight);
-
- o.grid = grid;
-
- if (isMinWidth) {
- newWidth += gridX;
- }
- if (isMinHeight) {
- newHeight += gridY;
- }
- if (isMaxWidth) {
- newWidth -= gridX;
- }
- if (isMaxHeight) {
- newHeight -= gridY;
- }
-
- if (/^(se|s|e)$/.test(a)) {
- that.size.width = newWidth;
- that.size.height = newHeight;
- } else if (/^(ne)$/.test(a)) {
- that.size.width = newWidth;
- that.size.height = newHeight;
- that.position.top = op.top - oy;
- } else if (/^(sw)$/.test(a)) {
- that.size.width = newWidth;
- that.size.height = newHeight;
- that.position.left = op.left - ox;
- } else {
- if ( newHeight - gridY <= 0 || newWidth - gridX <= 0) {
- outerDimensions = that._getPaddingPlusBorderDimensions( this );
- }
-
- if ( newHeight - gridY > 0 ) {
- that.size.height = newHeight;
- that.position.top = op.top - oy;
- } else {
- newHeight = gridY - outerDimensions.height;
- that.size.height = newHeight;
- that.position.top = op.top + os.height - newHeight;
- }
- if ( newWidth - gridX > 0 ) {
- that.size.width = newWidth;
- that.position.left = op.left - ox;
- } else {
- newWidth = gridX - outerDimensions.width;
- that.size.width = newWidth;
- that.position.left = op.left + os.width - newWidth;
- }
- }
- }
-
-});
-
-var resizable = $.ui.resizable;
-
-
-/*!
- * jQuery UI Menu 1.11.4
- * http://jqueryui.com
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- *
- * http://api.jqueryui.com/menu/
- */
-
-
-var menu = $.widget( "ui.menu", {
- version: "1.11.4",
- defaultElement: "<ul>",
- delay: 300,
- options: {
- icons: {
- submenu: "ui-icon-carat-1-e"
- },
- items: "> *",
- menus: "ul",
- position: {
- my: "left-1 top",
- at: "right top"
- },
- role: "menu",
-
- // callbacks
- blur: null,
- focus: null,
- select: null
- },
-
- _create: function() {
- this.activeMenu = this.element;
-
- // Flag used to prevent firing of the click handler
- // as the event bubbles up through nested menus
- this.mouseHandled = false;
- this.element
- .uniqueId()
- .addClass( "ui-menu ui-widget ui-widget-content" )
- .toggleClass( "ui-menu-icons", !!this.element.find( ".ui-icon" ).length )
- .attr({
- role: this.options.role,
- tabIndex: 0
- });
-
- if ( this.options.disabled ) {
- this.element
- .addClass( "ui-state-disabled" )
- .attr( "aria-disabled", "true" );
- }
-
- this._on({
- // Prevent focus from sticking to links inside menu after clicking
- // them (focus should always stay on UL during navigation).
- "mousedown .ui-menu-item": function( event ) {
- event.preventDefault();
- },
- "click .ui-menu-item": function( event ) {
- var target = $( event.target );
- if ( !this.mouseHandled && target.not( ".ui-state-disabled" ).length ) {
- this.select( event );
-
- // Only set the mouseHandled flag if the event will bubble, see #9469.
- if ( !event.isPropagationStopped() ) {
- this.mouseHandled = true;
- }
-
- // Open submenu on click
- if ( target.has( ".ui-menu" ).length ) {
- this.expand( event );
- } else if ( !this.element.is( ":focus" ) && $( this.document[ 0 ].activeElement ).closest( ".ui-menu" ).length ) {
-
- // Redirect focus to the menu
- this.element.trigger( "focus", [ true ] );
-
- // If the active item is on the top level, let it stay active.
- // Otherwise, blur the active item since it is no longer visible.
- if ( this.active && this.active.parents( ".ui-menu" ).length === 1 ) {
- clearTimeout( this.timer );
- }
- }
- }
- },
- "mouseenter .ui-menu-item": function( event ) {
- // Ignore mouse events while typeahead is active, see #10458.
- // Prevents focusing the wrong item when typeahead causes a scroll while the mouse
- // is over an item in the menu
- if ( this.previousFilter ) {
- return;
- }
- var target = $( event.currentTarget );
- // Remove ui-state-active class from siblings of the newly focused menu item
- // to avoid a jump caused by adjacent elements both having a class with a border
- target.siblings( ".ui-state-active" ).removeClass( "ui-state-active" );
- this.focus( event, target );
- },
- mouseleave: "collapseAll",
- "mouseleave .ui-menu": "collapseAll",
- focus: function( event, keepActiveItem ) {
- // If there's already an active item, keep it active
- // If not, activate the first item
- var item = this.active || this.element.find( this.options.items ).eq( 0 );
-
- if ( !keepActiveItem ) {
- this.focus( event, item );
- }
- },
- blur: function( event ) {
- this._delay(function() {
- if ( !$.contains( this.element[0], this.document[0].activeElement ) ) {
- this.collapseAll( event );
- }
- });
- },
- keydown: "_keydown"
- });
-
- this.refresh();
-
- // Clicks outside of a menu collapse any open menus
- this._on( this.document, {
- click: function( event ) {
- if ( this._closeOnDocumentClick( event ) ) {
- this.collapseAll( event );
- }
-
- // Reset the mouseHandled flag
- this.mouseHandled = false;
- }
- });
- },
-
- _destroy: function() {
- // Destroy (sub)menus
- this.element
- .removeAttr( "aria-activedescendant" )
- .find( ".ui-menu" ).addBack()
- .removeClass( "ui-menu ui-widget ui-widget-content ui-menu-icons ui-front" )
- .removeAttr( "role" )
- .removeAttr( "tabIndex" )
- .removeAttr( "aria-labelledby" )
- .removeAttr( "aria-expanded" )
- .removeAttr( "aria-hidden" )
- .removeAttr( "aria-disabled" )
- .removeUniqueId()
- .show();
-
- // Destroy menu items
- this.element.find( ".ui-menu-item" )
- .removeClass( "ui-menu-item" )
- .removeAttr( "role" )
- .removeAttr( "aria-disabled" )
- .removeUniqueId()
- .removeClass( "ui-state-hover" )
- .removeAttr( "tabIndex" )
- .removeAttr( "role" )
- .removeAttr( "aria-haspopup" )
- .children().each( function() {
- var elem = $( this );
- if ( elem.data( "ui-menu-submenu-carat" ) ) {
- elem.remove();
- }
- });
-
- // Destroy menu dividers
- this.element.find( ".ui-menu-divider" ).removeClass( "ui-menu-divider ui-widget-content" );
- },
-
- _keydown: function( event ) {
- var match, prev, character, skip,
- preventDefault = true;
-
- switch ( event.keyCode ) {
- case $.ui.keyCode.PAGE_UP:
- this.previousPage( event );
- break;
- case $.ui.keyCode.PAGE_DOWN:
- this.nextPage( event );
- break;
- case $.ui.keyCode.HOME:
- this._move( "first", "first", event );
- break;
- case $.ui.keyCode.END:
- this._move( "last", "last", event );
- break;
- case $.ui.keyCode.UP:
- this.previous( event );
- break;
- case $.ui.keyCode.DOWN:
- this.next( event );
- break;
- case $.ui.keyCode.LEFT:
- this.collapse( event );
- break;
- case $.ui.keyCode.RIGHT:
- if ( this.active && !this.active.is( ".ui-state-disabled" ) ) {
- this.expand( event );
- }
- break;
- case $.ui.keyCode.ENTER:
- case $.ui.keyCode.SPACE:
- this._activate( event );
- break;
- case $.ui.keyCode.ESCAPE:
- this.collapse( event );
- break;
- default:
- preventDefault = false;
- prev = this.previousFilter || "";
- character = String.fromCharCode( event.keyCode );
- skip = false;
-
- clearTimeout( this.filterTimer );
-
- if ( character === prev ) {
- skip = true;
- } else {
- character = prev + character;
- }
-
- match = this._filterMenuItems( character );
- match = skip && match.index( this.active.next() ) !== -1 ?
- this.active.nextAll( ".ui-menu-item" ) :
- match;
-
- // If no matches on the current filter, reset to the last character pressed
- // to move down the menu to the first item that starts with that character
- if ( !match.length ) {
- character = String.fromCharCode( event.keyCode );
- match = this._filterMenuItems( character );
- }
-
- if ( match.length ) {
- this.focus( event, match );
- this.previousFilter = character;
- this.filterTimer = this._delay(function() {
- delete this.previousFilter;
- }, 1000 );
- } else {
- delete this.previousFilter;
- }
- }
-
- if ( preventDefault ) {
- event.preventDefault();
- }
- },
-
- _activate: function( event ) {
- if ( !this.active.is( ".ui-state-disabled" ) ) {
- if ( this.active.is( "[aria-haspopup='true']" ) ) {
- this.expand( event );
- } else {
- this.select( event );
- }
- }
- },
-
- refresh: function() {
- var menus, items,
- that = this,
- icon = this.options.icons.submenu,
- submenus = this.element.find( this.options.menus );
-
- this.element.toggleClass( "ui-menu-icons", !!this.element.find( ".ui-icon" ).length );
-
- // Initialize nested menus
- submenus.filter( ":not(.ui-menu)" )
- .addClass( "ui-menu ui-widget ui-widget-content ui-front" )
- .hide()
- .attr({
- role: this.options.role,
- "aria-hidden": "true",
- "aria-expanded": "false"
- })
- .each(function() {
- var menu = $( this ),
- item = menu.parent(),
- submenuCarat = $( "<span>" )
- .addClass( "ui-menu-icon ui-icon " + icon )
- .data( "ui-menu-submenu-carat", true );
-
- item
- .attr( "aria-haspopup", "true" )
- .prepend( submenuCarat );
- menu.attr( "aria-labelledby", item.attr( "id" ) );
- });
-
- menus = submenus.add( this.element );
- items = menus.find( this.options.items );
-
- // Initialize menu-items containing spaces and/or dashes only as dividers
- items.not( ".ui-menu-item" ).each(function() {
- var item = $( this );
- if ( that._isDivider( item ) ) {
- item.addClass( "ui-widget-content ui-menu-divider" );
- }
- });
-
- // Don't refresh list items that are already adapted
- items.not( ".ui-menu-item, .ui-menu-divider" )
- .addClass( "ui-menu-item" )
- .uniqueId()
- .attr({
- tabIndex: -1,
- role: this._itemRole()
- });
-
- // Add aria-disabled attribute to any disabled menu item
- items.filter( ".ui-state-disabled" ).attr( "aria-disabled", "true" );
-
- // If the active item has been removed, blur the menu
- if ( this.active && !$.contains( this.element[ 0 ], this.active[ 0 ] ) ) {
- this.blur();
- }
- },
-
- _itemRole: function() {
- return {
- menu: "menuitem",
- listbox: "option"
- }[ this.options.role ];
- },
-
- _setOption: function( key, value ) {
- if ( key === "icons" ) {
- this.element.find( ".ui-menu-icon" )
- .removeClass( this.options.icons.submenu )
- .addClass( value.submenu );
- }
- if ( key === "disabled" ) {
- this.element
- .toggleClass( "ui-state-disabled", !!value )
- .attr( "aria-disabled", value );
- }
- this._super( key, value );
- },
-
- focus: function( event, item ) {
- var nested, focused;
- this.blur( event, event && event.type === "focus" );
-
- this._scrollIntoView( item );
-
- this.active = item.first();
- focused = this.active.addClass( "ui-state-focus" ).removeClass( "ui-state-active" );
- // Only update aria-activedescendant if there's a role
- // otherwise we assume focus is managed elsewhere
- if ( this.options.role ) {
- this.element.attr( "aria-activedescendant", focused.attr( "id" ) );
- }
-
- // Highlight active parent menu item, if any
- this.active
- .parent()
- .closest( ".ui-menu-item" )
- .addClass( "ui-state-active" );
-
- if ( event && event.type === "keydown" ) {
- this._close();
- } else {
- this.timer = this._delay(function() {
- this._close();
- }, this.delay );
- }
-
- nested = item.children( ".ui-menu" );
- if ( nested.length && event && ( /^mouse/.test( event.type ) ) ) {
- this._startOpening(nested);
- }
- this.activeMenu = item.parent();
-
- this._trigger( "focus", event, { item: item } );
- },
-
- _scrollIntoView: function( item ) {
- var borderTop, paddingTop, offset, scroll, elementHeight, itemHeight;
- if ( this._hasScroll() ) {
- borderTop = parseFloat( $.css( this.activeMenu[0], "borderTopWidth" ) ) || 0;
- paddingTop = parseFloat( $.css( this.activeMenu[0], "paddingTop" ) ) || 0;
- offset = item.offset().top - this.activeMenu.offset().top - borderTop - paddingTop;
- scroll = this.activeMenu.scrollTop();
- elementHeight = this.activeMenu.height();
- itemHeight = item.outerHeight();
-
- if ( offset < 0 ) {
- this.activeMenu.scrollTop( scroll + offset );
- } else if ( offset + itemHeight > elementHeight ) {
- this.activeMenu.scrollTop( scroll + offset - elementHeight + itemHeight );
- }
- }
- },
-
- blur: function( event, fromFocus ) {
- if ( !fromFocus ) {
- clearTimeout( this.timer );
- }
-
- if ( !this.active ) {
- return;
- }
-
- this.active.removeClass( "ui-state-focus" );
- this.active = null;
-
- this._trigger( "blur", event, { item: this.active } );
- },
-
- _startOpening: function( submenu ) {
- clearTimeout( this.timer );
-
- // Don't open if already open fixes a Firefox bug that caused a .5 pixel
- // shift in the submenu position when mousing over the carat icon
- if ( submenu.attr( "aria-hidden" ) !== "true" ) {
- return;
- }
-
- this.timer = this._delay(function() {
- this._close();
- this._open( submenu );
- }, this.delay );
- },
-
- _open: function( submenu ) {
- var position = $.extend({
- of: this.active
- }, this.options.position );
-
- clearTimeout( this.timer );
- this.element.find( ".ui-menu" ).not( submenu.parents( ".ui-menu" ) )
- .hide()
- .attr( "aria-hidden", "true" );
-
- submenu
- .show()
- .removeAttr( "aria-hidden" )
- .attr( "aria-expanded", "true" )
- .position( position );
- },
-
- collapseAll: function( event, all ) {
- clearTimeout( this.timer );
- this.timer = this._delay(function() {
- // If we were passed an event, look for the submenu that contains the event
- var currentMenu = all ? this.element :
- $( event && event.target ).closest( this.element.find( ".ui-menu" ) );
-
- // If we found no valid submenu ancestor, use the main menu to close all sub menus anyway
- if ( !currentMenu.length ) {
- currentMenu = this.element;
- }
-
- this._close( currentMenu );
-
- this.blur( event );
- this.activeMenu = currentMenu;
- }, this.delay );
- },
-
- // With no arguments, closes the currently active menu - if nothing is active
- // it closes all menus. If passed an argument, it will search for menus BELOW
- _close: function( startMenu ) {
- if ( !startMenu ) {
- startMenu = this.active ? this.active.parent() : this.element;
- }
-
- startMenu
- .find( ".ui-menu" )
- .hide()
- .attr( "aria-hidden", "true" )
- .attr( "aria-expanded", "false" )
- .end()
- .find( ".ui-state-active" ).not( ".ui-state-focus" )
- .removeClass( "ui-state-active" );
- },
-
- _closeOnDocumentClick: function( event ) {
- return !$( event.target ).closest( ".ui-menu" ).length;
- },
-
- _isDivider: function( item ) {
-
- // Match hyphen, em dash, en dash
- return !/[^\-\u2014\u2013\s]/.test( item.text() );
- },
-
- collapse: function( event ) {
- var newItem = this.active &&
- this.active.parent().closest( ".ui-menu-item", this.element );
- if ( newItem && newItem.length ) {
- this._close();
- this.focus( event, newItem );
- }
- },
-
- expand: function( event ) {
- var newItem = this.active &&
- this.active
- .children( ".ui-menu " )
- .find( this.options.items )
- .first();
-
- if ( newItem && newItem.length ) {
- this._open( newItem.parent() );
-
- // Delay so Firefox will not hide activedescendant change in expanding submenu from AT
- this._delay(function() {
- this.focus( event, newItem );
- });
- }
- },
-
- next: function( event ) {
- this._move( "next", "first", event );
- },
-
- previous: function( event ) {
- this._move( "prev", "last", event );
- },
-
- isFirstItem: function() {
- return this.active && !this.active.prevAll( ".ui-menu-item" ).length;
- },
-
- isLastItem: function() {
- return this.active && !this.active.nextAll( ".ui-menu-item" ).length;
- },
-
- _move: function( direction, filter, event ) {
- var next;
- if ( this.active ) {
- if ( direction === "first" || direction === "last" ) {
- next = this.active
- [ direction === "first" ? "prevAll" : "nextAll" ]( ".ui-menu-item" )
- .eq( -1 );
- } else {
- next = this.active
- [ direction + "All" ]( ".ui-menu-item" )
- .eq( 0 );
- }
- }
- if ( !next || !next.length || !this.active ) {
- next = this.activeMenu.find( this.options.items )[ filter ]();
- }
-
- this.focus( event, next );
- },
-
- nextPage: function( event ) {
- var item, base, height;
-
- if ( !this.active ) {
- this.next( event );
- return;
- }
- if ( this.isLastItem() ) {
- return;
- }
- if ( this._hasScroll() ) {
- base = this.active.offset().top;
- height = this.element.height();
- this.active.nextAll( ".ui-menu-item" ).each(function() {
- item = $( this );
- return item.offset().top - base - height < 0;
- });
-
- this.focus( event, item );
- } else {
- this.focus( event, this.activeMenu.find( this.options.items )
- [ !this.active ? "first" : "last" ]() );
- }
- },
-
- previousPage: function( event ) {
- var item, base, height;
- if ( !this.active ) {
- this.next( event );
- return;
- }
- if ( this.isFirstItem() ) {
- return;
- }
- if ( this._hasScroll() ) {
- base = this.active.offset().top;
- height = this.element.height();
- this.active.prevAll( ".ui-menu-item" ).each(function() {
- item = $( this );
- return item.offset().top - base + height > 0;
- });
-
- this.focus( event, item );
- } else {
- this.focus( event, this.activeMenu.find( this.options.items ).first() );
- }
- },
-
- _hasScroll: function() {
- return this.element.outerHeight() < this.element.prop( "scrollHeight" );
- },
-
- select: function( event ) {
- // TODO: It should never be possible to not have an active item at this
- // point, but the tests don't trigger mouseenter before click.
- this.active = this.active || $( event.target ).closest( ".ui-menu-item" );
- var ui = { item: this.active };
- if ( !this.active.has( ".ui-menu" ).length ) {
- this.collapseAll( event, true );
- }
- this._trigger( "select", event, ui );
- },
-
- _filterMenuItems: function(character) {
- var escapedCharacter = character.replace( /[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&" ),
- regex = new RegExp( "^" + escapedCharacter, "i" );
-
- return this.activeMenu
- .find( this.options.items )
-
- // Only match on items, not dividers or other content (#10571)
- .filter( ".ui-menu-item" )
- .filter(function() {
- return regex.test( $.trim( $( this ).text() ) );
- });
- }
-});
-
-
-/*!
- * jQuery UI Autocomplete 1.11.4
- * http://jqueryui.com
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- *
- * http://api.jqueryui.com/autocomplete/
- */
-
-
-$.widget( "ui.autocomplete", {
- version: "1.11.4",
- defaultElement: "<input>",
- options: {
- appendTo: null,
- autoFocus: false,
- delay: 300,
- minLength: 1,
- position: {
- my: "left top",
- at: "left bottom",
- collision: "none"
- },
- source: null,
-
- // callbacks
- change: null,
- close: null,
- focus: null,
- open: null,
- response: null,
- search: null,
- select: null
- },
-
- requestIndex: 0,
- pending: 0,
-
- _create: function() {
- // Some browsers only repeat keydown events, not keypress events,
- // so we use the suppressKeyPress flag to determine if we've already
- // handled the keydown event. #7269
- // Unfortunately the code for & in keypress is the same as the up arrow,
- // so we use the suppressKeyPressRepeat flag to avoid handling keypress
- // events when we know the keydown event was used to modify the
- // search term. #7799
- var suppressKeyPress, suppressKeyPressRepeat, suppressInput,
- nodeName = this.element[ 0 ].nodeName.toLowerCase(),
- isTextarea = nodeName === "textarea",
- isInput = nodeName === "input";
-
- this.isMultiLine =
- // Textareas are always multi-line
- isTextarea ? true :
- // Inputs are always single-line, even if inside a contentEditable element
- // IE also treats inputs as contentEditable
- isInput ? false :
- // All other element types are determined by whether or not they're contentEditable
- this.element.prop( "isContentEditable" );
-
- this.valueMethod = this.element[ isTextarea || isInput ? "val" : "text" ];
- this.isNewMenu = true;
-
- this.element
- .addClass( "ui-autocomplete-input" )
- .attr( "autocomplete", "off" );
-
- this._on( this.element, {
- keydown: function( event ) {
- if ( this.element.prop( "readOnly" ) ) {
- suppressKeyPress = true;
- suppressInput = true;
- suppressKeyPressRepeat = true;
- return;
- }
-
- suppressKeyPress = false;
- suppressInput = false;
- suppressKeyPressRepeat = false;
- var keyCode = $.ui.keyCode;
- switch ( event.keyCode ) {
- case keyCode.PAGE_UP:
- suppressKeyPress = true;
- this._move( "previousPage", event );
- break;
- case keyCode.PAGE_DOWN:
- suppressKeyPress = true;
- this._move( "nextPage", event );
- break;
- case keyCode.UP:
- suppressKeyPress = true;
- this._keyEvent( "previous", event );
- break;
- case keyCode.DOWN:
- suppressKeyPress = true;
- this._keyEvent( "next", event );
- break;
- case keyCode.ENTER:
- // when menu is open and has focus
- if ( this.menu.active ) {
- // #6055 - Opera still allows the keypress to occur
- // which causes forms to submit
- suppressKeyPress = true;
- event.preventDefault();
- this.menu.select( event );
- }
- break;
- case keyCode.TAB:
- if ( this.menu.active ) {
- this.menu.select( event );
- }
- break;
- case keyCode.ESCAPE:
- if ( this.menu.element.is( ":visible" ) ) {
- if ( !this.isMultiLine ) {
- this._value( this.term );
- }
- this.close( event );
- // Different browsers have different default behavior for escape
- // Single press can mean undo or clear
- // Double press in IE means clear the whole form
- event.preventDefault();
- }
- break;
- default:
- suppressKeyPressRepeat = true;
- // search timeout should be triggered before the input value is changed
- this._searchTimeout( event );
- break;
- }
- },
- keypress: function( event ) {
- if ( suppressKeyPress ) {
- suppressKeyPress = false;
- if ( !this.isMultiLine || this.menu.element.is( ":visible" ) ) {
- event.preventDefault();
- }
- return;
- }
- if ( suppressKeyPressRepeat ) {
- return;
- }
-
- // replicate some key handlers to allow them to repeat in Firefox and Opera
- var keyCode = $.ui.keyCode;
- switch ( event.keyCode ) {
- case keyCode.PAGE_UP:
- this._move( "previousPage", event );
- break;
- case keyCode.PAGE_DOWN:
- this._move( "nextPage", event );
- break;
- case keyCode.UP:
- this._keyEvent( "previous", event );
- break;
- case keyCode.DOWN:
- this._keyEvent( "next", event );
- break;
- }
- },
- input: function( event ) {
- if ( suppressInput ) {
- suppressInput = false;
- event.preventDefault();
- return;
- }
- this._searchTimeout( event );
- },
- focus: function() {
- this.selectedItem = null;
- this.previous = this._value();
- },
- blur: function( event ) {
- if ( this.cancelBlur ) {
- delete this.cancelBlur;
- return;
- }
-
- clearTimeout( this.searching );
- this.close( event );
- this._change( event );
- }
- });
-
- this._initSource();
- this.menu = $( "<ul>" )
- .addClass( "ui-autocomplete ui-front" )
- .appendTo( this._appendTo() )
- .menu({
- // disable ARIA support, the live region takes care of that
- role: null
- })
- .hide()
- .menu( "instance" );
-
- this._on( this.menu.element, {
- mousedown: function( event ) {
- // prevent moving focus out of the text field
- event.preventDefault();
-
- // IE doesn't prevent moving focus even with event.preventDefault()
- // so we set a flag to know when we should ignore the blur event
- this.cancelBlur = true;
- this._delay(function() {
- delete this.cancelBlur;
- });
-
- // clicking on the scrollbar causes focus to shift to the body
- // but we can't detect a mouseup or a click immediately afterward
- // so we have to track the next mousedown and close the menu if
- // the user clicks somewhere outside of the autocomplete
- var menuElement = this.menu.element[ 0 ];
- if ( !$( event.target ).closest( ".ui-menu-item" ).length ) {
- this._delay(function() {
- var that = this;
- this.document.one( "mousedown", function( event ) {
- if ( event.target !== that.element[ 0 ] &&
- event.target !== menuElement &&
- !$.contains( menuElement, event.target ) ) {
- that.close();
- }
- });
- });
- }
- },
- menufocus: function( event, ui ) {
- var label, item;
- // support: Firefox
- // Prevent accidental activation of menu items in Firefox (#7024 #9118)
- if ( this.isNewMenu ) {
- this.isNewMenu = false;
- if ( event.originalEvent && /^mouse/.test( event.originalEvent.type ) ) {
- this.menu.blur();
-
- this.document.one( "mousemove", function() {
- $( event.target ).trigger( event.originalEvent );
- });
-
- return;
- }
- }
-
- item = ui.item.data( "ui-autocomplete-item" );
- if ( false !== this._trigger( "focus", event, { item: item } ) ) {
- // use value to match what will end up in the input, if it was a key event
- if ( event.originalEvent && /^key/.test( event.originalEvent.type ) ) {
- this._value( item.value );
- }
- }
-
- // Announce the value in the liveRegion
- label = ui.item.attr( "aria-label" ) || item.value;
- if ( label && $.trim( label ).length ) {
- this.liveRegion.children().hide();
- $( "<div>" ).text( label ).appendTo( this.liveRegion );
- }
- },
- menuselect: function( event, ui ) {
- var item = ui.item.data( "ui-autocomplete-item" ),
- previous = this.previous;
-
- // only trigger when focus was lost (click on menu)
- if ( this.element[ 0 ] !== this.document[ 0 ].activeElement ) {
- this.element.focus();
- this.previous = previous;
- // #6109 - IE triggers two focus events and the second
- // is asynchronous, so we need to reset the previous
- // term synchronously and asynchronously :-(
- this._delay(function() {
- this.previous = previous;
- this.selectedItem = item;
- });
- }
-
- if ( false !== this._trigger( "select", event, { item: item } ) ) {
- this._value( item.value );
- }
- // reset the term after the select event
- // this allows custom select handling to work properly
- this.term = this._value();
-
- this.close( event );
- this.selectedItem = item;
- }
- });
-
- this.liveRegion = $( "<span>", {
- role: "status",
- "aria-live": "assertive",
- "aria-relevant": "additions"
- })
- .addClass( "ui-helper-hidden-accessible" )
- .appendTo( this.document[ 0 ].body );
-
- // turning off autocomplete prevents the browser from remembering the
- // value when navigating through history, so we re-enable autocomplete
- // if the page is unloaded before the widget is destroyed. #7790
- this._on( this.window, {
- beforeunload: function() {
- this.element.removeAttr( "autocomplete" );
- }
- });
- },
-
- _destroy: function() {
- clearTimeout( this.searching );
- this.element
- .removeClass( "ui-autocomplete-input" )
- .removeAttr( "autocomplete" );
- this.menu.element.remove();
- this.liveRegion.remove();
- },
-
- _setOption: function( key, value ) {
- this._super( key, value );
- if ( key === "source" ) {
- this._initSource();
- }
- if ( key === "appendTo" ) {
- this.menu.element.appendTo( this._appendTo() );
- }
- if ( key === "disabled" && value && this.xhr ) {
- this.xhr.abort();
- }
- },
-
- _appendTo: function() {
- var element = this.options.appendTo;
-
- if ( element ) {
- element = element.jquery || element.nodeType ?
- $( element ) :
- this.document.find( element ).eq( 0 );
- }
-
- if ( !element || !element[ 0 ] ) {
- element = this.element.closest( ".ui-front" );
- }
-
- if ( !element.length ) {
- element = this.document[ 0 ].body;
- }
-
- return element;
- },
-
- _initSource: function() {
- var array, url,
- that = this;
- if ( $.isArray( this.options.source ) ) {
- array = this.options.source;
- this.source = function( request, response ) {
- response( $.ui.autocomplete.filter( array, request.term ) );
- };
- } else if ( typeof this.options.source === "string" ) {
- url = this.options.source;
- this.source = function( request, response ) {
- if ( that.xhr ) {
- that.xhr.abort();
- }
- that.xhr = $.ajax({
- url: url,
- data: request,
- dataType: "json",
- success: function( data ) {
- response( data );
- },
- error: function() {
- response([]);
- }
- });
- };
- } else {
- this.source = this.options.source;
- }
- },
-
- _searchTimeout: function( event ) {
- clearTimeout( this.searching );
- this.searching = this._delay(function() {
-
- // Search if the value has changed, or if the user retypes the same value (see #7434)
- var equalValues = this.term === this._value(),
- menuVisible = this.menu.element.is( ":visible" ),
- modifierKey = event.altKey || event.ctrlKey || event.metaKey || event.shiftKey;
-
- if ( !equalValues || ( equalValues && !menuVisible && !modifierKey ) ) {
- this.selectedItem = null;
- this.search( null, event );
- }
- }, this.options.delay );
- },
-
- search: function( value, event ) {
- value = value != null ? value : this._value();
-
- // always save the actual value, not the one passed as an argument
- this.term = this._value();
-
- if ( value.length < this.options.minLength ) {
- return this.close( event );
- }
-
- if ( this._trigger( "search", event ) === false ) {
- return;
- }
-
- return this._search( value );
- },
-
- _search: function( value ) {
- this.pending++;
- this.element.addClass( "ui-autocomplete-loading" );
- this.cancelSearch = false;
-
- this.source( { term: value }, this._response() );
- },
-
- _response: function() {
- var index = ++this.requestIndex;
-
- return $.proxy(function( content ) {
- if ( index === this.requestIndex ) {
- this.__response( content );
- }
-
- this.pending--;
- if ( !this.pending ) {
- this.element.removeClass( "ui-autocomplete-loading" );
- }
- }, this );
- },
-
- __response: function( content ) {
- if ( content ) {
- content = this._normalize( content );
- }
- this._trigger( "response", null, { content: content } );
- if ( !this.options.disabled && content && content.length && !this.cancelSearch ) {
- this._suggest( content );
- this._trigger( "open" );
- } else {
- // use ._close() instead of .close() so we don't cancel future searches
- this._close();
- }
- },
-
- close: function( event ) {
- this.cancelSearch = true;
- this._close( event );
- },
-
- _close: function( event ) {
- if ( this.menu.element.is( ":visible" ) ) {
- this.menu.element.hide();
- this.menu.blur();
- this.isNewMenu = true;
- this._trigger( "close", event );
- }
- },
-
- _change: function( event ) {
- if ( this.previous !== this._value() ) {
- this._trigger( "change", event, { item: this.selectedItem } );
- }
- },
-
- _normalize: function( items ) {
- // assume all items have the right format when the first item is complete
- if ( items.length && items[ 0 ].label && items[ 0 ].value ) {
- return items;
- }
- return $.map( items, function( item ) {
- if ( typeof item === "string" ) {
- return {
- label: item,
- value: item
- };
- }
- return $.extend( {}, item, {
- label: item.label || item.value,
- value: item.value || item.label
- });
- });
- },
-
- _suggest: function( items ) {
- var ul = this.menu.element.empty();
- this._renderMenu( ul, items );
- this.isNewMenu = true;
- this.menu.refresh();
-
- // size and position menu
- ul.show();
- this._resizeMenu();
- ul.position( $.extend({
- of: this.element
- }, this.options.position ) );
-
- if ( this.options.autoFocus ) {
- this.menu.next();
- }
- },
-
- _resizeMenu: function() {
- var ul = this.menu.element;
- ul.outerWidth( Math.max(
- // Firefox wraps long text (possibly a rounding bug)
- // so we add 1px to avoid the wrapping (#7513)
- ul.width( "" ).outerWidth() + 1,
- this.element.outerWidth()
- ) );
- },
-
- _renderMenu: function( ul, items ) {
- var that = this;
- $.each( items, function( index, item ) {
- that._renderItemData( ul, item );
- });
- },
-
- _renderItemData: function( ul, item ) {
- return this._renderItem( ul, item ).data( "ui-autocomplete-item", item );
- },
-
- _renderItem: function( ul, item ) {
- return $( "<li>" ).text( item.label ).appendTo( ul );
- },
-
- _move: function( direction, event ) {
- if ( !this.menu.element.is( ":visible" ) ) {
- this.search( null, event );
- return;
- }
- if ( this.menu.isFirstItem() && /^previous/.test( direction ) ||
- this.menu.isLastItem() && /^next/.test( direction ) ) {
-
- if ( !this.isMultiLine ) {
- this._value( this.term );
- }
-
- this.menu.blur();
- return;
- }
- this.menu[ direction ]( event );
- },
-
- widget: function() {
- return this.menu.element;
- },
-
- _value: function() {
- return this.valueMethod.apply( this.element, arguments );
- },
-
- _keyEvent: function( keyEvent, event ) {
- if ( !this.isMultiLine || this.menu.element.is( ":visible" ) ) {
- this._move( keyEvent, event );
-
- // prevents moving cursor to beginning/end of the text field in some browsers
- event.preventDefault();
- }
- }
-});
-
-$.extend( $.ui.autocomplete, {
- escapeRegex: function( value ) {
- return value.replace( /[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&" );
- },
- filter: function( array, term ) {
- var matcher = new RegExp( $.ui.autocomplete.escapeRegex( term ), "i" );
- return $.grep( array, function( value ) {
- return matcher.test( value.label || value.value || value );
- });
- }
-});
-
-// live region extension, adding a `messages` option
-// NOTE: This is an experimental API. We are still investigating
-// a full solution for string manipulation and internationalization.
-$.widget( "ui.autocomplete", $.ui.autocomplete, {
- options: {
- messages: {
- noResults: "No search results.",
- results: function( amount ) {
- return amount + ( amount > 1 ? " results are" : " result is" ) +
- " available, use up and down arrow keys to navigate.";
- }
- }
- },
-
- __response: function( content ) {
- var message;
- this._superApply( arguments );
- if ( this.options.disabled || this.cancelSearch ) {
- return;
- }
- if ( content && content.length ) {
- message = this.options.messages.results( content.length );
- } else {
- message = this.options.messages.noResults;
- }
- this.liveRegion.children().hide();
- $( "<div>" ).text( message ).appendTo( this.liveRegion );
- }
-});
-
-var autocomplete = $.ui.autocomplete;
-
-
-/*!
- * jQuery UI Datepicker 1.11.4
- * http://jqueryui.com
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- *
- * http://api.jqueryui.com/datepicker/
- */
-
-
-$.extend($.ui, { datepicker: { version: "1.11.4" } });
-
-var datepicker_instActive;
-
-function datepicker_getZindex( elem ) {
- var position, value;
- while ( elem.length && elem[ 0 ] !== document ) {
- // Ignore z-index if position is set to a value where z-index is ignored by the browser
- // This makes behavior of this function consistent across browsers
- // WebKit always returns auto if the element is positioned
- position = elem.css( "position" );
- if ( position === "absolute" || position === "relative" || position === "fixed" ) {
- // IE returns 0 when zIndex is not specified
- // other browsers return a string
- // we ignore the case of nested elements with an explicit value of 0
- // <div style="z-index: -10;"><div style="z-index: 0;"></div></div>
- value = parseInt( elem.css( "zIndex" ), 10 );
- if ( !isNaN( value ) && value !== 0 ) {
- return value;
- }
- }
- elem = elem.parent();
- }
-
- return 0;
-}
-/* Date picker manager.
- Use the singleton instance of this class, $.datepicker, to interact with the date picker.
- Settings for (groups of) date pickers are maintained in an instance object,
- allowing multiple different settings on the same page. */
-
-function Datepicker() {
- this._curInst = null; // The current instance in use
- this._keyEvent = false; // If the last event was a key event
- this._disabledInputs = []; // List of date picker inputs that have been disabled
- this._datepickerShowing = false; // True if the popup picker is showing , false if not
- this._inDialog = false; // True if showing within a "dialog", false if not
- this._mainDivId = "ui-datepicker-div"; // The ID of the main datepicker division
- this._inlineClass = "ui-datepicker-inline"; // The name of the inline marker class
- this._appendClass = "ui-datepicker-append"; // The name of the append marker class
- this._triggerClass = "ui-datepicker-trigger"; // The name of the trigger marker class
- this._dialogClass = "ui-datepicker-dialog"; // The name of the dialog marker class
- this._disableClass = "ui-datepicker-disabled"; // The name of the disabled covering marker class
- this._unselectableClass = "ui-datepicker-unselectable"; // The name of the unselectable cell marker class
- this._currentClass = "ui-datepicker-current-day"; // The name of the current day marker class
- this._dayOverClass = "ui-datepicker-days-cell-over"; // The name of the day hover marker class
- this.regional = []; // Available regional settings, indexed by language code
- this.regional[""] = { // Default regional settings
- closeText: "Done", // Display text for close link
- prevText: "Prev", // Display text for previous month link
- nextText: "Next", // Display text for next month link
- currentText: "Today", // Display text for current month link
- monthNames: ["January","February","March","April","May","June",
- "July","August","September","October","November","December"], // Names of months for drop-down and formatting
- monthNamesShort: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"], // For formatting
- dayNames: ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"], // For formatting
- dayNamesShort: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"], // For formatting
- dayNamesMin: ["Su","Mo","Tu","We","Th","Fr","Sa"], // Column headings for days starting at Sunday
- weekHeader: "Wk", // Column header for week of the year
- dateFormat: "mm/dd/yy", // See format options on parseDate
- firstDay: 0, // The first day of the week, Sun = 0, Mon = 1, ...
- weekendDays: [0, 6], //List of days considered as weekend, Sun = 0, Mon = 1, ...
- isRTL: false, // True if right-to-left language, false if left-to-right
- showMonthAfterYear: false, // True if the year select precedes month, false for month then year
- yearSuffix: "" // Additional text to append to the year in the month headers
- };
- this._defaults = { // Global defaults for all the date picker instances
- showOn: "focus", // "focus" for popup on focus,
- // "button" for trigger button, or "both" for either
- showAnim: "fadeIn", // Name of jQuery animation for popup
- showOptions: {}, // Options for enhanced animations
- defaultDate: null, // Used when field is blank: actual date,
- // +/-number for offset from today, null for today
- appendText: "", // Display text following the input box, e.g. showing the format
- buttonText: "...", // Text for trigger button
- buttonImage: "", // URL for trigger button image
- buttonImageOnly: false, // True if the image appears alone, false if it appears on a button
- hideIfNoPrevNext: false, // True to hide next/previous month links
- // if not applicable, false to just disable them
- navigationAsDateFormat: false, // True if date formatting applied to prev/today/next links
- gotoCurrent: false, // True if today link goes back to current selection instead
- changeMonth: false, // True if month can be selected directly, false if only prev/next
- changeYear: false, // True if year can be selected directly, false if only prev/next
- yearRange: "c-10:c+10", // Range of years to display in drop-down,
- // either relative to today's year (-nn:+nn), relative to currently displayed year
- // (c-nn:c+nn), absolute (nnnn:nnnn), or a combination of the above (nnnn:-n)
- showOtherMonths: false, // True to show dates in other months, false to leave blank
- selectOtherMonths: false, // True to allow selection of dates in other months, false for unselectable
- showWeek: false, // True to show week of the year, false to not show it
- calculateWeek: this.iso8601Week, // How to calculate the week of the year,
- // takes a Date and returns the number of the week for it
- shortYearCutoff: "+10", // Short year values < this are in the current century,
- // > this are in the previous century,
- // string value starting with "+" for current year + value
- minDate: null, // The earliest selectable date, or null for no limit
- maxDate: null, // The latest selectable date, or null for no limit
- duration: "fast", // Duration of display/closure
- beforeShowDay: null, // Function that takes a date and returns an array with
- // [0] = true if selectable, false if not, [1] = custom CSS class name(s) or "",
- // [2] = cell title (optional), e.g. $.datepicker.noWeekends
- beforeShow: null, // Function that takes an input field and
- // returns a set of custom settings for the date picker
- onSelect: null, // Define a callback function when a date is selected
- onChangeMonthYear: null, // Define a callback function when the month or year is changed
- onClose: null, // Define a callback function when the datepicker is closed
- numberOfMonths: 1, // Number of months to show at a time
- showCurrentAtPos: 0, // The position in multipe months at which to show the current month (starting at 0)
- stepMonths: 1, // Number of months to step back/forward
- stepBigMonths: 12, // Number of months to step back/forward for the big links
- altField: "", // Selector for an alternate field to store selected dates into
- altFormat: "", // The date format to use for the alternate field
- constrainInput: true, // The input is constrained by the current date format
- showButtonPanel: false, // True to show button panel, false to not show it
- autoSize: false, // True to size the input for the date format, false to leave as is
- disabled: false // The initial disabled state
- };
- $.extend(this._defaults, this.regional[""]);
- this.regional.en = $.extend( true, {}, this.regional[ "" ]);
- this.regional[ "en-US" ] = $.extend( true, {}, this.regional.en );
- this.dpDiv = datepicker_bindHover($("<div id='" + this._mainDivId + "' class='ui-datepicker ui-widget ui-widget-content ui-helper-clearfix ui-corner-all'></div>"));
-}
-
-$.extend(Datepicker.prototype, {
- /* Class name added to elements to indicate already configured with a date picker. */
- markerClassName: "hasDatepicker",
-
- //Keep track of the maximum number of rows displayed (see #7043)
- maxRows: 4,
-
- // TODO rename to "widget" when switching to widget factory
- _widgetDatepicker: function() {
- return this.dpDiv;
- },
-
- /* Override the default settings for all instances of the date picker.
- * @param settings object - the new settings to use as defaults (anonymous object)
- * @return the manager object
- */
- setDefaults: function(settings) {
- datepicker_extendRemove(this._defaults, settings || {});
- return this;
- },
-
- /* Attach the date picker to a jQuery selection.
- * @param target element - the target input field or division or span
- * @param settings object - the new settings to use for this date picker instance (anonymous)
- */
- _attachDatepicker: function(target, settings) {
- var nodeName, inline, inst;
- nodeName = target.nodeName.toLowerCase();
- inline = (nodeName === "div" || nodeName === "span");
- if (!target.id) {
- this.uuid += 1;
- target.id = "dp" + this.uuid;
- }
- inst = this._newInst($(target), inline);
- inst.settings = $.extend({}, settings || {});
- if (nodeName === "input") {
- this._connectDatepicker(target, inst);
- } else if (inline) {
- this._inlineDatepicker(target, inst);
- }
- },
-
- /* Create a new instance object. */
- _newInst: function(target, inline) {
- var id = target[0].id.replace(/([^A-Za-z0-9_\-])/g, "\\\\$1"); // escape jQuery meta chars
- return {id: id, input: target, // associated target
- selectedDay: 0, selectedMonth: 0, selectedYear: 0, // current selection
- drawMonth: 0, drawYear: 0, // month being drawn
- inline: inline, // is datepicker inline or not
- dpDiv: (!inline ? this.dpDiv : // presentation div
- datepicker_bindHover($("<div class='" + this._inlineClass + " ui-datepicker ui-widget ui-widget-content ui-helper-clearfix ui-corner-all'></div>")))};
- },
-
- /* Attach the date picker to an input field. */
- _connectDatepicker: function(target, inst) {
- var input = $(target);
- inst.append = $([]);
- inst.trigger = $([]);
- if (input.hasClass(this.markerClassName)) {
- return;
- }
- this._attachments(input, inst);
- input.addClass(this.markerClassName).keydown(this._doKeyDown).
- keypress(this._doKeyPress).keyup(this._doKeyUp);
- this._autoSize(inst);
- $.data(target, "datepicker", inst);
- //If disabled option is true, disable the datepicker once it has been attached to the input (see ticket #5665)
- if( inst.settings.disabled ) {
- this._disableDatepicker( target );
- }
- },
-
- /* Make attachments based on settings. */
- _attachments: function(input, inst) {
- var showOn, buttonText, buttonImage,
- appendText = this._get(inst, "appendText"),
- isRTL = this._get(inst, "isRTL");
-
- if (inst.append) {
- inst.append.remove();
- }
- if (appendText) {
- inst.append = $("<span class='" + this._appendClass + "'>" + appendText + "</span>");
- input[isRTL ? "before" : "after"](inst.append);
- }
-
- input.unbind("focus", this._showDatepicker);
-
- if (inst.trigger) {
- inst.trigger.remove();
- }
-
- showOn = this._get(inst, "showOn");
- if (showOn === "focus" || showOn === "both") { // pop-up date picker when in the marked field
- input.focus(this._showDatepicker);
- }
- if (showOn === "button" || showOn === "both") { // pop-up date picker when button clicked
- buttonText = this._get(inst, "buttonText");
- buttonImage = this._get(inst, "buttonImage");
- inst.trigger = $(this._get(inst, "buttonImageOnly") ?
- $("<img/>").addClass(this._triggerClass).
- attr({ src: buttonImage, alt: buttonText, title: buttonText }) :
- $("<button type='button'></button>").addClass(this._triggerClass).
- html(!buttonImage ? buttonText : $("<img/>").attr(
- { src:buttonImage, alt:buttonText, title:buttonText })));
- input[isRTL ? "before" : "after"](inst.trigger);
- inst.trigger.click(function() {
- if ($.datepicker._datepickerShowing && $.datepicker._lastInput === input[0]) {
- $.datepicker._hideDatepicker();
- } else if ($.datepicker._datepickerShowing && $.datepicker._lastInput !== input[0]) {
- $.datepicker._hideDatepicker();
- $.datepicker._showDatepicker(input[0]);
- } else {
- $.datepicker._showDatepicker(input[0]);
- }
- return false;
- });
- }
- },
-
- /* Apply the maximum length for the date format. */
- _autoSize: function(inst) {
- if (this._get(inst, "autoSize") && !inst.inline) {
- var findMax, max, maxI, i,
- date = new Date(2009, 12 - 1, 20), // Ensure double digits
- dateFormat = this._get(inst, "dateFormat");
-
- if (dateFormat.match(/[DM]/)) {
- findMax = function(names) {
- max = 0;
- maxI = 0;
- for (i = 0; i < names.length; i++) {
- if (names[i].length > max) {
- max = names[i].length;
- maxI = i;
- }
- }
- return maxI;
- };
- date.setMonth(findMax(this._get(inst, (dateFormat.match(/MM/) ?
- "monthNames" : "monthNamesShort"))));
- date.setDate(findMax(this._get(inst, (dateFormat.match(/DD/) ?
- "dayNames" : "dayNamesShort"))) + 20 - date.getDay());
- }
- inst.input.attr("size", this._formatDate(inst, date).length);
- }
- },
-
- /* Attach an inline date picker to a div. */
- _inlineDatepicker: function(target, inst) {
- var divSpan = $(target);
- if (divSpan.hasClass(this.markerClassName)) {
- return;
- }
- divSpan.addClass(this.markerClassName).append(inst.dpDiv);
- $.data(target, "datepicker", inst);
- this._setDate(inst, this._getDefaultDate(inst), true);
- this._updateDatepicker(inst);
- this._updateAlternate(inst);
- //If disabled option is true, disable the datepicker before showing it (see ticket #5665)
- if( inst.settings.disabled ) {
- this._disableDatepicker( target );
- }
- // Set display:block in place of inst.dpDiv.show() which won't work on disconnected elements
- // http://bugs.jqueryui.com/ticket/7552 - A Datepicker created on a detached div has zero height
- inst.dpDiv.css( "display", "block" );
- },
-
- /* Pop-up the date picker in a "dialog" box.
- * @param input element - ignored
- * @param date string or Date - the initial date to display
- * @param onSelect function - the function to call when a date is selected
- * @param settings object - update the dialog date picker instance's settings (anonymous object)
- * @param pos int[2] - coordinates for the dialog's position within the screen or
- * event - with x/y coordinates or
- * leave empty for default (screen centre)
- * @return the manager object
- */
- _dialogDatepicker: function(input, date, onSelect, settings, pos) {
- var id, browserWidth, browserHeight, scrollX, scrollY,
- inst = this._dialogInst; // internal instance
-
- if (!inst) {
- this.uuid += 1;
- id = "dp" + this.uuid;
- this._dialogInput = $("<input type='text' id='" + id +
- "' style='position: absolute; top: -100px; width: 0px;'/>");
- this._dialogInput.keydown(this._doKeyDown);
- $("body").append(this._dialogInput);
- inst = this._dialogInst = this._newInst(this._dialogInput, false);
- inst.settings = {};
- $.data(this._dialogInput[0], "datepicker", inst);
- }
- datepicker_extendRemove(inst.settings, settings || {});
- date = (date && date.constructor === Date ? this._formatDate(inst, date) : date);
- this._dialogInput.val(date);
-
- this._pos = (pos ? (pos.length ? pos : [pos.pageX, pos.pageY]) : null);
- if (!this._pos) {
- browserWidth = document.documentElement.clientWidth;
- browserHeight = document.documentElement.clientHeight;
- scrollX = document.documentElement.scrollLeft || document.body.scrollLeft;
- scrollY = document.documentElement.scrollTop || document.body.scrollTop;
- this._pos = // should use actual width/height below
- [(browserWidth / 2) - 100 + scrollX, (browserHeight / 2) - 150 + scrollY];
- }
-
- // move input on screen for focus, but hidden behind dialog
- this._dialogInput.css("left", (this._pos[0] + 20) + "px").css("top", this._pos[1] + "px");
- inst.settings.onSelect = onSelect;
- this._inDialog = true;
- this.dpDiv.addClass(this._dialogClass);
- this._showDatepicker(this._dialogInput[0]);
- if ($.blockUI) {
- $.blockUI(this.dpDiv);
- }
- $.data(this._dialogInput[0], "datepicker", inst);
- return this;
- },
-
- /* Detach a datepicker from its control.
- * @param target element - the target input field or division or span
- */
- _destroyDatepicker: function(target) {
- var nodeName,
- $target = $(target),
- inst = $.data(target, "datepicker");
-
- if (!$target.hasClass(this.markerClassName)) {
- return;
- }
-
- nodeName = target.nodeName.toLowerCase();
- $.removeData(target, "datepicker");
- if (nodeName === "input") {
- inst.append.remove();
- inst.trigger.remove();
- $target.removeClass(this.markerClassName).
- unbind("focus", this._showDatepicker).
- unbind("keydown", this._doKeyDown).
- unbind("keypress", this._doKeyPress).
- unbind("keyup", this._doKeyUp);
- } else if (nodeName === "div" || nodeName === "span") {
- $target.removeClass(this.markerClassName).empty();
- }
-
- if ( datepicker_instActive === inst ) {
- datepicker_instActive = null;
- }
- },
-
- /* Enable the date picker to a jQuery selection.
- * @param target element - the target input field or division or span
- */
- _enableDatepicker: function(target) {
- var nodeName, inline,
- $target = $(target),
- inst = $.data(target, "datepicker");
-
- if (!$target.hasClass(this.markerClassName)) {
- return;
- }
-
- nodeName = target.nodeName.toLowerCase();
- if (nodeName === "input") {
- target.disabled = false;
- inst.trigger.filter("button").
- each(function() { this.disabled = false; }).end().
- filter("img").css({opacity: "1.0", cursor: ""});
- } else if (nodeName === "div" || nodeName === "span") {
- inline = $target.children("." + this._inlineClass);
- inline.children().removeClass("ui-state-disabled");
- inline.find("select.ui-datepicker-month, select.ui-datepicker-year").
- prop("disabled", false);
- }
- this._disabledInputs = $.map(this._disabledInputs,
- function(value) { return (value === target ? null : value); }); // delete entry
- },
-
- /* Disable the date picker to a jQuery selection.
- * @param target element - the target input field or division or span
- */
- _disableDatepicker: function(target) {
- var nodeName, inline,
- $target = $(target),
- inst = $.data(target, "datepicker");
-
- if (!$target.hasClass(this.markerClassName)) {
- return;
- }
-
- nodeName = target.nodeName.toLowerCase();
- if (nodeName === "input") {
- target.disabled = true;
- inst.trigger.filter("button").
- each(function() { this.disabled = true; }).end().
- filter("img").css({opacity: "0.5", cursor: "default"});
- } else if (nodeName === "div" || nodeName === "span") {
- inline = $target.children("." + this._inlineClass);
- inline.children().addClass("ui-state-disabled");
- inline.find("select.ui-datepicker-month, select.ui-datepicker-year").
- prop("disabled", true);
- }
- this._disabledInputs = $.map(this._disabledInputs,
- function(value) { return (value === target ? null : value); }); // delete entry
- this._disabledInputs[this._disabledInputs.length] = target;
- },
-
- /* Is the first field in a jQuery collection disabled as a datepicker?
- * @param target element - the target input field or division or span
- * @return boolean - true if disabled, false if enabled
- */
- _isDisabledDatepicker: function(target) {
- if (!target) {
- return false;
- }
- for (var i = 0; i < this._disabledInputs.length; i++) {
- if (this._disabledInputs[i] === target) {
- return true;
- }
- }
- return false;
- },
-
- /* Retrieve the instance data for the target control.
- * @param target element - the target input field or division or span
- * @return object - the associated instance data
- * @throws error if a jQuery problem getting data
- */
- _getInst: function(target) {
- try {
- return $.data(target, "datepicker");
- }
- catch (err) {
- throw "Missing instance data for this datepicker";
- }
- },
-
- /* Update or retrieve the settings for a date picker attached to an input field or division.
- * @param target element - the target input field or division or span
- * @param name object - the new settings to update or
- * string - the name of the setting to change or retrieve,
- * when retrieving also "all" for all instance settings or
- * "defaults" for all global defaults
- * @param value any - the new value for the setting
- * (omit if above is an object or to retrieve a value)
- */
- _optionDatepicker: function(target, name, value) {
- var settings, date, minDate, maxDate,
- inst = this._getInst(target);
-
- if (arguments.length === 2 && typeof name === "string") {
- return (name === "defaults" ? $.extend({}, $.datepicker._defaults) :
- (inst ? (name === "all" ? $.extend({}, inst.settings) :
- this._get(inst, name)) : null));
- }
-
- settings = name || {};
- if (typeof name === "string") {
- settings = {};
- settings[name] = value;
- }
-
- if (inst) {
- if (this._curInst === inst) {
- this._hideDatepicker();
- }
-
- date = this._getDateDatepicker(target, true);
- minDate = this._getMinMaxDate(inst, "min");
- maxDate = this._getMinMaxDate(inst, "max");
- datepicker_extendRemove(inst.settings, settings);
- // reformat the old minDate/maxDate values if dateFormat changes and a new minDate/maxDate isn't provided
- if (minDate !== null && settings.dateFormat !== undefined && settings.minDate === undefined) {
- inst.settings.minDate = this._formatDate(inst, minDate);
- }
- if (maxDate !== null && settings.dateFormat !== undefined && settings.maxDate === undefined) {
- inst.settings.maxDate = this._formatDate(inst, maxDate);
- }
- if ( "disabled" in settings ) {
- if ( settings.disabled ) {
- this._disableDatepicker(target);
- } else {
- this._enableDatepicker(target);
- }
- }
- this._attachments($(target), inst);
- this._autoSize(inst);
- this._setDate(inst, date);
- this._updateAlternate(inst);
- this._updateDatepicker(inst);
- }
- },
-
- // change method deprecated
- _changeDatepicker: function(target, name, value) {
- this._optionDatepicker(target, name, value);
- },
-
- /* Redraw the date picker attached to an input field or division.
- * @param target element - the target input field or division or span
- */
- _refreshDatepicker: function(target) {
- var inst = this._getInst(target);
- if (inst) {
- this._updateDatepicker(inst);
- }
- },
-
- /* Set the dates for a jQuery selection.
- * @param target element - the target input field or division or span
- * @param date Date - the new date
- */
- _setDateDatepicker: function(target, date) {
- var inst = this._getInst(target);
- if (inst) {
- this._setDate(inst, date);
- this._updateDatepicker(inst);
- this._updateAlternate(inst);
- }
- },
-
- /* Get the date(s) for the first entry in a jQuery selection.
- * @param target element - the target input field or division or span
- * @param noDefault boolean - true if no default date is to be used
- * @return Date - the current date
- */
- _getDateDatepicker: function(target, noDefault) {
- var inst = this._getInst(target);
- if (inst && !inst.inline) {
- this._setDateFromField(inst, noDefault);
- }
- return (inst ? this._getDate(inst) : null);
- },
-
- /* Handle keystrokes. */
- _doKeyDown: function(event) {
- var onSelect, dateStr, sel,
- inst = $.datepicker._getInst(event.target),
- handled = true,
- isRTL = inst.dpDiv.is(".ui-datepicker-rtl");
-
- inst._keyEvent = true;
- if ($.datepicker._datepickerShowing) {
- switch (event.keyCode) {
- case 9: $.datepicker._hideDatepicker();
- handled = false;
- break; // hide on tab out
- case 13: sel = $("td." + $.datepicker._dayOverClass + ":not(." +
- $.datepicker._currentClass + ")", inst.dpDiv);
- if (sel[0]) {
- $.datepicker._selectDay(event.target, inst.selectedMonth, inst.selectedYear, sel[0]);
- }
-
- onSelect = $.datepicker._get(inst, "onSelect");
- if (onSelect) {
- dateStr = $.datepicker._formatDate(inst);
-
- // trigger custom callback
- onSelect.apply((inst.input ? inst.input[0] : null), [dateStr, inst]);
- } else {
- $.datepicker._hideDatepicker();
- }
-
- return false; // don't submit the form
- case 27: $.datepicker._hideDatepicker();
- break; // hide on escape
- case 33: $.datepicker._adjustDate(event.target, (event.ctrlKey ?
- -$.datepicker._get(inst, "stepBigMonths") :
- -$.datepicker._get(inst, "stepMonths")), "M");
- break; // previous month/year on page up/+ ctrl
- case 34: $.datepicker._adjustDate(event.target, (event.ctrlKey ?
- +$.datepicker._get(inst, "stepBigMonths") :
- +$.datepicker._get(inst, "stepMonths")), "M");
- break; // next month/year on page down/+ ctrl
- case 35: if (event.ctrlKey || event.metaKey) {
- $.datepicker._clearDate(event.target);
- }
- handled = event.ctrlKey || event.metaKey;
- break; // clear on ctrl or command +end
- case 36: if (event.ctrlKey || event.metaKey) {
- $.datepicker._gotoToday(event.target);
- }
- handled = event.ctrlKey || event.metaKey;
- break; // current on ctrl or command +home
- case 37: if (event.ctrlKey || event.metaKey) {
- $.datepicker._adjustDate(event.target, (isRTL ? +1 : -1), "D");
- }
- handled = event.ctrlKey || event.metaKey;
- // -1 day on ctrl or command +left
- if (event.originalEvent.altKey) {
- $.datepicker._adjustDate(event.target, (event.ctrlKey ?
- -$.datepicker._get(inst, "stepBigMonths") :
- -$.datepicker._get(inst, "stepMonths")), "M");
- }
- // next month/year on alt +left on Mac
- break;
- case 38: if (event.ctrlKey || event.metaKey) {
- $.datepicker._adjustDate(event.target, -7, "D");
- }
- handled = event.ctrlKey || event.metaKey;
- break; // -1 week on ctrl or command +up
- case 39: if (event.ctrlKey || event.metaKey) {
- $.datepicker._adjustDate(event.target, (isRTL ? -1 : +1), "D");
- }
- handled = event.ctrlKey || event.metaKey;
- // +1 day on ctrl or command +right
- if (event.originalEvent.altKey) {
- $.datepicker._adjustDate(event.target, (event.ctrlKey ?
- +$.datepicker._get(inst, "stepBigMonths") :
- +$.datepicker._get(inst, "stepMonths")), "M");
- }
- // next month/year on alt +right
- break;
- case 40: if (event.ctrlKey || event.metaKey) {
- $.datepicker._adjustDate(event.target, +7, "D");
- }
- handled = event.ctrlKey || event.metaKey;
- break; // +1 week on ctrl or command +down
- default: handled = false;
- }
- } else if (event.keyCode === 36 && event.ctrlKey) { // display the date picker on ctrl+home
- $.datepicker._showDatepicker(this);
- } else {
- handled = false;
- }
-
- if (handled) {
- event.preventDefault();
- event.stopPropagation();
- }
- },
-
- /* Filter entered characters - based on date format. */
- _doKeyPress: function(event) {
- var chars, chr,
- inst = $.datepicker._getInst(event.target);
-
- if ($.datepicker._get(inst, "constrainInput")) {
- chars = $.datepicker._possibleChars($.datepicker._get(inst, "dateFormat"));
- chr = String.fromCharCode(event.charCode == null ? event.keyCode : event.charCode);
- return event.ctrlKey || event.metaKey || (chr < " " || !chars || chars.indexOf(chr) > -1);
- }
- },
-
- /* Synchronise manual entry and field/alternate field. */
- _doKeyUp: function(event) {
- var date,
- inst = $.datepicker._getInst(event.target);
-
- if (inst.input.val() !== inst.lastVal) {
- try {
- date = $.datepicker.parseDate($.datepicker._get(inst, "dateFormat"),
- (inst.input ? inst.input.val() : null),
- $.datepicker._getFormatConfig(inst));
-
- if (date) { // only if valid
- $.datepicker._setDateFromField(inst);
- $.datepicker._updateAlternate(inst);
- $.datepicker._updateDatepicker(inst);
- }
- }
- catch (err) {
- }
- }
- return true;
- },
-
- /* Pop-up the date picker for a given input field.
- * If false returned from beforeShow event handler do not show.
- * @param input element - the input field attached to the date picker or
- * event - if triggered by focus
- */
- _showDatepicker: function(input) {
- input = input.target || input;
- if (input.nodeName.toLowerCase() !== "input") { // find from button/image trigger
- input = $("input", input.parentNode)[0];
- }
-
- if ($.datepicker._isDisabledDatepicker(input) || $.datepicker._lastInput === input) { // already here
- return;
- }
-
- var inst, beforeShow, beforeShowSettings, isFixed,
- offset, showAnim, duration;
-
- inst = $.datepicker._getInst(input);
- if ($.datepicker._curInst && $.datepicker._curInst !== inst) {
- $.datepicker._curInst.dpDiv.stop(true, true);
- if ( inst && $.datepicker._datepickerShowing ) {
- $.datepicker._hideDatepicker( $.datepicker._curInst.input[0] );
- }
- }
-
- beforeShow = $.datepicker._get(inst, "beforeShow");
- beforeShowSettings = beforeShow ? beforeShow.apply(input, [input, inst]) : {};
- if(beforeShowSettings === false){
- return;
- }
- datepicker_extendRemove(inst.settings, beforeShowSettings);
-
- inst.lastVal = null;
- $.datepicker._lastInput = input;
- $.datepicker._setDateFromField(inst);
-
- if ($.datepicker._inDialog) { // hide cursor
- input.value = "";
- }
- if (!$.datepicker._pos) { // position below input
- $.datepicker._pos = $.datepicker._findPos(input);
- $.datepicker._pos[1] += input.offsetHeight; // add the height
- }
-
- isFixed = false;
- $(input).parents().each(function() {
- isFixed |= $(this).css("position") === "fixed";
- return !isFixed;
- });
-
- offset = {left: $.datepicker._pos[0], top: $.datepicker._pos[1]};
- $.datepicker._pos = null;
- //to avoid flashes on Firefox
- inst.dpDiv.empty();
- // determine sizing offscreen
- inst.dpDiv.css({position: "absolute", display: "block", top: "-1000px"});
- $.datepicker._updateDatepicker(inst);
- // fix width for dynamic number of date pickers
- // and adjust position before showing
- offset = $.datepicker._checkOffset(inst, offset, isFixed);
- inst.dpDiv.css({position: ($.datepicker._inDialog && $.blockUI ?
- "static" : (isFixed ? "fixed" : "absolute")), display: "none",
- left: offset.left + "px", top: offset.top + "px"});
-
- if (!inst.inline) {
- showAnim = $.datepicker._get(inst, "showAnim");
- duration = $.datepicker._get(inst, "duration");
- inst.dpDiv.css( "z-index", datepicker_getZindex( $( input ) ) + 1 );
- $.datepicker._datepickerShowing = true;
-
- if ( $.effects && $.effects.effect[ showAnim ] ) {
- inst.dpDiv.show(showAnim, $.datepicker._get(inst, "showOptions"), duration);
- } else {
- inst.dpDiv[showAnim || "show"](showAnim ? duration : null);
- }
-
- if ( $.datepicker._shouldFocusInput( inst ) ) {
- inst.input.focus();
- }
-
- $.datepicker._curInst = inst;
- }
- },
-
- /* Generate the date picker content. */
- _updateDatepicker: function(inst) {
- this.maxRows = 4; //Reset the max number of rows being displayed (see #7043)
- datepicker_instActive = inst; // for delegate hover events
- inst.dpDiv.empty().append(this._generateHTML(inst));
- this._attachHandlers(inst);
-
- var origyearshtml,
- numMonths = this._getNumberOfMonths(inst),
- cols = numMonths[1],
- width = 17,
- activeCell = inst.dpDiv.find( "." + this._dayOverClass + " a" );
-
- if ( activeCell.length > 0 ) {
- datepicker_handleMouseover.apply( activeCell.get( 0 ) );
- }
-
- inst.dpDiv.removeClass("ui-datepicker-multi-2 ui-datepicker-multi-3 ui-datepicker-multi-4").width("");
- if (cols > 1) {
- inst.dpDiv.addClass("ui-datepicker-multi-" + cols).css("width", (width * cols) + "em");
- }
- inst.dpDiv[(numMonths[0] !== 1 || numMonths[1] !== 1 ? "add" : "remove") +
- "Class"]("ui-datepicker-multi");
- inst.dpDiv[(this._get(inst, "isRTL") ? "add" : "remove") +
- "Class"]("ui-datepicker-rtl");
-
- if (inst === $.datepicker._curInst && $.datepicker._datepickerShowing && $.datepicker._shouldFocusInput( inst ) ) {
- inst.input.focus();
- }
-
- // deffered render of the years select (to avoid flashes on Firefox)
- if( inst.yearshtml ){
- origyearshtml = inst.yearshtml;
- setTimeout(function(){
- //assure that inst.yearshtml didn't change.
- if( origyearshtml === inst.yearshtml && inst.yearshtml ){
- inst.dpDiv.find("select.ui-datepicker-year:first").replaceWith(inst.yearshtml);
- }
- origyearshtml = inst.yearshtml = null;
- }, 0);
- }
-
- var afterUpdate = this._get(inst, "afterUpdate");
- if(afterUpdate)
- afterUpdate.apply((inst.input ? inst.input[0] : null), [inst]);
- },
-
- // #6694 - don't focus the input if it's already focused
- // this breaks the change event in IE
- // Support: IE and jQuery <1.9
- _shouldFocusInput: function( inst ) {
- return inst.input && inst.input.is( ":visible" ) && !inst.input.is( ":disabled" ) && !inst.input.is( ":focus" );
- },
-
- /* Check positioning to remain on screen. */
- _checkOffset: function(inst, offset, isFixed) {
- var dpWidth = inst.dpDiv.outerWidth(),
- dpHeight = inst.dpDiv.outerHeight(),
- inputWidth = inst.input ? inst.input.outerWidth() : 0,
- inputHeight = inst.input ? inst.input.outerHeight() : 0,
- viewWidth = document.documentElement.clientWidth + (isFixed ? 0 : $(document).scrollLeft()),
- viewHeight = document.documentElement.clientHeight + (isFixed ? 0 : $(document).scrollTop());
-
- offset.left -= (this._get(inst, "isRTL") ? (dpWidth - inputWidth) : 0);
- offset.left -= (isFixed && offset.left === inst.input.offset().left) ? $(document).scrollLeft() : 0;
- offset.top -= (isFixed && offset.top === (inst.input.offset().top + inputHeight)) ? $(document).scrollTop() : 0;
-
- // now check if datepicker is showing outside window viewport - move to a better place if so.
- offset.left -= Math.min(offset.left, (offset.left + dpWidth > viewWidth && viewWidth > dpWidth) ?
- Math.abs(offset.left + dpWidth - viewWidth) : 0);
- offset.top -= Math.min(offset.top, (offset.top + dpHeight > viewHeight && viewHeight > dpHeight) ?
- Math.abs(dpHeight + inputHeight) : 0);
-
- return offset;
- },
-
- /* Find an object's position on the screen. */
- _findPos: function(obj) {
- var position,
- inst = this._getInst(obj),
- isRTL = this._get(inst, "isRTL");
-
- while (obj && (obj.type === "hidden" || obj.nodeType !== 1 || $.expr.filters.hidden(obj))) {
- obj = obj[isRTL ? "previousSibling" : "nextSibling"];
- }
-
- position = $(obj).offset();
- return [position.left, position.top];
- },
-
- /* Hide the date picker from view.
- * @param input element - the input field attached to the date picker
- */
- _hideDatepicker: function(input) {
- var showAnim, duration, postProcess, onClose,
- inst = this._curInst;
-
- if (!inst || (input && inst !== $.data(input, "datepicker"))) {
- return;
- }
-
- if (this._datepickerShowing) {
- showAnim = this._get(inst, "showAnim");
- duration = this._get(inst, "duration");
- postProcess = function() {
- $.datepicker._tidyDialog(inst);
- };
-
- // DEPRECATED: after BC for 1.8.x $.effects[ showAnim ] is not needed
- if ( $.effects && ( $.effects.effect[ showAnim ] || $.effects[ showAnim ] ) ) {
- inst.dpDiv.hide(showAnim, $.datepicker._get(inst, "showOptions"), duration, postProcess);
- } else {
- inst.dpDiv[(showAnim === "slideDown" ? "slideUp" :
- (showAnim === "fadeIn" ? "fadeOut" : "hide"))]((showAnim ? duration : null), postProcess);
- }
-
- if (!showAnim) {
- postProcess();
- }
- this._datepickerShowing = false;
-
- onClose = this._get(inst, "onClose");
- if (onClose) {
- onClose.apply((inst.input ? inst.input[0] : null), [(inst.input ? inst.input.val() : ""), inst]);
- }
-
- this._lastInput = null;
- if (this._inDialog) {
- this._dialogInput.css({ position: "absolute", left: "0", top: "-100px" });
- if ($.blockUI) {
- $.unblockUI();
- $("body").append(this.dpDiv);
- }
- }
- this._inDialog = false;
- }
- },
-
- /* Tidy up after a dialog display. */
- _tidyDialog: function(inst) {
- inst.dpDiv.removeClass(this._dialogClass).unbind(".ui-datepicker-calendar");
- },
-
- /* Close date picker if clicked elsewhere. */
- _checkExternalClick: function(event) {
- if (!$.datepicker._curInst) {
- return;
- }
-
- var $target = $(event.target),
- inst = $.datepicker._getInst($target[0]);
-
- if ( ( ( $target[0].id !== $.datepicker._mainDivId &&
- $target.parents("#" + $.datepicker._mainDivId).length === 0 &&
- !$target.hasClass($.datepicker.markerClassName) &&
- !$target.closest("." + $.datepicker._triggerClass).length &&
- $.datepicker._datepickerShowing && !($.datepicker._inDialog && $.blockUI) ) ) ||
- ( $target.hasClass($.datepicker.markerClassName) && $.datepicker._curInst !== inst ) ) {
- $.datepicker._hideDatepicker();
- }
- },
-
- /* Adjust one of the date sub-fields. */
- _adjustDate: function(id, offset, period) {
- var target = $(id),
- inst = this._getInst(target[0]);
-
- if (this._isDisabledDatepicker(target[0])) {
- return;
- }
- this._adjustInstDate(inst, offset +
- (period === "M" ? this._get(inst, "showCurrentAtPos") : 0), // undo positioning
- period);
- this._updateDatepicker(inst);
- },
-
- /* Action for current link. */
- _gotoToday: function(id) {
- var date,
- target = $(id),
- inst = this._getInst(target[0]);
-
- if (this._get(inst, "gotoCurrent") && inst.currentDay) {
- inst.selectedDay = inst.currentDay;
- inst.drawMonth = inst.selectedMonth = inst.currentMonth;
- inst.drawYear = inst.selectedYear = inst.currentYear;
- } else {
- date = new Date();
- inst.selectedDay = date.getDate();
- inst.drawMonth = inst.selectedMonth = date.getMonth();
- inst.drawYear = inst.selectedYear = date.getFullYear();
- }
- this._notifyChange(inst);
- this._adjustDate(target);
- },
-
- /* Action for selecting a new month/year. */
- _selectMonthYear: function(id, select, period) {
- var target = $(id),
- inst = this._getInst(target[0]);
-
- inst["selected" + (period === "M" ? "Month" : "Year")] =
- inst["draw" + (period === "M" ? "Month" : "Year")] =
- parseInt(select.options[select.selectedIndex].value,10);
-
- this._notifyChange(inst);
- this._adjustDate(target);
- },
-
- /* Action for selecting a day. */
- _selectDay: function(id, month, year, td) {
- var inst,
- target = $(id);
-
- if ($(td).hasClass(this._unselectableClass) || this._isDisabledDatepicker(target[0])) {
- return;
- }
-
- inst = this._getInst(target[0]);
- inst.selectedDay = inst.currentDay = $("a", td).html();
- inst.selectedMonth = inst.currentMonth = month;
- inst.selectedYear = inst.currentYear = year;
- this._selectDate(id, this._formatDate(inst,
- inst.currentDay, inst.currentMonth, inst.currentYear));
- },
-
- /* Erase the input field and hide the date picker. */
- _clearDate: function(id) {
- var target = $(id);
- this._selectDate(target, "");
- },
-
- /* Update the input field with the selected date. */
- _selectDate: function(id, dateStr) {
- var onSelect,
- target = $(id),
- inst = this._getInst(target[0]);
-
- dateStr = (dateStr != null ? dateStr : this._formatDate(inst));
- if (inst.input) {
- inst.input.val(dateStr);
- }
- this._updateAlternate(inst);
-
- onSelect = this._get(inst, "onSelect");
- if (onSelect) {
- onSelect.apply((inst.input ? inst.input[0] : null), [dateStr, inst]); // trigger custom callback
- } else if (inst.input) {
- inst.input.trigger("change"); // fire the change event
- }
-
- if (inst.inline){
- this._updateDatepicker(inst);
- } else {
- this._hideDatepicker();
- this._lastInput = inst.input[0];
- if (typeof(inst.input[0]) !== "object") {
- inst.input.focus(); // restore focus
- }
- this._lastInput = null;
- }
- },
-
- /* Update any alternate field to synchronise with the main field. */
- _updateAlternate: function(inst) {
- var altFormat, date, dateStr,
- altField = this._get(inst, "altField");
-
- if (altField) { // update alternate field too
- altFormat = this._get(inst, "altFormat") || this._get(inst, "dateFormat");
- date = this._getDate(inst);
- dateStr = this.formatDate(altFormat, date, this._getFormatConfig(inst));
- $(altField).each(function() { $(this).val(dateStr); });
- }
- },
-
- /* Set as beforeShowDay function to prevent selection of weekends.
- * @param date Date - the date to customise
- * @return [boolean, string] - is this date selectable?, what is its CSS class?
- */
- noWeekends: function(date) {
- var day = date.getDay();
- return [(day > 0 && day < 6), ""];
- },
-
- /* Set as calculateWeek to determine the week of the year based on the ISO 8601 definition.
- * @param date Date - the date to get the week for
- * @return number - the number of the week within the year that contains this date
- */
- iso8601Week: function(date) {
- var time,
- checkDate = new Date(date.getTime());
-
- // Find Thursday of this week starting on Monday
- checkDate.setDate(checkDate.getDate() + 4 - (checkDate.getDay() || 7));
-
- time = checkDate.getTime();
- checkDate.setMonth(0); // Compare with Jan 1
- checkDate.setDate(1);
- return Math.floor(Math.round((time - checkDate) / 86400000) / 7) + 1;
- },
-
- /* Parse a string value into a date object.
- * See formatDate below for the possible formats.
- *
- * @param format string - the expected format of the date
- * @param value string - the date in the above format
- * @param settings Object - attributes include:
- * shortYearCutoff number - the cutoff year for determining the century (optional)
- * dayNamesShort string[7] - abbreviated names of the days from Sunday (optional)
- * dayNames string[7] - names of the days from Sunday (optional)
- * monthNamesShort string[12] - abbreviated names of the months (optional)
- * monthNames string[12] - names of the months (optional)
- * @return Date - the extracted date value or null if value is blank
- */
- parseDate: function (format, value, settings) {
- if (format == null || value == null) {
- throw "Invalid arguments";
- }
-
- value = (typeof value === "object" ? value.toString() : value + "");
- if (value === "") {
- return null;
- }
-
- var iFormat, dim, extra,
- iValue = 0,
- shortYearCutoffTemp = (settings ? settings.shortYearCutoff : null) || this._defaults.shortYearCutoff,
- shortYearCutoff = (typeof shortYearCutoffTemp !== "string" ? shortYearCutoffTemp :
- new Date().getFullYear() % 100 + parseInt(shortYearCutoffTemp, 10)),
- dayNamesShort = (settings ? settings.dayNamesShort : null) || this._defaults.dayNamesShort,
- dayNames = (settings ? settings.dayNames : null) || this._defaults.dayNames,
- monthNamesShort = (settings ? settings.monthNamesShort : null) || this._defaults.monthNamesShort,
- monthNames = (settings ? settings.monthNames : null) || this._defaults.monthNames,
- year = -1,
- month = -1,
- day = -1,
- doy = -1,
- literal = false,
- date,
- // Check whether a format character is doubled
- lookAhead = function(match) {
- var matches = (iFormat + 1 < format.length && format.charAt(iFormat + 1) === match);
- if (matches) {
- iFormat++;
- }
- return matches;
- },
- // Extract a number from the string value
- getNumber = function(match) {
- var isDoubled = lookAhead(match),
- size = (match === "@" ? 14 : (match === "!" ? 20 :
- (match === "y" && isDoubled ? 4 : (match === "o" ? 3 : 2)))),
- minSize = (match === "y" ? size : 1),
- digits = new RegExp("^\\d{" + minSize + "," + size + "}"),
- num = value.substring(iValue).match(digits);
- if (!num) {
- throw "Missing number at position " + iValue;
- }
- iValue += num[0].length;
- return parseInt(num[0], 10);
- },
- // Extract a name from the string value and convert to an index
- getName = function(match, shortNames, longNames) {
- var index = -1,
- names = $.map(lookAhead(match) ? longNames : shortNames, function (v, k) {
- return [ [k, v] ];
- }).sort(function (a, b) {
- return -(a[1].length - b[1].length);
- });
-
- $.each(names, function (i, pair) {
- var name = pair[1];
- if (value.substr(iValue, name.length).toLowerCase() === name.toLowerCase()) {
- index = pair[0];
- iValue += name.length;
- return false;
- }
- });
- if (index !== -1) {
- return index + 1;
- } else {
- throw "Unknown name at position " + iValue;
- }
- },
- // Confirm that a literal character matches the string value
- checkLiteral = function() {
- if (value.charAt(iValue) !== format.charAt(iFormat)) {
- throw "Unexpected literal at position " + iValue;
- }
- iValue++;
- };
-
- for (iFormat = 0; iFormat < format.length; iFormat++) {
- if (literal) {
- if (format.charAt(iFormat) === "'" && !lookAhead("'")) {
- literal = false;
- } else {
- checkLiteral();
- }
- } else {
- switch (format.charAt(iFormat)) {
- case "d":
- day = getNumber("d");
- break;
- case "D":
- getName("D", dayNamesShort, dayNames);
- break;
- case "o":
- doy = getNumber("o");
- break;
- case "m":
- month = getNumber("m");
- break;
- case "M":
- month = getName("M", monthNamesShort, monthNames);
- break;
- case "y":
- year = getNumber("y");
- break;
- case "@":
- date = new Date(getNumber("@"));
- year = date.getFullYear();
- month = date.getMonth() + 1;
- day = date.getDate();
- break;
- case "!":
- date = new Date((getNumber("!") - this._ticksTo1970) / 10000);
- year = date.getFullYear();
- month = date.getMonth() + 1;
- day = date.getDate();
- break;
- case "'":
- if (lookAhead("'")){
- checkLiteral();
- } else {
- literal = true;
- }
- break;
- default:
- checkLiteral();
- }
- }
- }
-
- if (iValue < value.length){
- extra = value.substr(iValue);
- if (!/^\s+/.test(extra)) {
- throw "Extra/unparsed characters found in date: " + extra;
- }
- }
-
- if (year === -1) {
- year = new Date().getFullYear();
- } else if (year < 100) {
- year += new Date().getFullYear() - new Date().getFullYear() % 100 +
- (year <= shortYearCutoff ? 0 : -100);
- }
-
- if (doy > -1) {
- month = 1;
- day = doy;
- do {
- dim = this._getDaysInMonth(year, month - 1);
- if (day <= dim) {
- break;
- }
- month++;
- day -= dim;
- } while (true);
- }
-
- date = this._daylightSavingAdjust(new Date(year, month - 1, day));
- if (date.getFullYear() !== year || date.getMonth() + 1 !== month || date.getDate() !== day) {
- throw "Invalid date"; // E.g. 31/02/00
- }
- return date;
- },
-
- /* Standard date formats. */
- ATOM: "yy-mm-dd", // RFC 3339 (ISO 8601)
- COOKIE: "D, dd M yy",
- ISO_8601: "yy-mm-dd",
- RFC_822: "D, d M y",
- RFC_850: "DD, dd-M-y",
- RFC_1036: "D, d M y",
- RFC_1123: "D, d M yy",
- RFC_2822: "D, d M yy",
- RSS: "D, d M y", // RFC 822
- TICKS: "!",
- TIMESTAMP: "@",
- W3C: "yy-mm-dd", // ISO 8601
-
- _ticksTo1970: (((1970 - 1) * 365 + Math.floor(1970 / 4) - Math.floor(1970 / 100) +
- Math.floor(1970 / 400)) * 24 * 60 * 60 * 10000000),
-
- /* Format a date object into a string value.
- * The format can be combinations of the following:
- * d - day of month (no leading zero)
- * dd - day of month (two digit)
- * o - day of year (no leading zeros)
- * oo - day of year (three digit)
- * D - day name short
- * DD - day name long
- * m - month of year (no leading zero)
- * mm - month of year (two digit)
- * M - month name short
- * MM - month name long
- * y - year (two digit)
- * yy - year (four digit)
- * @ - Unix timestamp (ms since 01/01/1970)
- * ! - Windows ticks (100ns since 01/01/0001)
- * "..." - literal text
- * '' - single quote
- *
- * @param format string - the desired format of the date
- * @param date Date - the date value to format
- * @param settings Object - attributes include:
- * dayNamesShort string[7] - abbreviated names of the days from Sunday (optional)
- * dayNames string[7] - names of the days from Sunday (optional)
- * monthNamesShort string[12] - abbreviated names of the months (optional)
- * monthNames string[12] - names of the months (optional)
- * @return string - the date in the above format
- */
- formatDate: function (format, date, settings) {
- if (!date) {
- return "";
- }
-
- var iFormat,
- dayNamesShort = (settings ? settings.dayNamesShort : null) || this._defaults.dayNamesShort,
- dayNames = (settings ? settings.dayNames : null) || this._defaults.dayNames,
- monthNamesShort = (settings ? settings.monthNamesShort : null) || this._defaults.monthNamesShort,
- monthNames = (settings ? settings.monthNames : null) || this._defaults.monthNames,
- // Check whether a format character is doubled
- lookAhead = function(match) {
- var matches = (iFormat + 1 < format.length && format.charAt(iFormat + 1) === match);
- if (matches) {
- iFormat++;
- }
- return matches;
- },
- // Format a number, with leading zero if necessary
- formatNumber = function(match, value, len) {
- var num = "" + value;
- if (lookAhead(match)) {
- while (num.length < len) {
- num = "0" + num;
- }
- }
- return num;
- },
- // Format a name, short or long as requested
- formatName = function(match, value, shortNames, longNames) {
- return (lookAhead(match) ? longNames[value] : shortNames[value]);
- },
- output = "",
- literal = false;
-
- if (date) {
- for (iFormat = 0; iFormat < format.length; iFormat++) {
- if (literal) {
- if (format.charAt(iFormat) === "'" && !lookAhead("'")) {
- literal = false;
- } else {
- output += format.charAt(iFormat);
- }
- } else {
- switch (format.charAt(iFormat)) {
- case "d":
- output += formatNumber("d", date.getDate(), 2);
- break;
- case "D":
- output += formatName("D", date.getDay(), dayNamesShort, dayNames);
- break;
- case "o":
- output += formatNumber("o",
- Math.round((new Date(date.getFullYear(), date.getMonth(), date.getDate()).getTime() - new Date(date.getFullYear(), 0, 0).getTime()) / 86400000), 3);
- break;
- case "m":
- output += formatNumber("m", date.getMonth() + 1, 2);
- break;
- case "M":
- output += formatName("M", date.getMonth(), monthNamesShort, monthNames);
- break;
- case "y":
- output += (lookAhead("y") ? date.getFullYear() :
- (date.getYear() % 100 < 10 ? "0" : "") + date.getYear() % 100);
- break;
- case "@":
- output += date.getTime();
- break;
- case "!":
- output += date.getTime() * 10000 + this._ticksTo1970;
- break;
- case "'":
- if (lookAhead("'")) {
- output += "'";
- } else {
- literal = true;
- }
- break;
- default:
- output += format.charAt(iFormat);
- }
- }
- }
- }
- return output;
- },
-
- /* Extract all possible characters from the date format. */
- _possibleChars: function (format) {
- var iFormat,
- chars = "",
- literal = false,
- // Check whether a format character is doubled
- lookAhead = function(match) {
- var matches = (iFormat + 1 < format.length && format.charAt(iFormat + 1) === match);
- if (matches) {
- iFormat++;
- }
- return matches;
- };
-
- for (iFormat = 0; iFormat < format.length; iFormat++) {
- if (literal) {
- if (format.charAt(iFormat) === "'" && !lookAhead("'")) {
- literal = false;
- } else {
- chars += format.charAt(iFormat);
- }
- } else {
- switch (format.charAt(iFormat)) {
- case "d": case "m": case "y": case "@":
- chars += "0123456789";
- break;
- case "D": case "M":
- return null; // Accept anything
- case "'":
- if (lookAhead("'")) {
- chars += "'";
- } else {
- literal = true;
- }
- break;
- default:
- chars += format.charAt(iFormat);
- }
- }
- }
- return chars;
- },
-
- /* Get a setting value, defaulting if necessary. */
- _get: function(inst, name) {
- return inst.settings[name] !== undefined ?
- inst.settings[name] : this._defaults[name];
- },
-
- /* Parse existing date and initialise date picker. */
- _setDateFromField: function(inst, noDefault) {
- if (inst.input.val() === inst.lastVal) {
- return;
- }
-
- var dateFormat = this._get(inst, "dateFormat"),
- dates = inst.lastVal = inst.input ? inst.input.val() : null,
- defaultDate = this._getDefaultDate(inst),
- date = defaultDate,
- settings = this._getFormatConfig(inst);
-
- try {
- date = this.parseDate(dateFormat, dates, settings) || defaultDate;
- } catch (event) {
- dates = (noDefault ? "" : dates);
- }
- inst.selectedDay = date.getDate();
- inst.drawMonth = inst.selectedMonth = date.getMonth();
- inst.drawYear = inst.selectedYear = date.getFullYear();
- inst.currentDay = (dates ? date.getDate() : 0);
- inst.currentMonth = (dates ? date.getMonth() : 0);
- inst.currentYear = (dates ? date.getFullYear() : 0);
- this._adjustInstDate(inst);
- },
-
- /* Retrieve the default date shown on opening. */
- _getDefaultDate: function(inst) {
- return this._restrictMinMax(inst,
- this._determineDate(inst, this._get(inst, "defaultDate"), new Date()));
- },
-
- /* A date may be specified as an exact value or a relative one. */
- _determineDate: function(inst, date, defaultDate) {
- var offsetNumeric = function(offset) {
- var date = new Date();
- date.setDate(date.getDate() + offset);
- return date;
- },
- offsetString = function(offset) {
- try {
- return $.datepicker.parseDate($.datepicker._get(inst, "dateFormat"),
- offset, $.datepicker._getFormatConfig(inst));
- }
- catch (e) {
- // Ignore
- }
-
- var date = (offset.toLowerCase().match(/^c/) ?
- $.datepicker._getDate(inst) : null) || new Date(),
- year = date.getFullYear(),
- month = date.getMonth(),
- day = date.getDate(),
- pattern = /([+\-]?[0-9]+)\s*(d|D|w|W|m|M|y|Y)?/g,
- matches = pattern.exec(offset);
-
- while (matches) {
- switch (matches[2] || "d") {
- case "d" : case "D" :
- day += parseInt(matches[1],10); break;
- case "w" : case "W" :
- day += parseInt(matches[1],10) * 7; break;
- case "m" : case "M" :
- month += parseInt(matches[1],10);
- day = Math.min(day, $.datepicker._getDaysInMonth(year, month));
- break;
- case "y": case "Y" :
- year += parseInt(matches[1],10);
- day = Math.min(day, $.datepicker._getDaysInMonth(year, month));
- break;
- }
- matches = pattern.exec(offset);
- }
- return new Date(year, month, day);
- },
- newDate = (date == null || date === "" ? defaultDate : (typeof date === "string" ? offsetString(date) :
- (typeof date === "number" ? (isNaN(date) ? defaultDate : offsetNumeric(date)) : new Date(date.getTime()))));
-
- newDate = (newDate && newDate.toString() === "Invalid Date" ? defaultDate : newDate);
- if (newDate) {
- newDate.setHours(0);
- newDate.setMinutes(0);
- newDate.setSeconds(0);
- newDate.setMilliseconds(0);
- }
- return this._daylightSavingAdjust(newDate);
- },
-
- /* Handle switch to/from daylight saving.
- * Hours may be non-zero on daylight saving cut-over:
- * > 12 when midnight changeover, but then cannot generate
- * midnight datetime, so jump to 1AM, otherwise reset.
- * @param date (Date) the date to check
- * @return (Date) the corrected date
- */
- _daylightSavingAdjust: function(date) {
- if (!date) {
- return null;
- }
- date.setHours(date.getHours() > 12 ? date.getHours() + 2 : 0);
- return date;
- },
-
- /* Set the date(s) directly. */
- _setDate: function(inst, date, noChange) {
- var clear = !date,
- origMonth = inst.selectedMonth,
- origYear = inst.selectedYear,
- newDate = this._restrictMinMax(inst, this._determineDate(inst, date, new Date()));
-
- inst.selectedDay = inst.currentDay = newDate.getDate();
- inst.drawMonth = inst.selectedMonth = inst.currentMonth = newDate.getMonth();
- inst.drawYear = inst.selectedYear = inst.currentYear = newDate.getFullYear();
- if ((origMonth !== inst.selectedMonth || origYear !== inst.selectedYear) && !noChange) {
- this._notifyChange(inst);
- }
- this._adjustInstDate(inst);
- if (inst.input) {
- inst.input.val(clear ? "" : this._formatDate(inst));
- }
- },
-
- /* Retrieve the date(s) directly. */
- _getDate: function(inst) {
- var startDate = (!inst.currentYear || (inst.input && inst.input.val() === "") ? null :
- this._daylightSavingAdjust(new Date(
- inst.currentYear, inst.currentMonth, inst.currentDay)));
- return startDate;
- },
-
- /* Attach the onxxx handlers. These are declared statically so
- * they work with static code transformers like Caja.
- */
- _attachHandlers: function(inst) {
- var stepMonths = this._get(inst, "stepMonths"),
- id = "#" + inst.id.replace( /\\\\/g, "\\" );
- inst.dpDiv.find("[data-handler]").map(function () {
- var handler = {
- prev: function () {
- $.datepicker._adjustDate(id, -stepMonths, "M");
- },
- next: function () {
- $.datepicker._adjustDate(id, +stepMonths, "M");
- },
- hide: function () {
- $.datepicker._hideDatepicker();
- },
- today: function () {
- $.datepicker._gotoToday(id);
- },
- selectDay: function () {
- $.datepicker._selectDay(id, +this.getAttribute("data-month"), +this.getAttribute("data-year"), this);
- return false;
- },
- selectMonth: function () {
- $.datepicker._selectMonthYear(id, this, "M");
- return false;
- },
- selectYear: function () {
- $.datepicker._selectMonthYear(id, this, "Y");
- return false;
- }
- };
- $(this).bind(this.getAttribute("data-event"), handler[this.getAttribute("data-handler")]);
- });
- },
-
- /* Generate the HTML for the current state of the date picker. */
- _generateHTML: function(inst) {
- var maxDraw, prevText, prev, nextText, next, currentText, gotoDate,
- controls, buttonPanel, firstDay, weekendDays, showWeek, dayNames, dayNamesMin,
- monthNames, monthNamesShort, beforeShowDay, showOtherMonths,
- selectOtherMonths, defaultDate, html, dow, row, group, col, selectedDate,
- cornerClass, calender, thead, day, daysInMonth, leadDays, curRows, numRows,
- printDate, dRow, tbody, daySettings, otherMonth, unselectable,
- tempDate = new Date(),
- today = this._daylightSavingAdjust(
- new Date(tempDate.getFullYear(), tempDate.getMonth(), tempDate.getDate())), // clear time
- isRTL = this._get(inst, "isRTL"),
- showButtonPanel = this._get(inst, "showButtonPanel"),
- hideIfNoPrevNext = this._get(inst, "hideIfNoPrevNext"),
- navigationAsDateFormat = this._get(inst, "navigationAsDateFormat"),
- numMonths = this._getNumberOfMonths(inst),
- showCurrentAtPos = this._get(inst, "showCurrentAtPos"),
- stepMonths = this._get(inst, "stepMonths"),
- isMultiMonth = (numMonths[0] !== 1 || numMonths[1] !== 1),
- currentDate = this._daylightSavingAdjust((!inst.currentDay ? new Date(9999, 9, 9) :
- new Date(inst.currentYear, inst.currentMonth, inst.currentDay))),
- minDate = this._getMinMaxDate(inst, "min"),
- maxDate = this._getMinMaxDate(inst, "max"),
- drawMonth = inst.drawMonth - showCurrentAtPos,
- drawYear = inst.drawYear;
-
- if (drawMonth < 0) {
- drawMonth += 12;
- drawYear--;
- }
- if (maxDate) {
- maxDraw = this._daylightSavingAdjust(new Date(maxDate.getFullYear(),
- maxDate.getMonth() - (numMonths[0] * numMonths[1]) + 1, maxDate.getDate()));
- maxDraw = (minDate && maxDraw < minDate ? minDate : maxDraw);
- while (this._daylightSavingAdjust(new Date(drawYear, drawMonth, 1)) > maxDraw) {
- drawMonth--;
- if (drawMonth < 0) {
- drawMonth = 11;
- drawYear--;
- }
- }
- }
- inst.drawMonth = drawMonth;
- inst.drawYear = drawYear;
-
- prevText = this._get(inst, "prevText");
- prevText = (!navigationAsDateFormat ? prevText : this.formatDate(prevText,
- this._daylightSavingAdjust(new Date(drawYear, drawMonth - stepMonths, 1)),
- this._getFormatConfig(inst)));
-
- prev = (this._canAdjustMonth(inst, -1, drawYear, drawMonth) ?
- "<a class='ui-datepicker-prev ui-corner-all' data-handler='prev' data-event='click'" +
- " title='" + prevText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "e" : "w") + "'>" + prevText + "</span></a>" :
- (hideIfNoPrevNext ? "" : "<a class='ui-datepicker-prev ui-corner-all ui-state-disabled' title='"+ prevText +"'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "e" : "w") + "'>" + prevText + "</span></a>"));
-
- nextText = this._get(inst, "nextText");
- nextText = (!navigationAsDateFormat ? nextText : this.formatDate(nextText,
- this._daylightSavingAdjust(new Date(drawYear, drawMonth + stepMonths, 1)),
- this._getFormatConfig(inst)));
-
- next = (this._canAdjustMonth(inst, +1, drawYear, drawMonth) ?
- "<a class='ui-datepicker-next ui-corner-all' data-handler='next' data-event='click'" +
- " title='" + nextText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "w" : "e") + "'>" + nextText + "</span></a>" :
- (hideIfNoPrevNext ? "" : "<a class='ui-datepicker-next ui-corner-all ui-state-disabled' title='"+ nextText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "w" : "e") + "'>" + nextText + "</span></a>"));
-
- currentText = this._get(inst, "currentText");
- gotoDate = (this._get(inst, "gotoCurrent") && inst.currentDay ? currentDate : today);
- currentText = (!navigationAsDateFormat ? currentText :
- this.formatDate(currentText, gotoDate, this._getFormatConfig(inst)));
-
- controls = (!inst.inline ? "<button type='button' class='ui-datepicker-close ui-state-default ui-priority-primary ui-corner-all' data-handler='hide' data-event='click'>" +
- this._get(inst, "closeText") + "</button>" : "");
-
- buttonPanel = (showButtonPanel) ? "<div class='ui-datepicker-buttonpane ui-widget-content'>" + (isRTL ? controls : "") +
- (this._isInRange(inst, gotoDate) ? "<button type='button' class='ui-datepicker-current ui-state-default ui-priority-secondary ui-corner-all' data-handler='today' data-event='click'" +
- ">" + currentText + "</button>" : "") + (isRTL ? "" : controls) + "</div>" : "";
-
- firstDay = parseInt(this._get(inst, "firstDay"),10);
- firstDay = (isNaN(firstDay) ? 0 : firstDay);
-
- weekendDays = this._get(inst, "weekendDays");
- showWeek = this._get(inst, "showWeek");
- dayNames = this._get(inst, "dayNames");
- dayNamesMin = this._get(inst, "dayNamesMin");
- monthNames = this._get(inst, "monthNames");
- monthNamesShort = this._get(inst, "monthNamesShort");
- beforeShowDay = this._get(inst, "beforeShowDay");
- showOtherMonths = this._get(inst, "showOtherMonths");
- selectOtherMonths = this._get(inst, "selectOtherMonths");
- defaultDate = this._getDefaultDate(inst);
- html = "";
- dow;
- for (row = 0; row < numMonths[0]; row++) {
- group = "";
- this.maxRows = 4;
- for (col = 0; col < numMonths[1]; col++) {
- selectedDate = this._daylightSavingAdjust(new Date(drawYear, drawMonth, inst.selectedDay));
- cornerClass = " ui-corner-all";
- calender = "";
- if (isMultiMonth) {
- calender += "<div class='ui-datepicker-group";
- if (numMonths[1] > 1) {
- switch (col) {
- case 0: calender += " ui-datepicker-group-first";
- cornerClass = " ui-corner-" + (isRTL ? "right" : "left"); break;
- case numMonths[1]-1: calender += " ui-datepicker-group-last";
- cornerClass = " ui-corner-" + (isRTL ? "left" : "right"); break;
- default: calender += " ui-datepicker-group-middle"; cornerClass = ""; break;
- }
- }
- calender += "'>";
- }
- calender += "<div class='ui-datepicker-header ui-widget-header ui-helper-clearfix" + cornerClass + "'>" +
- (/all|left/.test(cornerClass) && row === 0 ? (isRTL ? next : prev) : "") +
- (/all|right/.test(cornerClass) && row === 0 ? (isRTL ? prev : next) : "") +
- this._generateMonthYearHeader(inst, drawMonth, drawYear, minDate, maxDate,
- row > 0 || col > 0, monthNames, monthNamesShort) + // draw month headers
- "</div><table class='ui-datepicker-calendar'><thead>" +
- "<tr>";
- thead = (showWeek ? "<th class='ui-datepicker-week-col'>" + this._get(inst, "weekHeader") + "</th>" : "");
- for (dow = 0; dow < 7; dow++) { // days of the week
- day = (dow + firstDay) % 7;
- thead += "<th scope='col'" + (weekendDays.indexOf(day)!=-1 ? " class='ui-datepicker-week-end'" : "") + ">" +
- "<span title='" + dayNames[day] + "'>" + dayNamesMin[day] + "</span></th>";
- }
- calender += thead + "</tr></thead><tbody>";
- daysInMonth = this._getDaysInMonth(drawYear, drawMonth);
- if (drawYear === inst.selectedYear && drawMonth === inst.selectedMonth) {
- inst.selectedDay = Math.min(inst.selectedDay, daysInMonth);
- }
- leadDays = (this._getFirstDayOfMonth(drawYear, drawMonth) - firstDay + 7) % 7;
- curRows = Math.ceil((leadDays + daysInMonth) / 7); // calculate the number of rows to generate
- numRows = (isMultiMonth ? this.maxRows > curRows ? this.maxRows : curRows : curRows); //If multiple months, use the higher number of rows (see #7043)
- this.maxRows = numRows;
- printDate = this._daylightSavingAdjust(new Date(drawYear, drawMonth, 1 - leadDays));
- for (dRow = 0; dRow < numRows; dRow++) { // create date picker rows
- calender += "<tr>";
- tbody = (!showWeek ? "" : "<td class='ui-datepicker-week-col'>" +
- this._get(inst, "calculateWeek")(printDate) + "</td>");
- for (dow = 0; dow < 7; dow++) { // create date picker days
- daySettings = (beforeShowDay ?
- beforeShowDay.apply((inst.input ? inst.input[0] : null), [printDate]) : [true, ""]);
- otherMonth = (printDate.getMonth() !== drawMonth);
- unselectable = (otherMonth && !selectOtherMonths) || !daySettings[0] ||
- (minDate && printDate < minDate) || (maxDate && printDate > maxDate);
- tbody += "<td class='" +
- (weekendDays.indexOf((dow + firstDay) % 7)!=-1 ? " ui-datepicker-week-end" : "") + // highlight weekends
- (otherMonth ? " ui-datepicker-other-month" : "") + // highlight days from other months
- ((printDate.getTime() === selectedDate.getTime() && drawMonth === inst.selectedMonth && inst._keyEvent) || // user pressed key
- (defaultDate.getTime() === printDate.getTime() && defaultDate.getTime() === selectedDate.getTime()) ?
- // or defaultDate is current printedDate and defaultDate is selectedDate
- " " + this._dayOverClass : "") + // highlight selected day
- (unselectable ? " " + this._unselectableClass + " ui-state-disabled": "") + // highlight unselectable days
- (otherMonth && !showOtherMonths ? "" : " " + daySettings[1] + // highlight custom dates
- (printDate.getTime() === currentDate.getTime() ? " " + this._currentClass : "") + // highlight selected day
- (printDate.getTime() === today.getTime() ? " ui-datepicker-today" : "")) + "'" + // highlight today (if different)
- ((!otherMonth || showOtherMonths) && daySettings[2] ? " title='" + daySettings[2].replace(/'/g, "&#39;") + "'" : "") + // cell title
- (unselectable ? "" : " data-handler='selectDay' data-event='click' data-month='" + printDate.getMonth() + "' data-year='" + printDate.getFullYear() + "'") + ">" + // actions
- (otherMonth && !showOtherMonths ? "&#xa0;" : // display for other months
- (unselectable ? "<span class='ui-state-default'>" + printDate.getDate() + "</span>" : "<a class='ui-state-default" +
- (printDate.getTime() === today.getTime() ? " ui-state-highlight" : "") +
- (printDate.getTime() === currentDate.getTime() ? " ui-state-active" : "") + // highlight selected day
- (otherMonth ? " ui-priority-secondary" : "") + // distinguish dates from other months
- "' href='#'>" + printDate.getDate() + "</a>")) + "</td>"; // display selectable date
- printDate.setDate(printDate.getDate() + 1);
- printDate = this._daylightSavingAdjust(printDate);
- }
- calender += tbody + "</tr>";
- }
- drawMonth++;
- if (drawMonth > 11) {
- drawMonth = 0;
- drawYear++;
- }
- calender += "</tbody></table>" + (isMultiMonth ? "</div>" +
- ((numMonths[0] > 0 && col === numMonths[1]-1) ? "<div class='ui-datepicker-row-break'></div>" : "") : "");
- group += calender;
- }
- html += group;
- }
- html += buttonPanel;
- inst._keyEvent = false;
- return html;
- },
-
- /* Generate the month and year header. */
- _generateMonthYearHeader: function(inst, drawMonth, drawYear, minDate, maxDate,
- secondary, monthNames, monthNamesShort) {
-
- var inMinYear, inMaxYear, month, years, thisYear, determineYear, year, endYear,
- changeMonth = this._get(inst, "changeMonth"),
- changeYear = this._get(inst, "changeYear"),
- showMonthAfterYear = this._get(inst, "showMonthAfterYear"),
- html = "<div class='ui-datepicker-title'>",
- monthHtml = "";
-
- // month selection
- if (secondary || !changeMonth) {
- monthHtml += "<span class='ui-datepicker-month'>" + monthNames[drawMonth] + "</span>";
- } else {
- inMinYear = (minDate && minDate.getFullYear() === drawYear);
- inMaxYear = (maxDate && maxDate.getFullYear() === drawYear);
- monthHtml += "<select class='ui-datepicker-month' data-handler='selectMonth' data-event='change'>";
- for ( month = 0; month < 12; month++) {
- if ((!inMinYear || month >= minDate.getMonth()) && (!inMaxYear || month <= maxDate.getMonth())) {
- monthHtml += "<option value='" + month + "'" +
- (month === drawMonth ? " selected='selected'" : "") +
- ">" + monthNamesShort[month] + "</option>";
- }
- }
- monthHtml += "</select>";
- }
-
- if (!showMonthAfterYear) {
- html += monthHtml + (secondary || !(changeMonth && changeYear) ? "&#xa0;" : "");
- }
-
- // year selection
- if ( !inst.yearshtml ) {
- inst.yearshtml = "";
- if (secondary || !changeYear) {
- html += "<span class='ui-datepicker-year'>" + drawYear + "</span>";
- } else {
- // determine range of years to display
- years = this._get(inst, "yearRange").split(":");
- thisYear = new Date().getFullYear();
- determineYear = function(value) {
- var year = (value.match(/c[+\-].*/) ? drawYear + parseInt(value.substring(1), 10) :
- (value.match(/[+\-].*/) ? thisYear + parseInt(value, 10) :
- parseInt(value, 10)));
- return (isNaN(year) ? thisYear : year);
- };
- year = determineYear(years[0]);
- endYear = Math.max(year, determineYear(years[1] || ""));
- year = (minDate ? Math.max(year, minDate.getFullYear()) : year);
- endYear = (maxDate ? Math.min(endYear, maxDate.getFullYear()) : endYear);
- inst.yearshtml += "<select class='ui-datepicker-year' data-handler='selectYear' data-event='change'>";
- for (; year <= endYear; year++) {
- inst.yearshtml += "<option value='" + year + "'" +
- (year === drawYear ? " selected='selected'" : "") +
- ">" + year + "</option>";
- }
- inst.yearshtml += "</select>";
-
- html += inst.yearshtml;
- inst.yearshtml = null;
- }
- }
-
- html += this._get(inst, "yearSuffix");
- if (showMonthAfterYear) {
- html += (secondary || !(changeMonth && changeYear) ? "&#xa0;" : "") + monthHtml;
- }
- html += "</div>"; // Close datepicker_header
- return html;
- },
-
- /* Adjust one of the date sub-fields. */
- _adjustInstDate: function(inst, offset, period) {
- var year = inst.drawYear + (period === "Y" ? offset : 0),
- month = inst.drawMonth + (period === "M" ? offset : 0),
- day = Math.min(inst.selectedDay, this._getDaysInMonth(year, month)) + (period === "D" ? offset : 0),
- date = this._restrictMinMax(inst, this._daylightSavingAdjust(new Date(year, month, day)));
-
- inst.selectedDay = date.getDate();
- inst.drawMonth = inst.selectedMonth = date.getMonth();
- inst.drawYear = inst.selectedYear = date.getFullYear();
- if (period === "M" || period === "Y") {
- this._notifyChange(inst);
- }
- },
-
- /* Ensure a date is within any min/max bounds. */
- _restrictMinMax: function(inst, date) {
- var minDate = this._getMinMaxDate(inst, "min"),
- maxDate = this._getMinMaxDate(inst, "max"),
- newDate = (minDate && date < minDate ? minDate : date);
- return (maxDate && newDate > maxDate ? maxDate : newDate);
- },
-
- /* Notify change of month/year. */
- _notifyChange: function(inst) {
- var onChange = this._get(inst, "onChangeMonthYear");
- if (onChange) {
- onChange.apply((inst.input ? inst.input[0] : null),
- [inst.selectedYear, inst.selectedMonth + 1, inst]);
- }
- },
-
- /* Determine the number of months to show. */
- _getNumberOfMonths: function(inst) {
- var numMonths = this._get(inst, "numberOfMonths");
- return (numMonths == null ? [1, 1] : (typeof numMonths === "number" ? [1, numMonths] : numMonths));
- },
-
- /* Determine the current maximum date - ensure no time components are set. */
- _getMinMaxDate: function(inst, minMax) {
- return this._determineDate(inst, this._get(inst, minMax + "Date"), null);
- },
-
- /* Find the number of days in a given month. */
- _getDaysInMonth: function(year, month) {
- return 32 - this._daylightSavingAdjust(new Date(year, month, 32)).getDate();
- },
-
- /* Find the day of the week of the first of a month. */
- _getFirstDayOfMonth: function(year, month) {
- return new Date(year, month, 1).getDay();
- },
-
- /* Determines if we should allow a "next/prev" month display change. */
- _canAdjustMonth: function(inst, offset, curYear, curMonth) {
- var numMonths = this._getNumberOfMonths(inst),
- date = this._daylightSavingAdjust(new Date(curYear,
- curMonth + (offset < 0 ? offset : numMonths[0] * numMonths[1]), 1));
-
- if (offset < 0) {
- date.setDate(this._getDaysInMonth(date.getFullYear(), date.getMonth()));
- }
- return this._isInRange(inst, date);
- },
-
- /* Is the given date in the accepted range? */
- _isInRange: function(inst, date) {
- var yearSplit, currentYear,
- minDate = this._getMinMaxDate(inst, "min"),
- maxDate = this._getMinMaxDate(inst, "max"),
- minYear = null,
- maxYear = null,
- years = this._get(inst, "yearRange");
- if (years){
- yearSplit = years.split(":");
- currentYear = new Date().getFullYear();
- minYear = parseInt(yearSplit[0], 10);
- maxYear = parseInt(yearSplit[1], 10);
- if ( yearSplit[0].match(/[+\-].*/) ) {
- minYear += currentYear;
- }
- if ( yearSplit[1].match(/[+\-].*/) ) {
- maxYear += currentYear;
- }
- }
-
- return ((!minDate || date.getTime() >= minDate.getTime()) &&
- (!maxDate || date.getTime() <= maxDate.getTime()) &&
- (!minYear || date.getFullYear() >= minYear) &&
- (!maxYear || date.getFullYear() <= maxYear));
- },
-
- /* Provide the configuration settings for formatting/parsing. */
- _getFormatConfig: function(inst) {
- var shortYearCutoff = this._get(inst, "shortYearCutoff");
- shortYearCutoff = (typeof shortYearCutoff !== "string" ? shortYearCutoff :
- new Date().getFullYear() % 100 + parseInt(shortYearCutoff, 10));
- return {shortYearCutoff: shortYearCutoff,
- dayNamesShort: this._get(inst, "dayNamesShort"), dayNames: this._get(inst, "dayNames"),
- monthNamesShort: this._get(inst, "monthNamesShort"), monthNames: this._get(inst, "monthNames")};
- },
-
- /* Format the given date for display. */
- _formatDate: function(inst, day, month, year) {
- if (!day) {
- inst.currentDay = inst.selectedDay;
- inst.currentMonth = inst.selectedMonth;
- inst.currentYear = inst.selectedYear;
- }
- var date = (day ? (typeof day === "object" ? day :
- this._daylightSavingAdjust(new Date(year, month, day))) :
- this._daylightSavingAdjust(new Date(inst.currentYear, inst.currentMonth, inst.currentDay)));
- return this.formatDate(this._get(inst, "dateFormat"), date, this._getFormatConfig(inst));
- }
-});
-
-/*
- * Bind hover events for datepicker elements.
- * Done via delegate so the binding only occurs once in the lifetime of the parent div.
- * Global datepicker_instActive, set by _updateDatepicker allows the handlers to find their way back to the active picker.
- */
-function datepicker_bindHover(dpDiv) {
- var selector = "button, .ui-datepicker-prev, .ui-datepicker-next, .ui-datepicker-calendar td a";
- return dpDiv.delegate(selector, "mouseout", function() {
- $(this).removeClass("ui-state-hover");
- if (this.className.indexOf("ui-datepicker-prev") !== -1) {
- $(this).removeClass("ui-datepicker-prev-hover");
- }
- if (this.className.indexOf("ui-datepicker-next") !== -1) {
- $(this).removeClass("ui-datepicker-next-hover");
- }
- })
- .delegate( selector, "mouseover", datepicker_handleMouseover );
-}
-
-function datepicker_handleMouseover() {
- if (!$.datepicker._isDisabledDatepicker( datepicker_instActive.inline? datepicker_instActive.dpDiv.parent()[0] : datepicker_instActive.input[0])) {
- $(this).parents(".ui-datepicker-calendar").find("a").removeClass("ui-state-hover");
- $(this).addClass("ui-state-hover");
- if (this.className.indexOf("ui-datepicker-prev") !== -1) {
- $(this).addClass("ui-datepicker-prev-hover");
- }
- if (this.className.indexOf("ui-datepicker-next") !== -1) {
- $(this).addClass("ui-datepicker-next-hover");
- }
- }
-}
-
-/* jQuery extend now ignores nulls! */
-function datepicker_extendRemove(target, props) {
- $.extend(target, props);
- for (var name in props) {
- if (props[name] == null) {
- target[name] = props[name];
- }
- }
- return target;
-}
-
-/* Invoke the datepicker functionality.
- @param options string - a command, optionally followed by additional parameters or
- Object - settings for attaching new datepicker functionality
- @return jQuery object */
-$.fn.datepicker = function(options){
-
- /* Verify an empty collection wasn't passed - Fixes #6976 */
- if ( !this.length ) {
- return this;
- }
-
- /* Initialise the date picker. */
- if (!$.datepicker.initialized) {
- $(document).mousedown($.datepicker._checkExternalClick);
- $.datepicker.initialized = true;
- }
-
- /* Append datepicker main container to body if not exist. */
- if ($("#"+$.datepicker._mainDivId).length === 0) {
- $("body").append($.datepicker.dpDiv);
- }
-
- var otherArgs = Array.prototype.slice.call(arguments, 1);
- if (typeof options === "string" && (options === "isDisabled" || options === "getDate" || options === "widget")) {
- return $.datepicker["_" + options + "Datepicker"].
- apply($.datepicker, [this[0]].concat(otherArgs));
- }
- if (options === "option" && arguments.length === 2 && typeof arguments[1] === "string") {
- return $.datepicker["_" + options + "Datepicker"].
- apply($.datepicker, [this[0]].concat(otherArgs));
- }
- return this.each(function() {
- typeof options === "string" ?
- $.datepicker["_" + options + "Datepicker"].
- apply($.datepicker, [this].concat(otherArgs)) :
- $.datepicker._attachDatepicker(this, options);
- });
-};
-
-$.datepicker = new Datepicker(); // singleton instance
-$.datepicker.initialized = false;
-$.datepicker.uuid = new Date().getTime();
-$.datepicker.version = "1.11.4";
-
-var datepicker = $.datepicker;
-
-
-/*!
- * jQuery UI Slider 1.11.4
- * http://jqueryui.com
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- *
- * http://api.jqueryui.com/slider/
- */
-
-
-var slider = $.widget( "ui.slider", $.ui.mouse, {
- version: "1.11.4",
- widgetEventPrefix: "slide",
-
- options: {
- animate: false,
- distance: 0,
- max: 100,
- min: 0,
- orientation: "horizontal",
- range: false,
- step: 1,
- value: 0,
- values: null,
-
- // callbacks
- change: null,
- slide: null,
- start: null,
- stop: null
- },
-
- // number of pages in a slider
- // (how many times can you page up/down to go through the whole range)
- numPages: 5,
-
- _create: function() {
- this._keySliding = false;
- this._mouseSliding = false;
- this._animateOff = true;
- this._handleIndex = null;
- this._detectOrientation();
- this._mouseInit();
- this._calculateNewMax();
-
- this.element
- .addClass( "ui-slider" +
- " ui-slider-" + this.orientation +
- " ui-widget" +
- " ui-widget-content" +
- " ui-corner-all");
-
- this._refresh();
- this._setOption( "disabled", this.options.disabled );
-
- this._animateOff = false;
- },
-
- _refresh: function() {
- this._createRange();
- this._createHandles();
- this._setupEvents();
- this._refreshValue();
- },
-
- _createHandles: function() {
- var i, handleCount,
- options = this.options,
- existingHandles = this.element.find( ".ui-slider-handle" ).addClass( "ui-state-default ui-corner-all" ),
- handle = "<span class='ui-slider-handle ui-state-default ui-corner-all' tabindex='0'></span>",
- handles = [];
-
- handleCount = ( options.values && options.values.length ) || 1;
-
- if ( existingHandles.length > handleCount ) {
- existingHandles.slice( handleCount ).remove();
- existingHandles = existingHandles.slice( 0, handleCount );
- }
-
- for ( i = existingHandles.length; i < handleCount; i++ ) {
- handles.push( handle );
- }
-
- this.handles = existingHandles.add( $( handles.join( "" ) ).appendTo( this.element ) );
-
- this.handle = this.handles.eq( 0 );
-
- this.handles.each(function( i ) {
- $( this ).data( "ui-slider-handle-index", i );
- });
- },
-
- _createRange: function() {
- var options = this.options,
- classes = "";
-
- if ( options.range ) {
- if ( options.range === true ) {
- if ( !options.values ) {
- options.values = [ this._valueMin(), this._valueMin() ];
- } else if ( options.values.length && options.values.length !== 2 ) {
- options.values = [ options.values[0], options.values[0] ];
- } else if ( $.isArray( options.values ) ) {
- options.values = options.values.slice(0);
- }
- }
-
- if ( !this.range || !this.range.length ) {
- this.range = $( "<div></div>" )
- .appendTo( this.element );
-
- classes = "ui-slider-range" +
- // note: this isn't the most fittingly semantic framework class for this element,
- // but worked best visually with a variety of themes
- " ui-widget-header ui-corner-all";
- } else {
- this.range.removeClass( "ui-slider-range-min ui-slider-range-max" )
- // Handle range switching from true to min/max
- .css({
- "left": "",
- "bottom": ""
- });
- }
-
- this.range.addClass( classes +
- ( ( options.range === "min" || options.range === "max" ) ? " ui-slider-range-" + options.range : "" ) );
- } else {
- if ( this.range ) {
- this.range.remove();
- }
- this.range = null;
- }
- },
-
- _setupEvents: function() {
- this._off( this.handles );
- this._on( this.handles, this._handleEvents );
- this._hoverable( this.handles );
- this._focusable( this.handles );
- },
-
- _destroy: function() {
- this.handles.remove();
- if ( this.range ) {
- this.range.remove();
- }
-
- this.element
- .removeClass( "ui-slider" +
- " ui-slider-horizontal" +
- " ui-slider-vertical" +
- " ui-widget" +
- " ui-widget-content" +
- " ui-corner-all" );
-
- this._mouseDestroy();
- },
-
- _mouseCapture: function( event ) {
- var position, normValue, distance, closestHandle, index, allowed, offset, mouseOverHandle,
- that = this,
- o = this.options;
-
- if ( o.disabled ) {
- return false;
- }
-
- this.elementSize = {
- width: this.element.outerWidth(),
- height: this.element.outerHeight()
- };
- this.elementOffset = this.element.offset();
-
- position = { x: event.pageX, y: event.pageY };
- normValue = this._normValueFromMouse( position );
- distance = this._valueMax() - this._valueMin() + 1;
- this.handles.each(function( i ) {
- var thisDistance = Math.abs( normValue - that.values(i) );
- if (( distance > thisDistance ) ||
- ( distance === thisDistance &&
- (i === that._lastChangedValue || that.values(i) === o.min ))) {
- distance = thisDistance;
- closestHandle = $( this );
- index = i;
- }
- });
-
- allowed = this._start( event, index );
- if ( allowed === false ) {
- return false;
- }
- this._mouseSliding = true;
-
- this._handleIndex = index;
-
- closestHandle
- .addClass( "ui-state-active" )
- .focus();
-
- offset = closestHandle.offset();
- mouseOverHandle = !$( event.target ).parents().addBack().is( ".ui-slider-handle" );
- this._clickOffset = mouseOverHandle ? { left: 0, top: 0 } : {
- left: event.pageX - offset.left - ( closestHandle.width() / 2 ),
- top: event.pageY - offset.top -
- ( closestHandle.height() / 2 ) -
- ( parseInt( closestHandle.css("borderTopWidth"), 10 ) || 0 ) -
- ( parseInt( closestHandle.css("borderBottomWidth"), 10 ) || 0) +
- ( parseInt( closestHandle.css("marginTop"), 10 ) || 0)
- };
-
- if ( !this.handles.hasClass( "ui-state-hover" ) ) {
- this._slide( event, index, normValue );
- }
- this._animateOff = true;
- return true;
- },
-
- _mouseStart: function() {
- return true;
- },
-
- _mouseDrag: function( event ) {
- var position = { x: event.pageX, y: event.pageY },
- normValue = this._normValueFromMouse( position );
-
- this._slide( event, this._handleIndex, normValue );
-
- return false;
- },
-
- _mouseStop: function( event ) {
- this.handles.removeClass( "ui-state-active" );
- this._mouseSliding = false;
-
- this._stop( event, this._handleIndex );
- this._change( event, this._handleIndex );
-
- this._handleIndex = null;
- this._clickOffset = null;
- this._animateOff = false;
-
- return false;
- },
-
- _detectOrientation: function() {
- this.orientation = ( this.options.orientation === "vertical" ) ? "vertical" : "horizontal";
- },
-
- _normValueFromMouse: function( position ) {
- var pixelTotal,
- pixelMouse,
- percentMouse,
- valueTotal,
- valueMouse;
-
- if ( this.orientation === "horizontal" ) {
- pixelTotal = this.elementSize.width;
- pixelMouse = position.x - this.elementOffset.left - ( this._clickOffset ? this._clickOffset.left : 0 );
- } else {
- pixelTotal = this.elementSize.height;
- pixelMouse = position.y - this.elementOffset.top - ( this._clickOffset ? this._clickOffset.top : 0 );
- }
-
- percentMouse = ( pixelMouse / pixelTotal );
- if ( percentMouse > 1 ) {
- percentMouse = 1;
- }
- if ( percentMouse < 0 ) {
- percentMouse = 0;
- }
- if ( this.orientation === "vertical" ) {
- percentMouse = 1 - percentMouse;
- }
-
- valueTotal = this._valueMax() - this._valueMin();
- valueMouse = this._valueMin() + percentMouse * valueTotal;
-
- return this._trimAlignValue( valueMouse );
- },
-
- _start: function( event, index ) {
- var uiHash = {
- handle: this.handles[ index ],
- value: this.value()
- };
- if ( this.options.values && this.options.values.length ) {
- uiHash.value = this.values( index );
- uiHash.values = this.values();
- }
- return this._trigger( "start", event, uiHash );
- },
-
- _slide: function( event, index, newVal ) {
- var otherVal,
- newValues,
- allowed;
-
- if ( this.options.values && this.options.values.length ) {
- otherVal = this.values( index ? 0 : 1 );
-
- if ( ( this.options.values.length === 2 && this.options.range === true ) &&
- ( ( index === 0 && newVal > otherVal) || ( index === 1 && newVal < otherVal ) )
- ) {
- newVal = otherVal;
- }
-
- if ( newVal !== this.values( index ) ) {
- newValues = this.values();
- newValues[ index ] = newVal;
- // A slide can be canceled by returning false from the slide callback
- allowed = this._trigger( "slide", event, {
- handle: this.handles[ index ],
- value: newVal,
- values: newValues
- } );
- otherVal = this.values( index ? 0 : 1 );
- if ( allowed !== false ) {
- this.values( index, newVal );
- }
- }
- } else {
- if ( newVal !== this.value() ) {
- // A slide can be canceled by returning false from the slide callback
- allowed = this._trigger( "slide", event, {
- handle: this.handles[ index ],
- value: newVal
- } );
- if ( allowed !== false ) {
- this.value( newVal );
- }
- }
- }
- },
-
- _stop: function( event, index ) {
- var uiHash = {
- handle: this.handles[ index ],
- value: this.value()
- };
- if ( this.options.values && this.options.values.length ) {
- uiHash.value = this.values( index );
- uiHash.values = this.values();
- }
-
- this._trigger( "stop", event, uiHash );
- },
-
- _change: function( event, index ) {
- if ( !this._keySliding && !this._mouseSliding ) {
- var uiHash = {
- handle: this.handles[ index ],
- value: this.value()
- };
- if ( this.options.values && this.options.values.length ) {
- uiHash.value = this.values( index );
- uiHash.values = this.values();
- }
-
- //store the last changed value index for reference when handles overlap
- this._lastChangedValue = index;
-
- this._trigger( "change", event, uiHash );
- }
- },
-
- value: function( newValue ) {
- if ( arguments.length ) {
- this.options.value = this._trimAlignValue( newValue );
- this._refreshValue();
- this._change( null, 0 );
- return;
- }
-
- return this._value();
- },
-
- values: function( index, newValue ) {
- var vals,
- newValues,
- i;
-
- if ( arguments.length > 1 ) {
- this.options.values[ index ] = this._trimAlignValue( newValue );
- this._refreshValue();
- this._change( null, index );
- return;
- }
-
- if ( arguments.length ) {
- if ( $.isArray( arguments[ 0 ] ) ) {
- vals = this.options.values;
- newValues = arguments[ 0 ];
- for ( i = 0; i < vals.length; i += 1 ) {
- vals[ i ] = this._trimAlignValue( newValues[ i ] );
- this._change( null, i );
- }
- this._refreshValue();
- } else {
- if ( this.options.values && this.options.values.length ) {
- return this._values( index );
- } else {
- return this.value();
- }
- }
- } else {
- return this._values();
- }
- },
-
- _setOption: function( key, value ) {
- var i,
- valsLength = 0;
-
- if ( key === "range" && this.options.range === true ) {
- if ( value === "min" ) {
- this.options.value = this._values( 0 );
- this.options.values = null;
- } else if ( value === "max" ) {
- this.options.value = this._values( this.options.values.length - 1 );
- this.options.values = null;
- }
- }
-
- if ( $.isArray( this.options.values ) ) {
- valsLength = this.options.values.length;
- }
-
- if ( key === "disabled" ) {
- this.element.toggleClass( "ui-state-disabled", !!value );
- }
-
- this._super( key, value );
-
- switch ( key ) {
- case "orientation":
- this._detectOrientation();
- this.element
- .removeClass( "ui-slider-horizontal ui-slider-vertical" )
- .addClass( "ui-slider-" + this.orientation );
- this._refreshValue();
-
- // Reset positioning from previous orientation
- this.handles.css( value === "horizontal" ? "bottom" : "left", "" );
- break;
- case "value":
- this._animateOff = true;
- this._refreshValue();
- this._change( null, 0 );
- this._animateOff = false;
- break;
- case "values":
- this._animateOff = true;
- this._refreshValue();
- for ( i = 0; i < valsLength; i += 1 ) {
- this._change( null, i );
- }
- this._animateOff = false;
- break;
- case "step":
- case "min":
- case "max":
- this._animateOff = true;
- this._calculateNewMax();
- this._refreshValue();
- this._animateOff = false;
- break;
- case "range":
- this._animateOff = true;
- this._refresh();
- this._animateOff = false;
- break;
- }
- },
-
- //internal value getter
- // _value() returns value trimmed by min and max, aligned by step
- _value: function() {
- var val = this.options.value;
- val = this._trimAlignValue( val );
-
- return val;
- },
-
- //internal values getter
- // _values() returns array of values trimmed by min and max, aligned by step
- // _values( index ) returns single value trimmed by min and max, aligned by step
- _values: function( index ) {
- var val,
- vals,
- i;
-
- if ( arguments.length ) {
- val = this.options.values[ index ];
- val = this._trimAlignValue( val );
-
- return val;
- } else if ( this.options.values && this.options.values.length ) {
- // .slice() creates a copy of the array
- // this copy gets trimmed by min and max and then returned
- vals = this.options.values.slice();
- for ( i = 0; i < vals.length; i += 1) {
- vals[ i ] = this._trimAlignValue( vals[ i ] );
- }
-
- return vals;
- } else {
- return [];
- }
- },
-
- // returns the step-aligned value that val is closest to, between (inclusive) min and max
- _trimAlignValue: function( val ) {
- if ( val <= this._valueMin() ) {
- return this._valueMin();
- }
- if ( val >= this._valueMax() ) {
- return this._valueMax();
- }
- var step = ( this.options.step > 0 ) ? this.options.step : 1,
- valModStep = (val - this._valueMin()) % step,
- alignValue = val - valModStep;
-
- if ( Math.abs(valModStep) * 2 >= step ) {
- alignValue += ( valModStep > 0 ) ? step : ( -step );
- }
-
- // Since JavaScript has problems with large floats, round
- // the final value to 5 digits after the decimal point (see #4124)
- return parseFloat( alignValue.toFixed(5) );
- },
-
- _calculateNewMax: function() {
- var max = this.options.max,
- min = this._valueMin(),
- step = this.options.step,
- aboveMin = Math.floor( ( +( max - min ).toFixed( this._precision() ) ) / step ) * step;
- max = aboveMin + min;
- this.max = parseFloat( max.toFixed( this._precision() ) );
- },
-
- _precision: function() {
- var precision = this._precisionOf( this.options.step );
- if ( this.options.min !== null ) {
- precision = Math.max( precision, this._precisionOf( this.options.min ) );
- }
- return precision;
- },
-
- _precisionOf: function( num ) {
- var str = num.toString(),
- decimal = str.indexOf( "." );
- return decimal === -1 ? 0 : str.length - decimal - 1;
- },
-
- _valueMin: function() {
- return this.options.min;
- },
-
- _valueMax: function() {
- return this.max;
- },
-
- _refreshValue: function() {
- var lastValPercent, valPercent, value, valueMin, valueMax,
- oRange = this.options.range,
- o = this.options,
- that = this,
- animate = ( !this._animateOff ) ? o.animate : false,
- _set = {};
-
- if ( this.options.values && this.options.values.length ) {
- this.handles.each(function( i ) {
- valPercent = ( that.values(i) - that._valueMin() ) / ( that._valueMax() - that._valueMin() ) * 100;
- _set[ that.orientation === "horizontal" ? "left" : "bottom" ] = valPercent + "%";
- $( this ).stop( 1, 1 )[ animate ? "animate" : "css" ]( _set, o.animate );
- if ( that.options.range === true ) {
- if ( that.orientation === "horizontal" ) {
- if ( i === 0 ) {
- that.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( { left: valPercent + "%" }, o.animate );
- }
- if ( i === 1 ) {
- that.range[ animate ? "animate" : "css" ]( { width: ( valPercent - lastValPercent ) + "%" }, { queue: false, duration: o.animate } );
- }
- } else {
- if ( i === 0 ) {
- that.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( { bottom: ( valPercent ) + "%" }, o.animate );
- }
- if ( i === 1 ) {
- that.range[ animate ? "animate" : "css" ]( { height: ( valPercent - lastValPercent ) + "%" }, { queue: false, duration: o.animate } );
- }
- }
- }
- lastValPercent = valPercent;
- });
- } else {
- value = this.value();
- valueMin = this._valueMin();
- valueMax = this._valueMax();
- valPercent = ( valueMax !== valueMin ) ?
- ( value - valueMin ) / ( valueMax - valueMin ) * 100 :
- 0;
- _set[ this.orientation === "horizontal" ? "left" : "bottom" ] = valPercent + "%";
- this.handle.stop( 1, 1 )[ animate ? "animate" : "css" ]( _set, o.animate );
-
- if ( oRange === "min" && this.orientation === "horizontal" ) {
- this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( { width: valPercent + "%" }, o.animate );
- }
- if ( oRange === "max" && this.orientation === "horizontal" ) {
- this.range[ animate ? "animate" : "css" ]( { width: ( 100 - valPercent ) + "%" }, { queue: false, duration: o.animate } );
- }
- if ( oRange === "min" && this.orientation === "vertical" ) {
- this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( { height: valPercent + "%" }, o.animate );
- }
- if ( oRange === "max" && this.orientation === "vertical" ) {
- this.range[ animate ? "animate" : "css" ]( { height: ( 100 - valPercent ) + "%" }, { queue: false, duration: o.animate } );
- }
- }
- },
-
- _handleEvents: {
- keydown: function( event ) {
- var allowed, curVal, newVal, step,
- index = $( event.target ).data( "ui-slider-handle-index" );
-
- switch ( event.keyCode ) {
- case $.ui.keyCode.HOME:
- case $.ui.keyCode.END:
- case $.ui.keyCode.PAGE_UP:
- case $.ui.keyCode.PAGE_DOWN:
- case $.ui.keyCode.UP:
- case $.ui.keyCode.RIGHT:
- case $.ui.keyCode.DOWN:
- case $.ui.keyCode.LEFT:
- event.preventDefault();
- if ( !this._keySliding ) {
- this._keySliding = true;
- $( event.target ).addClass( "ui-state-active" );
- allowed = this._start( event, index );
- if ( allowed === false ) {
- return;
- }
- }
- break;
- }
-
- step = this.options.step;
- if ( this.options.values && this.options.values.length ) {
- curVal = newVal = this.values( index );
- } else {
- curVal = newVal = this.value();
- }
-
- switch ( event.keyCode ) {
- case $.ui.keyCode.HOME:
- newVal = this._valueMin();
- break;
- case $.ui.keyCode.END:
- newVal = this._valueMax();
- break;
- case $.ui.keyCode.PAGE_UP:
- newVal = this._trimAlignValue(
- curVal + ( ( this._valueMax() - this._valueMin() ) / this.numPages )
- );
- break;
- case $.ui.keyCode.PAGE_DOWN:
- newVal = this._trimAlignValue(
- curVal - ( (this._valueMax() - this._valueMin()) / this.numPages ) );
- break;
- case $.ui.keyCode.UP:
- case $.ui.keyCode.RIGHT:
- if ( curVal === this._valueMax() ) {
- return;
- }
- newVal = this._trimAlignValue( curVal + step );
- break;
- case $.ui.keyCode.DOWN:
- case $.ui.keyCode.LEFT:
- if ( curVal === this._valueMin() ) {
- return;
- }
- newVal = this._trimAlignValue( curVal - step );
- break;
- }
-
- this._slide( event, index, newVal );
- },
- keyup: function( event ) {
- var index = $( event.target ).data( "ui-slider-handle-index" );
-
- if ( this._keySliding ) {
- this._keySliding = false;
- this._stop( event, index );
- this._change( event, index );
- $( event.target ).removeClass( "ui-state-active" );
- }
- }
- }
-});
-
-
-
-})); \ No newline at end of file
diff --git a/radicale_web/web/infcloud/lib/jquery.autosize.js b/radicale_web/web/infcloud/lib/jquery.autosize.js
deleted file mode 100644
index b0a3f00..0000000
--- a/radicale_web/web/infcloud/lib/jquery.autosize.js
+++ /dev/null
@@ -1,258 +0,0 @@
-/*!
- Autosize v1.18.0 - 2013-10-20
- Automatically adjust textarea height based on user input.
- (c) 2013 Jack Moore - http://www.jacklmoore.com/autosize
- license: http://www.opensource.org/licenses/mit-license.php
-*/
-(function (factory) {
- if (typeof define === 'function' && define.amd) {
- // AMD. Register as an anonymous module.
- define(['jquery'], factory);
- } else {
- // Browser globals: jQuery or jQuery-like library, such as Zepto
- factory(window.jQuery || window.$);
- }
-}(function ($) {
- var
- defaults = {
- className: 'autosizejs',
- append: '',
- callback: false,
- resizeDelay: 10
- },
-
- // border:0 is unnecessary, but avoids a bug in FireFox on OSX
- copy = '<textarea tabindex="-1" style="position:absolute; top:-999px; left:0; right:auto; bottom:auto; border:0; padding: 0; -moz-box-sizing:content-box; -webkit-box-sizing:content-box; box-sizing:content-box; word-wrap:break-word; height:0 !important; min-height:0 !important; overflow:hidden; transition:none; -webkit-transition:none; -moz-transition:none;"/>',
-
- // line-height is conditionally included because IE7/IE8/old Opera do not return the correct value.
- typographyStyles = [
- 'fontFamily',
- 'fontSize',
- 'fontWeight',
- 'fontStyle',
- 'letterSpacing',
- 'textTransform',
- 'wordSpacing',
- 'textIndent'
- ],
-
- // to keep track which textarea is being mirrored when adjust() is called.
- mirrored,
-
- // the mirror element, which is used to calculate what size the mirrored element should be.
- mirror = $(copy).data('autosize', true)[0];
-
- // test that line-height can be accurately copied.
- mirror.style.lineHeight = '99px';
- if ($(mirror).css('lineHeight') === '99px') {
- typographyStyles.push('lineHeight');
- }
- mirror.style.lineHeight = '';
-
- $.fn.autosize = function (options) {
- if (!this.length) {
- return this;
- }
-
- options = $.extend({}, defaults, options || {});
-
- if (mirror.parentNode !== document.body) {
- $(document.body).append(mirror);
- }
-
- return this.each(function () {
- var
- ta = this,
- $ta = $(ta),
- maxHeight,
- minHeight,
- boxOffset = 0,
- callback = $.isFunction(options.callback),
- originalStyles = {
- height: options.defaultStyles!=undefined && options.defaultStyles['height']!=undefined ? options.defaultStyles['height'] : ta.style.height,
- overflow: options.defaultStyles!=undefined && options.defaultStyles['overflow']!=undefined ? options.defaultStyles['overflow'] : ta.style.overflow,
- overflowY: options.defaultStyles!=undefined && options.defaultStyles['overflow-y']!=undefined ? options.defaultStyles['overflow-y'] : ta.style.overflowY,
- wordWrap: options.defaultStyles!=undefined && options.defaultStyles['word-wrap']!=undefined ? options.defaultStyles['word-wrap'] : ta.style.wordWrap,
- resize: options.defaultStyles!=undefined && options.defaultStyles['resize']!=undefined ? options.defaultStyles['resize'] : ta.style.resize
- },
- timeout,
- width = $ta.width();
-
- if ($ta.data('autosize')) {
- // exit if autosize has already been applied, or if the textarea is the mirror element.
- return;
- }
- $ta.data('autosize', true);
-
- if ($ta.css('box-sizing') === 'border-box' || $ta.css('-moz-box-sizing') === 'border-box' || $ta.css('-webkit-box-sizing') === 'border-box'){
- boxOffset = $ta.outerHeight() - $ta.height();
- }
-
- // IE8 and lower return 'auto', which parses to NaN, if no min-height is set.
- minHeight = Math.max(parseInt($ta.css('minHeight'), 10) - boxOffset || 0, originalStyles.height);
-
- $ta.css({
- overflow: 'hidden',
- overflowY: 'hidden',
- wordWrap: 'break-word', // horizontal overflow is hidden, so break-word is necessary for handling words longer than the textarea width
- resize: (originalStyles.resize === 'none' || originalStyles.resize === 'vertical') ? 'none' : 'horizontal'
- });
-
- // The mirror width must exactly match the textarea width, so using getBoundingClientRect because it doesn't round the sub-pixel value.
- function setWidth() {
- var style, width;
-
- if ('getComputedStyle' in window) {
- style = window.getComputedStyle(ta, null);
- width = ta.getBoundingClientRect().width;
-
- $.each(['paddingLeft', 'paddingRight', 'borderLeftWidth', 'borderRightWidth'], function(i,val){
- width -= parseInt(style[val],10);
- });
-
- mirror.style.width = width + 'px';
- }
- else {
- // window.getComputedStyle, getBoundingClientRect returning a width are unsupported and unneeded in IE8 and lower.
- mirror.style.width = Math.max($ta.width(), 0) + 'px';
- }
- }
-
- function initMirror() {
- var styles = {};
-
- mirrored = ta;
- mirror.className = options.className;
- maxHeight = parseInt($ta.css('maxHeight'), 10);
-
- // mirror is a duplicate textarea located off-screen that
- // is automatically updated to contain the same text as the
- // original textarea. mirror always has a height of 0.
- // This gives a cross-browser supported way getting the actual
- // height of the text, through the scrollTop property.
- $.each(typographyStyles, function(i,val){
- styles[val] = $ta.css(val);
- });
- $(mirror).css(styles);
-
- setWidth();
-
- // Chrome-specific fix:
- // When the textarea y-overflow is hidden, Chrome doesn't reflow the text to account for the space
- // made available by removing the scrollbar. This workaround triggers the reflow for Chrome.
- if (window.chrome) {
- var width = ta.style.width;
- ta.style.width = '0px';
- var ignore = ta.offsetWidth;
- ta.style.width = width;
- }
- }
-
- // Using mainly bare JS in this function because it is going
- // to fire very often while typing, and needs to very efficient.
- function adjust() {
- var height, original;
-
- if (mirrored !== ta) {
- initMirror();
- } else {
- setWidth();
- }
-
- mirror.value = ta.value + options.append;
- mirror.style.overflowY = ta.style.overflowY;
- original = parseInt(ta.style.height,10);
-
- // Setting scrollTop to zero is needed in IE8 and lower for the next step to be accurately applied
- mirror.scrollTop = 0;
-
- mirror.scrollTop = 9e4;
-
- // Using scrollTop rather than scrollHeight because scrollHeight is non-standard and includes padding.
- height = mirror.scrollTop;
-
- if (maxHeight && height > maxHeight) {
- ta.style.overflowY = 'scroll';
- height = maxHeight;
- } else {
- ta.style.overflowY = 'hidden';
- if (height < minHeight) {
- height = minHeight;
- }
- }
-
- height += boxOffset;
-
- if (original !== height) {
- ta.style.height = height + 'px';
- if (callback) {
- options.callback.call(ta,ta);
- }
- }
- }
-
- function resize () {
- clearTimeout(timeout);
- timeout = setTimeout(function(){
- var newWidth = $ta.width();
-
- if (newWidth !== width) {
- width = newWidth;
- adjust();
- }
- }, parseInt(options.resizeDelay,10));
- }
-
- if ('onpropertychange' in ta) {
- if ('oninput' in ta) {
- // Detects IE9. IE9 does not fire onpropertychange or oninput for deletions,
- // so binding to onkeyup to catch most of those occasions. There is no way that I
- // know of to detect something like 'cut' in IE9.
- $ta.on('input.autosize keyup.autosize', adjust);
- } else {
- // IE7 / IE8
- $ta.on('propertychange.autosize', function(){
- if(event.propertyName === 'value'){
- adjust();
- }
- });
- }
- } else {
- // Modern Browsers
- $ta.on('input.autosize', adjust);
- }
-
- // Set options.resizeDelay to false if using fixed-width textarea elements.
- // Uses a timeout and width check to reduce the amount of times adjust needs to be called after window resize.
-
- if (options.resizeDelay !== false) {
- $(window).on('resize.autosize', resize);
- }
-
- // Event for manual triggering if needed.
- // Should only be needed when the value of the textarea is changed through JavaScript rather than user input.
- $ta.on('autosize.resize', adjust);
-
- // Event for manual triggering that also forces the styles to update as well.
- // Should only be needed if one of typography styles of the textarea change, and the textarea is already the target of the adjust method.
- $ta.on('autosize.resizeIncludeStyle', function() {
- mirrored = null;
- adjust();
- });
-
- $ta.on('autosize.destroy', function(){
- mirrored = null;
- clearTimeout(timeout);
- $(window).off('resize', resize);
- $ta
- .off('autosize')
- .off('.autosize')
- .css(originalStyles)
- .removeData('autosize');
- });
-
- // Call adjust in case the textarea already contains text.
- adjust();
- });
- };
-}));
diff --git a/radicale_web/web/infcloud/lib/jquery.browser.js b/radicale_web/web/infcloud/lib/jquery.browser.js
deleted file mode 100644
index c2eba36..0000000
--- a/radicale_web/web/infcloud/lib/jquery.browser.js
+++ /dev/null
@@ -1,43 +0,0 @@
-// jQuery.browser from 1.8.x
-// Limit scope pollution from any deprecated API
-(function() {
-
-var matched, browser;
-
-// Use of jQuery.browser is frowned upon.
-// More details: http://api.jquery.com/jQuery.browser
-// jQuery.uaMatch maintained for back-compat
-jQuery.uaMatch = function( ua ) {
- ua = ua.toLowerCase();
-
- var match = /(chrome)[ \/]([\w.]+)/.exec( ua ) ||
- /(webkit)[ \/]([\w.]+)/.exec( ua ) ||
- /(opera)(?:.*version|)[ \/]([\w.]+)/.exec( ua ) ||
- /(msie) ([\w.]+)/.exec( ua ) ||
- ua.indexOf("compatible") < 0 && /(mozilla)(?:.*? rv:([\w.]+)|)/.exec( ua ) ||
- [];
-
- return {
- browser: match[ 1 ] || "",
- version: match[ 2 ] || "0"
- };
-};
-
-matched = jQuery.uaMatch( navigator.userAgent );
-browser = {};
-
-if ( matched.browser ) {
- browser[ matched.browser ] = true;
- browser.version = matched.version;
-}
-
-// Chrome is Webkit, but Webkit is also Safari.
-if ( browser.chrome ) {
- browser.webkit = true;
-} else if ( browser.webkit ) {
- browser.safari = true;
-}
-
-jQuery.browser = browser;
-
-})();
diff --git a/radicale_web/web/infcloud/lib/jquery.placeholder-1.1.9.js b/radicale_web/web/infcloud/lib/jquery.placeholder-1.1.9.js
deleted file mode 100644
index f1ecba8..0000000
--- a/radicale_web/web/infcloud/lib/jquery.placeholder-1.1.9.js
+++ /dev/null
@@ -1,195 +0,0 @@
-/*****************************************************************************
-jQuery Placeholder 1.1.9 (with minor modifications for CardDavMATE & CalDavZAP)
-
-Copyright (c) 2010 Michael J. Ryan (http://tracker1.info/)
-
-Dual licensed under the MIT and GPL licenses:
- http://www.opensource.org/licenses/mit-license.php
- http://www.gnu.org/licenses/gpl.html
-
-------------------------------------------------------------------------------
-
-Sets up a watermark for inputted fields... this will create a LABEL.watermark
-tag immediately following the input tag, the positioning will be set absolute,
-and it will be positioned to match the input tag.
-
-To activate:
-
- $('input[placeholder],textarea[placeholder]').placeholder();
-
-
-NOTE, when changing a value via script:
-
- $('#input_id').val('new value').change(); //force change event, so placeholder sets properly
-
-
-To style the tags as appropriate (you'll want to make sure the font matches):
-
- label.placeholder {
- cursor: text; <--- display a cursor to match the text input
-
- padding: 4px 4px 4px 4px; <--- this should match the border+padding
- for the input field(s)
- color: #999999; <--- this will display as faded
- }
-
-You'll also want to have the color set for browsers with native support
- input:placeholder, textarea:placeholder {
- color: #999999;
- }
- input::-webkit-input-placeholder, textarea::-webkit-input-placeholder {
- color: #999999;
- }
-
-------------------------------------------------------------------------------
-
-Thanks to...
- http://www.alistapart.com/articles/makingcompactformsmoreaccessible
- http://plugins.jquery.com/project/overlabel
-
- This works similar to the overlabel, but creates the actual label tag
- based on the placeholder attribute on the input tag, instead of
- relying on the markup to provide it.
-
-*****************************************************************************/
-(function($){
-
- var ph = "PLACEHOLDER-INPUT";
- var phl = "PLACEHOLDER-LABEL";
- var boundEvents = false;
- var default_options = {
- labelClass: 'placeholder'
- };
-
- //check for native support for placeholder attribute, if so stub methods and return
- var input = document.createElement("input");
- if ('placeholder' in input) {
- $.fn.placeholder = $.fn.unplaceholder = function(){}; //empty function
- delete input; //cleanup IE memory
- return;
- };
- delete input;
-
- //bind to resize to fix placeholders when the page resizes (fields are hidden/displayed, which can change positioning).
- $(window).resize(checkResize);
-
-
- $.fn.placeholder = function(options) {
- bindEvents();
-
- var opts = $.extend(default_options, options)
-
- this.each(function(){
- var rnd=Math.random().toString(32).replace(/\./,'')
- ,input=$(this)
- ,label=$('<label style="position:absolute;display:none;top:0;left:0;"></label>');
-
- if (!input.attr('placeholder') || input.data(ph) === ph) return; //already watermarked
-
- //make sure the input tag has an ID assigned, if not, assign one.
- if (!input.attr('id')) input.attr('id', 'input_' + rnd);
-
- label .attr('id',input.attr('id') + "_placeholder")
- .data(ph, '#' + input.attr('id')) //reference to the input tag
- .attr('for',input.attr('id'))
- .addClass(opts.labelClass)
- .addClass(opts.labelClass + '-for-' + this.tagName.toLowerCase()) //ex: watermark-for-textarea
- .addClass(phl)
- .text(input.attr('placeholder'));
-
- input
- .data(phl, '#' + label.attr('id')) //set a reference to the label
- .data(ph,ph) //set that the field is watermarked
- .addClass(ph) //add the watermark class
- .after(label) //add the label field to the page
-
- //setup overlay
- itemFocus.call(this);
- itemBlur.call(this);
- });
- };
-
- $.fn.unplaceholder = function(){
- this.each(function(){
- var input=$(this),
- label=$(input.data(phl));
-
- if (input.data(ph) !== ph) return;
-
- label.remove();
- input.removeData(ph).removeData(phl).removeClass(ph).unbind('change',itemChange);
- });
- };
-
- function bindEvents() {
- if (boundEvents) return;
-
- //prepare live bindings if not already done.
- $(document).on('reset', 'form', function(){$(this).find('.'+ph).each(itemBlur);});
- $(document).on('keydown mousedown mouseclick focus focusin', '.'+ph, itemFocus);
- $(document).on('blur focusout', '.'+ph, itemBlur);
- $(document).on('change', '.'+ph, itemChange);
- $(document).on('click mouseup', '.'+phl, function(){$($(this).data(ph)).focus();});
-
- bound = true;
- boundEvents = true;
- };
-
- function itemChange() {
- var input = $(this);
- if (!!input.val()) {
- $(input.data(phl)).hide();
- return;
- }
- if (input.data(ph+'FOCUSED') != 1) {
- showPHL(input);
- }
- }
-
- function itemFocus() {
- $($(this).data(ph+'FOCUSED',1).data(phl)).hide();
- };
-
- function itemBlur() {
- var that = this;
- showPHL($(this).removeData(ph+'FOCUSED'));
-
- //use timeout to let other validators/formatters directly bound to blur/focusout work
- setTimeout(function(){
- var input = $(that);
-
- //if the item wasn't refocused, test the item
- if (input.data(ph+'FOCUSED') != 1) {
- showPHL(input);
- }
- }, 200);
- };
-
- function showPHL(input, forced) {
- var label = $(input.data(phl));
-
- //if not already shown, and needs to be, show it.
- if ((forced || label.css('display') == 'none') && !input.val())
- label
- .text(input.attr('placeholder'))
- .css('top', input.position().top + 'px')
- .css('left', input.position().left + 'px')
- .css('display', 'block');
-
- //console.dir({ 'input': { 'id':input.attr('id'), 'pos': input.position() }});
- }
-
- var cr;
- function checkResize() {
- if (cr) window.clearTimeout(cr);
- cr = window.setTimeout(checkResize2, 50);
- }
- function checkResize2() {
- $('.' + ph).each(function(){
- var input = $(this);
- var focused = $(this).data(ph+'FOCUSED');
- if (!focused) showPHL(input, true);
- });
- }
-
-}(jQuery)); \ No newline at end of file
diff --git a/radicale_web/web/infcloud/lib/jquery.quicksearch.js b/radicale_web/web/infcloud/lib/jquery.quicksearch.js
deleted file mode 100644
index fe2f0a5..0000000
--- a/radicale_web/web/infcloud/lib/jquery.quicksearch.js
+++ /dev/null
@@ -1,205 +0,0 @@
-(function($, window, document, undefined) {
- $.fn.quicksearch = function (target, opt) {
-
- var timeout, cache, rowcache, jq_results, val = '', e = this, options = $.extend({
- delay: 100,
- selector: null,
- stripeRows: null,
- loader: null,
- noResults: '',
- matchedResultsCount: 0,
- bind: 'keyup',
- onBefore: function () {
- return;
- },
- onAfter: function () {
- return;
- },
- show: function () {
- this.style.display = "";
- },
- hide: function () {
- this.style.display = "none";
- },
- prepareQuery: function (val) {
- return val.toLowerCase().split(' ');
- },
- testQuery: function (query, txt, _row) {
- for (var i = 0; i < query.length; i += 1) {
- if (txt.indexOf(query[i]) === -1) {
- return false;
- }
- }
- return true;
- }
- }, opt);
-
- this.go = function () {
-
- var i = 0,
- numMatchedRows = 0,
- noresults = true,
- query = options.prepareQuery(val),
- val_empty = (val.replace(' ', '').length === 0);
-
- for (var i = 0, len = rowcache.length; i < len; i++) {
- if (val_empty || options.testQuery(query, cache[i], rowcache[i])) {
- options.show.apply(rowcache[i]);
- noresults = false;
- numMatchedRows++;
- } else {
- options.hide.apply(rowcache[i]);
- }
- }
-
- if (noresults) {
- this.results(false);
- } else {
- this.results(true);
- this.stripe();
- }
-
- this.matchedResultsCount = numMatchedRows;
- this.loader(false);
- options.onAfter();
-
- return this;
- };
-
- /*
- * External API so that users can perform search programatically.
- * */
- this.search = function (submittedVal) {
- val = submittedVal;
- e.trigger();
- };
-
- /*
- * External API to get the number of matched results as seen in
- * https://github.com/ruiz107/quicksearch/commit/f78dc440b42d95ce9caed1d087174dd4359982d6
- * */
- this.currentMatchedResults = function() {
- return this.matchedResultsCount;
- };
-
- this.stripe = function () {
-
- if (typeof options.stripeRows === "object" && options.stripeRows !== null)
- {
- var joined = options.stripeRows.join(' ');
- var stripeRows_length = options.stripeRows.length;
-
- jq_results.not(':hidden').each(function (i) {
- $(this).removeClass(joined).addClass(options.stripeRows[i % stripeRows_length]);
- });
- }
-
- return this;
- };
-
- this.strip = function (input) {
- return $.trim(input.toLowerCase());
- };
-
- this.strip_html = function (input) {
- var output = input.replace(new RegExp('<[^<]+\>', 'g'), "");
- output = $.trim(output.toLowerCase());
- return output;
- };
-
- this.results = function (bool) {
- if (typeof options.noResults === "string" && options.noResults !== "") {
- if (bool) {
- $(options.noResults).hide();
- } else {
- $(options.noResults).show();
- }
- }
- return this;
- };
-
- this.loader = function (bool) {
- if (typeof options.loader === "string" && options.loader !== "") {
- (bool) ? $(options.loader).show() : $(options.loader).hide();
- }
- return this;
- };
-
- this.cache = function () {
- var type = $.type(target);
-
- // Target is a string - selector for HTML elements
- if(type==='string')
- jq_results = $(target);
- // Target is an array of objects
- else if(type==='array') {
- jq_results=target.slice();
- }
- // Target is an object containing ...
- else if(type==='object') {
- jq_results = [];
- $.each(target, function(key, val){
- // ... arrays of objects
- if(val instanceof Array)
- $.merge(jq_results,val);
- // ... other objects
- else
- jq_results.push(val);
- });
- }
-
- // if (typeof options.noResults==="string" && options.noResults!=="") {
- // jq_results = jq_results.not(options.noResults);
- // }
-
- // var t = (typeof options.selector === "string") ? jq_results.find(options.selector) : $(target).not(options.noResults);
-
- cache = $.map(jq_results, function (item) {
- return (type==='string') ? e.strip_html(item.innerHTML) : (typeof item.searchvalue==='string') ? e.strip(item.searchvalue) : '';
- });
-
- rowcache = $.map(jq_results, function (item) {
- return item;
- });
-
- /*
- * Modified fix for sync-ing "val".
- * Original fix https://github.com/michaellwest/quicksearch/commit/4ace4008d079298a01f97f885ba8fa956a9703d1
- * */
- val = val || this.val() || "";
-
- return this.go();
- };
-
- this.trigger = function () {
- this.loader(true);
- options.onBefore();
-
- window.clearTimeout(timeout);
- timeout = window.setTimeout(function () {
- e.go();
- }, options.delay);
-
- return this;
- };
-
- this.cache();
- this.results(true);
- this.stripe();
- this.loader(false);
-
- return this.each(function () {
-
- /*
- * Changed from .bind to .on.
- * */
- $(this).on(options.bind, function () {
-
- val = $(this).val();
- e.trigger();
- });
- });
-
- };
-
-}(jQuery, this, document));
diff --git a/radicale_web/web/infcloud/lib/jquery.tagsinput.js b/radicale_web/web/infcloud/lib/jquery.tagsinput.js
deleted file mode 100644
index 1493079..0000000
--- a/radicale_web/web/infcloud/lib/jquery.tagsinput.js
+++ /dev/null
@@ -1,436 +0,0 @@
-/*
-
- jQuery Tags Input Plugin 1.3.3 (with minor modifications for CardDavMATE)
-
- Copyright (c) 2011 XOXCO, Inc
-
- Documentation for this plugin lives here:
- http://xoxco.com/clickable/jquery-tags-input
-
- Licensed under the MIT license:
- http://www.opensource.org/licenses/mit-license.php
-
- ben@xoxco.com
-
-*/
-
-(function($){
- var tags_settings=new Array();
- var tags_callbacks=new Array();
-
- String.prototype.escapeCustom=function(inputDelimiter)
- {
- var value=(this==undefined ? '' : this),
- output='';
-
- for(var i=0; i<value.length; i++)
- {
- if(value[i]==inputDelimiter || value[i]=='\\')
- output+='\\';
-
- output+=value[i];
- }
- return output;
- }
-
- // split and unescape values
- String.prototype.splitCustom=function(inputDelimiter)
- {
- var outputArray=new Array(),
- value=this,
- j=0;
-
- for(var i=0; i<value.length; i++)
- {
- if(value[i]==inputDelimiter)
- {
- if(outputArray[j]==undefined)
- outputArray[j]='';
- ++j;
- continue;
- }
- else if(value[i]=='\\')
- ++i;
-
- outputArray[j]=(outputArray[j]==undefined ? '' : outputArray[j])+value[i];
- }
- return outputArray;
- }
-
- $.fn.doAutosize=function(o)
- {
- var minWidth=$(this).data('minwidth'),
- maxWidth=$(this).data('maxwidth'),
- val='',
- input=$(this),
- testSubject=$('#'+$(this).data('tester_id'));
-
- if(val===(val=input.val()))
- return;
-
- // Enter new content into testSubject
- var escaped=val.replace(/\s/g,'&nbsp;'); // get proper width for values with leading spaces (or only spaces)
- testSubject.html(escaped);
-
- // Calculate new width + whether to change
- var testerWidth=testSubject.width(),
- newWidth=(testerWidth+o.comfortZone)>=minWidth ? testerWidth+o.comfortZone : minWidth,
- currentWidth=input.width(),
- isValidWidthChange=(newWidth<currentWidth && newWidth>=minWidth) || (newWidth>minWidth && newWidth<maxWidth);
-
- // Animate width
- if(isValidWidthChange)
- input.width(newWidth);
- };
-
- $.fn.resetAutosize=function(options)
- {
- // alert(JSON.stringify(options));
- var minWidth=$(this).data('minwidth') || options.minInputWidth || $(this).width(),
- maxWidth=$(this).data('maxwidth') || options.maxInputWidth || ($(this).closest('.tagsinput').width()-options.inputPadding),
- val='',
- input=$(this),
- testSubject=$('<tester/>').css({
- position: 'absolute',
- top: -9999,
- left: -9999,
- width: 'auto',
- fontSize: input.css('fontSize'),
- fontFamily: input.css('fontFamily'),
- fontWeight: input.css('fontWeight'),
- letterSpacing: input.css('letterSpacing'),
- whiteSpace: 'nowrap'
- }),
- testerId=$(this).attr('id')+'_autosize_tester';
-
- if(!$('#'+testerId).length>0)
- {
- testSubject.attr('id', testerId);
- testSubject.appendTo('body');
- }
-
- input.data('minwidth', minWidth);
- input.data('maxwidth', maxWidth);
- input.data('tester_id', testerId);
- input.css('width', minWidth);
- };
-
- $.fn.addTag=function(value, options)
- {
- options=jQuery.extend({focus: false, callback: true, imported: false}, options);
-
- this.each(function()
- {
- var id=$(this).attr('id');
-
- if(tags_settings[id].allowDelimiterInValue==true)
- var tagslist=$(this).val().splitCustom(tags_settings[id].delimiter);
- else
- var tagslist=$(this).val().split(delimiter[id]);
-
- if(tagslist[0]=='')
- tagslist=new Array();
-
- if(options.trimInput==true)
- value=jQuery.trim(value);
-
- var skipTag=false;
- var duplicate=$(tagslist).tagExist(value);
- if(tags_callbacks[id] && tags_callbacks[id]['validateTag'])
- skipTag=!tags_callbacks[id]['validateTag'].call(this, value, options.imported, duplicate);
- if(!skipTag && options.unique)
- skipTag=duplicate;
-
- if(skipTag)
- $(this).parent().find('#'+id+'_tag').addClass('not_valid'); //Marks fake input as not_valid to let styling it
-
- if(value!='' && skipTag!=true)
- {
- $('<span>').addClass('tag').append(
- $('<span>').text(value),
- $('<a>', {
- href: '#',
- title: 'Removing tag',
- text: 'x'
- }).click(function(){return $('#'+id).removeTag(value)})
- ).insertBefore($(this).parent().find('#'+id+'_addTag'));
-
- tagslist.push(value);
-
- var tmpRef=$(this).parent().find('#'+id+'_tag');
- tmpRef.val('');
- if(options.focus)
- tmpRef.focus();
- else
- tmpRef.blur();
-
- $.fn.tagsInput.updateTagsField(this, tagslist);
-
- if(options.callback && tags_callbacks[id] && tags_callbacks[id]['onAddTag'])
- {
- var f=tags_callbacks[id]['onAddTag'];
- f.call(this, value);
- }
- if(tags_callbacks[id] && tags_callbacks[id]['onChange'])
- {
- var i=tagslist.length;
- var f=tags_callbacks[id]['onChange'];
- f.call(this, tagslist[i-1], options.imported);
- }
- }
- });
- return false;
- };
-
- $.fn.removeTag = function(value)
- {
- this.each(function()
- {
- var id=$(this).attr('id');
-
- if(tags_settings[id].allowDelimiterInValue==true)
- var old=$(this).val().splitCustom(tags_settings[id].delimiter);
- else
- var old=$(this).val().split(delimiter[id]);
-
- $(this).parent().find('#'+id+'_tagsinput .tag').remove();
-
- var str='';
- for(i=0; i<old.length; i++)
- if(old[i]!=value)
- str=(str=='' ? '' : str+tags_settings[id].delimiter)+(tags_settings[id].allowDelimiterInValue==true ? old[i].escapeCustom(tags_settings[id].delimiter) : old[i]);
-
- $.fn.tagsInput.importTags(this, str);
- if(tags_callbacks[id] && tags_callbacks[id]['onRemoveTag'])
- {
- var f=tags_callbacks[id]['onRemoveTag'];
- f.call(this, value);
- }
- });
- return false;
- };
-
- $.fn.tagExist=function(val)
- {
- return (jQuery.inArray(val, $(this))>=0); //true when tag exists, false when not
- };
-
- // clear all existing tags and import new ones from a string
- $.fn.importTags=function(str)
- {
- $(this).parent().find('#'+$(this).attr('id')+'_tagsinput .tag').remove();
- $.fn.tagsInput.importTags(this, str);
- }
-
- $.fn.tagsInput=function(options)
- {
- var settings=jQuery.extend({
- interactive: true,
- defaultText: 'add a tag',
- useNativePlaceholder:false,
- minChars: 0,
- width: '300px',
- height: '100px',
- autocomplete: {selectFirst: false},
- hide: true,
- delimiter: ',',
- allowDelimiterInValue: false,
- trimInput: true,
- unique: true,
- removeWithBackspace: true,
- color: '#000000',
- placeholderColor: '#666666',
- autosize: true,
- comfortZone: 20,
- inputPadding: 6*2
- }, options);
-
- this.each(function()
- {
- if(settings.hide)
- $(this).hide();
-
- var id=$(this).attr('id');
- var data=jQuery.extend({
- real_inputObj: $(this),
- pid: id,
- real_input: '#'+id,
- holder: '#'+id+'_tagsinput',
- input_wrapper: '#'+id+'_addTag',
- fake_input: '#'+id+'_tag'
- }, settings);
-
- tags_settings[id]={delimiter: data.delimiter, allowDelimiterInValue: data.allowDelimiterInValue};
-
- if(settings.onAddTag || settings.onRemoveTag || settings.onChange || settings.validateTag)
- {
- tags_callbacks[id] = new Array();
- tags_callbacks[id]['onAddTag'] = settings.onAddTag;
- tags_callbacks[id]['onRemoveTag'] = settings.onRemoveTag;
- tags_callbacks[id]['onChange'] = settings.onChange;
- tags_callbacks[id]['validateTag'] = settings.validateTag;
- }
-
- var markup='<div id="'+id+'_tagsinput" class="tagsinput"><div id="'+id+'_addTag">';
- if(settings.interactive)
- markup=markup+'<div class="input_container"><input id="'+id+'_tag" type="text" value=""'+(settings.useNativePlaceholder==true ? ' placeholder="'+settings.defaultText+'" data-default=""' : ' data-default="'+settings.defaultText+'"')+' /></div>';
- markup=markup+'</div><div class="tags_clear"></div></div>';
-
- var tmpMarkupObj=$(markup).insertAfter(this);
-
- if(settings.width!=null)
- tmpMarkupObj.css('width', settings.width);
- if(settings.height!=null)
- tmpMarkupObj.css('height', settings.height);
-
- if($(this).val()!='')
- $.fn.tagsInput.importTags($(this), $(this).val());
-
- if(settings.interactive)
- {
- tmpMarkupObj.val(tmpMarkupObj.attr('data-default'));
- tmpMarkupObj.css('color', settings.placeholderColor);
- tmpMarkupObj.resetAutosize(settings);
-
- tmpMarkupObj.bind('click', data, function(event)
- {
- $(this).find(event.data.fake_input).focus();
- });
-
- tmpMarkupObj.find(data.fake_input).bind('focus', data, function(event)
- {
- if($(this).val() == $(this).attr('data-default'))
- $(this).val('');
-
- $(this).css('color', settings.color);
- });
-
- if(settings.autocomplete_url!=undefined)
- {
- var autocomplete_options={source: settings.autocomplete_url};
- for(var attrname in settings.autocomplete)
- autocomplete_options[attrname]=settings.autocomplete[attrname];
-
- if(jQuery.Autocompleter!==undefined)
- {
- tmpMarkupObj.find(data.fake_input).autocomplete(settings.autocomplete_url, settings.autocomplete);
- tmpMarkupObj.find(data.fake_input).bind('result', data, function(event, data, formatted)
- {
- if(data)
- event.data.real_inputObj.addTag(data[0] + "", {focus: true, unique: settings.unique, trimInput: settings.trimInput});
- });
- }
- else if(jQuery.ui.autocomplete!==undefined)
- {
- tmpMarkupObj.find(data.fake_input).autocomplete(autocomplete_options);
- tmpMarkupObj.find(data.fake_input).bind('autocompleteselect', data, function(event,ui)
- {
- event.data.real_inputObj.addTag(ui.item.value, {focus: true, unique: settings.unique, trimInput: settings.trimInput});
- return false;
- });
- }
-
- // if a user tabs out of the field, create a new tag
- // this is only available if autocomplete is not used.
- tmpMarkupObj.find(data.fake_input).bind('blur', data, function(event)
- {
- var d=$(this).attr('data-default');
-
- if($(this).val()!='' && $(this).val()!=d)
- {
- if((event.data.minChars<=$(this).val().length) && (!event.data.maxChars || (event.data.maxChars>=$(this).val().length)))
- event.data.real_inputObj.addTag($(this).val(), {focus: true, unique: settings.unique, trimInput: settings.trimInput});
- }
- else
- $(this).val($(this).attr('data-default'));
-
- $(this).css('color', settings.placeholderColor);
- return false;
- });
- }
-
- // if user types a comma, create a new tag
- tmpMarkupObj.find(data.fake_input).bind('keypress', data, function(event)
- {
- if(settings.allowDelimiterInValue==false && event.which==event.data.delimiter.charCodeAt(0) || event.which==13)
- {
- event.preventDefault();
- if((event.data.minChars<=$(this).val().length) && (!event.data.maxChars || (event.data.maxChars>=$(this).val().length)))
- event.data.real_inputObj.addTag($(event.data.fake_input).val(), {focus: true, unique: settings.unique, trimInput: settings.trimInput});
- $(this).resetAutosize(settings);
- return false;
- }
- else if(event.data.autosize)
- $(this).doAutosize(settings);
- });
-
- //Delete last tag on backspace
- data.removeWithBackspace && tmpMarkupObj.find(data.fake_input).bind('keydown', data, function(event)
- {
- if($(this).closest('.tagsinput').hasClass('readonly')==false && event.keyCode==8 && $(this).val()=='')
- {
- event.preventDefault();
- var last_tag=$(this).closest('.tagsinput').find('.tag:last').text();
- var id=$(this).attr('id').replace(/_tag$/, '');
- last_tag=last_tag.replace(/x$/, '');
- event.data.real_inputObj.removeTag(last_tag);
- $(this).trigger('focus');
- }
- });
-
- tmpMarkupObj.find(data.fake_input).blur();
-
- //Removes the not_valid class when user changes the value of the fake input
- if(data.unique)
- {
- tmpMarkupObj.find(data.fake_input).keydown(function(event)
- {
- if(event.keyCode==8 || String.fromCharCode(event.which).match(/\w+|[áéíóúÁÉÍÓÚñÑ,/]+/))
- $(this).removeClass('not_valid');
- });
- }
- } // if settings.interactive
-
- // store settings
- $(this).data('tagsOptions', settings);
-
- return false;
- });
- return this;
- };
-
- $.fn.tagsInput.updateTagsField=function(obj, tagslist)
- {
- var id = $(obj).attr('id');
-
- if(tags_settings[id].allowDelimiterInValue==true)
- for(var i=0;i<tagslist.length;i++)
- tagslist[i]=tagslist[i].escapeCustom(tags_settings[id].delimiter);
-
- $(obj).val(tagslist.join(tags_settings[id].delimiter));
- };
-
- $.fn.tagsInput.importTags=function(obj, val)
- {
- var settings=jQuery.extend({
- trimInput: true,
- unique: true
- }, $(obj).data('tagsOptions'));
-
- $(obj).val('');
- var id=$(obj).attr('id');
-
- if(tags_settings[id].allowDelimiterInValue==true)
- var tags=val.splitCustom(tags_settings[id].delimiter);
- else
- var tags=val.split(delimiter[id]);
-
- for(var i=0; i<tags.length; i++)
- $(obj).addTag(tags[i], {focus: true, unique: settings.unique, trimInput: settings.trimInput, callback: false, imported: true});
- if(tags_callbacks[id] && tags_callbacks[id]['onChange'])
- {
- var f=tags_callbacks[id]['onChange'];
- f.call(obj, tags[i], true);
- }
- };
-})(jQuery);
diff --git a/radicale_web/web/infcloud/lib/rrule.js b/radicale_web/web/infcloud/lib/rrule.js
deleted file mode 100644
index ed2689e..0000000
--- a/radicale_web/web/infcloud/lib/rrule.js
+++ /dev/null
@@ -1,1910 +0,0 @@
-/*!
- * rrule.js - Library for working with recurrence rules for calendar dates.
- * https://github.com/jakubroztocil/rrule
- *
- * Copyright 2010, Jakub Roztocil and Lars Schoning
- * Licenced under the BSD licence.
- * https://github.com/jakubroztocil/rrule/blob/master/LICENCE
- *
- * Based on:
- * python-dateutil - Extensions to the standard Python datetime module.
- * Copyright (c) 2003-2011 - Gustavo Niemeyer <gustavo@niemeyer.net>
- * Copyright (c) 2012 - Tomi Pieviläinen <tomi.pievilainen@iki.fi>
- * https://github.com/jakubroztocil/rrule/blob/master/LICENCE
- *
- */
-(function(root){
-
-var serverSide = typeof module !== 'undefined' && module.exports;
-
-
-var getnlp = function() {
- if (!getnlp._nlp) {
- if (serverSide) {
- // Lazy, runtime import to avoid circular refs.
- getnlp._nlp = require('./nlp')
- } else if (!(getnlp._nlp = root._RRuleNLP)) {
- throw new Error(
- 'You need to include rrule/nlp.js for fromText/toText to work.'
- )
- }
- }
- return getnlp._nlp;
-};
-
-
-//=============================================================================
-// Date utilities
-//=============================================================================
-
-/**
- * General date-related utilities.
- * Also handles several incompatibilities between JavaScript and Python
- *
- */
-var dateutil = {
-
- MONTH_DAYS: [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31],
-
- /**
- * Number of milliseconds of one day
- */
- ONE_DAY: 1000 * 60 * 60 * 24,
-
- /**
- * @see: <http://docs.python.org/library/datetime.html#datetime.MAXYEAR>
- */
- MAXYEAR: 9999,
-
- /**
- * Python uses 1-Jan-1 as the base for calculating ordinals but we don't
- * want to confuse the JS engine with milliseconds > Number.MAX_NUMBER,
- * therefore we use 1-Jan-1970 instead
- */
- ORDINAL_BASE: new Date(1970, 0, 1),
-
- /**
- * Python: MO-SU: 0 - 6
- * JS: SU-SAT 0 - 6
- */
- PY_WEEKDAYS: [6, 0, 1, 2, 3, 4, 5],
-
- /**
- * py_date.timetuple()[7]
- */
- getYearDay: function(date) {
- var dateNoTime = new Date(
- date.getFullYear(), date.getMonth(), date.getDate());
- return Math.ceil(
- (dateNoTime - new Date(date.getFullYear(), 0, 1))
- / dateutil.ONE_DAY) + 1;
- },
-
- isLeapYear: function(year) {
- if (year instanceof Date) {
- year = year.getFullYear();
- }
- return ((year % 4 === 0) && (year % 100 !== 0)) || (year % 400 === 0);
- },
-
- /**
- * @return {Number} the date's timezone offset in ms
- */
- tzOffset: function(date) {
- return date.getTimezoneOffset() * 60 * 1000
- },
-
- /**
- * @see: <http://www.mcfedries.com/JavaScript/DaysBetween.asp>
- */
- daysBetween: function(date1, date2) {
- // The number of milliseconds in one day
- // Convert both dates to milliseconds
- var date1_ms = date1.getTime() - dateutil.tzOffset(date1);
- var date2_ms = date2.getTime() - dateutil.tzOffset(date2);
- // Calculate the difference in milliseconds
- var difference_ms = Math.abs(date1_ms - date2_ms);
- // Convert back to days and return
- return Math.round(difference_ms / dateutil.ONE_DAY);
- },
-
- /**
- * @see: <http://docs.python.org/library/datetime.html#datetime.date.toordinal>
- */
- toOrdinal: function(date) {
- return dateutil.daysBetween(date, dateutil.ORDINAL_BASE);
- },
-
- /**
- * @see - <http://docs.python.org/library/datetime.html#datetime.date.fromordinal>
- */
- fromOrdinal: function(ordinal) {
- var millisecsFromBase = ordinal * dateutil.ONE_DAY;
- return new Date(dateutil.ORDINAL_BASE.getTime()
- - dateutil.tzOffset(dateutil.ORDINAL_BASE)
- + millisecsFromBase
- + dateutil.tzOffset(new Date(millisecsFromBase)));
- },
-
- /**
- * @see: <http://docs.python.org/library/calendar.html#calendar.monthrange>
- */
- monthRange: function(year, month) {
- var date = new Date(year, month, 1);
- return [dateutil.getWeekday(date), dateutil.getMonthDays(date)];
- },
-
- getMonthDays: function(date) {
- var month = date.getMonth();
- return month == 1 && dateutil.isLeapYear(date)
- ? 29
- : dateutil.MONTH_DAYS[month];
- },
-
- /**
- * @return {Number} python-like weekday
- */
- getWeekday: function(date) {
- return dateutil.PY_WEEKDAYS[date.getDay()];
- },
-
- /**
- * @see: <http://docs.python.org/library/datetime.html#datetime.datetime.combine>
- */
- combine: function(date, time) {
- time = time || date;
- return new Date(
- date.getFullYear(), date.getMonth(), date.getDate(),
- time.getHours(), time.getMinutes(), time.getSeconds()
- );
- },
-
- clone: function(date) {
- var dolly = new Date(date.getTime());
- dolly.setMilliseconds(0);
- return dolly;
- },
-
- cloneDates: function(dates) {
- var clones = [];
- for (var i = 0; i < dates.length; i++) {
- clones.push(dateutil.clone(dates[i]));
- }
- return clones;
- },
-
- /**
- * Sorts an array of Date or dateutil.Time objects
- */
- sort: function(dates) {
- dates.sort(function(a, b){
- return a.getTime() - b.getTime();
- });
- },
-
- timeToUntilString: function(time) {
- var date = new Date(time);
- var comp, comps = [
- date.getUTCFullYear(),
- date.getUTCMonth() + 1,
- date.getUTCDate(),
- 'T',
- date.getUTCHours(),
- date.getUTCMinutes(),
- date.getUTCSeconds(),
- 'Z'
- ];
- for (var i = 0; i < comps.length; i++) {
- comp = comps[i];
- if (!/[TZ]/.test(comp) && comp < 10) {
- comps[i] = '0' + String(comp);
- }
- }
- return comps.join('');
- },
-
- untilStringToDate: function(until) {
- var re = /^(\d{4})(\d{2})(\d{2})(T(\d{2})(\d{2})(\d{2})Z)?$/;
- var bits = re.exec(until);
- if (!bits) {
- throw new Error('Invalid UNTIL value: ' + until)
- }
- return new Date(
- Date.UTC(bits[1],
- bits[2] - 1,
- bits[3],
- bits[5] || 0,
- bits[6] || 0,
- bits[7] || 0
- ));
- }
-
-};
-
-dateutil.Time = function(hour, minute, second) {
- this.hour = hour;
- this.minute = minute;
- this.second = second;
-};
-
-dateutil.Time.prototype = {
- getHours: function() {
- return this.hour;
- },
- getMinutes: function() {
- return this.minute;
- },
- getSeconds: function() {
- return this.second;
- },
- getTime: function() {
- return ((this.hour * 60 * 60)
- + (this.minute * 60)
- + this.second)
- * 1000;
- }
-};
-
-
-//=============================================================================
-// Helper functions
-//=============================================================================
-
-
-/**
- * Simplified version of python's range()
- */
-var range = function(start, end) {
- if (arguments.length === 1) {
- end = start;
- start = 0;
- }
- var rang = [];
- for (var i = start; i < end; i++) {
- rang.push(i);
- }
- return rang;
-};
-var repeat = function(value, times) {
- var i = 0, array = [];
- if (value instanceof Array) {
- for (; i < times; i++) {
- array[i] = [].concat(value);
- }
- } else {
- for (; i < times; i++) {
- array[i] = value;
- }
- }
- return array;
-};
-
-
-/**
- * closure/goog/math/math.js:modulo
- * Copyright 2006 The Closure Library Authors.
- * The % operator in JavaScript returns the remainder of a / b, but differs from
- * some other languages in that the result will have the same sign as the
- * dividend. For example, -1 % 8 == -1, whereas in some other languages
- * (such as Python) the result would be 7. This function emulates the more
- * correct modulo behavior, which is useful for certain applications such as
- * calculating an offset index in a circular list.
- *
- * @param {number} a The dividend.
- * @param {number} b The divisor.
- * @return {number} a % b where the result is between 0 and b (either 0 <= x < b
- * or b < x <= 0, depending on the sign of b).
- */
-var pymod = function(a, b) {
- var r = a % b;
- // If r and b differ in sign, add b to wrap the result to the correct sign.
- return (r * b < 0) ? r + b : r;
-};
-
-
-/**
- * @see: <http://docs.python.org/library/functions.html#divmod>
- */
-var divmod = function(a, b) {
- return {div: Math.floor(a / b), mod: pymod(a, b)};
-};
-
-
-/**
- * Python-like boolean
- * @return {Boolean} value of an object/primitive, taking into account
- * the fact that in Python an empty list's/tuple's
- * boolean value is False, whereas in JS it's true
- */
-var plb = function(obj) {
- return (obj instanceof Array && obj.length == 0)
- ? false
- : Boolean(obj);
-};
-
-
-/**
- * Return true if a value is in an array
- */
-var contains = function(arr, val) {
- return arr.indexOf(val) != -1;
-};
-
-
-//=============================================================================
-// Date masks
-//=============================================================================
-
-// Every mask is 7 days longer to handle cross-year weekly periods.
-
-var M365MASK = [].concat(
- repeat(1, 31), repeat(2, 28), repeat(3, 31),
- repeat(4, 30), repeat(5, 31), repeat(6, 30),
- repeat(7, 31), repeat(8, 31), repeat(9, 30),
- repeat(10, 31), repeat(11, 30), repeat(12, 31),
- repeat(1, 7)
-);
-var M366MASK = [].concat(
- repeat(1, 31), repeat(2, 29), repeat(3, 31),
- repeat(4, 30), repeat(5, 31), repeat(6, 30),
- repeat(7, 31), repeat(8, 31), repeat(9, 30),
- repeat(10, 31), repeat(11, 30), repeat(12, 31),
- repeat(1, 7)
-);
-
-var
- M28 = range(1, 29),
- M29 = range(1, 30),
- M30 = range(1, 31),
- M31 = range(1, 32);
-var MDAY366MASK = [].concat(
- M31, M29, M31,
- M30, M31, M30,
- M31, M31, M30,
- M31, M30, M31,
- M31.slice(0, 7)
-);
-var MDAY365MASK = [].concat(
- M31, M28, M31,
- M30, M31, M30,
- M31, M31, M30,
- M31, M30, M31,
- M31.slice(0, 7)
-);
-
-M28 = range(-28, 0);
-M29 = range(-29, 0);
-M30 = range(-30, 0);
-M31 = range(-31, 0);
-var NMDAY366MASK = [].concat(
- M31, M29, M31,
- M30, M31, M30,
- M31, M31, M30,
- M31, M30, M31,
- M31.slice(0, 7)
-);
-var NMDAY365MASK = [].concat(
- M31, M28, M31,
- M30, M31, M30,
- M31, M31, M30,
- M31, M30, M31,
- M31.slice(0, 7)
-);
-
-var M366RANGE = [0, 31, 60, 91, 121, 152, 182, 213, 244, 274, 305, 335, 366];
-var M365RANGE = [0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334, 365];
-
-var WDAYMASK = (function() {
- for (var wdaymask = [], i = 0; i < 55; i++) {
- wdaymask = wdaymask.concat(range(7));
- }
- return wdaymask;
-}());
-
-
-//=============================================================================
-// Weekday
-//=============================================================================
-
-var Weekday = function(weekday, n) {
- if (n === 0) {
- throw new Error('Can\'t create weekday with n == 0');
- }
- this.weekday = weekday;
- this.n = n;
-};
-
-Weekday.prototype = {
-
- // __call__ - Cannot call the object directly, do it through
- // e.g. RRule.TH.nth(-1) instead,
- nth: function(n) {
- return this.n == n ? this : new Weekday(this.weekday, n);
- },
-
- // __eq__
- equals: function(other) {
- return this.weekday == other.weekday && this.n == other.n;
- },
-
- // __repr__
- toString: function() {
- var s = ['MO', 'TU', 'WE', 'TH', 'FR', 'SA', 'SU'][this.weekday];
- if (this.n) {
- s = (this.n > 0 ? '+' : '') + String(this.n) + s;
- }
- return s;
- },
-
- getJsWeekday: function() {
- return this.weekday == 6 ? 0 : this.weekday + 1;
- }
-
-};
-
-
-//=============================================================================
-// RRule
-//=============================================================================
-
-/**
- *
- * @param {Object?} options - see <http://labix.org/python-dateutil/#head-cf004ee9a75592797e076752b2a889c10f445418>
- * The only required option is `freq`, one of RRule.YEARLY, RRule.MONTHLY, ...
- * @constructor
- */
-var RRule = function(options, noCache) {
-
- // RFC string
- this._string = null;
-
- options = options || {};
-
- this._cache = noCache ? null : {
- all: false,
- before: [],
- after: [],
- between: []
- };
-
- // used by toString()
- this.origOptions = {};
-
- var invalid = [],
- keys = Object.keys(options),
- defaultKeys = Object.keys(RRule.DEFAULT_OPTIONS);
-
- // Shallow copy for origOptions and check for invalid
- keys.forEach(function(key) {
- this.origOptions[key] = options[key];
- if (!contains(defaultKeys, key)) invalid.push(key);
- }, this);
-
- if (invalid.length) {
- throw new Error('Invalid options: ' + invalid.join(', '))
- }
-
- if (!RRule.FREQUENCIES[options.freq] && options.byeaster === null) {
- throw new Error('Invalid frequency: ' + String(options.freq))
- }
-
- // Merge in default options
- defaultKeys.forEach(function(key) {
- if (!contains(keys, key)) options[key] = RRule.DEFAULT_OPTIONS[key];
- });
-
- var opts = this.options = options;
-
- if (opts.byeaster !== null) {
- opts.freq = RRule.YEARLY;
- }
-
- if (!opts.dtstart) {
- opts.dtstart = new Date();
- opts.dtstart.setMilliseconds(0);
- }
-
- if (opts.wkst === null) {
- opts.wkst = RRule.MO.weekday;
- } else if (typeof opts.wkst == 'number') {
- // cool, just keep it like that
- } else {
- opts.wkst = opts.wkst.weekday;
- }
-
- if (opts.bysetpos !== null) {
- if (typeof opts.bysetpos == 'number') {
- opts.bysetpos = [opts.bysetpos];
- }
- for (var i = 0; i < opts.bysetpos.length; i++) {
- var v = opts.bysetpos[i];
- if (v == 0 || !(-366 <= v && v <= 366)) {
- throw new Error(
- 'bysetpos must be between 1 and 366,' +
- ' or between -366 and -1'
- );
- }
- }
- }
-
- if (!(plb(opts.byweekno) || plb(opts.byyearday)
- || plb(opts.bymonthday) || opts.byweekday !== null
- || opts.byeaster !== null))
- {
- switch (opts.freq) {
- case RRule.YEARLY:
- if (!opts.bymonth) {
- opts.bymonth = opts.dtstart.getMonth() + 1;
- }
- opts.bymonthday = opts.dtstart.getDate();
- break;
- case RRule.MONTHLY:
- opts.bymonthday = opts.dtstart.getDate();
- break;
- case RRule.WEEKLY:
- opts.byweekday = dateutil.getWeekday(
- opts.dtstart);
- break;
- }
- }
-
- // bymonth
- if (opts.bymonth !== null
- && !(opts.bymonth instanceof Array)) {
- opts.bymonth = [opts.bymonth];
- }
-
- // byyearday
- if (opts.byyearday !== null
- && !(opts.byyearday instanceof Array)) {
- opts.byyearday = [opts.byyearday];
- }
-
- // bymonthday
- if (opts.bymonthday === null) {
- opts.bymonthday = [];
- opts.bynmonthday = [];
- } else if (opts.bymonthday instanceof Array) {
- var bymonthday = [], bynmonthday = [];
-
- for (i = 0; i < opts.bymonthday.length; i++) {
- var v = opts.bymonthday[i];
- if (v > 0) {
- bymonthday.push(v);
- } else if (v < 0) {
- bynmonthday.push(v);
- }
- }
- opts.bymonthday = bymonthday;
- opts.bynmonthday = bynmonthday;
- } else {
- if (opts.bymonthday < 0) {
- opts.bynmonthday = [opts.bymonthday];
- opts.bymonthday = [];
- } else {
- opts.bynmonthday = [];
- opts.bymonthday = [opts.bymonthday];
- }
- }
-
- // byweekno
- if (opts.byweekno !== null
- && !(opts.byweekno instanceof Array)) {
- opts.byweekno = [opts.byweekno];
- }
-
- // byweekday / bynweekday
- if (opts.byweekday === null) {
- opts.bynweekday = null;
- } else if (typeof opts.byweekday == 'number') {
- opts.byweekday = [opts.byweekday];
- opts.bynweekday = null;
-
- } else if (opts.byweekday instanceof Weekday) {
-
- if (!opts.byweekday.n || opts.freq > RRule.MONTHLY) {
- opts.byweekday = [opts.byweekday.weekday];
- opts.bynweekday = null;
- } else {
- opts.bynweekday = [
- [opts.byweekday.weekday,
- opts.byweekday.n]
- ];
- opts.byweekday = null;
- }
-
- } else {
- var byweekday = [], bynweekday = [];
-
- for (i = 0; i < opts.byweekday.length; i++) {
- var wday = opts.byweekday[i];
-
- if (typeof wday == 'number') {
- byweekday.push(wday);
- } else if (!wday.n || opts.freq > RRule.MONTHLY) {
- byweekday.push(wday.weekday);
- } else {
- bynweekday.push([wday.weekday, wday.n]);
- }
- }
- opts.byweekday = plb(byweekday) ? byweekday : null;
- opts.bynweekday = plb(bynweekday) ? bynweekday : null;
- }
-
- // byhour
- if (opts.byhour === null) {
- opts.byhour = (opts.freq < RRule.HOURLY)
- ? [opts.dtstart.getHours()]
- : null;
- } else if (typeof opts.byhour == 'number') {
- opts.byhour = [opts.byhour];
- }
-
- // byminute
- if (opts.byminute === null) {
- opts.byminute = (opts.freq < RRule.MINUTELY)
- ? [opts.dtstart.getMinutes()]
- : null;
- } else if (typeof opts.byminute == 'number') {
- opts.byminute = [opts.byminute];
- }
-
- // bysecond
- if (opts.bysecond === null) {
- opts.bysecond = (opts.freq < RRule.SECONDLY)
- ? [opts.dtstart.getSeconds()]
- : null;
- } else if (typeof opts.bysecond == 'number') {
- opts.bysecond = [opts.bysecond];
- }
-
- if (opts.freq >= RRule.HOURLY) {
- this.timeset = null;
- } else {
- this.timeset = [];
- for (i = 0; i < opts.byhour.length; i++) {
- var hour = opts.byhour[i];
- for (var j = 0; j < opts.byminute.length; j++) {
- var minute = opts.byminute[j];
- for (var k = 0; k < opts.bysecond.length; k++) {
- var second = opts.bysecond[k];
- // python:
- // datetime.time(hour, minute, second,
- // tzinfo=self._tzinfo))
- this.timeset.push(new dateutil.Time(hour, minute, second));
- }
- }
- }
- dateutil.sort(this.timeset);
- }
-
-};
-//}}}
-
-// RRule class 'constants'
-
-RRule.FREQUENCIES = [
- 'YEARLY', 'MONTHLY', 'WEEKLY', 'DAILY',
- 'HOURLY', 'MINUTELY', 'SECONDLY'
-];
-
-RRule.YEARLY = 0;
-RRule.MONTHLY = 1;
-RRule.WEEKLY = 2;
-RRule.DAILY = 3;
-RRule.HOURLY = 4;
-RRule.MINUTELY = 5;
-RRule.SECONDLY = 6;
-
-RRule.MO = new Weekday(0);
-RRule.TU = new Weekday(1);
-RRule.WE = new Weekday(2);
-RRule.TH = new Weekday(3);
-RRule.FR = new Weekday(4);
-RRule.SA = new Weekday(5);
-RRule.SU = new Weekday(6);
-
-RRule.DEFAULT_OPTIONS = {
- freq: null,
- dtstart: null,
- interval: 1,
- wkst: RRule.MO,
- count: null,
- until: null,
- bysetpos: null,
- bymonth: null,
- bymonthday: null,
- byyearday: null,
- byweekno: null,
- byweekday: null,
- byhour: null,
- byminute: null,
- bysecond: null,
- byeaster: null
-};
-
-
-
-RRule.parseText = function(text, language) {
- return getnlp().parseText(text, language)
-};
-
-RRule.fromText = function(text, language) {
- return getnlp().fromText(text, language)
-};
-
-RRule.optionsToString = function(options) {
- var key, keys, defaultKeys, value, strValues, pairs = [];
-
- keys = Object.keys(options);
- defaultKeys = Object.keys(RRule.DEFAULT_OPTIONS);
-
- for (var i = 0; i < keys.length; i++) {
-
- if (!contains(defaultKeys, keys[i])) continue;
-
- key = keys[i].toUpperCase();
- value = options[keys[i]];
- strValues = [];
-
- if (value === null || value instanceof Array && !value.length) {
- continue;
- }
-
- switch (key) {
- case 'FREQ':
- value = RRule.FREQUENCIES[options.freq];
- break;
- case 'WKST':
- value = value.toString();
- break;
- case 'BYWEEKDAY':
- /*
- NOTE: BYWEEKDAY is a special case.
- RRule() deconstructs the rule.options.byweekday array
- into an array of Weekday arguments.
- On the other hand, rule.origOptions is an array of Weekdays.
- We need to handle both cases here.
- It might be worth change RRule to keep the Weekdays.
-
- Also, BYWEEKDAY (used by RRule) vs. BYDAY (RFC)
-
- */
- key = 'BYDAY';
- if (!(value instanceof Array)) {
- value = [value];
- }
- for (var wday, j = 0; j < value.length; j++) {
- wday = value[j];
- if (wday instanceof Weekday) {
- // good
- } else if (wday instanceof Array) {
- wday = new Weekday(wday[0], wday[1]);
- } else {
- wday = new Weekday(wday);
- }
- strValues[j] = wday.toString();
- }
- value = strValues;
- break;
- case'DTSTART':
- case'UNTIL':
- value = dateutil.timeToUntilString(value);
- break;
- default:
- if (value instanceof Array) {
- for (var j = 0; j < value.length; j++) {
- strValues[j] = String(value[j]);
- }
- value = strValues;
- } else {
- value = String(value);
- }
-
- }
- pairs.push([key, value]);
- }
-
- var strings = [];
- for (var i = 0; i < pairs.length; i++) {
- var attr = pairs[i];
- strings.push(attr[0] + '=' + attr[1].toString());
- }
- return strings.join(';');
-
-};
-
-RRule.prototype = {
-
- /**
- * @param {Function} iterator - optional function that will be called
- * on each date that is added. It can return false
- * to stop the iteration.
- * @return Array containing all recurrences.
- */
- all: function(iterator) {
- if (iterator) {
- return this._iter(new CallbackIterResult('all', {}, iterator));
- } else {
- var result = this._cacheGet('all');
- if (result === false) {
- result = this._iter(new IterResult('all', {}));
- this._cacheAdd('all', result);
- }
- return result;
- }
- },
-
- /**
- * Returns all the occurrences of the rrule between after and before.
- * The inc keyword defines what happens if after and/or before are
- * themselves occurrences. With inc == True, they will be included in the
- * list, if they are found in the recurrence set.
- * @return Array
- */
- between: function(after, before, inc, iterator) {
- var args = {
- before: before,
- after: after,
- inc: inc
- }
-
- if (iterator) {
- return this._iter(
- new CallbackIterResult('between', args, iterator));
- } else {
- var result = this._cacheGet('between', args);
- if (result === false) {
- result = this._iter(new IterResult('between', args));
- this._cacheAdd('between', result, args);
- }
- return result;
- }
- },
-
- /**
- * Returns the last recurrence before the given datetime instance.
- * The inc keyword defines what happens if dt is an occurrence.
- * With inc == True, if dt itself is an occurrence, it will be returned.
- * @return Date or null
- */
- before: function(dt, inc) {
- var args = {
- dt: dt,
- inc: inc
- },
- result = this._cacheGet('before', args);
- if (result === false) {
- result = this._iter(new IterResult('before', args));
- this._cacheAdd('before', result, args);
- }
- return result;
- },
-
- /**
- * Returns the first recurrence after the given datetime instance.
- * The inc keyword defines what happens if dt is an occurrence.
- * With inc == True, if dt itself is an occurrence, it will be returned.
- * @return Date or null
- */
- after: function(dt, inc) {
- var args = {
- dt: dt,
- inc: inc
- },
- result = this._cacheGet('after', args);
- if (result === false) {
- result = this._iter(new IterResult('after', args));
- this._cacheAdd('after', result, args);
- }
- return result;
- },
-
- /**
- * Returns the number of recurrences in this set. It will have go trough
- * the whole recurrence, if this hasn't been done before.
- */
- count: function() {
- return this.all().length;
- },
-
- /**
- * Converts the rrule into its string representation
- * @see <http://www.ietf.org/rfc/rfc2445.txt>
- * @return String
- */
- toString: function() {
- return RRule.optionsToString(this.origOptions);
- },
-
- /**
- * Will convert all rules described in nlp:ToText
- * to text.
- */
- toText: function(gettext, language) {
- return getnlp().toText(this, gettext, language);
- },
-
- isFullyConvertibleToText: function() {
- return getnlp().isFullyConvertible(this)
- },
-
- /**
- * @param {String} what - all/before/after/between
- * @param {Array,Date} value - an array of dates, one date, or null
- * @param {Object?} args - _iter arguments
- */
- _cacheAdd: function(what, value, args) {
-
- if (!this._cache) return;
-
- if (value) {
- value = (value instanceof Date)
- ? dateutil.clone(value)
- : dateutil.cloneDates(value);
- }
-
- if (what == 'all') {
- this._cache.all = value;
- } else {
- args._value = value;
- this._cache[what].push(args);
- }
-
- },
-
- /**
- * @return false - not in the cache
- * null - cached, but zero occurrences (before/after)
- * Date - cached (before/after)
- * [] - cached, but zero occurrences (all/between)
- * [Date1, DateN] - cached (all/between)
- */
- _cacheGet: function(what, args) {
-
- if (!this._cache) {
- return false;
- }
-
- var cached = false;
-
- if (what == 'all') {
- cached = this._cache.all;
- } else {
- // Let's see whether we've already called the
- // 'what' method with the same 'args'
- loopItems:
- for (var item, i = 0; i < this._cache[what].length; i++) {
- item = this._cache[what][i];
- for (var k in args) {
- if (args.hasOwnProperty(k)
- && String(args[k]) != String(item[k])) {
- continue loopItems;
- }
- }
- cached = item._value;
- break;
- }
- }
-
- if (!cached && this._cache.all) {
- // Not in the cache, but we already know all the occurrences,
- // so we can find the correct dates from the cached ones.
- var iterResult = new IterResult(what, args);
- for (var i = 0; i < this._cache.all.length; i++) {
- if (!iterResult.accept(this._cache.all[i])) {
- break;
- }
- }
- cached = iterResult.getValue();
- this._cacheAdd(what, cached, args);
- }
-
- return cached instanceof Array
- ? dateutil.cloneDates(cached)
- : (cached instanceof Date
- ? dateutil.clone(cached)
- : cached);
- },
-
- /**
- * @return a RRule instance with the same freq and options
- * as this one (cache is not cloned)
- */
- clone: function() {
- return new RRule(this.origOptions);
- },
-
- _iter: function(iterResult) {
-
- /* Since JavaScript doesn't have the python's yield operator (<1.7),
- we use the IterResult object that tells us when to stop iterating.
-
- */
-
- var dtstart = this.options.dtstart;
-
- var
- year = dtstart.getFullYear(),
- month = dtstart.getMonth() + 1,
- day = dtstart.getDate(),
- hour = dtstart.getHours(),
- minute = dtstart.getMinutes(),
- second = dtstart.getSeconds(),
- weekday = dateutil.getWeekday(dtstart),
- yearday = dateutil.getYearDay(dtstart);
-
- // Some local variables to speed things up a bit
- var
- freq = this.options.freq,
- interval = this.options.interval,
- wkst = this.options.wkst,
- until = this.options.until,
- bymonth = this.options.bymonth,
- byweekno = this.options.byweekno,
- byyearday = this.options.byyearday,
- byweekday = this.options.byweekday,
- byeaster = this.options.byeaster,
- bymonthday = this.options.bymonthday,
- bynmonthday = this.options.bynmonthday,
- bysetpos = this.options.bysetpos,
- byhour = this.options.byhour,
- byminute = this.options.byminute,
- bysecond = this.options.bysecond;
-
- var ii = new Iterinfo(this);
- ii.rebuild(year, month);
-
- var getdayset = {};
- getdayset[RRule.YEARLY] = ii.ydayset;
- getdayset[RRule.MONTHLY] = ii.mdayset;
- getdayset[RRule.WEEKLY] = ii.wdayset;
- getdayset[RRule.DAILY] = ii.ddayset;
- getdayset[RRule.HOURLY] = ii.ddayset;
- getdayset[RRule.MINUTELY] = ii.ddayset;
- getdayset[RRule.SECONDLY] = ii.ddayset;
-
- getdayset = getdayset[freq];
-
- var timeset;
- if (freq < RRule.HOURLY) {
- timeset = this.timeset;
- } else {
- var gettimeset = {};
- gettimeset[RRule.HOURLY] = ii.htimeset;
- gettimeset[RRule.MINUTELY] = ii.mtimeset;
- gettimeset[RRule.SECONDLY] = ii.stimeset;
- gettimeset = gettimeset[freq];
- if ((freq >= RRule.HOURLY && plb(byhour) && !contains(byhour, hour)) ||
- (freq >= RRule.MINUTELY && plb(byminute) && !contains(byminute, minute)) ||
- (freq >= RRule.SECONDLY && plb(bysecond) && !contains(bysecond, minute)))
- {
- timeset = [];
- } else {
- timeset = gettimeset.call(ii, hour, minute, second);
- }
- }
-
- var filtered, total = 0, count = this.options.count;
-
- var iterNo = 0;
-
- var i, j, k, dm, div, mod, tmp, pos, dayset, start, end, fixday;
-
- while (true) {
-
- // Get dayset with the right frequency
- tmp = getdayset.call(ii, year, month, day);
- dayset = tmp[0]; start = tmp[1]; end = tmp[2];
-
- // Do the "hard" work ;-)
- filtered = false;
- for (j = start; j < end; j++) {
-
- i = dayset[j];
-
- if ((plb(bymonth) && !contains(bymonth, ii.mmask[i])) ||
- (plb(byweekno) && !ii.wnomask[i]) ||
- (plb(byweekday) && !contains(byweekday, ii.wdaymask[i])) ||
- (plb(ii.nwdaymask) && !ii.nwdaymask[i]) ||
- (byeaster !== null && !contains(ii.eastermask, i)) ||
- (
- (plb(bymonthday) || plb(bynmonthday)) &&
- !contains(bymonthday, ii.mdaymask[i]) &&
- !contains(bynmonthday, ii.nmdaymask[i])
- )
- ||
- (
- plb(byyearday)
- &&
- (
- (
- i < ii.yearlen &&
- !contains(byyearday, i + 1) &&
- !contains(byyearday, -ii.yearlen + i)
- )
- ||
- (
- i >= ii.yearlen &&
- !contains(byyearday, i + 1 - ii.yearlen) &&
- !contains(byyearday, -ii.nextyearlen + i - ii.yearlen)
- )
- )
- )
- )
- {
- dayset[i] = null;
- filtered = true;
- }
- }
-
- // Output results
- if (plb(bysetpos) && plb(timeset)) {
-
- var daypos, timepos, poslist = [];
-
- for (i, j = 0; j < bysetpos.length; j++) {
- var pos = bysetpos[j];
- if (pos < 0) {
- daypos = Math.floor(pos / timeset.length);
- timepos = pymod(pos, timeset.length);
- } else {
- daypos = Math.floor((pos - 1) / timeset.length);
- timepos = pymod((pos - 1), timeset.length);
- }
-
- try {
- tmp = [];
- for (k = start; k < end; k++) {
- var val = dayset[k];
- if (val === null) {
- continue;
- }
- tmp.push(val);
- }
- if (daypos < 0) {
- // we're trying to emulate python's aList[-n]
- i = tmp.slice(daypos)[0];
- } else {
- i = tmp[daypos];
- }
-
- var time = timeset[timepos];
-
- var date = dateutil.fromOrdinal(ii.yearordinal + i);
- var res = dateutil.combine(date, time);
- // XXX: can this ever be in the array?
- // - compare the actual date instead?
- if (!contains(poslist, res)) {
- poslist.push(res);
- }
- } catch (e) {}
- }
-
- dateutil.sort(poslist);
-
- for (j = 0; j < poslist.length; j++) {
- var res = poslist[j];
- if (until && res > until) {
- this._len = total;
- return iterResult.getValue();
- } else if (res >= dtstart) {
- ++total;
- if (!iterResult.accept(res)) {
- return iterResult.getValue();
- }
- if (count) {
- --count;
- if (!count) {
- this._len = total;
- return iterResult.getValue();
- }
- }
- }
- }
-
- } else {
- for (j = start; j < end; j++) {
- i = dayset[j];
- if (i !== null) {
- var date = dateutil.fromOrdinal(ii.yearordinal + i);
- for (k = 0; k < timeset.length; k++) {
- var time = timeset[k];
- var res = dateutil.combine(date, time);
- if (until && res > until) {
- this._len = total;
- return iterResult.getValue();
- } else if (res >= dtstart) {
- ++total;
- if (!iterResult.accept(res)) {
- return iterResult.getValue();
- }
- if (count) {
- --count;
- if (!count) {
- this._len = total;
- return iterResult.getValue();
- }
- }
- }
- }
- }
- }
- }
-
- // Handle frequency and interval
- fixday = false;
- if (freq == RRule.YEARLY) {
- year += interval;
- if (year > dateutil.MAXYEAR) {
- this._len = total;
- return iterResult.getValue();
- }
- ii.rebuild(year, month);
- } else if (freq == RRule.MONTHLY) {
- month += interval;
- if (month > 12) {
- div = Math.floor(month / 12);
- mod = pymod(month, 12);
- month = mod;
- year += div;
- if (month == 0) {
- month = 12;
- --year;
- }
- if (year > dateutil.MAXYEAR) {
- this._len = total;
- return iterResult.getValue();
- }
- }
- ii.rebuild(year, month);
- } else if (freq == RRule.WEEKLY) {
- if (wkst > weekday) {
- day += -(weekday + 1 + (6 - wkst)) + interval * 7;
- } else {
- day += -(weekday - wkst) + interval * 7;
- }
- weekday = wkst;
- fixday = true;
- } else if (freq == RRule.DAILY) {
- day += interval;
- fixday = true;
- } else if (freq == RRule.HOURLY) {
- if (filtered) {
- // Jump to one iteration before next day
- hour += Math.floor((23 - hour) / interval) * interval;
- }
- while (true) {
- hour += interval;
- dm = divmod(hour, 24);
- div = dm.div;
- mod = dm.mod;
- if (div) {
- hour = mod;
- day += div;
- fixday = true;
- }
- if (!plb(byhour) || contains(byhour, hour)) {
- break;
- }
- }
- timeset = gettimeset.call(ii, hour, minute, second);
- } else if (freq == RRule.MINUTELY) {
- if (filtered) {
- // Jump to one iteration before next day
- minute += Math.floor(
- (1439 - (hour * 60 + minute)) / interval) * interval;
- }
- while(true) {
- minute += interval;
- dm = divmod(minute, 60);
- div = dm.div;
- mod = dm.mod;
- if (div) {
- minute = mod;
- hour += div;
- dm = divmod(hour, 24);
- div = dm.div;
- mod = dm.mod;
- if (div) {
- hour = mod;
- day += div;
- fixday = true;
- filtered = false;
- }
- }
- if ((!plb(byhour) || contains(byhour, hour)) &&
- (!plb(byminute) || contains(byminute, minute))) {
- break;
- }
- }
- timeset = gettimeset.call(ii, hour, minute, second);
- } else if (freq == RRule.SECONDLY) {
- if (filtered) {
- // Jump to one iteration before next day
- second += Math.floor(
- (86399 - (hour * 3600 + minute * 60 + second))
- / interval) * interval;
- }
- while (true) {
- second += interval;
- dm = divmod(second, 60);
- div = dm.div;
- mod = dm.mod;
- if (div) {
- second = mod;
- minute += div;
- dm = divmod(minute, 60);
- div = dm.div;
- mod = dm.mod;
- if (div) {
- minute = mod;
- hour += div;
- dm = divmod(hour, 24);
- div = dm.div;
- mod = dm.mod;
- if (div) {
- hour = mod;
- day += div;
- fixday = true;
- }
- }
- }
- if ((!plb(byhour) || contains(byhour, hour)) &&
- (!plb(byminute) || contains(byminute, minute)) &&
- (!plb(bysecond) || contains(bysecond, second)))
- {
- break;
- }
- }
- timeset = gettimeset.call(ii, hour, minute, second);
- }
-
- if (fixday && day > 28) {
- var daysinmonth = dateutil.monthRange(year, month - 1)[1];
- if (day > daysinmonth) {
- while (day > daysinmonth) {
- day -= daysinmonth;
- ++month;
- if (month == 13) {
- month = 1;
- ++year;
- if (year > dateutil.MAXYEAR) {
- this._len = total;
- return iterResult.getValue();
- }
- }
- daysinmonth = dateutil.monthRange(year, month - 1)[1];
- }
- ii.rebuild(year, month);
- }
- }
- }
- }
-
-};
-
-
-RRule.parseString = function(rfcString) {
- rfcString = rfcString.replace(/^\s+|\s+$/, '');
- if (!rfcString.length) {
- return null;
- }
-
- var i, j, key, value, attr,
- attrs = rfcString.split(';'),
- options = {};
-
- for (i = 0; i < attrs.length; i++) {
- attr = attrs[i].split('=');
- key = attr[0];
- value = attr[1];
- switch (key) {
- case 'FREQ':
- options.freq = RRule[value];
- break;
- case 'WKST':
- options.wkst = RRule[value];
- break;
- case 'COUNT':
- case 'INTERVAL':
- case 'BYSETPOS':
- case 'BYMONTH':
- case 'BYMONTHDAY':
- case 'BYYEARDAY':
- case 'BYWEEKNO':
- case 'BYHOUR':
- case 'BYMINUTE':
- case 'BYSECOND':
- if (value.indexOf(',') != -1) {
- value = value.split(',');
- for (j = 0; j < value.length; j++) {
- if (/^[+-]?\d+$/.test(value[j])) {
- value[j] = Number(value[j]);
- }
- }
- } else if (/^[+-]?\d+$/.test(value)) {
- value = Number(value);
- }
- key = key.toLowerCase();
- options[key] = value;
- break;
- case 'BYDAY': // => byweekday
- var n, wday, day, days = value.split(',');
- options.byweekday = [];
- for (j = 0; j < days.length; j++) {
- day = days[j];
- if (day.length == 2) { // MO, TU, ...
- wday = RRule[day]; // wday instanceof Weekday
- options.byweekday.push(wday);
- } else { // -1MO, +3FR, 1SO, ...
- day = day.match(/^([+-]?\d)([A-Z]{2})$/);
- n = Number(day[1]);
- wday = day[2];
- wday = RRule[wday].weekday;
- options.byweekday.push(new Weekday(wday, n));
- }
- }
- break;
- case 'DTSTART':
- options.dtstart = dateutil.untilStringToDate(value);
- break;
- case 'UNTIL':
- options.until = dateutil.untilStringToDate(value);
- break;
- case 'BYEASTER':
- options.byeaster = Number(value);
- break;
- default:
- throw new Error("Unknown RRULE property '" + key + "'");
- }
- }
- return options;
-};
-
-
-RRule.fromString = function(string) {
- return new RRule(RRule.parseString(string));
-};
-
-
-//=============================================================================
-// Iterinfo
-//=============================================================================
-
-var Iterinfo = function(rrule) {
- this.rrule = rrule;
- this.lastyear = null;
- this.lastmonth = null;
- this.yearlen = null;
- this.nextyearlen = null;
- this.yearordinal = null;
- this.yearweekday = null;
- this.mmask = null;
- this.mrange = null;
- this.mdaymask = null;
- this.nmdaymask = null;
- this.wdaymask = null;
- this.wnomask = null;
- this.nwdaymask = null;
- this.eastermask = null;
-};
-
-Iterinfo.prototype.easter = function(y, offset) {
- offset = offset || 0;
-
- var a = y % 19,
- b = Math.floor(y / 100),
- c = y % 100,
- d = Math.floor(b / 4),
- e = b % 4,
- f = Math.floor((b + 8) / 25),
- g = Math.floor((b - f + 1) / 3),
- h = Math.floor(19 * a + b - d - g + 15) % 30,
- i = Math.floor(c / 4),
- k = c % 4,
- l = Math.floor(32 + 2 * e + 2 * i - h - k) % 7,
- m = Math.floor((a + 11 * h + 22 * l) / 451),
- month = Math.floor((h + l - 7 * m + 114) / 31),
- day = (h + l - 7 * m + 114) % 31 + 1,
- date = Date.UTC(y, month - 1, day + offset),
- yearStart = Date.UTC(y, 0, 1);
-
- return [ Math.ceil((date - yearStart) / (1000 * 60 * 60 * 24)) ];
-}
-
-Iterinfo.prototype.rebuild = function(year, month) {
-
- var rr = this.rrule;
-
- if (year != this.lastyear) {
-
- this.yearlen = dateutil.isLeapYear(year) ? 366 : 365;
- this.nextyearlen = dateutil.isLeapYear(year + 1) ? 366 : 365;
- var firstyday = new Date(year, 0, 1);
-
- this.yearordinal = dateutil.toOrdinal(firstyday);
- this.yearweekday = dateutil.getWeekday(firstyday);
-
- var wday = dateutil.getWeekday(new Date(year, 0, 1));
-
- if (this.yearlen == 365) {
- this.mmask = [].concat(M365MASK);
- this.mdaymask = [].concat(MDAY365MASK);
- this.nmdaymask = [].concat(NMDAY365MASK);
- this.wdaymask = WDAYMASK.slice(wday);
- this.mrange = [].concat(M365RANGE);
- } else {
- this.mmask = [].concat(M366MASK);
- this.mdaymask = [].concat(MDAY366MASK);
- this.nmdaymask = [].concat(NMDAY366MASK);
- this.wdaymask = WDAYMASK.slice(wday);
- this.mrange = [].concat(M366RANGE);
- }
-
- if (!plb(rr.options.byweekno)) {
- this.wnomask = null;
- } else {
- this.wnomask = repeat(0, this.yearlen + 7);
- var no1wkst, firstwkst, wyearlen;
- no1wkst = firstwkst = pymod(
- 7 - this.yearweekday + rr.options.wkst, 7);
- if (no1wkst >= 4) {
- no1wkst = 0;
- // Number of days in the year, plus the days we got
- // from last year.
- wyearlen = this.yearlen + pymod(
- this.yearweekday - rr.options.wkst, 7);
- } else {
- // Number of days in the year, minus the days we
- // left in last year.
- wyearlen = this.yearlen - no1wkst;
- }
- var div = Math.floor(wyearlen / 7);
- var mod = pymod(wyearlen, 7);
- var numweeks = Math.floor(div + (mod / 4));
- for (var n, i, j = 0; j < rr.options.byweekno.length; j++) {
- n = rr.options.byweekno[j];
- if (n < 0) {
- n += numweeks + 1;
- } if (!(0 < n && n <= numweeks)) {
- continue;
- } if (n > 1) {
- i = no1wkst + (n - 1) * 7;
- if (no1wkst != firstwkst) {
- i -= 7-firstwkst;
- }
- } else {
- i = no1wkst;
- }
- for (var k = 0; k < 7; k++) {
- this.wnomask[i] = 1;
- i++;
- if (this.wdaymask[i] == rr.options.wkst) {
- break;
- }
- }
- }
-
- if (contains(rr.options.byweekno, 1)) {
- // Check week number 1 of next year as well
- // orig-TODO : Check -numweeks for next year.
- var i = no1wkst + numweeks * 7;
- if (no1wkst != firstwkst) {
- i -= 7 - firstwkst;
- }
- if (i < this.yearlen) {
- // If week starts in next year, we
- // don't care about it.
- for (var j = 0; j < 7; j++) {
- this.wnomask[i] = 1;
- i += 1;
- if (this.wdaymask[i] == rr.options.wkst) {
- break;
- }
- }
- }
- }
-
- if (no1wkst) {
- // Check last week number of last year as
- // well. If no1wkst is 0, either the year
- // started on week start, or week number 1
- // got days from last year, so there are no
- // days from last year's last week number in
- // this year.
- var lnumweeks;
- if (!contains(rr.options.byweekno, -1)) {
- var lyearweekday = dateutil.getWeekday(
- new Date(year - 1, 0, 1));
- var lno1wkst = pymod(
- 7 - lyearweekday + rr.options.wkst, 7);
- var lyearlen = dateutil.isLeapYear(year - 1) ? 366 : 365;
- if (lno1wkst >= 4) {
- lno1wkst = 0;
- lnumweeks = Math.floor(
- 52
- + pymod(
- lyearlen + pymod(
- lyearweekday - rr.options.wkst, 7), 7)
- / 4);
- } else {
- lnumweeks = Math.floor(
- 52 + pymod(this.yearlen - no1wkst, 7) / 4);
- }
- } else {
- lnumweeks = -1;
- }
- if (contains(rr.options.byweekno, lnumweeks)) {
- for (var i = 0; i < no1wkst; i++) {
- this.wnomask[i] = 1;
- }
- }
- }
- }
- }
-
- if (plb(rr.options.bynweekday)
- && (month != this.lastmonth || year != this.lastyear)) {
- var ranges = [];
- if (rr.options.freq == RRule.YEARLY) {
- if (plb(rr.options.bymonth)) {
- for (j = 0; j < rr.options.bymonth.length; j++) {
- month = rr.options.bymonth[j];
- ranges.push(this.mrange.slice(month - 1, month + 1));
- }
- } else {
- ranges = [[0, this.yearlen]];
- }
- } else if (rr.options.freq == RRule.MONTHLY) {
- ranges = [this.mrange.slice(month - 1, month + 1)];
- }
- if (plb(ranges)) {
- // Weekly frequency won't get here, so we may not
- // care about cross-year weekly periods.
- this.nwdaymask = repeat(0, this.yearlen);
-
- for (var j = 0; j < ranges.length; j++) {
- var rang = ranges[j];
- var first = rang[0], last = rang[1];
- last -= 1;
- for (var k = 0; k < rr.options.bynweekday.length; k++) {
- var wday = rr.options.bynweekday[k][0],
- n = rr.options.bynweekday[k][1];
- if (n < 0) {
- i = last + (n + 1) * 7;
- i -= pymod(this.wdaymask[i] - wday, 7);
- } else {
- i = first + (n - 1) * 7;
- i += pymod(7 - this.wdaymask[i] + wday, 7);
- }
- if (first <= i && i <= last) {
- this.nwdaymask[i] = 1;
- }
- }
- }
-
- }
-
- this.lastyear = year;
- this.lastmonth = month;
- }
-
- if (rr.options.byeaster !== null) {
- this.eastermask = this.easter(year, rr.options.byeaster);
- }
-};
-
-Iterinfo.prototype.ydayset = function(year, month, day) {
- return [range(this.yearlen), 0, this.yearlen];
-};
-
-Iterinfo.prototype.mdayset = function(year, month, day) {
- var set = repeat(null, this.yearlen);
- var start = this.mrange[month-1];
- var end = this.mrange[month];
- for (var i = start; i < end; i++) {
- set[i] = i;
- }
- return [set, start, end];
-};
-
-Iterinfo.prototype.wdayset = function(year, month, day) {
-
- // We need to handle cross-year weeks here.
- var set = repeat(null, this.yearlen + 7);
- var i = dateutil.toOrdinal(
- new Date(year, month - 1, day)) - this.yearordinal;
- var start = i;
- for (var j = 0; j < 7; j++) {
- set[i] = i;
- ++i;
- if (this.wdaymask[i] == this.rrule.options.wkst) {
- break;
- }
- }
- return [set, start, i];
-};
-
-Iterinfo.prototype.ddayset = function(year, month, day) {
- var set = repeat(null, this.yearlen);
- var i = dateutil.toOrdinal(
- new Date(year, month - 1, day)) - this.yearordinal;
- set[i] = i;
- return [set, i, i + 1];
-};
-
-Iterinfo.prototype.htimeset = function(hour, minute, second) {
- var set = [], rr = this.rrule;
- for (var i = 0; i < rr.options.byminute.length; i++) {
- minute = rr.options.byminute[i];
- for (var j = 0; j < rr.options.bysecond.length; j++) {
- second = rr.options.bysecond[j];
- set.push(new dateutil.Time(hour, minute, second));
- }
- }
- dateutil.sort(set);
- return set;
-};
-
-Iterinfo.prototype.mtimeset = function(hour, minute, second) {
- var set = [], rr = this.rrule;
- for (var j = 0; j < rr.options.bysecond.length; j++) {
- second = rr.options.bysecond[j];
- set.push(new dateutil.Time(hour, minute, second));
- }
- dateutil.sort(set);
- return set;
-};
-
-Iterinfo.prototype.stimeset = function(hour, minute, second) {
- return [new dateutil.Time(hour, minute, second)];
-};
-
-
-//=============================================================================
-// Results
-//=============================================================================
-
-/**
- * This class helps us to emulate python's generators, sorta.
- */
-var IterResult = function(method, args) {
- this.init(method, args)
-};
-
-IterResult.prototype = {
-
- init: function(method, args) {
- this.method = method;
- this.args = args;
-
- this._result = [];
-
- this.minDate = null;
- this.maxDate = null;
-
- if (method == 'between') {
- this.maxDate = args.inc
- ? args.before
- : new Date(args.before.getTime() - 1);
- this.minDate = args.inc
- ? args.after
- : new Date(args.after.getTime() + 1);
- } else if (method == 'before') {
- this.maxDate = args.inc ? args.dt : new Date(args.dt.getTime() - 1);
- } else if (method == 'after') {
- this.minDate = args.inc ? args.dt : new Date(args.dt.getTime() + 1);
- }
- },
-
- /**
- * Possibly adds a date into the result.
- *
- * @param {Date} date - the date isn't necessarly added to the result
- * list (if it is too late/too early)
- * @return {Boolean} true if it makes sense to continue the iteration;
- * false if we're done.
- */
- accept: function(date) {
- var tooEarly = this.minDate && date < this.minDate,
- tooLate = this.maxDate && date > this.maxDate;
-
- if (this.method == 'between') {
- if (tooEarly)
- return true;
- if (tooLate)
- return false;
- } else if (this.method == 'before') {
- if (tooLate)
- return false;
- } else if (this.method == 'after') {
- if (tooEarly)
- return true;
- this.add(date);
- return false;
- }
-
- return this.add(date);
-
- },
-
- /**
- *
- * @param {Date} date that is part of the result.
- * @return {Boolean} whether we are interested in more values.
- */
- add: function(date) {
- this._result.push(date);
- return true;
- },
-
- /**
- * 'before' and 'after' return only one date, whereas 'all'
- * and 'between' an array.
- * @return {Date,Array?}
- */
- getValue: function() {
- switch (this.method) {
- case 'all':
- case 'between':
- return this._result;
- case 'before':
- case 'after':
- return this._result.length
- ? this._result[this._result.length - 1]
- : null;
- }
- }
-
-};
-
-
-/**
- * IterResult subclass that calls a callback function on each add,
- * and stops iterating when the callback returns false.
- */
-var CallbackIterResult = function(method, args, iterator) {
- var allowedMethods = ['all', 'between'];
- if (!contains(allowedMethods, method)) {
- throw new Error('Invalid method "' + method
- + '". Only all and between works with iterator.');
- }
- this.add = function(date) {
- if (iterator(date, this._result.length)) {
- this._result.push(date);
- return true;
- }
- return false;
-
- };
-
- this.init(method, args);
-
-};
-CallbackIterResult.prototype = IterResult.prototype;
-
-
-//=============================================================================
-// Export
-//=============================================================================
-
-if (serverSide) {
- module.exports = {
- RRule: RRule
- // rruleset: rruleset
- }
-}
-if (typeof ender === 'undefined') {
- root['RRule'] = RRule;
- // root['rruleset'] = rruleset;
-}
-
-if (typeof define === "function" && define.amd) {
- /*global define:false */
- define("rrule", [], function () {
- return RRule;
- });
-}
-
-}(this));
diff --git a/radicale_web/web/infcloud/lib/sha256.js b/radicale_web/web/infcloud/lib/sha256.js
deleted file mode 100644
index 529db30..0000000
--- a/radicale_web/web/infcloud/lib/sha256.js
+++ /dev/null
@@ -1,16 +0,0 @@
-/*
-CryptoJS v3.1.2
-code.google.com/p/crypto-js
-(c) 2009-2013 by Jeff Mott. All rights reserved.
-code.google.com/p/crypto-js/wiki/License
-*/
-var CryptoJS=CryptoJS||function(h,s){var f={},t=f.lib={},g=function(){},j=t.Base={extend:function(a){g.prototype=this;var c=new g;a&&c.mixIn(a);c.hasOwnProperty("init")||(c.init=function(){c.$super.init.apply(this,arguments)});c.init.prototype=c;c.$super=this;return c},create:function(){var a=this.extend();a.init.apply(a,arguments);return a},init:function(){},mixIn:function(a){for(var c in a)a.hasOwnProperty(c)&&(this[c]=a[c]);a.hasOwnProperty("toString")&&(this.toString=a.toString)},clone:function(){return this.init.prototype.extend(this)}},
-q=t.WordArray=j.extend({init:function(a,c){a=this.words=a||[];this.sigBytes=c!=s?c:4*a.length},toString:function(a){return(a||u).stringify(this)},concat:function(a){var c=this.words,d=a.words,b=this.sigBytes;a=a.sigBytes;this.clamp();if(b%4)for(var e=0;e<a;e++)c[b+e>>>2]|=(d[e>>>2]>>>24-8*(e%4)&255)<<24-8*((b+e)%4);else if(65535<d.length)for(e=0;e<a;e+=4)c[b+e>>>2]=d[e>>>2];else c.push.apply(c,d);this.sigBytes+=a;return this},clamp:function(){var a=this.words,c=this.sigBytes;a[c>>>2]&=4294967295<<
-32-8*(c%4);a.length=h.ceil(c/4)},clone:function(){var a=j.clone.call(this);a.words=this.words.slice(0);return a},random:function(a){for(var c=[],d=0;d<a;d+=4)c.push(4294967296*h.random()|0);return new q.init(c,a)}}),v=f.enc={},u=v.Hex={stringify:function(a){var c=a.words;a=a.sigBytes;for(var d=[],b=0;b<a;b++){var e=c[b>>>2]>>>24-8*(b%4)&255;d.push((e>>>4).toString(16));d.push((e&15).toString(16))}return d.join("")},parse:function(a){for(var c=a.length,d=[],b=0;b<c;b+=2)d[b>>>3]|=parseInt(a.substr(b,
-2),16)<<24-4*(b%8);return new q.init(d,c/2)}},k=v.Latin1={stringify:function(a){var c=a.words;a=a.sigBytes;for(var d=[],b=0;b<a;b++)d.push(String.fromCharCode(c[b>>>2]>>>24-8*(b%4)&255));return d.join("")},parse:function(a){for(var c=a.length,d=[],b=0;b<c;b++)d[b>>>2]|=(a.charCodeAt(b)&255)<<24-8*(b%4);return new q.init(d,c)}},l=v.Utf8={stringify:function(a){try{return decodeURIComponent(escape(k.stringify(a)))}catch(c){throw Error("Malformed UTF-8 data");}},parse:function(a){return k.parse(unescape(encodeURIComponent(a)))}},
-x=t.BufferedBlockAlgorithm=j.extend({reset:function(){this._data=new q.init;this._nDataBytes=0},_append:function(a){"string"==typeof a&&(a=l.parse(a));this._data.concat(a);this._nDataBytes+=a.sigBytes},_process:function(a){var c=this._data,d=c.words,b=c.sigBytes,e=this.blockSize,f=b/(4*e),f=a?h.ceil(f):h.max((f|0)-this._minBufferSize,0);a=f*e;b=h.min(4*a,b);if(a){for(var m=0;m<a;m+=e)this._doProcessBlock(d,m);m=d.splice(0,a);c.sigBytes-=b}return new q.init(m,b)},clone:function(){var a=j.clone.call(this);
-a._data=this._data.clone();return a},_minBufferSize:0});t.Hasher=x.extend({cfg:j.extend(),init:function(a){this.cfg=this.cfg.extend(a);this.reset()},reset:function(){x.reset.call(this);this._doReset()},update:function(a){this._append(a);this._process();return this},finalize:function(a){a&&this._append(a);return this._doFinalize()},blockSize:16,_createHelper:function(a){return function(c,d){return(new a.init(d)).finalize(c)}},_createHmacHelper:function(a){return function(c,d){return(new w.HMAC.init(a,
-d)).finalize(c)}}});var w=f.algo={};return f}(Math);
-(function(h){for(var s=CryptoJS,f=s.lib,t=f.WordArray,g=f.Hasher,f=s.algo,j=[],q=[],v=function(a){return 4294967296*(a-(a|0))|0},u=2,k=0;64>k;){var l;a:{l=u;for(var x=h.sqrt(l),w=2;w<=x;w++)if(!(l%w)){l=!1;break a}l=!0}l&&(8>k&&(j[k]=v(h.pow(u,0.5))),q[k]=v(h.pow(u,1/3)),k++);u++}var a=[],f=f.SHA256=g.extend({_doReset:function(){this._hash=new t.init(j.slice(0))},_doProcessBlock:function(c,d){for(var b=this._hash.words,e=b[0],f=b[1],m=b[2],h=b[3],p=b[4],j=b[5],k=b[6],l=b[7],n=0;64>n;n++){if(16>n)a[n]=
-c[d+n]|0;else{var r=a[n-15],g=a[n-2];a[n]=((r<<25|r>>>7)^(r<<14|r>>>18)^r>>>3)+a[n-7]+((g<<15|g>>>17)^(g<<13|g>>>19)^g>>>10)+a[n-16]}r=l+((p<<26|p>>>6)^(p<<21|p>>>11)^(p<<7|p>>>25))+(p&j^~p&k)+q[n]+a[n];g=((e<<30|e>>>2)^(e<<19|e>>>13)^(e<<10|e>>>22))+(e&f^e&m^f&m);l=k;k=j;j=p;p=h+r|0;h=m;m=f;f=e;e=r+g|0}b[0]=b[0]+e|0;b[1]=b[1]+f|0;b[2]=b[2]+m|0;b[3]=b[3]+h|0;b[4]=b[4]+p|0;b[5]=b[5]+j|0;b[6]=b[6]+k|0;b[7]=b[7]+l|0},_doFinalize:function(){var a=this._data,d=a.words,b=8*this._nDataBytes,e=8*a.sigBytes;
-d[e>>>5]|=128<<24-e%32;d[(e+64>>>9<<4)+14]=h.floor(b/4294967296);d[(e+64>>>9<<4)+15]=b;a.sigBytes=4*d.length;this._process();return this._hash},clone:function(){var a=g.clone.call(this);a._hash=this._hash.clone();return a}});s.SHA256=g._createHelper(f);s.HmacSHA256=g._createHmacHelper(f)})(Math);
diff --git a/radicale_web/web/infcloud/lib/spectrum.js b/radicale_web/web/infcloud/lib/spectrum.js
deleted file mode 100644
index 4b99b07..0000000
--- a/radicale_web/web/infcloud/lib/spectrum.js
+++ /dev/null
@@ -1,2027 +0,0 @@
-// Spectrum Colorpicker v1.2.0
-// https://github.com/bgrins/spectrum
-// Author: Brian Grinstead
-// License: MIT
-
-(function (window, $, undefined) {
- var defaultOpts = {
-
- // Callbacks
- beforeShow: noop,
- move: noop,
- change: noop,
- show: noop,
- hide: noop,
-
- // Options
- color: false,
- flat: false,
- showInput: false,
- allowEmpty: false,
- showButtons: true,
- clickoutFiresChange: false,
- showInitial: false,
- showPalette: false,
- showPaletteOnly: false,
- showSelectionPalette: true,
- localStorageKey: false,
- appendTo: "body",
- maxSelectionSize: 7,
- cancelText: "cancel",
- chooseText: "choose",
- preferredFormat: false,
- className: "",
- showAlpha: false,
- theme: "sp-light",
- palette: ['fff', '000'],
- selectionPalette: [],
- disabled: false
- },
- spectrums = [],
- IE = !!/msie/i.exec( window.navigator.userAgent ),
- rgbaSupport = (function() {
- function contains( str, substr ) {
- return !!~('' + str).indexOf(substr);
- }
-
- var elem = document.createElement('div');
- var style = elem.style;
- style.cssText = 'background-color:rgba(0,0,0,.5)';
- return contains(style.backgroundColor, 'rgba') || contains(style.backgroundColor, 'hsla');
- })(),
- inputTypeColorSupport = (function() {
- var colorInput = $("<input type='color' value='!' />")[0];
- return colorInput.type === "color" && colorInput.value !== "!";
- })(),
- replaceInput = [
- "<div class='sp-replacer'>",
- "<div class='sp-preview'><div class='sp-preview-inner'></div></div>",
- "<div class='sp-dd'>&#9660;</div>",
- "</div>"
- ].join(''),
- markup = (function () {
-
- // IE does not support gradients with multiple stops, so we need to simulate
- // that for the rainbow slider with 8 divs that each have a single gradient
- var gradientFix = "";
- if (IE) {
- for (var i = 1; i <= 6; i++) {
- gradientFix += "<div class='sp-" + i + "'></div>";
- }
- }
-
- return [
- "<div class='sp-container sp-hidden'>",
- "<div class='sp-arrow'></div>",
- "<div class='sp-palette-container'>",
- "<div class='sp-palette sp-thumb sp-cf'></div>",
- "</div>",
- "<div class='sp-picker-container'>",
- "<div class='sp-top sp-cf'>",
- "<div class='sp-fill'></div>",
- "<div class='sp-top-inner'>",
- "<div class='sp-color'>",
- "<div class='sp-sat'>",
- "<div class='sp-val'>",
- "<div class='sp-dragger'></div>",
- "</div>",
- "</div>",
- "</div>",
- "<div class='sp-clear sp-clear-display' title='Clear Color Selection'>",
- "</div>",
- "<div class='sp-hue'>",
- "<div class='sp-slider'></div>",
- gradientFix,
- "</div>",
- "</div>",
- "<div class='sp-alpha'><div class='sp-alpha-inner'><div class='sp-alpha-handle'></div></div></div>",
- "</div>",
- "<div class='sp-input-container sp-cf'>",
- "<input class='sp-input' type='text' spellcheck='false' />",
- "<img data-type='invalidColor' style='margin-top: 1px;margin-left: -20px;display: inline;vertical-align: top;' src='images/error_b.svg' alt='invalid'>",
- "</div>",
- "<div class='sp-initial sp-thumb sp-cf'></div>",
- "<div class='sp-button-container sp-cf'>",
- "<input type='button' class='sp-choose' />",
- "<input type='button' class='sp-cancel' />",
- "</div>",
- "</div>",
- "</div>"
- ].join("");
- })();
-
- function paletteTemplate (p, color, className) {
- var html = [];
- for (var i = 0; i < p.length; i++) {
- var current = p[i];
- if(current) {
- var tiny = tinycolor(current);
- var c = tiny.toHsl().l < 0.5 ? "sp-thumb-el sp-thumb-dark" : "sp-thumb-el sp-thumb-light";
- c += (tinycolor.equals(color, current)) ? " sp-thumb-active" : "";
-
- var swatchStyle = rgbaSupport ? ("background-color:" + tiny.toRgbString()) : "filter:" + tiny.toFilter();
- html.push('<span title="' + tiny.toRgbString() + '" data-color="' + tiny.toRgbString() + '" class="' + c + '"><span class="sp-thumb-inner" style="' + swatchStyle + ';" /></span>');
- } else {
- var cls = 'sp-clear-display';
- html.push('<span title="No Color Selected" data-color="" style="background-color:transparent;" class="' + cls + '"></span>');
- }
- }
- return "<div class='sp-cf " + className + "'>" + html.join('') + "</div>";
- }
-
- function hideAll() {
- for (var i = 0; i < spectrums.length; i++) {
- if (spectrums[i]) {
- spectrums[i].hide();
- }
- }
- }
-
- function instanceOptions(o, callbackContext) {
- var opts = $.extend({}, defaultOpts, o);
- opts.callbacks = {
- 'move': bind(opts.move, callbackContext),
- 'change': bind(opts.change, callbackContext),
- 'show': bind(opts.show, callbackContext),
- 'hide': bind(opts.hide, callbackContext),
- 'beforeShow': bind(opts.beforeShow, callbackContext)
- };
-
- return opts;
- }
-
- function spectrum(element, o) {
-
- var opts = instanceOptions(o, element),
- flat = opts.flat,
- showSelectionPalette = opts.showSelectionPalette,
- localStorageKey = opts.localStorageKey,
- theme = opts.theme,
- callbacks = opts.callbacks,
- resize = throttle(reflow, 10),
- visible = false,
- dragWidth = 0,
- dragHeight = 0,
- dragHelperHeight = 0,
- slideHeight = 0,
- slideWidth = 0,
- alphaWidth = 0,
- alphaSlideHelperWidth = 0,
- slideHelperHeight = 0,
- currentHue = 0,
- currentSaturation = 0,
- currentValue = 0,
- currentAlpha = 1,
- palette = opts.palette.slice(0),
- paletteArray = $.isArray(palette[0]) ? palette : [palette],
- selectionPalette = opts.selectionPalette.slice(0),
- maxSelectionSize = opts.maxSelectionSize,
- draggingClass = "sp-dragging",
- shiftMovementDirection = null;
-
- var doc = element.ownerDocument,
- body = doc.body,
- boundElement = $(element),
- disabled = false,
- container = $(markup, doc).addClass(theme),
- dragger = container.find(".sp-color"),
- dragHelper = container.find(".sp-dragger"),
- slider = container.find(".sp-hue"),
- slideHelper = container.find(".sp-slider"),
- alphaSliderInner = container.find(".sp-alpha-inner"),
- alphaSlider = container.find(".sp-alpha"),
- alphaSlideHelper = container.find(".sp-alpha-handle"),
- textInput = container.find(".sp-input"),
- invalidImage = container.find('img[data-type="invalidColor"]'),
- paletteContainer = container.find(".sp-palette"),
- initialColorContainer = container.find(".sp-initial"),
- cancelButton = container.find(".sp-cancel"),
- clearButton = container.find(".sp-clear"),
- chooseButton = container.find(".sp-choose"),
- isInput = boundElement.is("input"),
- isInputTypeColor = isInput && inputTypeColorSupport && boundElement.attr("type") === "color",
- shouldReplace = isInput && !flat,
- replacer = (shouldReplace) ? $(replaceInput).addClass(theme).addClass(opts.className) : $([]),
- offsetElement = (shouldReplace) ? replacer : boundElement,
- previewElement = replacer.find(".sp-preview-inner"),
- initialColor = opts.color || (isInput && boundElement.val()),
- colorOnShow = false,
- preferredFormat = opts.preferredFormat,
- currentPreferredFormat = preferredFormat,
- clickoutFiresChange = !opts.showButtons || opts.clickoutFiresChange,
- isEmpty = !initialColor,
- allowEmpty = opts.allowEmpty && !isInputTypeColor;
-
- function applyOptions() {
-
- if (opts.showPaletteOnly) {
- opts.showPalette = true;
- }
-
- container.toggleClass("sp-flat", flat);
- container.toggleClass("sp-input-disabled", !opts.showInput);
- container.toggleClass("sp-alpha-enabled", opts.showAlpha);
- container.toggleClass("sp-clear-enabled", allowEmpty);
- container.toggleClass("sp-buttons-disabled", !opts.showButtons);
- container.toggleClass("sp-palette-disabled", !opts.showPalette);
- container.toggleClass("sp-palette-only", opts.showPaletteOnly);
- container.toggleClass("sp-initial-disabled", !opts.showInitial);
- container.addClass(opts.className);
-
- reflow();
- }
-
- function initialize() {
-
- if (IE) {
- container.find("*:not(input)").attr("unselectable", "on");
- }
-
- applyOptions();
-
- if (shouldReplace) {
- boundElement.after(replacer).hide();
- }
-
- if (!allowEmpty) {
- clearButton.hide();
- }
-
- if (flat) {
- boundElement.after(container).hide();
- }
- else {
-
- var appendTo = opts.appendTo === "parent" ? boundElement.parent() : $(opts.appendTo);
- if (appendTo.length !== 1) {
- appendTo = $("body");
- }
-
- appendTo.append(container);
- }
-
- if (localStorageKey && window.localStorage) {
-
- // Migrate old palettes over to new format. May want to remove this eventually.
- try {
- var oldPalette = window.localStorage[localStorageKey].split(",#");
- if (oldPalette.length > 1) {
- delete window.localStorage[localStorageKey];
- $.each(oldPalette, function(i, c) {
- addColorToSelectionPalette(c);
- });
- }
- }
- catch(e) { }
-
- try {
- selectionPalette = window.localStorage[localStorageKey].split(";");
- }
- catch (e) { }
- }
-
- offsetElement.bind("click.spectrum touchstart.spectrum", function (e) {
- if (!disabled) {
- toggle();
- }
-
- e.stopPropagation();
-
- if (!$(e.target).is("input")) {
- e.preventDefault();
- }
- });
-
- if(boundElement.is(":disabled") || (opts.disabled === true)) {
- disable();
- }
-
- // Prevent clicks from bubbling up to document. This would cause it to be hidden.
- container.click(stopPropagation);
-
- // Handle user typed input
- textInput.change(setFromTextInput);
- textInput.bind("paste", function () {
- setTimeout(setFromTextInput, 1);
- });
- textInput.keydown(function (e) { if (e.keyCode == 13) { setFromTextInput(); } });
-
- cancelButton.val(opts.cancelText);
- cancelButton.bind("click.spectrum", function (e) {
- e.stopPropagation();
- e.preventDefault();
- hide("cancel");
- });
-
-
- clearButton.bind("click.spectrum", function (e) {
- e.stopPropagation();
- e.preventDefault();
-
- isEmpty = true;
-
- move();
- if(flat) {
- //for the flat style, this is a change event
- updateOriginalInput(true);
- }
- });
-
-
- chooseButton.val(opts.chooseText);
- chooseButton.bind("click.spectrum", function (e) {
- e.stopPropagation();
- e.preventDefault();
-
- if (isValid()) {
- updateOriginalInput(true);
- hide();
- }
- });
-
- draggable(alphaSlider, function (dragX, dragY, e) {
- currentAlpha = (dragX / alphaWidth);
- isEmpty = false;
- if (e.shiftKey) {
- currentAlpha = Math.round(currentAlpha * 10) / 10;
- }
-
- move();
- });
-
- draggable(slider, function (dragX, dragY) {
- currentHue = parseFloat(dragY / slideHeight);
- isEmpty = false;
- move();
- }, dragStart, dragStop);
-
- draggable(dragger, function (dragX, dragY, e) {
-
- // shift+drag should snap the movement to either the x or y axis.
- if (!e.shiftKey) {
- shiftMovementDirection = null;
- }
- else if (!shiftMovementDirection) {
- var oldDragX = currentSaturation * dragWidth;
- var oldDragY = dragHeight - (currentValue * dragHeight);
- var furtherFromX = Math.abs(dragX - oldDragX) > Math.abs(dragY - oldDragY);
-
- shiftMovementDirection = furtherFromX ? "x" : "y";
- }
-
- var setSaturation = !shiftMovementDirection || shiftMovementDirection === "x";
- var setValue = !shiftMovementDirection || shiftMovementDirection === "y";
-
- if (setSaturation) {
- currentSaturation = parseFloat(dragX / dragWidth);
- }
- if (setValue) {
- currentValue = parseFloat((dragHeight - dragY) / dragHeight);
- }
-
- isEmpty = false;
-
- move();
-
- }, dragStart, dragStop);
-
- if (!!initialColor) {
- set(initialColor);
-
- // In case color was black - update the preview UI and set the format
- // since the set function will not run (default color is black).
- updateUI();
- currentPreferredFormat = preferredFormat || tinycolor(initialColor).format;
-
- addColorToSelectionPalette(initialColor);
- }
- else {
- updateUI();
- }
-
- if (flat) {
- show();
- }
-
- function palletElementClick(e) {
- if (e.data && e.data.ignore) {
- set($(this).data("color"));
- move();
- }
- else {
- set($(this).data("color"));
- updateOriginalInput(true);
- move();
- hide();
- }
-
- return false;
- }
-
- var paletteEvent = IE ? "mousedown.spectrum" : "click.spectrum touchstart.spectrum";
- paletteContainer.delegate(".sp-thumb-el", paletteEvent, palletElementClick);
- initialColorContainer.delegate(".sp-thumb-el:nth-child(1)", paletteEvent, { ignore: true }, palletElementClick);
- }
-
- function addColorToSelectionPalette(color) {
- if (showSelectionPalette) {
- var colorRgb = tinycolor(color).toRgbString();
- if ($.inArray(colorRgb, selectionPalette) === -1) {
- selectionPalette.push(colorRgb);
- while(selectionPalette.length > maxSelectionSize) {
- selectionPalette.shift();
- }
- }
-
- if (localStorageKey && window.localStorage) {
- try {
- window.localStorage[localStorageKey] = selectionPalette.join(";");
- }
- catch(e) { }
- }
- }
- }
-
- function getUniqueSelectionPalette() {
- var unique = [];
- var p = selectionPalette;
- var paletteLookup = {};
- var rgb;
-
- if (opts.showPalette) {
-
- for (var i = 0; i < paletteArray.length; i++) {
- for (var j = 0; j < paletteArray[i].length; j++) {
- rgb = tinycolor(paletteArray[i][j]).toRgbString();
- paletteLookup[rgb] = true;
- }
- }
-
- for (i = 0; i < p.length; i++) {
- rgb = tinycolor(p[i]).toRgbString();
-
- if (!paletteLookup.hasOwnProperty(rgb)) {
- unique.push(p[i]);
- paletteLookup[rgb] = true;
- }
- }
- }
-
- return unique.reverse().slice(0, opts.maxSelectionSize);
- }
-
- function drawPalette() {
-
- var currentColor = get();
-
- var html = $.map(paletteArray, function (palette, i) {
- return paletteTemplate(palette, currentColor, "sp-palette-row sp-palette-row-" + i);
- });
-
- if (selectionPalette) {
- html.push(paletteTemplate(getUniqueSelectionPalette(), currentColor, "sp-palette-row sp-palette-row-selection"));
- }
-
- paletteContainer.html(html.join(""));
- }
-
- function drawInitial() {
- if (opts.showInitial) {
- var initial = colorOnShow;
- var current = get();
- initialColorContainer.html(paletteTemplate([initial, current], current, "sp-palette-row-initial"));
- }
- }
-
- function dragStart() {
- if (dragHeight <= 0 || dragWidth <= 0 || slideHeight <= 0) {
- reflow();
- }
- container.addClass(draggingClass);
- shiftMovementDirection = null;
- }
-
- function dragStop() {
- container.removeClass(draggingClass);
- }
-
- function setFromTextInput() {
-
- var value = textInput.val();
-
- if ((value === null || value === "") && allowEmpty) {
- set(null);
- }
- else {
- var tiny = tinycolor(value);
- if (tiny.ok) {
- set(tiny);
- }
- else {
- textInput.addClass("sp-validation-error");
- invalidImage.css('display','inline');
- }
- }
- }
-
- function toggle() {
- if (visible) {
- hide();
- }
- else {
- show();
- }
- }
-
- function show() {
- var event = $.Event('beforeShow.spectrum');
-
- if (visible) {
- reflow();
- return;
- }
-
- boundElement.trigger(event, [ get() ]);
-
- if (callbacks.beforeShow(get()) === false || event.isDefaultPrevented()) {
- return;
- }
-
- hideAll();
- visible = true;
-
- $(doc).bind("click.spectrum", hide);
- $(window).bind("resize.spectrum", resize);
- replacer.addClass("sp-active");
- container.removeClass("sp-hidden");
-
- if (opts.showPalette) {
- drawPalette();
- }
- reflow();
- updateUI();
-
- colorOnShow = get();
-
- drawInitial();
- callbacks.show(colorOnShow);
- boundElement.trigger('show.spectrum', [ colorOnShow ]);
- }
-
- function hide(e) {
-
- // Return on right click
- if (e && e.type == "click" && e.button == 2) { return; }
-
- // Return if hiding is unnecessary
- if (!visible || flat) { return; }
- visible = false;
-
- $(doc).unbind("click.spectrum", hide);
- $(window).unbind("resize.spectrum", resize);
-
- replacer.removeClass("sp-active");
- container.addClass("sp-hidden");
-
- var colorHasChanged = !tinycolor.equals(get(), colorOnShow);
-
- if (colorHasChanged) {
- if (clickoutFiresChange && e !== "cancel") {
- updateOriginalInput(true);
- }
- else {
- revert();
- }
- }
-
- callbacks.hide(get());
- boundElement.trigger('hide.spectrum', [ get() ]);
- }
-
- function revert() {
- set(colorOnShow, true);
- }
-
- function set(color, ignoreFormatChange) {
- if (tinycolor.equals(color, get())) {
- return;
- }
-
- var newColor;
- if (!color && allowEmpty) {
- isEmpty = true;
- } else {
- isEmpty = false;
- newColor = tinycolor(color);
- var newHsv = newColor.toHsv();
-
- currentHue = (newHsv.h % 360) / 360;
- currentSaturation = newHsv.s;
- currentValue = newHsv.v;
- currentAlpha = newHsv.a;
- }
- updateUI();
-
- if (newColor && newColor.ok && !ignoreFormatChange) {
- currentPreferredFormat = preferredFormat || newColor.format;
- }
- }
-
- function get(opts) {
- opts = opts || { };
-
- if (allowEmpty && isEmpty) {
- return null;
- }
-
- return tinycolor.fromRatio({
- h: currentHue,
- s: currentSaturation,
- v: currentValue,
- a: Math.round(currentAlpha * 100) / 100
- }, { format: opts.format || currentPreferredFormat });
- }
-
- function isValid() {
- return !textInput.hasClass("sp-validation-error");
- }
-
- function move() {
- updateUI();
-
- callbacks.move(get());
- boundElement.trigger('move.spectrum', [ get() ]);
- }
-
- function updateUI() {
-
- textInput.removeClass("sp-validation-error");
- invalidImage.css('display','none');
-
- updateHelperLocations();
-
- // Update dragger background color (gradients take care of saturation and value).
- var flatColor = tinycolor.fromRatio({ h: currentHue, s: 1, v: 1 });
- dragger.css("background-color", flatColor.toHexString());
-
- // Get a format that alpha will be included in (hex and names ignore alpha)
- var format = currentPreferredFormat;
- if (currentAlpha < 1) {
- if (format === "hex" || format === "hex3" || format === "hex6" || format === "name") {
- format = "rgb";
- }
- }
-
- var realColor = get({ format: format }),
- displayColor = '';
-
- //reset background info for preview element
- previewElement.removeClass("sp-clear-display");
- previewElement.css('background-color', 'transparent');
-
- if (!realColor && allowEmpty) {
- // Update the replaced elements background with icon indicating no color selection
- previewElement.addClass("sp-clear-display");
- }
- else {
- var realHex = realColor.toHexString(),
- realRgb = realColor.toRgbString();
-
- // Update the replaced elements background color (with actual selected color)
- if (rgbaSupport || realColor.alpha === 1) {
- previewElement.css("background-color", realRgb);
- }
- else {
- previewElement.css("background-color", "transparent");
- previewElement.css("filter", realColor.toFilter());
- }
-
- if (opts.showAlpha) {
- var rgb = realColor.toRgb();
- rgb.a = 0;
- var realAlpha = tinycolor(rgb).toRgbString();
- var gradient = "linear-gradient(left, " + realAlpha + ", " + realHex + ")";
-
- if (IE) {
- alphaSliderInner.css("filter", tinycolor(realAlpha).toFilter({ gradientType: 1 }, realHex));
- }
- else {
- alphaSliderInner.css("background", "-webkit-" + gradient);
- alphaSliderInner.css("background", "-moz-" + gradient);
- alphaSliderInner.css("background", "-ms-" + gradient);
- alphaSliderInner.css("background", gradient);
- }
- }
-
- displayColor = realColor.toString(format);
- }
- // Update the text entry input as it changes happen
- if (opts.showInput) {
- textInput.val(displayColor);
- }
-
- if (opts.showPalette) {
- drawPalette();
- }
-
- drawInitial();
- }
-
- function updateHelperLocations() {
- var s = currentSaturation;
- var v = currentValue;
-
- if(allowEmpty && isEmpty) {
- //if selected color is empty, hide the helpers
- alphaSlideHelper.hide();
- slideHelper.hide();
- dragHelper.hide();
- }
- else {
- //make sure helpers are visible
- alphaSlideHelper.show();
- slideHelper.show();
- dragHelper.show();
-
- // Where to show the little circle in that displays your current selected color
- var dragX = s * dragWidth;
- var dragY = dragHeight - (v * dragHeight);
- dragX = Math.max(
- -dragHelperHeight,
- Math.min(dragWidth - dragHelperHeight, dragX - dragHelperHeight)
- );
- dragY = Math.max(
- -dragHelperHeight,
- Math.min(dragHeight - dragHelperHeight, dragY - dragHelperHeight)
- );
- dragHelper.css({
- "top": dragY,
- "left": dragX
- });
-
- var alphaX = currentAlpha * alphaWidth;
- alphaSlideHelper.css({
- "left": alphaX - (alphaSlideHelperWidth / 2)
- });
-
- // Where to show the bar that displays your current selected hue
- var slideY = (currentHue) * slideHeight;
- slideHelper.css({
- "top": slideY - slideHelperHeight
- });
- }
- }
-
- function updateOriginalInput(fireCallback) {
- var color = get(),
- displayColor = '',
- hasChanged = !tinycolor.equals(color, colorOnShow);
-
- if(color) {
- displayColor = color.toString(currentPreferredFormat);
- // Update the selection palette with the current color
- addColorToSelectionPalette(color);
- }
-
- if (isInput) {
- boundElement.val(displayColor);
- }
-
- colorOnShow = color;
-
- if (fireCallback && hasChanged) {
- callbacks.change(color);
- boundElement.trigger('change', [ color ]);
- }
- }
-
- function reflow() {
- dragWidth = dragger.width();
- dragHeight = dragger.height();
- dragHelperHeight = dragHelper.height();
- slideWidth = slider.width();
- slideHeight = slider.height();
- slideHelperHeight = slideHelper.height();
- alphaWidth = alphaSlider.width();
- alphaSlideHelperWidth = alphaSlideHelper.width();
-
- if (!flat) {
- container.css("position", "absolute");
- container.offset(getOffset(container, offsetElement));
- }
-
- updateHelperLocations();
- }
-
- function destroy() {
- boundElement.show();
- offsetElement.unbind("click.spectrum touchstart.spectrum");
- container.remove();
- replacer.remove();
- spectrums[spect.id] = null;
- }
-
- function option(optionName, optionValue) {
- if(optionName === undefined) {
- return $.extend({}, opts);
- }
- if(optionValue === undefined) {
- return opts[optionName];
- }
- opts[optionName] = optionValue;
- applyOptions();
-
- if(optionName=='showInput')
- {
- // Get a format that alpha will be included in (hex and names ignore alpha)
- var format = currentPreferredFormat;
- if (currentAlpha < 1) {
- if (format === "hex" || format === "hex3" || format === "hex6" || format === "name") {
- format = "rgb";
- }
- }
-
- textInput.val(get({ format: format }).toString(format));
- }
- }
-
- function enable() {
- disabled = false;
- boundElement.attr("disabled", false);
- offsetElement.removeClass("sp-disabled");
- }
-
- function disable() {
- hide();
- disabled = true;
- boundElement.attr("disabled", true);
- offsetElement.addClass("sp-disabled");
- }
-
- initialize();
-
- var spect = {
- show: show,
- hide: hide,
- toggle: toggle,
- reflow: reflow,
- option: option,
- enable: enable,
- disable: disable,
- set: function (c) {
- set(c);
- updateOriginalInput();
- },
- get: get,
- destroy: destroy,
- container: container
- };
-
- spect.id = spectrums.push(spect) - 1;
-
- return spect;
- }
-
- /**
- * checkOffset - get the offset below/above and left/right element depending on screen position
- * Thanks https://github.com/jquery/jquery-ui/blob/master/ui/jquery.ui.datepicker.js
- */
- function getOffset(picker, input) {
- var extraY = 0;
- var dpWidth = picker.outerWidth();
- var dpHeight = picker.outerHeight();
- var inputHeight = input.outerHeight();
- var doc = picker[0].ownerDocument;
- var docElem = doc.documentElement;
- var viewWidth = docElem.clientWidth + $(doc).scrollLeft();
- var viewHeight = docElem.clientHeight + $(doc).scrollTop();
- var offset = input.offset();
- offset.top += inputHeight;
-
- offset.left -=
- Math.min(offset.left, (offset.left + dpWidth > viewWidth && viewWidth > dpWidth) ?
- Math.abs(offset.left + dpWidth - viewWidth) : 0);
-
- offset.top -=
- Math.min(offset.top, ((offset.top + dpHeight > viewHeight && viewHeight > dpHeight) ?
- Math.abs(dpHeight + inputHeight - extraY) : extraY));
-
- return offset;
- }
-
- /**
- * noop - do nothing
- */
- function noop() {
-
- }
-
- /**
- * stopPropagation - makes the code only doing this a little easier to read in line
- */
- function stopPropagation(e) {
- e.stopPropagation();
- }
-
- /**
- * Create a function bound to a given object
- * Thanks to underscore.js
- */
- function bind(func, obj) {
- var slice = Array.prototype.slice;
- var args = slice.call(arguments, 2);
- return function () {
- return func.apply(obj, args.concat(slice.call(arguments)));
- };
- }
-
- /**
- * Lightweight drag helper. Handles containment within the element, so that
- * when dragging, the x is within [0,element.width] and y is within [0,element.height]
- */
- function draggable(element, onmove, onstart, onstop) {
- onmove = onmove || function () { };
- onstart = onstart || function () { };
- onstop = onstop || function () { };
- var doc = element.ownerDocument || document;
- var dragging = false;
- var offset = {};
- var maxHeight = 0;
- var maxWidth = 0;
- var hasTouch = ('ontouchstart' in window);
-
- var duringDragEvents = {};
- duringDragEvents["selectstart"] = prevent;
- duringDragEvents["dragstart"] = prevent;
- duringDragEvents["touchmove mousemove"] = move;
- duringDragEvents["touchend mouseup"] = stop;
-
- function prevent(e) {
- if (e.stopPropagation) {
- e.stopPropagation();
- }
- if (e.preventDefault) {
- e.preventDefault();
- }
- e.returnValue = false;
- }
-
- function move(e) {
- if (dragging) {
- // Mouseup happened outside of window
- if (IE && document.documentMode < 9 && !e.button) {
- return stop();
- }
-
- var touches = e.originalEvent.touches;
- var pageX = touches ? touches[0].pageX : e.pageX;
- var pageY = touches ? touches[0].pageY : e.pageY;
-
- var dragX = Math.max(0, Math.min(pageX - offset.left, maxWidth));
- var dragY = Math.max(0, Math.min(pageY - offset.top, maxHeight));
-
- if (hasTouch) {
- // Stop scrolling in iOS
- prevent(e);
- }
-
- onmove.apply(element, [dragX, dragY, e]);
- }
- }
- function start(e) {
- var rightclick = (e.which) ? (e.which == 3) : (e.button == 2);
- var touches = e.originalEvent.touches;
-
- if (!rightclick && !dragging) {
- if (onstart.apply(element, arguments) !== false) {
- dragging = true;
- maxHeight = $(element).height();
- maxWidth = $(element).width();
- offset = $(element).offset();
-
- $(doc).bind(duringDragEvents);
- $(doc.body).addClass("sp-dragging");
-
- if (!hasTouch) {
- move(e);
- }
-
- prevent(e);
- }
- }
- }
- function stop() {
- if (dragging) {
- $(doc).unbind(duringDragEvents);
- $(doc.body).removeClass("sp-dragging");
- onstop.apply(element, arguments);
- }
- dragging = false;
- }
-
- $(element).bind("touchstart mousedown", start);
- }
-
- function throttle(func, wait, debounce) {
- var timeout;
- return function () {
- var context = this, args = arguments;
- var throttler = function () {
- timeout = null;
- func.apply(context, args);
- };
- if (debounce) clearTimeout(timeout);
- if (debounce || !timeout) timeout = setTimeout(throttler, wait);
- };
- }
-
-
- function log(){/* jshint -W021 */if(window.console){if(Function.prototype.bind)log=Function.prototype.bind.call(console.log,console);else log=function(){Function.prototype.apply.call(console.log,console,arguments);};log.apply(this,arguments);}}
-
- /**
- * Define a jQuery plugin
- */
- var dataID = "spectrum.id";
- $.fn.spectrum = function (opts, extra) {
-
- if (typeof opts == "string") {
-
- var returnValue = this;
- var args = Array.prototype.slice.call( arguments, 1 );
-
- this.each(function () {
- var spect = spectrums[$(this).data(dataID)];
- if (spect) {
-
- var method = spect[opts];
- if (!method) {
- throw new Error( "Spectrum: no such method: '" + opts + "'" );
- }
-
- if (opts == "get") {
- returnValue = spect.get();
- }
- else if (opts == "container") {
- returnValue = spect.container;
- }
- else if (opts == "option") {
- returnValue = spect.option.apply(spect, args);
- }
- else if (opts == "destroy") {
- spect.destroy();
- $(this).removeData(dataID);
- }
- else {
- method.apply(spect, args);
- }
- }
- });
-
- return returnValue;
- }
-
- // Initializing a new instance of spectrum
- return this.spectrum("destroy").each(function () {
- var spect = spectrum(this, opts);
- $(this).data(dataID, spect.id);
- });
- };
-
- $.fn.spectrum.load = true;
- $.fn.spectrum.loadOpts = {};
- $.fn.spectrum.draggable = draggable;
- $.fn.spectrum.defaults = defaultOpts;
-
- $.spectrum = { };
- $.spectrum.localization = { };
- $.spectrum.palettes = { };
-
- $.fn.spectrum.processNativeColorInputs = function () {
- if (!inputTypeColorSupport) {
- $("input[type=color]").spectrum({
- preferredFormat: "hex6"
- });
- }
- };
-
- // TinyColor v0.9.16
- // https://github.com/bgrins/TinyColor
- // 2013-08-10, Brian Grinstead, MIT License
-
- (function() {
-
- var trimLeft = /^[\s,#]+/,
- trimRight = /\s+$/,
- tinyCounter = 0,
- math = Math,
- mathRound = math.round,
- mathMin = math.min,
- mathMax = math.max,
- mathRandom = math.random;
-
- function tinycolor (color, opts) {
-
- color = (color) ? color : '';
- opts = opts || { };
-
- // If input is already a tinycolor, return itself
- if (typeof color == "object" && color.hasOwnProperty("_tc_id")) {
- return color;
- }
-
- var rgb = inputToRGB(color);
- var r = rgb.r,
- g = rgb.g,
- b = rgb.b,
- a = rgb.a,
- roundA = mathRound(100*a) / 100,
- format = opts.format || rgb.format;
-
- // Don't let the range of [0,255] come back in [0,1].
- // Potentially lose a little bit of precision here, but will fix issues where
- // .5 gets interpreted as half of the total, instead of half of 1
- // If it was supposed to be 128, this was already taken care of by `inputToRgb`
- if (r < 1) { r = mathRound(r); }
- if (g < 1) { g = mathRound(g); }
- if (b < 1) { b = mathRound(b); }
-
- return {
- ok: rgb.ok,
- format: format,
- _tc_id: tinyCounter++,
- alpha: a,
- getAlpha: function() {
- return a;
- },
- setAlpha: function(value) {
- a = boundAlpha(value);
- roundA = mathRound(100*a) / 100;
- },
- toHsv: function() {
- var hsv = rgbToHsv(r, g, b);
- return { h: hsv.h * 360, s: hsv.s, v: hsv.v, a: a };
- },
- toHsvString: function() {
- var hsv = rgbToHsv(r, g, b);
- var h = mathRound(hsv.h * 360), s = mathRound(hsv.s * 100), v = mathRound(hsv.v * 100);
- return (a == 1) ?
- "hsv(" + h + ", " + s + "%, " + v + "%)" :
- "hsva(" + h + ", " + s + "%, " + v + "%, "+ roundA + ")";
- },
- toHsl: function() {
- var hsl = rgbToHsl(r, g, b);
- return { h: hsl.h * 360, s: hsl.s, l: hsl.l, a: a };
- },
- toHslString: function() {
- var hsl = rgbToHsl(r, g, b);
- var h = mathRound(hsl.h * 360), s = mathRound(hsl.s * 100), l = mathRound(hsl.l * 100);
- return (a == 1) ?
- "hsl(" + h + ", " + s + "%, " + l + "%)" :
- "hsla(" + h + ", " + s + "%, " + l + "%, "+ roundA + ")";
- },
- toHex: function(allow3Char) {
- return rgbToHex(r, g, b, allow3Char);
- },
- toHexString: function(allow3Char) {
- return '#' + rgbToHex(r, g, b, allow3Char);
- },
- toRgb: function() {
- return { r: mathRound(r), g: mathRound(g), b: mathRound(b), a: a };
- },
- toRgbString: function() {
- return (a == 1) ?
- "rgb(" + mathRound(r) + ", " + mathRound(g) + ", " + mathRound(b) + ")" :
- "rgba(" + mathRound(r) + ", " + mathRound(g) + ", " + mathRound(b) + ", " + roundA + ")";
- },
- toPercentageRgb: function() {
- return { r: mathRound(bound01(r, 255) * 100) + "%", g: mathRound(bound01(g, 255) * 100) + "%", b: mathRound(bound01(b, 255) * 100) + "%", a: a };
- },
- toPercentageRgbString: function() {
- return (a == 1) ?
- "rgb(" + mathRound(bound01(r, 255) * 100) + "%, " + mathRound(bound01(g, 255) * 100) + "%, " + mathRound(bound01(b, 255) * 100) + "%)" :
- "rgba(" + mathRound(bound01(r, 255) * 100) + "%, " + mathRound(bound01(g, 255) * 100) + "%, " + mathRound(bound01(b, 255) * 100) + "%, " + roundA + ")";
- },
- toName: function() {
- if (a === 0) {
- return "transparent";
- }
-
- return hexNames[rgbToHex(r, g, b, true)] || false;
- },
- toFilter: function(secondColor) {
- var hex = rgbToHex(r, g, b);
- var secondHex = hex;
- var alphaHex = Math.round(parseFloat(a) * 255).toString(16);
- var secondAlphaHex = alphaHex;
- var gradientType = opts && opts.gradientType ? "GradientType = 1, " : "";
-
- if (secondColor) {
- var s = tinycolor(secondColor);
- secondHex = s.toHex();
- secondAlphaHex = Math.round(parseFloat(s.alpha) * 255).toString(16);
- }
-
- return "progid:DXImageTransform.Microsoft.gradient("+gradientType+"startColorstr=#" + pad2(alphaHex) + hex + ",endColorstr=#" + pad2(secondAlphaHex) + secondHex + ")";
- },
- toString: function(format) {
- var formatSet = !!format;
- format = format || this.format;
-
- var formattedString = false;
- var hasAlphaAndFormatNotSet = !formatSet && a < 1 && a > 0;
- var formatWithAlpha = hasAlphaAndFormatNotSet && (format === "hex" || format === "hex6" || format === "hex3" || format === "name");
-
- if (format === "rgb") {
- formattedString = this.toRgbString();
- }
- if (format === "prgb") {
- formattedString = this.toPercentageRgbString();
- }
- if (format === "hex" || format === "hex6") {
- formattedString = this.toHexString();
- }
- if (format === "hex3") {
- formattedString = this.toHexString(true);
- }
- if (format === "name") {
- formattedString = this.toName();
- }
- if (format === "hsl") {
- formattedString = this.toHslString();
- }
- if (format === "hsv") {
- formattedString = this.toHsvString();
- }
-
- if (formatWithAlpha) {
- return this.toRgbString();
- }
-
- return formattedString || this.toHexString();
- }
- };
- }
-
- // If input is an object, force 1 into "1.0" to handle ratios properly
- // String input requires "1.0" as input, so 1 will be treated as 1
- tinycolor.fromRatio = function(color, opts) {
- if (typeof color == "object") {
- var newColor = {};
- for (var i in color) {
- if (color.hasOwnProperty(i)) {
- if (i === "a") {
- newColor[i] = color[i];
- }
- else {
- newColor[i] = convertToPercentage(color[i]);
- }
- }
- }
- color = newColor;
- }
-
- return tinycolor(color, opts);
- };
-
- // Given a string or object, convert that input to RGB
- // Possible string inputs:
- //
- // "red"
- // "#f00" or "f00"
- // "#ff0000" or "ff0000"
- // "rgb 255 0 0" or "rgb (255, 0, 0)"
- // "rgb 1.0 0 0" or "rgb (1, 0, 0)"
- // "rgba (255, 0, 0, 1)" or "rgba 255, 0, 0, 1"
- // "rgba (1.0, 0, 0, 1)" or "rgba 1.0, 0, 0, 1"
- // "hsl(0, 100%, 50%)" or "hsl 0 100% 50%"
- // "hsla(0, 100%, 50%, 1)" or "hsla 0 100% 50%, 1"
- // "hsv(0, 100%, 100%)" or "hsv 0 100% 100%"
- //
- function inputToRGB(color) {
-
- var rgb = { r: 0, g: 0, b: 0 };
- var a = 1;
- var ok = false;
- var format = false;
-
- if (typeof color == "string") {
- color = stringInputToObject(color);
- }
-
- if (typeof color == "object") {
- if (color.hasOwnProperty("r") && color.hasOwnProperty("g") && color.hasOwnProperty("b")) {
- rgb = rgbToRgb(color.r, color.g, color.b);
- ok = true;
- format = String(color.r).substr(-1) === "%" ? "prgb" : "rgb";
- }
- else if (color.hasOwnProperty("h") && color.hasOwnProperty("s") && color.hasOwnProperty("v")) {
- color.s = convertToPercentage(color.s);
- color.v = convertToPercentage(color.v);
- rgb = hsvToRgb(color.h, color.s, color.v);
- ok = true;
- format = "hsv";
- }
- else if (color.hasOwnProperty("h") && color.hasOwnProperty("s") && color.hasOwnProperty("l")) {
- color.s = convertToPercentage(color.s);
- color.l = convertToPercentage(color.l);
- rgb = hslToRgb(color.h, color.s, color.l);
- ok = true;
- format = "hsl";
- }
-
- if (color.hasOwnProperty("a")) {
- a = color.a;
- }
- }
-
- a = boundAlpha(a);
-
- return {
- ok: ok,
- format: color.format || format,
- r: mathMin(255, mathMax(rgb.r, 0)),
- g: mathMin(255, mathMax(rgb.g, 0)),
- b: mathMin(255, mathMax(rgb.b, 0)),
- a: a
- };
- }
-
-
- // Conversion Functions
- // --------------------
-
- // `rgbToHsl`, `rgbToHsv`, `hslToRgb`, `hsvToRgb` modified from:
- // <http://mjijackson.com/2008/02/rgb-to-hsl-and-rgb-to-hsv-color-model-conversion-algorithms-in-javascript>
-
- // `rgbToRgb`
- // Handle bounds / percentage checking to conform to CSS color spec
- // <http://www.w3.org/TR/css3-color/>
- // *Assumes:* r, g, b in [0, 255] or [0, 1]
- // *Returns:* { r, g, b } in [0, 255]
- function rgbToRgb(r, g, b){
- return {
- r: bound01(r, 255) * 255,
- g: bound01(g, 255) * 255,
- b: bound01(b, 255) * 255
- };
- }
-
- // `rgbToHsl`
- // Converts an RGB color value to HSL.
- // *Assumes:* r, g, and b are contained in [0, 255] or [0, 1]
- // *Returns:* { h, s, l } in [0,1]
- function rgbToHsl(r, g, b) {
-
- r = bound01(r, 255);
- g = bound01(g, 255);
- b = bound01(b, 255);
-
- var max = mathMax(r, g, b), min = mathMin(r, g, b);
- var h, s, l = (max + min) / 2;
-
- if(max == min) {
- h = s = 0; // achromatic
- }
- else {
- var d = max - min;
- s = l > 0.5 ? d / (2 - max - min) : d / (max + min);
- switch(max) {
- case r: h = (g - b) / d + (g < b ? 6 : 0); break;
- case g: h = (b - r) / d + 2; break;
- case b: h = (r - g) / d + 4; break;
- }
-
- h /= 6;
- }
-
- return { h: h, s: s, l: l };
- }
-
- // `hslToRgb`
- // Converts an HSL color value to RGB.
- // *Assumes:* h is contained in [0, 1] or [0, 360] and s and l are contained [0, 1] or [0, 100]
- // *Returns:* { r, g, b } in the set [0, 255]
- function hslToRgb(h, s, l) {
- var r, g, b;
-
- h = bound01(h, 360);
- s = bound01(s, 100);
- l = bound01(l, 100);
-
- function hue2rgb(p, q, t) {
- if(t < 0) t += 1;
- if(t > 1) t -= 1;
- if(t < 1/6) return p + (q - p) * 6 * t;
- if(t < 1/2) return q;
- if(t < 2/3) return p + (q - p) * (2/3 - t) * 6;
- return p;
- }
-
- if(s === 0) {
- r = g = b = l; // achromatic
- }
- else {
- var q = l < 0.5 ? l * (1 + s) : l + s - l * s;
- var p = 2 * l - q;
- r = hue2rgb(p, q, h + 1/3);
- g = hue2rgb(p, q, h);
- b = hue2rgb(p, q, h - 1/3);
- }
-
- return { r: r * 255, g: g * 255, b: b * 255 };
- }
-
- // `rgbToHsv`
- // Converts an RGB color value to HSV
- // *Assumes:* r, g, and b are contained in the set [0, 255] or [0, 1]
- // *Returns:* { h, s, v } in [0,1]
- function rgbToHsv(r, g, b) {
-
- r = bound01(r, 255);
- g = bound01(g, 255);
- b = bound01(b, 255);
-
- var max = mathMax(r, g, b), min = mathMin(r, g, b);
- var h, s, v = max;
-
- var d = max - min;
- s = max === 0 ? 0 : d / max;
-
- if(max == min) {
- h = 0; // achromatic
- }
- else {
- switch(max) {
- case r: h = (g - b) / d + (g < b ? 6 : 0); break;
- case g: h = (b - r) / d + 2; break;
- case b: h = (r - g) / d + 4; break;
- }
- h /= 6;
- }
- return { h: h, s: s, v: v };
- }
-
- // `hsvToRgb`
- // Converts an HSV color value to RGB.
- // *Assumes:* h is contained in [0, 1] or [0, 360] and s and v are contained in [0, 1] or [0, 100]
- // *Returns:* { r, g, b } in the set [0, 255]
- function hsvToRgb(h, s, v) {
-
- h = bound01(h, 360) * 6;
- s = bound01(s, 100);
- v = bound01(v, 100);
-
- var i = math.floor(h),
- f = h - i,
- p = v * (1 - s),
- q = v * (1 - f * s),
- t = v * (1 - (1 - f) * s),
- mod = i % 6,
- r = [v, q, p, p, t, v][mod],
- g = [t, v, v, q, p, p][mod],
- b = [p, p, t, v, v, q][mod];
-
- return { r: r * 255, g: g * 255, b: b * 255 };
- }
-
- // `rgbToHex`
- // Converts an RGB color to hex
- // Assumes r, g, and b are contained in the set [0, 255]
- // Returns a 3 or 6 character hex
- function rgbToHex(r, g, b, allow3Char) {
-
- var hex = [
- pad2(mathRound(r).toString(16)),
- pad2(mathRound(g).toString(16)),
- pad2(mathRound(b).toString(16))
- ];
-
- // Return a 3 character hex if possible
- if (allow3Char && hex[0].charAt(0) == hex[0].charAt(1) && hex[1].charAt(0) == hex[1].charAt(1) && hex[2].charAt(0) == hex[2].charAt(1)) {
- return hex[0].charAt(0) + hex[1].charAt(0) + hex[2].charAt(0);
- }
-
- return hex.join("");
- }
-
- // `equals`
- // Can be called with any tinycolor input
- tinycolor.equals = function (color1, color2) {
- if (!color1 || !color2) { return false; }
- return tinycolor(color1).toRgbString() == tinycolor(color2).toRgbString();
- };
- tinycolor.random = function() {
- return tinycolor.fromRatio({
- r: mathRandom(),
- g: mathRandom(),
- b: mathRandom()
- });
- };
-
-
- // Modification Functions
- // ----------------------
- // Thanks to less.js for some of the basics here
- // <https://github.com/cloudhead/less.js/blob/master/lib/less/functions.js>
-
- tinycolor.desaturate = function (color, amount) {
- amount = (amount === 0) ? 0 : (amount || 10);
- var hsl = tinycolor(color).toHsl();
- hsl.s -= amount / 100;
- hsl.s = clamp01(hsl.s);
- return tinycolor(hsl);
- };
- tinycolor.saturate = function (color, amount) {
- amount = (amount === 0) ? 0 : (amount || 10);
- var hsl = tinycolor(color).toHsl();
- hsl.s += amount / 100;
- hsl.s = clamp01(hsl.s);
- return tinycolor(hsl);
- };
- tinycolor.greyscale = function(color) {
- return tinycolor.desaturate(color, 100);
- };
- tinycolor.lighten = function(color, amount) {
- amount = (amount === 0) ? 0 : (amount || 10);
- var hsl = tinycolor(color).toHsl();
- hsl.l += amount / 100;
- hsl.l = clamp01(hsl.l);
- return tinycolor(hsl);
- };
- tinycolor.darken = function (color, amount) {
- amount = (amount === 0) ? 0 : (amount || 10);
- var hsl = tinycolor(color).toHsl();
- hsl.l -= amount / 100;
- hsl.l = clamp01(hsl.l);
- return tinycolor(hsl);
- };
- tinycolor.complement = function(color) {
- var hsl = tinycolor(color).toHsl();
- hsl.h = (hsl.h + 180) % 360;
- return tinycolor(hsl);
- };
-
-
- // Combination Functions
- // ---------------------
- // Thanks to jQuery xColor for some of the ideas behind these
- // <https://github.com/infusion/jQuery-xcolor/blob/master/jquery.xcolor.js>
-
- tinycolor.triad = function(color) {
- var hsl = tinycolor(color).toHsl();
- var h = hsl.h;
- return [
- tinycolor(color),
- tinycolor({ h: (h + 120) % 360, s: hsl.s, l: hsl.l }),
- tinycolor({ h: (h + 240) % 360, s: hsl.s, l: hsl.l })
- ];
- };
- tinycolor.tetrad = function(color) {
- var hsl = tinycolor(color).toHsl();
- var h = hsl.h;
- return [
- tinycolor(color),
- tinycolor({ h: (h + 90) % 360, s: hsl.s, l: hsl.l }),
- tinycolor({ h: (h + 180) % 360, s: hsl.s, l: hsl.l }),
- tinycolor({ h: (h + 270) % 360, s: hsl.s, l: hsl.l })
- ];
- };
- tinycolor.splitcomplement = function(color) {
- var hsl = tinycolor(color).toHsl();
- var h = hsl.h;
- return [
- tinycolor(color),
- tinycolor({ h: (h + 72) % 360, s: hsl.s, l: hsl.l}),
- tinycolor({ h: (h + 216) % 360, s: hsl.s, l: hsl.l})
- ];
- };
- tinycolor.analogous = function(color, results, slices) {
- results = results || 6;
- slices = slices || 30;
-
- var hsl = tinycolor(color).toHsl();
- var part = 360 / slices;
- var ret = [tinycolor(color)];
-
- for (hsl.h = ((hsl.h - (part * results >> 1)) + 720) % 360; --results; ) {
- hsl.h = (hsl.h + part) % 360;
- ret.push(tinycolor(hsl));
- }
- return ret;
- };
- tinycolor.monochromatic = function(color, results) {
- results = results || 6;
- var hsv = tinycolor(color).toHsv();
- var h = hsv.h, s = hsv.s, v = hsv.v;
- var ret = [];
- var modification = 1 / results;
-
- while (results--) {
- ret.push(tinycolor({ h: h, s: s, v: v}));
- v = (v + modification) % 1;
- }
-
- return ret;
- };
-
-
- // Readability Functions
- // ---------------------
- // <http://www.w3.org/TR/AERT#color-contrast>
-
- // `readability`
- // Analyze the 2 colors and returns an object with the following properties:
- // `brightness`: difference in brightness between the two colors
- // `color`: difference in color/hue between the two colors
- tinycolor.readability = function(color1, color2) {
- var a = tinycolor(color1).toRgb();
- var b = tinycolor(color2).toRgb();
- var brightnessA = (a.r * 299 + a.g * 587 + a.b * 114) / 1000;
- var brightnessB = (b.r * 299 + b.g * 587 + b.b * 114) / 1000;
- var colorDiff = (
- Math.max(a.r, b.r) - Math.min(a.r, b.r) +
- Math.max(a.g, b.g) - Math.min(a.g, b.g) +
- Math.max(a.b, b.b) - Math.min(a.b, b.b)
- );
-
- return {
- brightness: Math.abs(brightnessA - brightnessB),
- color: colorDiff
- };
- };
-
- // `readable`
- // http://www.w3.org/TR/AERT#color-contrast
- // Ensure that foreground and background color combinations provide sufficient contrast.
- // *Example*
- // tinycolor.readable("#000", "#111") => false
- tinycolor.readable = function(color1, color2) {
- var readability = tinycolor.readability(color1, color2);
- return readability.brightness > 125 && readability.color > 500;
- };
-
- // `mostReadable`
- // Given a base color and a list of possible foreground or background
- // colors for that base, returns the most readable color.
- // *Example*
- // tinycolor.mostReadable("#123", ["#fff", "#000"]) => "#000"
- tinycolor.mostReadable = function(baseColor, colorList) {
- var bestColor = null;
- var bestScore = 0;
- var bestIsReadable = false;
- for (var i=0; i < colorList.length; i++) {
-
- // We normalize both around the "acceptable" breaking point,
- // but rank brightness constrast higher than hue.
-
- var readability = tinycolor.readability(baseColor, colorList[i]);
- var readable = readability.brightness > 125 && readability.color > 500;
- var score = 3 * (readability.brightness / 125) + (readability.color / 500);
-
- if ((readable && ! bestIsReadable) ||
- (readable && bestIsReadable && score > bestScore) ||
- ((! readable) && (! bestIsReadable) && score > bestScore)) {
- bestIsReadable = readable;
- bestScore = score;
- bestColor = tinycolor(colorList[i]);
- }
- }
- return bestColor;
- };
-
-
- // Big List of Colors
- // ------------------
- // <http://www.w3.org/TR/css3-color/#svg-color>
- var names = tinycolor.names = {
- aliceblue: "f0f8ff",
- antiquewhite: "faebd7",
- aqua: "0ff",
- aquamarine: "7fffd4",
- azure: "f0ffff",
- beige: "f5f5dc",
- bisque: "ffe4c4",
- black: "000",
- blanchedalmond: "ffebcd",
- blue: "00f",
- blueviolet: "8a2be2",
- brown: "a52a2a",
- burlywood: "deb887",
- burntsienna: "ea7e5d",
- cadetblue: "5f9ea0",
- chartreuse: "7fff00",
- chocolate: "d2691e",
- coral: "ff7f50",
- cornflowerblue: "6495ed",
- cornsilk: "fff8dc",
- crimson: "dc143c",
- cyan: "0ff",
- darkblue: "00008b",
- darkcyan: "008b8b",
- darkgoldenrod: "b8860b",
- darkgray: "a9a9a9",
- darkgreen: "006400",
- darkgrey: "a9a9a9",
- darkkhaki: "bdb76b",
- darkmagenta: "8b008b",
- darkolivegreen: "556b2f",
- darkorange: "ff8c00",
- darkorchid: "9932cc",
- darkred: "8b0000",
- darksalmon: "e9967a",
- darkseagreen: "8fbc8f",
- darkslateblue: "483d8b",
- darkslategray: "2f4f4f",
- darkslategrey: "2f4f4f",
- darkturquoise: "00ced1",
- darkviolet: "9400d3",
- deeppink: "ff1493",
- deepskyblue: "00bfff",
- dimgray: "696969",
- dimgrey: "696969",
- dodgerblue: "1e90ff",
- firebrick: "b22222",
- floralwhite: "fffaf0",
- forestgreen: "228b22",
- fuchsia: "f0f",
- gainsboro: "dcdcdc",
- ghostwhite: "f8f8ff",
- gold: "ffd700",
- goldenrod: "daa520",
- gray: "808080",
- green: "008000",
- greenyellow: "adff2f",
- grey: "808080",
- honeydew: "f0fff0",
- hotpink: "ff69b4",
- indianred: "cd5c5c",
- indigo: "4b0082",
- ivory: "fffff0",
- khaki: "f0e68c",
- lavender: "e6e6fa",
- lavenderblush: "fff0f5",
- lawngreen: "7cfc00",
- lemonchiffon: "fffacd",
- lightblue: "add8e6",
- lightcoral: "f08080",
- lightcyan: "e0ffff",
- lightgoldenrodyellow: "fafad2",
- lightgray: "d3d3d3",
- lightgreen: "90ee90",
- lightgrey: "d3d3d3",
- lightpink: "ffb6c1",
- lightsalmon: "ffa07a",
- lightseagreen: "20b2aa",
- lightskyblue: "87cefa",
- lightslategray: "789",
- lightslategrey: "789",
- lightsteelblue: "b0c4de",
- lightyellow: "ffffe0",
- lime: "0f0",
- limegreen: "32cd32",
- linen: "faf0e6",
- magenta: "f0f",
- maroon: "800000",
- mediumaquamarine: "66cdaa",
- mediumblue: "0000cd",
- mediumorchid: "ba55d3",
- mediumpurple: "9370db",
- mediumseagreen: "3cb371",
- mediumslateblue: "7b68ee",
- mediumspringgreen: "00fa9a",
- mediumturquoise: "48d1cc",
- mediumvioletred: "c71585",
- midnightblue: "191970",
- mintcream: "f5fffa",
- mistyrose: "ffe4e1",
- moccasin: "ffe4b5",
- navajowhite: "ffdead",
- navy: "000080",
- oldlace: "fdf5e6",
- olive: "808000",
- olivedrab: "6b8e23",
- orange: "ffa500",
- orangered: "ff4500",
- orchid: "da70d6",
- palegoldenrod: "eee8aa",
- palegreen: "98fb98",
- paleturquoise: "afeeee",
- palevioletred: "db7093",
- papayawhip: "ffefd5",
- peachpuff: "ffdab9",
- peru: "cd853f",
- pink: "ffc0cb",
- plum: "dda0dd",
- powderblue: "b0e0e6",
- purple: "800080",
- red: "f00",
- rosybrown: "bc8f8f",
- royalblue: "4169e1",
- saddlebrown: "8b4513",
- salmon: "fa8072",
- sandybrown: "f4a460",
- seagreen: "2e8b57",
- seashell: "fff5ee",
- sienna: "a0522d",
- silver: "c0c0c0",
- skyblue: "87ceeb",
- slateblue: "6a5acd",
- slategray: "708090",
- slategrey: "708090",
- snow: "fffafa",
- springgreen: "00ff7f",
- steelblue: "4682b4",
- tan: "d2b48c",
- teal: "008080",
- thistle: "d8bfd8",
- tomato: "ff6347",
- turquoise: "40e0d0",
- violet: "ee82ee",
- wheat: "f5deb3",
- white: "fff",
- whitesmoke: "f5f5f5",
- yellow: "ff0",
- yellowgreen: "9acd32"
- };
-
- // Make it easy to access colors via `hexNames[hex]`
- var hexNames = tinycolor.hexNames = flip(names);
-
-
- // Utilities
- // ---------
-
- // `{ 'name1': 'val1' }` becomes `{ 'val1': 'name1' }`
- function flip(o) {
- var flipped = { };
- for (var i in o) {
- if (o.hasOwnProperty(i)) {
- flipped[o[i]] = i;
- }
- }
- return flipped;
- }
-
- // Return a valid alpha value [0,1] with all invalid values being set to 1
- function boundAlpha(a) {
- a = parseFloat(a);
-
- if (isNaN(a) || a < 0 || a > 1) {
- a = 1;
- }
-
- return a;
- }
-
- // Take input from [0, n] and return it as [0, 1]
- function bound01(n, max) {
- if (isOnePointZero(n)) { n = "100%"; }
-
- var processPercent = isPercentage(n);
- n = mathMin(max, mathMax(0, parseFloat(n)));
-
- // Automatically convert percentage into number
- if (processPercent) {
- n = parseInt(n * max, 10) / 100;
- }
-
- // Handle floating point rounding errors
- if ((math.abs(n - max) < 0.000001)) {
- return 1;
- }
-
- // Convert into [0, 1] range if it isn't already
- return (n % max) / parseFloat(max);
- }
-
- // Force a number between 0 and 1
- function clamp01(val) {
- return mathMin(1, mathMax(0, val));
- }
-
- // Parse an integer into hex
- function parseHex(val) {
- return parseInt(val, 16);
- }
-
- // Need to handle 1.0 as 100%, since once it is a number, there is no difference between it and 1
- // <http://stackoverflow.com/questions/7422072/javascript-how-to-detect-number-as-a-decimal-including-1-0>
- function isOnePointZero(n) {
- return typeof n == "string" && n.indexOf('.') != -1 && parseFloat(n) === 1;
- }
-
- // Check to see if string passed in is a percentage
- function isPercentage(n) {
- return typeof n === "string" && n.indexOf('%') != -1;
- }
-
- // Force a hex value to have 2 characters
- function pad2(c) {
- return c.length == 1 ? '0' + c : '' + c;
- }
-
- // Replace a decimal with it's percentage value
- function convertToPercentage(n) {
- if (n <= 1) {
- n = (n * 100) + "%";
- }
-
- return n;
- }
-
- var matchers = (function() {
-
- // <http://www.w3.org/TR/css3-values/#integers>
- var CSS_INTEGER = "[-\\+]?\\d+%?";
-
- // <http://www.w3.org/TR/css3-values/#number-value>
- var CSS_NUMBER = "[-\\+]?\\d*\\.\\d+%?";
-
- // Allow positive/negative integer/number. Don't capture the either/or, just the entire outcome.
- var CSS_UNIT = "(?:" + CSS_NUMBER + ")|(?:" + CSS_INTEGER + ")";
-
- // Actual matching.
- // Parentheses and commas are optional, but not required.
- // Whitespace can take the place of commas or opening paren
- var PERMISSIVE_MATCH3 = "[\\s|\\(]+(" + CSS_UNIT + ")[,|\\s]+(" + CSS_UNIT + ")[,|\\s]+(" + CSS_UNIT + ")\\s*\\)?";
- var PERMISSIVE_MATCH4 = "[\\s|\\(]+(" + CSS_UNIT + ")[,|\\s]+(" + CSS_UNIT + ")[,|\\s]+(" + CSS_UNIT + ")[,|\\s]+(" + CSS_UNIT + ")\\s*\\)?";
-
- return {
- rgb: new RegExp("rgb" + PERMISSIVE_MATCH3),
- rgba: new RegExp("rgba" + PERMISSIVE_MATCH4),
- hsl: new RegExp("hsl" + PERMISSIVE_MATCH3),
- hsla: new RegExp("hsla" + PERMISSIVE_MATCH4),
- hsv: new RegExp("hsv" + PERMISSIVE_MATCH3),
- hex3: /^([0-9a-fA-F]{1})([0-9a-fA-F]{1})([0-9a-fA-F]{1})$/,
- hex6: /^([0-9a-fA-F]{2})([0-9a-fA-F]{2})([0-9a-fA-F]{2})$/
- };
- })();
-
- // `stringInputToObject`
- // Permissive string parsing. Take in a number of formats, and output an object
- // based on detected format. Returns `{ r, g, b }` or `{ h, s, l }` or `{ h, s, v}`
- function stringInputToObject(color) {
-
- color = color.replace(trimLeft,'').replace(trimRight, '').toLowerCase();
- var named = false;
- if (names[color]) {
- color = names[color];
- named = true;
- }
- else if (color == 'transparent') {
- return { r: 0, g: 0, b: 0, a: 0, format: "name" };
- }
-
- // Try to match string input using regular expressions.
- // Keep most of the number bounding out of this function - don't worry about [0,1] or [0,100] or [0,360]
- // Just return an object and let the conversion functions handle that.
- // This way the result will be the same whether the tinycolor is initialized with string or object.
- var match;
- if ((match = matchers.rgb.exec(color))) {
- return { r: match[1], g: match[2], b: match[3] };
- }
- if ((match = matchers.rgba.exec(color))) {
- return { r: match[1], g: match[2], b: match[3], a: match[4] };
- }
- if ((match = matchers.hsl.exec(color))) {
- return { h: match[1], s: match[2], l: match[3] };
- }
- if ((match = matchers.hsla.exec(color))) {
- return { h: match[1], s: match[2], l: match[3], a: match[4] };
- }
- if ((match = matchers.hsv.exec(color))) {
- return { h: match[1], s: match[2], v: match[3] };
- }
- if ((match = matchers.hex6.exec(color))) {
- return {
- r: parseHex(match[1]),
- g: parseHex(match[2]),
- b: parseHex(match[3]),
- format: named ? "name" : "hex"
- };
- }
- if ((match = matchers.hex3.exec(color))) {
- return {
- r: parseHex(match[1] + '' + match[1]),
- g: parseHex(match[2] + '' + match[2]),
- b: parseHex(match[3] + '' + match[3]),
- format: named ? "name" : "hex"
- };
- }
-
- return false;
- }
-
- // Expose tinycolor to window, does not need to run in non-browser context.
- window.tinycolor = tinycolor;
-
- })();
-
-
- $(function () {
- if ($.fn.spectrum.load) {
- $.fn.spectrum.processNativeColorInputs();
- }
- });
-
-})(window, jQuery);
bgstack15