mtWeb  Home > PHP > Use PHP and JavaScript to Display Local TimeSitemap  Search

Use PHP and JavaScript to Display Local Time

Posted by martin on 1 Jun 2002.

How to display visitors' localtime using JavaScript and PHP without even asking them to select their timezone.

The decision

This can be done with the help of a little piece of JavaScript and the use of a server-side language like PHP, ASP, JSP or any other available to you.

In the example I will show I have used PHP with it's built-in session support (available since PHP 4.0).

Q: But why use JavaScript at all when PHP has it's own localtime() function?

A: PHP's localtime() function will give you the server local time not the user's and that's not what we want.

The concept

We want to show the visitor his/her local time, so what we need is way to get his time zone offset. We can do that in JavaScript with the help of the Date method getTimezoneOffset and then send it to the server to be saved as a session variable. We send this info by modifying all links in the document that point within our site by appending a query variable, e.g. we add ?offset=-180 if the link has no other query variables set. If it has then we add ;offset=-180.

Note: The additional query parameter is separated from the others with ; not & as the latter one has to be escaped as & in HTML.

When we have this info about the user we don't want him/her to send it over and over again as we have it already saved in our session so we don't send the JavaScript then. When displaying the time we use a function that adds the visitors offset to the time and then prints a string identifying the time zone.

An alternative that is not recommended though is to send the browser JavaScript code that uses document.write() to print the date.

Example code

JavaScript code

<?php
session_start();

if ( !isset($_SESSION['offset']) ) {
?>
  <script type="text/javascript">
  window.onload = setLinks

  function setLinks() {
    now = new Date()
    offset = now.getTimezoneOffset();

    for ( i = 0; i < document.links.length; i++ ) {
      with ( document.links[i] ) {
        if ( href.indexOf('http://martin.f2o.org') == 0 ) {
          if ( href.indexOf('?') == -1 ) {
            href += '?offset=' + offset;
          } else {
            href += ';offset=' + offset;
          }
        }
      }
    }
  }
  </script>

<?php
}
?>

We start by opening a PHP code block, and check if our session variable identifying that the user's time zone has been saved is not set. If it isn't then we should send the JavaScript code to the browser to process the links in the document.

Note: Opera 5 and 6 for Linux and Windows has a bug that causes it to strip out trailing slashes from URI's that may cause problems sometimes.

Now for that JavaScript: we first set a handler via window.onload = setLinks. This will execute the setLinks function upon loading of the document, i.e. all external images/CSS/JavaScript has been downloaded and the page is displayed.

The setLinks function will then create a new Date() to get the visitor's time zone, and will loop through all links in the document modifying them as mentioned earlier.

The server code (PHP in our case)

if ( !isset($_SESSION['GMT_offset']) ) {
  $_SESSION['GMT_offset'] = 0;
  $_SESSION['GMT_offset_str'] = '+0:00';
}

This code just sets default values for the GMT offset it none are stored in the session.

Note: In the whole example the new PHP 4.1 style session array is used. If you want to run that code in a previous version of PHP just change $_SESSION to $HTTP_SESSION_VARS, the former is also globally available and the latter has to be imported from the global namespace within functions with a declaration like:

global $HTTP_SESSION_VARS

track_vars must be on, use: php_flag track_vars true in a .htaccess file to achieve this, or set it directly in php.ini.

if ( isset($_GET['offset']) ) {
  $_SESSION['offset'] = $_GET['offset'];
  set_timezone($_GET['offset']);
}

This piece of code checks if the browsers sent a query parameter offset, if so sets the time offset to it by calling the set_timezone function (explanation of the function is given below).

function set_timezone( $offset ) {
  if ( $offset ) {
    $offset = -$offset;
    $_SESSION['GMT_offset'] = 60 * $offset;
    $GMT_offset_str = ( $offset > 0 ) ? '+' : '-';
    $GMT_offset_str .= floor($offset / 60) . ':';
    $GMT_offset_str .= (($offset % 60) < 10 ) ?
      '0' . $offset % 60 : $offset % 60;
    $_SESSION['GMT_offset_str'] = $GMT_offset_str;
  }
}

Now that's the function that does the hard work, it checks if there is an offset from GMT, if so negates its value (if you are located in a GMT +3:00 time zone the JavaScript function getTimezoneOffset() returns -180, i.e. the time in minutes that should be added to your local time to turn it into GMT).

