Skip to content

Instantly share code, notes, and snippets.

@skovalyov
Created June 5, 2012 07:46
Show Gist options
  • Save skovalyov/2873377 to your computer and use it in GitHub Desktop.
Save skovalyov/2873377 to your computer and use it in GitHub Desktop.
DateUtil class with getTimeSpan() method that formats the time span between now and the date specified in a "Facebook way"
package {
import mx.formatters.DateFormatter;
import mx.utils.StringUtil;
public class DateUtil {
public static const SECOND_IN_MILLISECONDS : int = 1000;
public static const FEW_SECONDS : int = 5;
public static const MINUTE_IN_SECONDS : int = 60;
public static const HOUR_IN_SECONDS : int = MINUTE_IN_SECONDS * 60;
private static const X_SECONDS_AGO : String = "{0} seconds ago";
private static const X_MINUTES_AGO : String = "{0} minutes ago";
private static const X_HOURS_AGO : String = "{0} hours ago";
private static const IN_X_SECONDS : String = "In {0} seconds";
private static const IN_X_MINUTES : String = "In {0} minutes";
private static const IN_X_HOURS : String = "In {0} hours";
private static const YESTERDAY_TOMORROW_PATTERN : String = "at L:NNA";
private static const THIS_WEEK_PATTERN : String = "EEEE at L:NNA";
private static const THIS_YEAR_PATTERN : String = "MMMM D at L:NNA";
private static const ANOTHER_YEAR_PATTERN : String = "MMMM D, YYYY at L:NNA";
/**
* Format the time span between now and the date specified in a "Facebook way".
*
* Examples:
*
* May 18, 2011 at 5:11AM
* December 25 at 8:43PM
* Friday at 3:53PM
* Tomorrow at 10:44AM
* In 10 hours
* In about an hour
* In 25 minutes
* In about a minute
* In 17 seconds
* In a few seconds
* A few seconds ago
* 31 seconds ago
* About a minute ago
* 47 minutes ago
* About an hour ago
* 4 hours ago
* Yesterday at 6:25PM
* Monday at 12:30AM
* September 11 at 7:11AM
* September 10, 2009 at 12:23PM
*/
public static function getTimeSpan(date : Date) : String {
var result : String;
var now : Date = new Date();
var dateFormatter : DateFormatter = new DateFormatter();
var range : Number = (now.time - date.time) / SECOND_IN_MILLISECONDS;
var nextYearStart : Date = new Date(now.fullYear + 1, 0, 1);
var nextWeekStart : Date = new Date(now.fullYear, now.month, now.date + (7 - now.day));
var tomorrowStart : Date = new Date(now.fullYear, now.month, now.date + 1);
var theDayAfterTomorrowStart : Date = new Date(now.fullYear, now.month, now.date + 2);
var todayStart : Date = new Date(now.fullYear, now.month, now.date);
var yesterdayStart : Date = new Date(now.fullYear, now.month, now.date - 1);
var thisWeekStart : Date = new Date(now.fullYear, now.month, now.date - now.day);
var thisYearStart : Date = new Date(now.fullYear, 0, 1);
var nextYearRange : Number = (now.time - nextYearStart.time) / SECOND_IN_MILLISECONDS;
var nextWeekRange : Number = (now.time - nextWeekStart.time) / SECOND_IN_MILLISECONDS;
var theDayAfterTomorrowRange : Number = (now.time - theDayAfterTomorrowStart.time) / SECOND_IN_MILLISECONDS;
var tomorrowRange : Number = (now.time - tomorrowStart.time) / SECOND_IN_MILLISECONDS;
var todayRange : Number = (now.time - todayStart.time) / SECOND_IN_MILLISECONDS;
var yesterdayRange : Number = (now.time - yesterdayStart.time) / SECOND_IN_MILLISECONDS;
var thisWeekRange : Number = (now.time - thisWeekStart.time) / SECOND_IN_MILLISECONDS;
var thisYearRange : Number = (now.time - thisYearStart.time) / SECOND_IN_MILLISECONDS;
if (range >= 0) {
if (range < FEW_SECONDS) {
result = "A few seconds ago";
} else if (range < MINUTE_IN_SECONDS) {
result = StringUtil.substitute(X_SECONDS_AGO, Math.floor(range));
} else if (range < MINUTE_IN_SECONDS * 2) {
result = "About a minute ago";
} else if (range < HOUR_IN_SECONDS) {
result = StringUtil.substitute(X_MINUTES_AGO, Math.floor(range / MINUTE_IN_SECONDS));
} else if (range < HOUR_IN_SECONDS * 2) {
result = "About an hour ago";
} else if (range < todayRange) {
result = StringUtil.substitute(X_HOURS_AGO, Math.floor(range / HOUR_IN_SECONDS));
} else if (range < yesterdayRange) {
dateFormatter.formatString = YESTERDAY_TOMORROW_PATTERN;
result = "Yesterday " + dateFormatter.format(date);
} else if (range < thisWeekRange) {
dateFormatter.formatString = THIS_WEEK_PATTERN;
result = dateFormatter.format(date);
} else if (range < thisYearRange) {
dateFormatter.formatString = THIS_YEAR_PATTERN;
result = dateFormatter.format(date);
} else {
dateFormatter.formatString = ANOTHER_YEAR_PATTERN;
result = dateFormatter.format(date);
}
} else {
if (range > -FEW_SECONDS) {
result = "In a few seconds";
} else if (range > -MINUTE_IN_SECONDS) {
result = StringUtil.substitute(IN_X_SECONDS, Math.floor(-range));
} else if (range > -MINUTE_IN_SECONDS * 2) {
result = "In about a minute";
} else if (range > -HOUR_IN_SECONDS) {
result = StringUtil.substitute(IN_X_MINUTES, Math.floor(-range / MINUTE_IN_SECONDS));
} else if (range > -HOUR_IN_SECONDS * 2) {
result = "In about an hour";
} else if (range > tomorrowRange) {
result = StringUtil.substitute(IN_X_HOURS, Math.floor(-range / HOUR_IN_SECONDS));
} else if (range > theDayAfterTomorrowRange) {
dateFormatter.formatString = YESTERDAY_TOMORROW_PATTERN;
result = "Tomorrow " + dateFormatter.format(date);
} else if (range > nextWeekRange) {
dateFormatter.formatString = THIS_WEEK_PATTERN;
result = dateFormatter.format(date);
} else if (range > nextYearRange) {
dateFormatter.formatString = THIS_YEAR_PATTERN;
result = dateFormatter.format(date);
} else {
dateFormatter.formatString = ANOTHER_YEAR_PATTERN;
result = dateFormatter.format(date);
}
}
return result;
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment