'+label[i]+''+tag+'>';
- }
- if (--count) {
- label[count] = 'and '+label[count];
- }
- return label.join(', ');
- };
-
- /**
- * Formats the entries as English labels
- *
- * @private
- * @param {Timespan} ts
- * @return {Array}
- */
- formatList = function(ts) {
- var list = [];
-
- var value = ts.millennia;
- if (value) {
- list.push(plurality(value, LABEL_MILLENNIA));
- }
-
- value = ts.centuries;
- if (value) {
- list.push(plurality(value, LABEL_CENTURIES));
- }
-
- value = ts.decades;
- if (value) {
- list.push(plurality(value, LABEL_DECADES));
- }
-
- value = ts.years;
- if (value) {
- list.push(plurality(value, LABEL_YEARS));
- }
-
- value = ts.months;
- if (value) {
- list.push(plurality(value, LABEL_MONTHS));
- }
-
- value = ts.weeks;
- if (value) {
- list.push(plurality(value, LABEL_WEEKS));
- }
-
- value = ts.days;
- if (value) {
- list.push(plurality(value, LABEL_DAYS));
- }
-
- value = ts.hours;
- if (value) {
- list.push(plurality(value, LABEL_HOURS));
- }
-
- value = ts.minutes;
- if (value) {
- list.push(plurality(value, LABEL_MINUTES));
- }
-
- value = ts.seconds;
- if (value) {
- list.push(plurality(value, LABEL_SECONDS));
- }
-
- value = ts.milliseconds;
- if (value) {
- list.push(plurality(value, LABEL_MILLISECONDS));
- }
-
- return list;
- };
-
- /**
- * Borrow any underflow units, carry any overflow units
- *
- * @private
- * @param {Timespan} ts
- * @param {string} toUnit
- */
- function rippleRounded(ts, toUnit) {
- switch (toUnit) {
- case 'seconds':
- if (ts.seconds !== SECONDS_PER_MINUTE || isNaN(ts.minutes)) {
- return;
- }
- // ripple seconds up to minutes
- ts.minutes++;
- ts.seconds = 0;
-
- /* falls through */
- case 'minutes':
- if (ts.minutes !== MINUTES_PER_HOUR || isNaN(ts.hours)) {
- return;
- }
- // ripple minutes up to hours
- ts.hours++;
- ts.minutes = 0;
-
- /* falls through */
- case 'hours':
- if (ts.hours !== HOURS_PER_DAY || isNaN(ts.days)) {
- return;
- }
- // ripple hours up to days
- ts.days++;
- ts.hours = 0;
-
- /* falls through */
- case 'days':
- if (ts.days !== DAYS_PER_WEEK || isNaN(ts.weeks)) {
- return;
- }
- // ripple days up to weeks
- ts.weeks++;
- ts.days = 0;
-
- /* falls through */
- case 'weeks':
- if (ts.weeks !== daysPerMonth(ts.refMonth)/DAYS_PER_WEEK || isNaN(ts.months)) {
- return;
- }
- // ripple weeks up to months
- ts.months++;
- ts.weeks = 0;
-
- /* falls through */
- case 'months':
- if (ts.months !== MONTHS_PER_YEAR || isNaN(ts.years)) {
- return;
- }
- // ripple months up to years
- ts.years++;
- ts.months = 0;
-
- /* falls through */
- case 'years':
- if (ts.years !== YEARS_PER_DECADE || isNaN(ts.decades)) {
- return;
- }
- // ripple years up to decades
- ts.decades++;
- ts.years = 0;
-
- /* falls through */
- case 'decades':
- if (ts.decades !== DECADES_PER_CENTURY || isNaN(ts.centuries)) {
- return;
- }
- // ripple decades up to centuries
- ts.centuries++;
- ts.decades = 0;
-
- /* falls through */
- case 'centuries':
- if (ts.centuries !== CENTURIES_PER_MILLENNIUM || isNaN(ts.millennia)) {
- return;
- }
- // ripple centuries up to millennia
- ts.millennia++;
- ts.centuries = 0;
- /* falls through */
- }
- }
-
- /**
- * Ripple up partial units one place
- *
- * @private
- * @param {Timespan} ts timespan
- * @param {number} frac accumulated fractional value
- * @param {string} fromUnit source unit name
- * @param {string} toUnit target unit name
- * @param {number} conversion multiplier between units
- * @param {number} digits max number of decimal digits to output
- * @return {number} new fractional value
- */
- function fraction(ts, frac, fromUnit, toUnit, conversion, digits) {
- if (ts[fromUnit] >= 0) {
- frac += ts[fromUnit];
- delete ts[fromUnit];
- }
-
- frac /= conversion;
- if (frac + 1 <= 1) {
- // drop if below machine epsilon
- return 0;
- }
-
- if (ts[toUnit] >= 0) {
- // ensure does not have more than specified number of digits
- ts[toUnit] = +(ts[toUnit] + frac).toFixed(digits);
- rippleRounded(ts, toUnit);
- return 0;
- }
-
- return frac;
- }
-
- /**
- * Ripple up partial units to next existing
- *
- * @private
- * @param {Timespan} ts
- * @param {number} digits max number of decimal digits to output
- */
- function fractional(ts, digits) {
- var frac = fraction(ts, 0, 'milliseconds', 'seconds', MILLISECONDS_PER_SECOND, digits);
- if (!frac) { return; }
-
- frac = fraction(ts, frac, 'seconds', 'minutes', SECONDS_PER_MINUTE, digits);
- if (!frac) { return; }
-
- frac = fraction(ts, frac, 'minutes', 'hours', MINUTES_PER_HOUR, digits);
- if (!frac) { return; }
-
- frac = fraction(ts, frac, 'hours', 'days', HOURS_PER_DAY, digits);
- if (!frac) { return; }
-
- frac = fraction(ts, frac, 'days', 'weeks', DAYS_PER_WEEK, digits);
- if (!frac) { return; }
-
- frac = fraction(ts, frac, 'weeks', 'months', daysPerMonth(ts.refMonth)/DAYS_PER_WEEK, digits);
- if (!frac) { return; }
-
- frac = fraction(ts, frac, 'months', 'years', daysPerYear(ts.refMonth)/daysPerMonth(ts.refMonth), digits);
- if (!frac) { return; }
-
- frac = fraction(ts, frac, 'years', 'decades', YEARS_PER_DECADE, digits);
- if (!frac) { return; }
-
- frac = fraction(ts, frac, 'decades', 'centuries', DECADES_PER_CENTURY, digits);
- if (!frac) { return; }
-
- frac = fraction(ts, frac, 'centuries', 'millennia', CENTURIES_PER_MILLENNIUM, digits);
-
- // should never reach this with remaining fractional value
- if (frac) { throw new Error('Fractional unit overflow'); }
- }
-
- /**
- * Borrow any underflow units, carry any overflow units
- *
- * @private
- * @param {Timespan} ts
- */
- function ripple(ts) {
- var x;
-
- if (ts.milliseconds < 0) {
- // ripple seconds down to milliseconds
- x = ceil(-ts.milliseconds / MILLISECONDS_PER_SECOND);
- ts.seconds -= x;
- ts.milliseconds += x * MILLISECONDS_PER_SECOND;
-
- } else if (ts.milliseconds >= MILLISECONDS_PER_SECOND) {
- // ripple milliseconds up to seconds
- ts.seconds += floor(ts.milliseconds / MILLISECONDS_PER_SECOND);
- ts.milliseconds %= MILLISECONDS_PER_SECOND;
- }
-
- if (ts.seconds < 0) {
- // ripple minutes down to seconds
- x = ceil(-ts.seconds / SECONDS_PER_MINUTE);
- ts.minutes -= x;
- ts.seconds += x * SECONDS_PER_MINUTE;
-
- } else if (ts.seconds >= SECONDS_PER_MINUTE) {
- // ripple seconds up to minutes
- ts.minutes += floor(ts.seconds / SECONDS_PER_MINUTE);
- ts.seconds %= SECONDS_PER_MINUTE;
- }
-
- if (ts.minutes < 0) {
- // ripple hours down to minutes
- x = ceil(-ts.minutes / MINUTES_PER_HOUR);
- ts.hours -= x;
- ts.minutes += x * MINUTES_PER_HOUR;
-
- } else if (ts.minutes >= MINUTES_PER_HOUR) {
- // ripple minutes up to hours
- ts.hours += floor(ts.minutes / MINUTES_PER_HOUR);
- ts.minutes %= MINUTES_PER_HOUR;
- }
-
- if (ts.hours < 0) {
- // ripple days down to hours
- x = ceil(-ts.hours / HOURS_PER_DAY);
- ts.days -= x;
- ts.hours += x * HOURS_PER_DAY;
-
- } else if (ts.hours >= HOURS_PER_DAY) {
- // ripple hours up to days
- ts.days += floor(ts.hours / HOURS_PER_DAY);
- ts.hours %= HOURS_PER_DAY;
- }
-
- while (ts.days < 0) {
- // NOTE: never actually seen this loop more than once
-
- // ripple months down to days
- ts.months--;
- ts.days += borrowMonths(ts.refMonth, 1);
- }
-
- // weeks is always zero here
-
- if (ts.days >= DAYS_PER_WEEK) {
- // ripple days up to weeks
- ts.weeks += floor(ts.days / DAYS_PER_WEEK);
- ts.days %= DAYS_PER_WEEK;
- }
-
- if (ts.months < 0) {
- // ripple years down to months
- x = ceil(-ts.months / MONTHS_PER_YEAR);
- ts.years -= x;
- ts.months += x * MONTHS_PER_YEAR;
-
- } else if (ts.months >= MONTHS_PER_YEAR) {
- // ripple months up to years
- ts.years += floor(ts.months / MONTHS_PER_YEAR);
- ts.months %= MONTHS_PER_YEAR;
- }
-
- // years is always non-negative here
- // decades, centuries and millennia are always zero here
-
- if (ts.years >= YEARS_PER_DECADE) {
- // ripple years up to decades
- ts.decades += floor(ts.years / YEARS_PER_DECADE);
- ts.years %= YEARS_PER_DECADE;
-
- if (ts.decades >= DECADES_PER_CENTURY) {
- // ripple decades up to centuries
- ts.centuries += floor(ts.decades / DECADES_PER_CENTURY);
- ts.decades %= DECADES_PER_CENTURY;
-
- if (ts.centuries >= CENTURIES_PER_MILLENNIUM) {
- // ripple centuries up to millennia
- ts.millennia += floor(ts.centuries / CENTURIES_PER_MILLENNIUM);
- ts.centuries %= CENTURIES_PER_MILLENNIUM;
- }
- }
- }
- }
-
- /**
- * Remove any units not requested
- *
- * @private
- * @param {Timespan} ts
- * @param {number} units the units to populate
- * @param {number} max number of labels to output
- * @param {number} digits max number of decimal digits to output
- */
- function pruneUnits(ts, units, max, digits) {
- var count = 0;
-
- // Calc from largest unit to smallest to prevent underflow
- if (!(units & MILLENNIA) || (count >= max)) {
- // ripple millennia down to centuries
- ts.centuries += ts.millennia * CENTURIES_PER_MILLENNIUM;
- delete ts.millennia;
-
- } else if (ts.millennia) {
- count++;
- }
-
- if (!(units & CENTURIES) || (count >= max)) {
- // ripple centuries down to decades
- ts.decades += ts.centuries * DECADES_PER_CENTURY;
- delete ts.centuries;
-
- } else if (ts.centuries) {
- count++;
- }
-
- if (!(units & DECADES) || (count >= max)) {
- // ripple decades down to years
- ts.years += ts.decades * YEARS_PER_DECADE;
- delete ts.decades;
-
- } else if (ts.decades) {
- count++;
- }
-
- if (!(units & YEARS) || (count >= max)) {
- // ripple years down to months
- ts.months += ts.years * MONTHS_PER_YEAR;
- delete ts.years;
-
- } else if (ts.years) {
- count++;
- }
-
- if (!(units & MONTHS) || (count >= max)) {
- // ripple months down to days
- if (ts.months) {
- ts.days += borrowMonths(ts.refMonth, ts.months);
- }
- delete ts.months;
-
- if (ts.days >= DAYS_PER_WEEK) {
- // ripple day overflow back up to weeks
- ts.weeks += floor(ts.days / DAYS_PER_WEEK);
- ts.days %= DAYS_PER_WEEK;
- }
-
- } else if (ts.months) {
- count++;
- }
-
- if (!(units & WEEKS) || (count >= max)) {
- // ripple weeks down to days
- ts.days += ts.weeks * DAYS_PER_WEEK;
- delete ts.weeks;
-
- } else if (ts.weeks) {
- count++;
- }
-
- if (!(units & DAYS) || (count >= max)) {
- //ripple days down to hours
- ts.hours += ts.days * HOURS_PER_DAY;
- delete ts.days;
-
- } else if (ts.days) {
- count++;
- }
-
- if (!(units & HOURS) || (count >= max)) {
- // ripple hours down to minutes
- ts.minutes += ts.hours * MINUTES_PER_HOUR;
- delete ts.hours;
-
- } else if (ts.hours) {
- count++;
- }
-
- if (!(units & MINUTES) || (count >= max)) {
- // ripple minutes down to seconds
- ts.seconds += ts.minutes * SECONDS_PER_MINUTE;
- delete ts.minutes;
-
- } else if (ts.minutes) {
- count++;
- }
-
- if (!(units & SECONDS) || (count >= max)) {
- // ripple seconds down to milliseconds
- ts.milliseconds += ts.seconds * MILLISECONDS_PER_SECOND;
- delete ts.seconds;
-
- } else if (ts.seconds) {
- count++;
- }
-
- // nothing to ripple milliseconds down to
- // so ripple back up to smallest existing unit as a fractional value
- if (!(units & MILLISECONDS) || (count >= max)) {
- fractional(ts, digits);
- }
- }
-
- /**
- * Populates the Timespan object
- *
- * @private
- * @param {Timespan} ts
- * @param {Date} start the starting date
- * @param {Date} end the ending date
- * @param {number} units the units to populate
- * @param {number} max number of labels to output
- * @param {number} digits max number of decimal digits to output
- */
- function populate(ts, start, end, units, max, digits) {
- ts.start = start;
- ts.end = end;
- ts.units = units;
-
- ts.value = end.getTime() - start.getTime();
- if (ts.value < 0) {
- // swap if reversed
- var temp = end;
- end = start;
- start = temp;
- }
-
- // reference month for determining days in month
- ts.refMonth = new Date(start.getFullYear(), start.getMonth(), 15);
- try {
- // reset to initial deltas
- ts.millennia = 0;
- ts.centuries = 0;
- ts.decades = 0;
- ts.years = end.getUTCFullYear() - start.getUTCFullYear();
- ts.months = end.getUTCMonth() - start.getUTCMonth();
- ts.weeks = 0;
- ts.days = end.getUTCDate() - start.getUTCDate();
- ts.hours = end.getUTCHours() - start.getUTCHours();
- ts.minutes = end.getUTCMinutes() - start.getUTCMinutes();
- ts.seconds = end.getUTCSeconds() - start.getUTCSeconds();
- ts.milliseconds = end.getUTCMilliseconds() - start.getUTCMilliseconds();
-
- ripple(ts);
- pruneUnits(ts, units, max, digits);
-
- } finally {
- delete ts.refMonth;
- }
-
- return ts;
- }
-
- /**
- * Determine an appropriate refresh rate based upon units
- *
- * @private
- * @param {number} units the units to populate
- * @return {number} milliseconds to delay
- */
- function getDelay(units) {
- if (units & MILLISECONDS) {
- // refresh very quickly
- return MILLISECONDS_PER_SECOND / 30; //30Hz
- }
-
- if (units & SECONDS) {
- // refresh every second
- return MILLISECONDS_PER_SECOND; //1Hz
- }
-
- if (units & MINUTES) {
- // refresh every minute
- return MILLISECONDS_PER_SECOND * SECONDS_PER_MINUTE;
- }
-
- if (units & HOURS) {
- // refresh hourly
- return MILLISECONDS_PER_SECOND * SECONDS_PER_MINUTE * MINUTES_PER_HOUR;
- }
-
- if (units & DAYS) {
- // refresh daily
- return MILLISECONDS_PER_SECOND * SECONDS_PER_MINUTE * MINUTES_PER_HOUR * HOURS_PER_DAY;
- }
-
- // refresh the rest weekly
- return MILLISECONDS_PER_SECOND * SECONDS_PER_MINUTE * MINUTES_PER_HOUR * HOURS_PER_DAY * DAYS_PER_WEEK;
- }
-
- /**
- * API entry point
- *
- * @public
- * @param {Date|number|null|function(Timespan,number)} start the starting date
- * @param {Date|number|null|function(Timespan,number)} end the ending date
- * @param {number} units the units to populate
- * @param {number} max number of labels to output
- * @param {number} digits max number of decimal digits to output
- * @return {Timespan|number}
- */
- function countdown(start, end, units, max, digits) {
- var callback;
-
- // ensure some units or use defaults
- units = +units || DEFAULTS;
- // max must be positive
- max = (max > 0) ? max : NaN;
- // clamp digits to an integer between [0, 20]
- digits = (digits > 0) ? (digits < 20) ? Math.round(digits) : 20 : 0;
-
- // ensure start date
- if ('function' === typeof start) {
- callback = start;
- start = null;
-
- } else if (!(start instanceof Date)) {
- start = (start !== null && isFinite(start)) ? new Date(start) : null;
- }
-
- // ensure end date
- if ('function' === typeof end) {
- callback = end;
- end = null;
-
- } else if (!(end instanceof Date)) {
- end = (end !== null && isFinite(end)) ? new Date(end) : null;
- }
-
- if (!start && !end) {
- // used for unit testing
- return new Timespan();
- }
-
- if (!callback) {
- return populate(new Timespan(), /** @type{Date} */(start||new Date()), /** @type{Date} */(end||new Date()), units, max, digits);
- }
-
- // base delay off units
- var delay = getDelay(units),
- timerId,
- fn = function() {
- callback(
- populate(new Timespan(), /** @type{Date} */(start||new Date()), /** @type{Date} */(end||new Date()), units, max, digits),
- timerId
- );
- };
-
- fn();
- return (timerId = setInterval(fn, delay));
- }
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.MILLISECONDS = MILLISECONDS;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.SECONDS = SECONDS;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.MINUTES = MINUTES;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.HOURS = HOURS;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.DAYS = DAYS;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.WEEKS = WEEKS;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.MONTHS = MONTHS;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.YEARS = YEARS;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.DECADES = DECADES;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.CENTURIES = CENTURIES;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.MILLENNIA = MILLENNIA;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.DEFAULTS = DEFAULTS;
-
- /**
- * @public
- * @const
- * @type {number}
- */
- countdown.ALL = MILLENNIA|CENTURIES|DECADES|YEARS|MONTHS|WEEKS|DAYS|HOURS|MINUTES|SECONDS|MILLISECONDS;
-
- /**
- * Override the unit labels
- * @public
- * @param {string|Array} singular a pipe ('|') delimited list of singular unit name overrides
- * @param {string|Array} plural a pipe ('|') delimited list of plural unit name overrides
- */
- var setLabels = countdown.setLabels = function(singular, plural) {
- singular = singular || [];
- if (singular.split) {
- singular = singular.split('|');
- }
- plural = plural || [];
- if (plural.split) {
- plural = plural.split('|');
- }
-
- for (var i=LABEL_MILLISECONDS; i<=LABEL_MILLENNIA; i++) {
- // override any specified units
- LABELS_SINGLUAR[i] = singular[i] || LABELS_SINGLUAR[i];
- LABELS_PLURAL[i] = plural[i] || LABELS_PLURAL[i];
- }
- };
-
- /**
- * Revert to the default unit labels
- * @public
- */
- var resetLabels = countdown.resetLabels = function() {
- LABELS_SINGLUAR = 'millisecond|s|m|h|d|w|month|year|decade|century|millennium'.split('|');
- LABELS_PLURAL = 'milliseconds|s|m|h|d|w|months|years|decades|centuries|millennia'.split('|');
- };
-
- resetLabels();
-
- if (module && module.exports) {
- module.exports = countdown;
-
- } else if (typeof window.define === 'function' && window.define.amd) {
- window.define('countdown', [], function() {
- return countdown;
- });
- }
-
- return countdown;
-
-})(module);
diff --git a/stock/static/js/dateformat.js b/stock/static/js/dateformat.js
deleted file mode 100644
index 50f499ae..00000000
--- a/stock/static/js/dateformat.js
+++ /dev/null
@@ -1,86 +0,0 @@
-(function() {
-
- Date.shortMonths = ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'];
- Date.longMonths = ['January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December'];
- Date.shortDays = ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'];
- Date.longDays = ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday'];
-
- // defining patterns
- var replaceChars = {
- // Day
- d: function() { return (this.getDate() < 10 ? '0' : '') + this.getDate(); },
- D: function() { return Date.shortDays[this.getDay()]; },
- j: function() { return this.getDate(); },
- l: function() { return Date.longDays[this.getDay()]; },
- N: function() { return (this.getDay() == 0 ? 7 : this.getDay()); },
- S: function() { return (this.getDate() % 10 == 1 && this.getDate() != 11 ? 'st' : (this.getDate() % 10 == 2 && this.getDate() != 12 ? 'nd' : (this.getDate() % 10 == 3 && this.getDate() != 13 ? 'rd' : 'th'))); },
- w: function() { return this.getDay(); },
- z: function() { var d = new Date(this.getFullYear(),0,1); return Math.ceil((this - d) / 86400000); }, // Fixed now
- // Week
- W: function() {
- var target = new Date(this.valueOf());
- var dayNr = (this.getDay() + 6) % 7;
- target.setDate(target.getDate() - dayNr + 3);
- var firstThursday = target.valueOf();
- target.setMonth(0, 1);
- if (target.getDay() !== 4) {
- target.setMonth(0, 1 + ((4 - target.getDay()) + 7) % 7);
- }
- return 1 + Math.ceil((firstThursday - target) / 604800000);
- },
- // Month
- F: function() { return Date.longMonths[this.getMonth()]; },
- m: function() { return (this.getMonth() < 9 ? '0' : '') + (this.getMonth() + 1); },
- M: function() { return Date.shortMonths[this.getMonth()]; },
- n: function() { return this.getMonth() + 1; },
- t: function() { var d = new Date(); return new Date(d.getFullYear(), d.getMonth(), 0).getDate() }, // Fixed now, gets #days of date
- // Year
- L: function() { var year = this.getFullYear(); return (year % 400 == 0 || (year % 100 != 0 && year % 4 == 0)); }, // Fixed now
- o: function() { var d = new Date(this.valueOf()); d.setDate(d.getDate() - ((this.getDay() + 6) % 7) + 3); return d.getFullYear();}, //Fixed now
- Y: function() { return this.getFullYear(); },
- y: function() { return ('' + this.getFullYear()).substr(2); },
- // Time
- a: function() { return this.getHours() < 12 ? 'am' : 'pm'; },
- A: function() { return this.getHours() < 12 ? 'AM' : 'PM'; },
- B: function() { return Math.floor((((this.getUTCHours() + 1) % 24) + this.getUTCMinutes() / 60 + this.getUTCSeconds() / 3600) * 1000 / 24); }, // Fixed now
- g: function() { return this.getHours() % 12 || 12; },
- G: function() { return this.getHours(); },
- h: function() { return ((this.getHours() % 12 || 12) < 10 ? '0' : '') + (this.getHours() % 12 || 12); },
- H: function() { return (this.getHours() < 10 ? '0' : '') + this.getHours(); },
- i: function() { return (this.getMinutes() < 10 ? '0' : '') + this.getMinutes(); },
- s: function() { return (this.getSeconds() < 10 ? '0' : '') + this.getSeconds(); },
- u: function() { var m = this.getMilliseconds(); return (m < 10 ? '00' : (m < 100 ?
- '0' : '')) + m; },
- // Timezone
- e: function() { return "Not Yet Supported"; },
- I: function() {
- var DST = null;
- for (var i = 0; i < 12; ++i) {
- var d = new Date(this.getFullYear(), i, 1);
- var offset = d.getTimezoneOffset();
-
- if (DST === null) DST = offset;
- else if (offset < DST) { DST = offset; break; } else if (offset > DST) break;
- }
- return (this.getTimezoneOffset() == DST) | 0;
- },
- O: function() { return (-this.getTimezoneOffset() < 0 ? '-' : '+') + (Math.abs(this.getTimezoneOffset() / 60) < 10 ? '0' : '') + (Math.abs(this.getTimezoneOffset() / 60)) + '00'; },
- P: function() { return (-this.getTimezoneOffset() < 0 ? '-' : '+') + (Math.abs(this.getTimezoneOffset() / 60) < 10 ? '0' : '') + (Math.abs(this.getTimezoneOffset() / 60)) + ':00'; }, // Fixed now
- T: function() { return this.toTimeString().replace(/^.+ \(?([^\)]+)\)?$/, '$1'); },
- Z: function() { return -this.getTimezoneOffset() * 60; },
- // Full Date/Time
- c: function() { return this.format("Y-m-d\\TH:i:sP"); }, // Fixed now
- r: function() { return this.toString(); },
- U: function() { return this.getTime() / 1000; }
- };
-
- // Simulates PHP's date function
- Date.prototype.format = function(format) {
- var date = this;
- return format.replace(/(\\?)(.)/g, function(_, esc, chr) {
- return (esc === '' && replaceChars[chr]) ? replaceChars[chr].call(date) : chr;
- });
- };
-
-}).call(this);
-
diff --git a/stock/static/js/timers.js b/stock/static/js/timers.js
new file mode 100644
index 00000000..9738f765
--- /dev/null
+++ b/stock/static/js/timers.js
@@ -0,0 +1,15 @@
+/**
+* Get a duration string like countdown.js
+* e.g. "1y 2d 3h 4m 5s"
+* @param duration moment.duration
+*/
+function getDurationString(duration) {
+ var out = "";
+ if (duration.years()) {
+ out += duration.years() + 'y ';
+ }
+ if (duration.days()) {
+ out += duration.days() + 'd ';
+ }
+ return out + duration.hours() + "h " + duration.minutes() + "m " + duration.seconds() + "s";
+}
diff --git a/stock/templates/registered/fleetup.html b/stock/templates/registered/fleetup.html
index c0224125..db1f067f 100644
--- a/stock/templates/registered/fleetup.html
+++ b/stock/templates/registered/fleetup.html
@@ -59,7 +59,10 @@
{{ start.end|date:"l d M H:i" }} {% trans "Eve Time" %} |
- |
+
+ Local time
+
+ |
|
@@ -197,22 +200,81 @@
-
-
-
+
+
{% endblock content %}
diff --git a/stock/templates/registered/operationmanagement.html b/stock/templates/registered/operationmanagement.html
index 34d677a9..215479f3 100644
--- a/stock/templates/registered/operationmanagement.html
+++ b/stock/templates/registered/operationmanagement.html
@@ -51,7 +51,7 @@
{{ ops.location }} |
{{ ops.start | date:"Y-m-d H:i" }} |
- |
+ |
{{ ops.duration }} |
{{ ops.fc }} |
{{ ops.details }} |
@@ -76,26 +76,80 @@
{% endif %}
-
-
-
+
+
+ // Start timed updates
+ setInterval(timedUpdate, 1000);
+ function timedUpdate() {
+ updateClock();
+ updateAllTimers();
+ }
+
+ function updateAllTimers () {
+ var l = timers.length;
+ for (var i=0; i < l; ++i) {
+ if (timers[i].expired) continue;
+ updateTimer(timers[i]);
+ }
+ }
+
+ /**
+ * Update a timer
+ * @param timer Timer information
+ * @param timer.start Date of the timer
+ * @param timer.id Id number of the timer
+ * @param timer.expired
+ */
+ function updateTimer(timer) {
+ if (timer.start.isAfter(Date.now())) {
+ var duration = moment.duration(timer.start - moment(), 'milliseconds');
+ document.getElementById("countdown" + timer.id).innerHTML = getDurationString(duration);
+ } else {
+ timer.expired = true;
+ document.getElementById("countdown" + timer.id).innerHTML = "";
+ }
+ }
+
+ /**
+ * Set all local time fields
+ */
+ function setAllLocalTimes() {
+ var l = timers.length;
+ for (var i=0; i < l; ++i) {
+ setLocalTime(timers[i]);
+ }
+ }
+
+ /**
+ * Set the local time info for the timer
+ * @param timer Timer information
+ * @param timer.start Date of the timer
+ * @param timer.id Id number of the timer
+ */
+ function setLocalTime(timer) {
+ document.getElementById("localtime" + timer.id).innerHTML = timer.start.format("ddd @ LT");
+ }
+
+ function updateClock() {
+ document.getElementById("current-time").innerHTML = "" + moment.utc().format('LLLL') + "";
+ }
+
{% endblock content %}
diff --git a/stock/templates/registered/timermanagement.html b/stock/templates/registered/timermanagement.html
index c76ad75c..4a9dab24 100755
--- a/stock/templates/registered/timermanagement.html
+++ b/stock/templates/registered/timermanagement.html
@@ -431,6 +431,7 @@
{% include 'bundles/moment-js.html' with locale=True %}
+