Then we store the offset in seconds in a session variable, and process to the more complicated code that just sets the suffix that identifies the time zone.

function format_datetime( $date ) {
  return ( date('d M Y g:ia', $date + $_SESSION['GMT_offset']) .
  ' GMT ' . $_SESSION['GMT_offset_str']);
}

The format_datetime function is used to display local time, its parameter is an Unix timestamp (a 32-bit unsigned integer representing the number of seconds since the Unix Epoch - 1 Jan 1970), it uses date to display a date in GMT but only after adding the offset seconds. It concatenates the result with the appropriate suffix for the user's time zone.

What else can be done

I tried to pass the offset through a hidden image which is actually a PHP script that sets the session variable but I didn't succeed by doing this.

If you think there's a better way to do it don't hesitate to contact me.

Comments

Local Time
by Andy (forforum@mail.com) on 29 Jul 2002 6:30am GMT

Sorry, why not you state clearly that which code needs to place and on where? Don't grab your tutorial much sense. Cause...I'm a newbie :)

yup
by root (wei189@yahoo.com) on 29 Jul 2002 6:32am GMT

Where's the full code???????? Don't break it up, its confusing!

Got that
by martin on 29 Jul 2002 11:54pm GMT

The code is available as a whole for viewing.

You don't say..
by humpy () on 27 Aug 2002 9:57am GMT

Hmmm, it doesn't seem to work for me. I tried putting the example in a gmt.php file, ran it, but when run it shows a blank page? Your tutorial is a little hard to understand.

Reliable?
by Hal (halide@tribes2.org) on 27 Aug 2002 2:13pm GMT

Is this method actually a reliable method? Couldn't you simply store the offset as a cookie? I'm interesting in this but I believe it would be easier to give the user a dropdown with all timezone offsets.

No output is supposed by the script
by martin on 28 Aug 2002 9:48am GMT

Humpy, it isn't supposed to output anything. Just include it from a different page.

Hal, it probably is a good idea to store it as a cookie - I am storing it for registered users in my database.

As for the dropdown menu with all timezones - it probably is a better idea to have a field where people can type in the offset. As far as I know not many people would actually do it, but most know how to follow a link.

Great idea
by Tom () on 4 Sep 2002 10:36pm GMT

I can't believe all the grumpy comments. I think this page is exceedingly well-done and a useful tip. Keep it up Martin!

Tom

A bit odd...
by trfc791 on 9 Sep 2002 12:51pm GMT

I agree, this page is well done, but why the need for PHP in this instance, since Javascript has enough functions to display the user's local time in many different ways already.

Why PHP
by martin on 10 Sep 2002 7:52am GMT

Well the most obvious reason is that you can't get your content from a database, etc. and you won't have so many dates to deal with if only using JavaScript.

Anyway it is a good suggestion for static sites that show dates.

Now I know
by trfc791 on 13 Oct 2002 10:45am GMT

I didn't try this, but I tried displaying my local time (only my local time) by adding the offset (+13 from f2o), and it didn't work because of other considerations. Suppose Singapore was one day ahead of f2o. One month. One year. Leap year. It's all possible.

My solution was slightly different. I used mktime to obtain the number of seconds since the UNIX epoch (1/1/1970) in server time, added the offset in seconds, then used the value returned by mktime as an argument in date(). This can be adapted for this script as well.

Why server local time?
by martin on 14 Oct 2002 9:57am GMT

Why do you use the server local time at all? You can always get the UTC time with PHP and then add the offset, which is usually within the range -12 to +12 hours.

time zone with flash and php
by francis (francis_tudlong@yahoo.com) on 15 Oct 2002 8:55am GMT

sir:

how would i send the exact time zone of a user and send it to flash or php..

thanks..

kindly email me the answer..

francis

how to display
by GDiddy (daniel@cyphredesigns.com) on 29 Oct 2002 7:25pm GMT

please bear with me... i am new to php but very interested to learn. how do i go about using this code to display the current date on the page.

Displaying dates
by martin on 29 Oct 2002 9:15pm GMT

To display dates in the users' localtime:

1 Include the file (localtime.php)

2 Use the format_datetime() function (the parameter is a Unix timestamp)

