3

I want to list for the user, all timezones with their native UTC/GMT offset, regardless of DST

How can I do it?

shealtiel
  • 8,020
  • 18
  • 50
  • 82
  • http://php.net/manual/en/timezones.php and http://www.php.net/manual/en/datetimezone.listabbreviations.php – Fivell Sep 08 '11 at 07:57
  • possible duplicate of [Generating a drop down list of timezones with PHP](http://stackoverflow.com/questions/1727077/generating-a-drop-down-list-of-timezones-with-php) – Gordon Sep 08 '11 at 08:00
  • 1
    It is related, but seems that this particular question is not asked and not answered there – shealtiel Sep 08 '11 at 08:17

1 Answers1

2

I 've come up with this function to do the job:

function standard_tz_offset($timezone) {
    $now = new DateTime('now', $timezone);
    $year = $now->format('Y');

    $startOfYear = new DateTime('1/1/'.$year, $timezone);
    $startOfNext = new DateTime('1/1/'.($year + 1), $timezone);

    $transitions = $timezone->getTransitions($startOfYear->getTimestamp(),
                                             $startOfNext->getTimestamp());
    foreach($transitions as $transition) {
        if(!$transition['isdst']) {
            return $transition['offset'];
        }
    }

    return false;
}

How it works

The function accepts a timezone and creates two DateTime objects: January 1st 00:00 of the current year and January 1st 00:00 of the next year, both specified in that timezone.

It then calculates the DST transitions during this year, and returns the offset for the first transition it finds where DST is not active.

PHP 5.3 is required because of the call to DateTimeZone::getTransitions with three parameters. If you want this to work in earlier versions you will have to accept a performance hit, because a whole lot of transitions will be generated by PHP (in this case, you don't need to bother with creating the $startOfYear and $startOfNext dates).

I have also tested this with timezones that do not observe DST (e.g. Asia/Calcutta) and it works for those as well.

To test it:

$timezone = new DateTimeZone("Europe/Athens");
echo standard_tz_offset($timezone);
Jon
  • 428,835
  • 81
  • 738
  • 806
  • I hopped that something like this will not be needed, and also wasn't sure how do I work with the transitions. Thanks – shealtiel Sep 08 '11 at 08:42