Skip to content

Commit 00d7c6b

Browse files
authored
Merge pull request #5065 from plotly/new-formats-in-period-ticklabelmode
handle various time formats in ticklabelmode period
2 parents 29b456e + 1c94ba9 commit 00d7c6b

File tree

5 files changed

+333
-17
lines changed

5 files changed

+333
-17
lines changed

src/constants/numerical.js

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,9 @@ module.exports = {
3232
* have the same length
3333
*/
3434
ONEAVGYEAR: 31557600000, // 365.25 days
35+
ONEAVGQUARTER: 7889400000, // 1/4 of ONEAVGYEAR
3536
ONEAVGMONTH: 2629800000, // 1/12 of ONEAVGYEAR
37+
ONEWEEK: 604800000, // 7 * ONEDAY
3638
ONEDAY: 86400000,
3739
ONEHOUR: 3600000,
3840
ONEMIN: 60000,

src/plots/cartesian/axes.js

Lines changed: 57 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,9 @@ var cleanTicks = require('./clean_ticks');
2424

2525
var constants = require('../../constants/numerical');
2626
var ONEAVGYEAR = constants.ONEAVGYEAR;
27+
var ONEAVGQUARTER = constants.ONEAVGQUARTER;
2728
var ONEAVGMONTH = constants.ONEAVGMONTH;
29+
var ONEWEEK = constants.ONEWEEK;
2830
var ONEDAY = constants.ONEDAY;
2931
var ONEHOUR = constants.ONEHOUR;
3032
var ONEMIN = constants.ONEMIN;
@@ -695,23 +697,51 @@ axes.calcTicks = function calcTicks(ax, opts) {
695697

696698
var definedDelta;
697699
if(isPeriod && ax.tickformat) {
698-
var _has = function(str) {
699-
return ax.tickformat.indexOf(str) !== -1;
700-
};
701-
702700
if(
703-
!_has('%f') &&
704-
!_has('%H') &&
705-
!_has('%I') &&
706-
!_has('%L') &&
707-
!_has('%Q') &&
708-
!_has('%S') &&
709-
!_has('%s') &&
710-
!_has('%X')
701+
!(/%[fLQsSMHIpX]/.test(ax.tickformat))
702+
// %f: microseconds as a decimal number [000000, 999999]
703+
// %L: milliseconds as a decimal number [000, 999]
704+
// %Q: milliseconds since UNIX epoch
705+
// %s: seconds since UNIX epoch
706+
// %S: second as a decimal number [00,61]
707+
// %M: minute as a decimal number [00,59]
708+
// %H: hour (24-hour clock) as a decimal number [00,23]
709+
// %I: hour (12-hour clock) as a decimal number [01,12]
710+
// %p: either AM or PM
711+
// %X: the locale’s time, such as %-I:%M:%S %p
711712
) {
712-
if(_has('%x') || _has('%d') || _has('%e') || _has('%j')) definedDelta = ONEDAY;
713-
else if(_has('%B') || _has('%b') || _has('%m')) definedDelta = ONEAVGMONTH;
714-
else if(_has('%Y') || _has('%y')) definedDelta = ONEAVGYEAR;
713+
if(
714+
/%[Aadejuwx]/.test(ax.tickformat)
715+
// %A: full weekday name
716+
// %a: abbreviated weekday name
717+
// %d: zero-padded day of the month as a decimal number [01,31]
718+
// %e: space-padded day of the month as a decimal number [ 1,31]
719+
// %j: day of the year as a decimal number [001,366]
720+
// %u: Monday-based (ISO 8601) weekday as a decimal number [1,7]
721+
// %w: Sunday-based weekday as a decimal number [0,6]
722+
// %x: the locale’s date, such as %-m/%-d/%Y
723+
) definedDelta = ONEDAY;
724+
else if(
725+
/%[UVW]/.test(ax.tickformat)
726+
// %U: Sunday-based week of the year as a decimal number [00,53]
727+
// %V: ISO 8601 week of the year as a decimal number [01, 53]
728+
// %W: Monday-based week of the year as a decimal number [00,53]
729+
) definedDelta = ONEWEEK;
730+
else if(
731+
/%[Bbm]/.test(ax.tickformat)
732+
// %B: full month name
733+
// %b: abbreviated month name
734+
// %m: month as a decimal number [01,12]
735+
) definedDelta = ONEAVGMONTH;
736+
else if(
737+
/%[q]/.test(ax.tickformat)
738+
// %q: quarter of the year as a decimal number [1,4]
739+
) definedDelta = ONEAVGQUARTER;
740+
else if(
741+
/%[Yy]/.test(ax.tickformat)
742+
// %Y: year with century as a decimal number, such as 1999
743+
// %y: year without century as a decimal number [00,99]
744+
) definedDelta = ONEAVGYEAR;
715745
}
716746
}
717747

@@ -748,8 +778,12 @@ axes.calcTicks = function calcTicks(ax, opts) {
748778
var delta = definedDelta || Math.abs(B - A);
749779
if(delta >= ONEDAY * 365) { // Years could have days less than ONEAVGYEAR period
750780
v += ONEAVGYEAR / 2;
781+
} else if(delta >= ONEAVGQUARTER) {
782+
v += ONEAVGQUARTER / 2;
751783
} else if(delta >= ONEDAY * 28) { // Months could have days less than ONEAVGMONTH period
752784
v += ONEAVGMONTH / 2;
785+
} else if(delta >= ONEWEEK) {
786+
v += ONEWEEK / 2;
753787
} else if(delta >= ONEDAY) {
754788
v += ONEDAY / 2;
755789
}
@@ -764,7 +798,7 @@ axes.calcTicks = function calcTicks(ax, opts) {
764798
}
765799

766800
if(removedPreTick0Label) {
767-
for(i = 1; i < ticksOut.length; i++) {
801+
for(i = 0; i < ticksOut.length; i++) {
768802
if(ticksOut[i].periodX <= maxRange && ticksOut[i].periodX >= minRange) {
769803
// redo first visible tick
770804
ax._prevDateHead = '';
@@ -882,6 +916,13 @@ axes.autoTicks = function(ax, roughDTick) {
882916
// this will also move the base tick off 2000-01-01 if dtick is
883917
// 2 or 3 days... but that's a weird enough case that we'll ignore it.
884918
ax.tick0 = Lib.dateTick0(ax.calendar, true);
919+
920+
if(/%[uVW]/.test(ax.tickformat)) {
921+
// replace Sunday with Monday for ISO and Monday-based formats
922+
var len = ax.tick0.length;
923+
var lastD = +ax.tick0[len - 1];
924+
ax.tick0 = ax.tick0.substring(0, len - 2) + String(lastD + 1);
925+
}
885926
} else if(roughX2 > ONEHOUR) {
886927
ax.dtick = roundDTick(roughDTick, ONEHOUR, roundBase24);
887928
} else if(roughX2 > ONEMIN) {

src/plots/cartesian/set_convert.js

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@ var numConstants = require('../../constants/numerical');
2323
var FP_SAFE = numConstants.FP_SAFE;
2424
var BADNUM = numConstants.BADNUM;
2525
var LOG_CLIP = numConstants.LOG_CLIP;
26+
var ONEWEEK = numConstants.ONEWEEK;
2627
var ONEDAY = numConstants.ONEDAY;
2728
var ONEHOUR = numConstants.ONEHOUR;
2829
var ONEMIN = numConstants.ONEMIN;
@@ -734,7 +735,7 @@ module.exports = function setConvert(ax, fullLayout) {
734735

735736
switch(brk.pattern) {
736737
case WEEKDAY_PATTERN:
737-
step = 7 * ONEDAY;
738+
step = ONEWEEK;
738739

739740
bndDelta = (
740741
(b1 < b0 ? 7 : 0) +
-134 Bytes
Loading

0 commit comments

Comments
 (0)