PS. And read the article.

no explanation on how to implement
by webber () on 18 Dec 2002 10:30pm GMT

I'm sure this is a great solution but this article is so diificult to read the viewer cannot follow how to use it.

sometimes explanations are above the code block sometimes they are below...

the "download" is also not working or is it explained somewhere else ?

please help possibly provide a working example ?

...
by stabby (stabby123@hotmail.com) on 18 Dec 2002 11:23pm GMT

<?

$time = date("H:i");

print "$time";

?>

If i just want the date to be UK time how can i alter the code i have atm (above) to make it 'just' GMT?

expected $date format
by webber () on 19 Dec 2002 5:13am GMT

what is the expected format of $date as input to function

maybe that is why nothing is working for me

header prolem
by Jamal (jamal_106@hotmail.com) on 21 Dec 2002 11:35pm GMT

Hi,

I wondered if you can explain how the above file could be used. I am a newbie. I get error message which is not understanding to me.

I tried to include the file above and call the date function but it was not working. This is the error message I got:

Warning: Cannot send session cookie - headers already sent by (output started at c:\inetpub\wwwroot\databases\localtime.inc:20) in c:\inetpub\wwwroot\databases\localtime.inc on line 22

Warning: Cannot send session cache limiter - headers already sent (output started at c:\inetpub\wwwroot\databases\localtime.inc:20) in c:\inetpub\wwwroot\databases\localtime.inc on line 22

00:26

Please give me your assistance.

God Bless You.

sessions
by martin on 24 Dec 2002 10:27am GMT

As this script uses sessions (they need to send cookies) you should call session_start() before any output from the page.

Cookies version
by Michael Park (mp@MikePark.net) on 28 Dec 2002 5:18am GMT

Mr. Martin,

Do you have this script in alternate version that stores the result in persistent cookies?

Another function that does the same
by chuayw2000 on 9 Feb 2003 7:35am GMT

I've wrote a function that does the time converting quite well. You just need to add the time zone you want to the function. For example -5 and 8. The following is the function:

function getGmt($timezone){

$time = gmdate("F j, Y, g:i a",time() + (3600 * $timezone));

return $time;

}

I explained it in more detail @ http://members.tripod.co.uk/chuayw2000/blog/generate.php?page=php

The exact opposite
by James Cridland (james@cridland.net) on 7 May 2003 12:50pm GMT

I've done the exact opposite to this - a constantly updating JavaScript clock that is accurate to your server, not to your user's local time. If you wanted that, it's at http://james.cridland.net/code/clock.html

I'm about to work on something that uses PHP and JavaScript to display a schedule (for a radio station, for example) that displays the programme times in local time, hence why I stumbled across this page.

Cookie Solution - An Example Script
by mados () on 10 Jul 2003 2:31pm GMT

I wrote a very similar example based on a Cookie: http://phpcenter.de/phorum/read.php?f=1&i=33573&t=33498 (Scroll to the bottom of the page. It's in German but my script comments are in English of course.)

Just an complete php alternative...
by BrK () on 27 Jul 2003 4:48am GMT

Hi, this is an alternative that could make things easier:

<?php

setlocale (LC_TIME, $_SERVER["HTTP_ACCEPT_LANGUAGE"]);

$mytime= gmstrftime("%b %d %Y %H:%M:%S", mktime ())."<br>";

echo $mytime;

?>

About displaying local time...
by BrK () on 27 Jul 2003 5:03am GMT

And, to replace u'r five page solution(just joking)

<?php

setlocale (LC_TIME, $_SERVER["HTTP_ACCEPT_LANGUAGE"]);

$mytime= strftime("%b %d %Y %H:%M:%S", mktime ())."<br>";

echo $mytime;

?>

DST
by mocha (mochaexpress@yahoo.com) on 12 Aug 2003 8:28pm GMT

The use of

$_SERVER["HTTP_ACCEPT_LANGUAGE"]

in setlocale isn't a good way of dealing with DST. en-us is what shows on my php_info() page for that variable. That doesn't tell me where my time zone is in the US.

Localtime question
by Kev () on 19 Sep 2003 6:31am GMT

Hi Martin,

It seems to work for me but not sure the result is right. Here is my MySQL query:

