barrierefreies Webdesign Ingo Turski

zum Inhalt

Ingo

Tips und Tricks:Jahrestag mit Javascript oder PHP hochzählen

CountDown-Skripte werden Sie bestimmt woanders finden, hier stelle ich Ihnen das Gegenteil - ein "CountUp"-Skript - vor. Es zählt die vergangenen Jahre, Monate, Tage, Stunden und Minuten seit einem (anzugebenden) Jahrestag. Die Berechnung ist nicht trivial, denn wieviele Tage sollen angegeben werden? Mein Skript wählt einen einfachen und meist passenden Kompromiß und berücksichtigt bei einem Übertrag die Anzahl der Tage des jeweils aktuellen Monats.
Als Beispiel habe ich (m)einen persönlichen Jahrestag gewählt:

Ich sollte seit an meinen Jahrestag denken.
<script type="text/javascript">
// <![CDATA[
function countUp() {
var jahr=1999, monat=9, tag=12, stunde=20, minute=30; // Jahrestag hier angeben

var akt=new Date();
var j=akt.getFullYear()-jahr;
var m=akt.getMonth()+1-monat;
var t=akt.getDate()-tag;
var s=akt.getHours()-stunde;
var u=akt.getMinutes()-minute;
if(u<0) {s--; u=60+u;}
if(s<0) {t--; s=24+s;}
if(t<0) {m--; t=new Date(akt.getFullYear(),akt.getMonth(),0).getDate()+t;}
if(m<0) {j--; m=12+m;}

var z = "";
if(j) { z = j + " Jahr"; if(j>1) z += "en"; }
if(m) {
  if(z) { if(t||s||u) z += ", "; else z += " und "; }
  z += (m + " Monat"); if(m>1) z += "en";
}
if(t) {
  if(z) { if(s||u) z += ", "; else z += " und "; }
  z += (t + " Tag"); if(t>1) z += "en";
}
if(s) {
  if(z) { if(u) z += ", "; else z += " und "; }
  z += (s + " Stunde"); if(s>1) z += "n";
}
if(u) {
  if(z) z += " und ";
  z += (u + " Minute"); if(u>1) z += "n";
}
document.write(z);
}
// ]]>
</script>

<div>Ich sollte seit
<strong><script type="text/javascript">countUp()</script></strong>
<noscript><div>dem 12.09.1999 20:30 Uhr</div></noscript>
an meinen Jahrestag denken.</div>

Wem PHP zur Verfügung steht, der sollte das gleiche serverseitig ausgeben lassen:

<?php
function countUp() {
$jahr=1999; $monat=9; $tag=12; $stunde=20; $minute=30; // Jahrestag hier angeben

$akt=getdate();
$j=$akt["year"]-$jahr;
$m=$akt["mon"]-$monat;
$t=$akt["mday"]-$tag;
$s=$akt["hours"]-$stunde;
$u=$akt["minutes"]-$minute;
if($u<0) {$s--; $u += 60;}
if($s<0) {$t--; $s += 24;}
if($t<0) {$m--; $t = date("t",mktime(0,0,0,$akt["mon"],0,$akt["year"]))+$t;}
if($m<0) {$j--; $m += 12;}

$z = "";
if($j) { $z = $j." Jahr"; if($j>1) $z .= "en"; }
if($m) {
  if($z) { if($t||$s||$u) $z += ", "; else $z += " und "; }
  $z .= $m." Monat"; if($m>1) $z .= "en";
}
if($t) {
  if($z) { if($s||$u) $z += ", "; else $z += " und "; }
  $z .= $t." Tag"; if($t>1) $z .= "en";}
if($s) {
  if($z) { if($u) $z += ", "; else $z += " und "; }
  $z .= $s." Stunde"; if($s>1) $z .= "n";
}
if($u) { if($z) $z .= " und ";
  $z .= $u." Minute"; if($u>1) $z .= "n";
}
return $z;
}
?>

<p>Ich sollte seit <strong><?php echo countUp();?></strong> an meinen Jahrestag denken.</p>

Diese simple, aber dennoch etwas umständliche Rechnerei ist notwendig, weil die einfache Auswertung der Differenz der Zeitstempel nicht die unterschiedliche Anzahl der Tage eines Monats berücksichtigt und dass z.B. bereits am 1. März ein Monat seit dem 1. Februar vergangen ist und nicht erst (nach Durchschnittsberechnung) am 3. März.

In beiden Fällen habe ich von einer speziellen Funktionalität Gebrauch gemacht, die weniger bekannt ist und die ich daher kurz erläutern möchte:
Wenn der aktuelle Tag des Monats kleiner als der Vergleichstag ist, ergibt sich eine negative Differenz, die teilweise von der Anzahl der Tage des Vormonats abgezogen werden muss. Das Date-Objekt von Javascript stellt hierzu einen Timestamp des letzten Tages des Vormonats zur Verfügung, wenn man als Tag 0 angibt. Die date()-Funktion von PHP stellt diese Anzahl über den Parameter "t" direkt zur Verfügung, wofür über die ähnlich wie bei Javascript aktivierbare Korrektur der Funktion mktime() der Vormonat gesetzt wird.