|
|
@@ -1,9 +1,8 @@
|
|
|
|
|
|
var Calendar = FC.Calendar = Class.extend(EmitterMixin, {
|
|
|
|
|
|
- viewsByType: null, // holds all instantiated view instances, current or not
|
|
|
- viewSpecCache: null, // cache of view definitions
|
|
|
view: null, // current View object
|
|
|
+ viewsByType: null, // holds all instantiated view instances, current or not
|
|
|
currentDate: null, // unzoned moment. private (public API should use getDate instead)
|
|
|
loadingLevel: 0, // number of simultaneous loading tasks
|
|
|
|
|
|
@@ -15,8 +14,8 @@ var Calendar = FC.Calendar = Class.extend(EmitterMixin, {
|
|
|
GlobalEmitter.needed();
|
|
|
|
|
|
this.el = el;
|
|
|
- this.viewSpecCache = {};
|
|
|
this.viewsByType = {};
|
|
|
+ this.viewSpecCache = {};
|
|
|
|
|
|
this.initOptionsInternals(overrides);
|
|
|
this.initMomentInternals(); // needs to happen after options hash initialized
|
|
|
@@ -32,164 +31,6 @@ var Calendar = FC.Calendar = Class.extend(EmitterMixin, {
|
|
|
},
|
|
|
|
|
|
|
|
|
- // Gets information about how to create a view. Will use a cache.
|
|
|
- getViewSpec: function(viewType) {
|
|
|
- var cache = this.viewSpecCache;
|
|
|
-
|
|
|
- return cache[viewType] || (cache[viewType] = this.buildViewSpec(viewType));
|
|
|
- },
|
|
|
-
|
|
|
-
|
|
|
- // Given a duration singular unit, like "week" or "day", finds a matching view spec.
|
|
|
- // Preference is given to views that have corresponding buttons.
|
|
|
- getUnitViewSpec: function(unit) {
|
|
|
- var viewTypes;
|
|
|
- var i;
|
|
|
- var spec;
|
|
|
-
|
|
|
- if ($.inArray(unit, unitsDesc) != -1) {
|
|
|
-
|
|
|
- // put views that have buttons first. there will be duplicates, but oh well
|
|
|
- viewTypes = this.header.getViewsWithButtons(); // TODO: include footer as well?
|
|
|
- $.each(FC.views, function(viewType) { // all views
|
|
|
- viewTypes.push(viewType);
|
|
|
- });
|
|
|
-
|
|
|
- for (i = 0; i < viewTypes.length; i++) {
|
|
|
- spec = this.getViewSpec(viewTypes[i]);
|
|
|
- if (spec) {
|
|
|
- if (spec.singleUnit == unit) {
|
|
|
- return spec;
|
|
|
- }
|
|
|
- }
|
|
|
- }
|
|
|
- }
|
|
|
- },
|
|
|
-
|
|
|
-
|
|
|
- // Builds an object with information on how to create a given view
|
|
|
- buildViewSpec: function(requestedViewType) {
|
|
|
- var viewOverrides = this.overrides.views || {};
|
|
|
- var specChain = []; // for the view. lowest to highest priority
|
|
|
- var defaultsChain = []; // for the view. lowest to highest priority
|
|
|
- var overridesChain = []; // for the view. lowest to highest priority
|
|
|
- var viewType = requestedViewType;
|
|
|
- var spec; // for the view
|
|
|
- var overrides; // for the view
|
|
|
- var durationInput;
|
|
|
- var duration;
|
|
|
- var unit;
|
|
|
-
|
|
|
- // iterate from the specific view definition to a more general one until we hit an actual View class
|
|
|
- while (viewType) {
|
|
|
- spec = fcViews[viewType];
|
|
|
- overrides = viewOverrides[viewType];
|
|
|
- viewType = null; // clear. might repopulate for another iteration
|
|
|
-
|
|
|
- if (typeof spec === 'function') { // TODO: deprecate
|
|
|
- spec = { 'class': spec };
|
|
|
- }
|
|
|
-
|
|
|
- if (spec) {
|
|
|
- specChain.unshift(spec);
|
|
|
- defaultsChain.unshift(spec.defaults || {});
|
|
|
- durationInput = durationInput || spec.duration;
|
|
|
- viewType = viewType || spec.type;
|
|
|
- }
|
|
|
-
|
|
|
- if (overrides) {
|
|
|
- overridesChain.unshift(overrides); // view-specific option hashes have options at zero-level
|
|
|
- durationInput = durationInput || overrides.duration;
|
|
|
- viewType = viewType || overrides.type;
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
- spec = mergeProps(specChain);
|
|
|
- spec.type = requestedViewType;
|
|
|
- if (!spec['class']) {
|
|
|
- return false;
|
|
|
- }
|
|
|
-
|
|
|
- // fall back to top-level `duration` option
|
|
|
- durationInput = durationInput ||
|
|
|
- this.dynamicOverrides.duration ||
|
|
|
- this.overrides.duration;
|
|
|
-
|
|
|
- if (durationInput) {
|
|
|
- duration = moment.duration(durationInput);
|
|
|
-
|
|
|
- if (duration.valueOf()) { // valid?
|
|
|
-
|
|
|
- unit = computeDurationGreatestUnit(duration, durationInput);
|
|
|
-
|
|
|
- spec.duration = duration;
|
|
|
- spec.durationUnit = unit;
|
|
|
-
|
|
|
- // view is a single-unit duration, like "week" or "day"
|
|
|
- // incorporate options for this. lowest priority
|
|
|
- if (duration.as(unit) === 1) {
|
|
|
- spec.singleUnit = unit;
|
|
|
- overridesChain.unshift(viewOverrides[unit] || {});
|
|
|
- }
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
- spec.defaults = mergeOptions(defaultsChain);
|
|
|
- spec.overrides = mergeOptions(overridesChain);
|
|
|
-
|
|
|
- this.buildViewSpecOptions(spec);
|
|
|
- this.buildViewSpecButtonText(spec, requestedViewType);
|
|
|
-
|
|
|
- return spec;
|
|
|
- },
|
|
|
-
|
|
|
-
|
|
|
- // Builds and assigns a view spec's options object from its already-assigned defaults and overrides
|
|
|
- buildViewSpecOptions: function(spec) {
|
|
|
- spec.options = mergeOptions([ // lowest to highest priority
|
|
|
- Calendar.defaults, // global defaults
|
|
|
- spec.defaults, // view's defaults (from ViewSubclass.defaults)
|
|
|
- this.dirDefaults,
|
|
|
- this.localeDefaults, // locale and dir take precedence over view's defaults!
|
|
|
- this.overrides, // calendar's overrides (options given to constructor)
|
|
|
- spec.overrides, // view's overrides (view-specific options)
|
|
|
- this.dynamicOverrides // dynamically set via setter. highest precedence
|
|
|
- ]);
|
|
|
- populateInstanceComputableOptions(spec.options);
|
|
|
- },
|
|
|
-
|
|
|
-
|
|
|
- // Computes and assigns a view spec's buttonText-related options
|
|
|
- buildViewSpecButtonText: function(spec, requestedViewType) {
|
|
|
-
|
|
|
- // given an options object with a possible `buttonText` hash, lookup the buttonText for the
|
|
|
- // requested view, falling back to a generic unit entry like "week" or "day"
|
|
|
- function queryButtonText(options) {
|
|
|
- var buttonText = options.buttonText || {};
|
|
|
- return buttonText[requestedViewType] ||
|
|
|
- // view can decide to look up a certain key
|
|
|
- (spec.buttonTextKey ? buttonText[spec.buttonTextKey] : null) ||
|
|
|
- // a key like "month"
|
|
|
- (spec.singleUnit ? buttonText[spec.singleUnit] : null);
|
|
|
- }
|
|
|
-
|
|
|
- // highest to lowest priority
|
|
|
- spec.buttonTextOverride =
|
|
|
- queryButtonText(this.dynamicOverrides) ||
|
|
|
- queryButtonText(this.overrides) || // constructor-specified buttonText lookup hash takes precedence
|
|
|
- spec.overrides.buttonText; // `buttonText` for view-specific options is a string
|
|
|
-
|
|
|
- // highest to lowest priority. mirrors buildViewSpecOptions
|
|
|
- spec.buttonTextDefault =
|
|
|
- queryButtonText(this.localeDefaults) ||
|
|
|
- queryButtonText(this.dirDefaults) ||
|
|
|
- spec.defaults.buttonText || // a single string. from ViewSubclass.defaults
|
|
|
- queryButtonText(Calendar.defaults) ||
|
|
|
- (spec.duration ? this.humanizeDuration(spec.duration) : null) || // like "3 days"
|
|
|
- requestedViewType; // fall back to given view name
|
|
|
- },
|
|
|
-
|
|
|
-
|
|
|
// Given a view name for a custom view or a standard view, creates a ready-to-go View object
|
|
|
instantiateView: function(viewType) {
|
|
|
var spec = this.getViewSpec(viewType);
|