$sql = "SELECT UNIX_TIMESTAMP(loaded_time) FROM dbload_delta";

$result = mysql_query("$sql");

list($loaded_time) = mysql_fetch_row($result);

$last_loaded = date("g:i:s A T M d, Y", $loaded_time);

echo("Last delta load @ $last_loaded.");

Output 1:

Last delta load @ 8:09:57 PM PDT Sep 05, 2003.

Using your format_datetime() func:

$user_localtime = format_datetime($loaded_time);

echo " Localtime: $user_localtime";

Output 2:

Localtime: 5 Sep 2003 8:09pm GMT

Where "Output 1" is PDT/PST TZ (Server Time)and "Output 2" is EST TZ (User Time). I'm in EST TZ. Am I supposed to get 5 Sep 2003 11:09pm GMT instead?

Short and Sweet
by Mike () on 28 Oct 2003 9:01pm GMT

echo gmdate("F j, Y, g:i a",time() + (3600 * $timezone));

This did the job for me!

Thanks, Martin
by David (dadler@vlgames.com) on 6 Nov 2003 7:25pm GMT

Thanks for writing your function and getting this discussion started. It has been very helpful!

time offset
by Robin () on 22 Nov 2003 11:10am GMT

Hey I have a problem that my forum is hosted on an american server so the time for all the posts is wrong, is there a way for the user to select an offset based on their location?

Remind u that it wont work all the time
by don (don@dons.com) on 27 Dec 2003 2:26am GMT

this depends that the user has the correct timezone set on their machine and also that javascript is running.

I suggest u all just think really hard about the best method for your scripts b4 trying this script

localtime() function
by alexandre plennevaux (alexandre@lab-au.com) on 30 Dec 2003 10:37pm GMT

here is a bit of code for displaying localtime with php:

-------------

<?

// USER LOCAL TIME

function GetTZOffset() {

$Offset = date("O", 0);

$Parity = $Offset < 0 ? -1 : 1;

$Offset = $Parity * $Offset;

$Offset = ($Offset - ($Offset % 100))/100*60 + $Offset % 100;

return $Parity * $Offset;

}

$TZOffset = GetTZOffset();

$t_time = time()-$TZOffset*60; #Counter adjust for localtime()

$t_arr = localtime($t_time);

$localTime = $t_arr[3].'-'.$t_arr[4].'-'.$t_arr[5].' '.$t_arr[2].':'.$t_arr[1].':'.$t_arr[0];

echo '<p>your time: '.$localTime;

?>

oups i'm wrong
by alexandre plennevaux () on 30 Dec 2003 11:34pm GMT

oups sorry, i'm wrong :(

Lots of Controversy
by The Man () on 12 Jan 2004 7:31pm GMT

There is no wrong way to do this - if you've found a way for it to work for you, post it here, and let someone try it. Don't tell someone their method is wrong simply because it doesn't fulfil the needs of your particular piece of software.

time/date
by George Kenkelen Jr. (knkln2@aol.com) on 15 Jan 2004 4:47am GMT

How would I change my time and date to read five hours before GMT time? It seems like the site is five hours ahead of my time, EST.

Thanks,

George.

time/date
by George Kenkelen Jr. (knkln2@aol.com) on 15 Jan 2004 4:47am GMT

How would I change my time and date to read five hours before GMT time? It seems like the site is five hours ahead of my time, EST.

Thanks,

George.

This is much simpler for me...
by John Woodell (woodie@netpress.com) on 20 Feb 2004 1:18pm GMT

You can swipe the gmt_offset,

and stick it into a hidden form element,

then figure out what the server offset

is in relation, and you're set.

<script type="text/javascript">

now = new Date();

loc = now.getTimezoneOffset()/60;

off = (-dif);

