From 84a7a273f2992a2ee11419a8ef287081631a0ef9 Mon Sep 17 00:00:00 2001
From: "olau@iola.dk"
Date: Fri, 4 Apr 2008 18:29:44 +0000
Subject: [PATCH] Display dates according to UTC instead of according to the
time zone of the visitor
git-svn-id: https://flot.googlecode.com/svn/trunk@67 1e0a6537-2640-0410-bfb7-f154510ff394
---
API.txt | 49 ++++++++++++++++++++++++++++++++---------
NEWS.txt | 8 +++++++
examples/time.html | 14 ++++++++----
examples/visitors.html | 14 ++++++++----
jquery.flot.js | 50 +++++++++++++++++++++---------------------
5 files changed, 92 insertions(+), 43 deletions(-)
diff --git a/API.txt b/API.txt
index 392de58..5f6bb90 100644
--- a/API.txt
+++ b/API.txt
@@ -260,20 +260,45 @@ an example of a custom formatter:
Time series data
================
+Time series are a bit more difficult than scalar data because
+calendars don't follow a simple base 10 system. For many cases, Flot
+abstracts most of this away, but it can still be a bit difficult to
+get the data into Flot. So we'll first discuss the data format.
+
The time series support in Flot is based on Javascript timestamps,
i.e. everywhere a time value is expected or handed over, a Javascript
-timestamp number is used. This is not the same as a Date object. A
+timestamp number is used. This is a number, not a Date object. A
Javascript timestamp is the number of milliseconds since January 1,
1970 00:00:00. This is almost the same as Unix timestamps, except it's
in milliseconds, so remember to multiply by 1000!
-You can see a timestamp by outputting
+You can see a timestamp like this
+
+ alert((new Date()).getTime())
+
+Normally you want the timestamps to be displayed according to a
+certain time zone, usually the time zone in which the data has been
+produced. However, Flot always displays timestamps according to UTC.
+It has to as the only alternative with core Javascript is to interpret
+the timestamps according to the time zone that the visitor is in,
+which means that the ticks will shift unpredictably with the time
+zone and daylight savings of each visitor.
- (new Date()).getTime()
+So given that there's no good support for custom time zones in
+Javascript, you'll have to take care of this server-side.
+
+The easiest way to think about it is to pretend that the data
+production time zone is UTC, even if it isn't. So if you have a
+datapoint at 2002-02-20 08:00, you can generate a timestamp for eight
+o'clock UTC even if it really happened eight o'clock UTC+0200. If
+you've already got the real UTC timestamp, it's too late to pretend -
+but you can fix it up by adding the time zone offset, e.g. for
+UTC+0200 you would add 2 hours to the timestamp. Then it'll look right
+on the plot.
In PHP you can get an appropriate timestamp with
-'strtotime("2002-02-20") * 1000', in Python with
-'time.mktime(datetime_object.timetuple()) * 1000', in .NET with
+'strtotime("2002-02-20 UTC") * 1000', in Python with
+'calendar.timegm(datetime_object.timetuple()) * 1000', in .NET with
something like:
public static int GetJavascriptTimestamp(System.DateTime input)
@@ -283,13 +308,17 @@ something like:
return (int)(time.Ticks / 10000);
}
+Javascript also has some support for parsing date strings, so it is
+possible to generate the timestamps client-side if you need to.
+
Once you've got the timestamps into the data and specified "time" as
the axis mode, Flot will automatically generate relevant ticks and
-format them. As always, you can tweak the ticks via the "ticks"
-option. Again the values should be timestamps, not Date objects!
+format them. As always, you can tweak the ticks via the "ticks" option
+- just remember that the values should be timestamps, not Date
+objects.
-Tick generation and formatting is controlled separately through the
-following axis options:
+Tick generation and formatting can also be controlled separately
+through the following axis options:
xaxis, yaxis: {
minTickSize
@@ -328,7 +357,7 @@ which will format December 24 as 24/12:
tickFormatter: function (val, axis) {
var d = new Date(val);
- return d.getDate() + "/" + (d.getMonth() + 1);
+ return d.getUTCDate() + "/" + (d.getUTCMonth() + 1);
}
Note that for the time mode "tickSize" and "minTickSize" are a bit
diff --git a/NEWS.txt b/NEWS.txt
index 9ec525f..2a7915e 100644
--- a/NEWS.txt
+++ b/NEWS.txt
@@ -1,6 +1,14 @@
Flot x.x
--------
+API changes: timestamps in time mode are now displayed according to
+UTC instead of the time zone of the visitor. This affects the way the
+timestamps should be input; you'll probably have to offset the
+timestamps according to your local time zone. It also affects any
+custom date handling code (which basically now should use the
+equivalent UTC date mehods, e.g. .setUTCMonth() instead of
+.setMonth().
+
Added support for specifying the size of tick labels (axis.labelWidth,
axis.labelHeight). Useful for specifying a max label size to keep
multiple plots aligned.
diff --git a/examples/time.html b/examples/time.html
index 754425d..f810a28 100644
--- a/examples/time.html
+++ b/examples/time.html
@@ -23,10 +23,16 @@
-
The timestamps must be specified as Javascript
- timestamps, as milliseconds since January 1, 1970 00:00. This is
- like Unix timestamps, but in milliseconds instead of seconds
- (remember to multiply with 1000!).
+
The timestamps must be specified as Javascript timestamps, as
+ milliseconds since January 1, 1970 00:00. This is like Unix
+ timestamps, but in milliseconds instead of seconds (remember to
+ multiply with 1000!).
+
+
As an extra caveat, the timestamps are interpreted according to
+ UTC to avoid having the graph shift with each visitor's local
+ time zone. So you might have to add your local time zone offset
+ to the timestamps or simply pretend that the data was produced
+ in UTC instead of your local time zone.