views:

57

answers:

1

How can I manipulate dates so that they show up as "just now"... "5 mins ago"... "3 hours ago"... "June 22nd, 2010 at 1:45pm" in similar fashion to how SO displays the dates next to the answers/comments to each question?

To further complicate matters, the dates stored in my database are in GMT time (which is fine), but I want them to appear in the timezone of each user's browser.

I've already tried John Resig's pretty date plugin: http://bassistance.de/jquery-plugins/jquery-plugin-prettydate/, and I've edited it so that it subtracts the timezone offset from the GMT time in the database. However, this solution only works in FireFox.

Here's the 'prettydate' funtion after I've added the timezone offset:

format : function(time) {
var date = new Date(time);
var currentDate = new Date();
var timezoneOffsetInMilliseconds = currentDate.getTimezoneOffset() * 60000;
var currentTimeInMillisecondsUtc = currentDate.getTime();
var givenTimeInMillisecondsUtc = date.getTime()- timezoneOffsetInMilliseconds;
var diffInSeconds = ((currentTimeInMillisecondsUtc - givenTimeInMillisecondsUtc) / 1000);
var day_diff = Math.floor(diffInSeconds / 86400);

if (isNaN(day_diff) || day_diff < 0)
    return;

        // If longer than a month, calculate the date w/ timezone offset
        if (day_diff >= 31)
            return new Date(givenTimeInMillisecondsUtc).toLocaleString();

        var messages = $.prettyDate.messages;
        return day_diff == 0 && (diffInSeconds < 60 && messages.now 
            || diffInSeconds < 120 && messages.minute
             || diffInSeconds < 3600
             && messages.minutes(Math.floor(diffInSeconds / 60))
            || diffInSeconds < 7200 && messages.hour || diffInSeconds < 86400
            && messages.hours(Math.floor(diffInSeconds / 3600)))
            || day_diff == 1 && messages.yesterday || day_diff < 7
            && messages.days(day_diff) || day_diff < 31
            && messages.weeks(Math.ceil(day_diff / 7));
    }

Edit: I'm using Python with Django templates (via Google Webapp), and the 'time' object I'm passing in a 'db.DateTimeProperty()' in the iso format like so:

<span class="prettyDate" title='{{ q.date.isoformat }}'>{{q.date.isoformat}}</span>
+2  A: 

Why not do this server-side, with the built-in template tag timesince, or a custom template tag?

In relative time, there is not meaning to timezones, as long the 2 times you are diffing are in the same zone. For the results that are farther away in the past, and you want to present as absolute times, you'll have to do the time shift yourself. for this, you'll have to ask the user for her timezone (or use some JS on a previous page to send it to you) and store it in the user profile.

this is also discussed in the mailing list.

Ofri Raviv
Mostly because I want the time to show up in the timezone setting of the user's browser. I also like the idea of JavaScript since the above plugin automatically updates the date every 10 seconds so that if the user leaves their browser open, it'll have the updated text.
Cuga
Edited a bit about the shifting to correct zone in server side option.
Ofri Raviv
Hmm I had previously not wanted to ask the user for his timezone because of those public users who won't have an account who will be viewing the site. I'll think about / look into that link you gave of sending the timezone through JS from a previous page, though I would still prefer a cross-browser JS solution for the automatic updates.
Cuga