document.write('<INPUT TYPE="hidden"

NAME="gmt_offset" VALUE='+ off +'>');

</script>

<?php

$offset_server = substr(strftime("%z"),0,-2) + 0;

?>

This will probably work
by John Woodell () on 20 Feb 2004 9:18pm GMT

offset = new Date().getTimezoneOffset()/(-60);

document.write('<INPUT NAME="gmt_offset" VALUE='+ offset +'>');

Use PHP and JavaScript to Display Local Time
by Mark Winder (mark.winder@quadriga.com) on 21 May 2004 10:54am GMT

I've tried this code and had a number of problems. Firstly I couldnt get any of the session stuff to work. Eventually I gave up on this, and just used a the form varieable each time. The code still operates.

Second the code that adds offset to all links is very neat, but the ; didnt work in m,y case. When I cahnged it to & it did work. There was no need to use & amp;

Third, I think there is a bug in the code. In format_datetime which is running on the server, you use date. I think it should be gmdate. Here in UK we are in daylight saving time, 1 hour from GMT and use of date here adds a 1 hour error. This is server code so there should be no dependency on the local time zone.

The last problem I had is that my browser does not know to report the time as BST (British Summer Time) but reports it as GMT +1. This is not really good enough. I've hard coded GMT +1 as BST, but my worry is that other parts of the world may report GMT +1 offset and then its not appropriate to describe this as BST.

Because I'm not using the code exactly as proscribed it may be that some of these factors have been introduced by me, especially the date/gmdate thing. What do you think.

regards,

Mark.

Jesus H. Christ
by El_Hober (god@greentinted.net) on 21 May 2004 11:15pm GMT

This isn't that complicated, most of the PHP up there isn't going to work except in very, very simple applications. The javascript and the first bit of PHP to put the time zone offset into a session variable is what's important. Once you have the user's time zone you can get your server's time zone by using

date("z")

The way a UNIX timestamp works is, it's a number of seconds since the beginning of the UNIX epoch until the time it represents. So to adjust it to GMT, you add the timestamp to date("z"), to adjust it to your user's timezone you add it to date("z") and then again to $_SESSION['offset']*60 (the javascript offset is in minutes, so you multiply it by 60 to get seconds).

Now that you know how to convert a date from server time to user time, if you can't do anything with it it's your problem.

By The Way
by El_Hober (god@greentinted.net) on 21 May 2004 11:16pm GMT

I think this is a great tutorial, very helpful.

about the suggesstio by El_Hober
by Anupam Saha (anupam@indiafin.com) on 27 May 2004 12:11pm GMT

I think date("Z") will have to be used instead of date("z").

Display of the Servers time
by Shailen (shailen.neewoor@currimjee.intnet.mu) on 8 Jul 2004 12:05pm GMT

Hi,

Just wanted to know if this piece of script will display the servers time on which the website is running. In other words can it show the time of the server from which the webpage is coming.

Would be very grateful if you could help. Thanks & Regards - Shailen

a simple way
by Adrian Parker (adrian@parker96.com) on 17 Jul 2004 3:43pm GMT

I've done this in a VB.Net website, all I do is add some code to the starting page that passes the tzoffset (found using javascript) to the first visible page. If that page finds the argument, it adds it to the session otherwise, it assumes it was already set. This should work from php too.

Help
by Derek (derek_dude12@yahoo.com) on 18 Jul 2004 1:40am GMT

ok i got some scripts from u guys, but i am a n00b, and i know nothing of what to do.

I have my html files for my website done, but i want a login to be able to go to a password protected page, how can i do this? If u don't know how, thanks anyways.

wow
by () on 21 Jul 2004 11:47am GMT

this is good :)

Another way to do it
by () on 30 Aug 2004 4:05am GMT

here is a VERY simple implementation of this concept

http://rehfeld.us/dev/timezone/

Umm..
by David () on 29 Sep 2004 6:28am GMT

I have tried all the scripts here, and all of them bring up different dates, and whats more; none are my time... how do I get it to show waht time it is on my computer?

-David

Detecting also DST
by Barx (barx@email.it) on 18 Oct 2004 3:40pm GMT

I tried this script and it works, but it reports only the offset ignoring if DST is active or not in that period. So I'm thinking of reporting through the javascript the current time in combination with offset, to allow to calculate the correct time. Any comment?

timezone
by devilsoulblack (devilsoulblack@orenses.net) on 18 Oct 2004 9:07pm GMT

<?php

$timezone = -6; //(GMT -6:00) Ecuador

echo gmdate("Y/m/j H:i:s", time() + 3600*($timezone+date("I")));

?>

pag. very good
by WILKSON RENART (ariproj5@estadao.com.br) on 9 Jan 2005 11:58am GMT

Achei muito interessante esta vossa PAG. / SITE. Legal mesmo.

Desejo muito sucesso.