[WinAPI] GetTimeZoneInformation

Pagina: 1
Acties:
  • 103 views sinds 30-01-2008
  • Reageer

  • BoomSmurf
  • Registratie: Maart 2003
  • Laatst online: 13-06-2025
Ik heb even een probleempje met GetTimeZoneInformation. Ik woon zoals de meesten hier gewoon in Nederland, timezone GMT+0100. Met zomertijd zou je zomaar denken dat het dus GMT+0200 is (zowel de Tweakers als Fok! RSS feeds zijn het hier met mij eens).

Voor mijn eigen RSS reader die ik in elkaar aan het prutsen ben wordt natuurlijk gebruik gemaakt van tijdconversies. Wel zo handig als ik dus ook weet wat de timezone hier is :) Daarvoor GetTimeZoneInformation in de API opgezocht en een lapje testcode gefrutseld:

Delphi:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
procedure TForm1.Button1Click(Sender: TObject);

  procedure Add(S: String);
  begin
    Memo1.Lines.Add(S);
  end;

var TZI: _TIME_ZONE_INFORMATION;
    Res: DWORD;
    S: String;
    IsPos: Boolean;
begin
  Res := GetTimeZoneInformation(TZI);

  case Res of
    TIME_ZONE_ID_INVALID: Add('TimeZone ID: Invalid');
    TIME_ZONE_ID_UNKNOWN: Add('TimeZone ID: Unknown');
    TIME_ZONE_ID_STANDARD: Add('TimeZone ID: Standard');
    TIME_ZONE_ID_DAYLIGHT: Add('TimeZone ID: Daylight');
  else
    Add('TimeZone ID: Error');
  end;

  Add('Bias: ' + IntToStr(TZI.Bias));
  Add('StandardName: ' + TZI.StandardName);
  Add('StandardBias: ' + IntToStr(TZI.StandardBias));
  Add('DaylightName: ' + TZI.DaylightName);
  Add('DaylightBias: ' + IntToStr(TZI.DaylightBias));

  // Bias is negatief -> GMT offset is positief
  IsPos := TZI.Bias < 0;
  TZI.Bias := Abs(TZI.Bias);
  S := IntToStr(TZI.Bias mod 60);
  while Length(S) < 2 do S := '0' + S;
  S := IntToStr(TZI.Bias div 60) + S;
  while Length(S) < 4 do S := '0' + S;
  if IsPos then
    S := '+' + S
  else
    S := '-' + S;
  Add('GMT String: ' + S); // bv +0100 of -1200
end;


Dit heeft als resultaat:

code:
1
2
3
4
5
6
7
TimeZone ID: Daylight
Bias: -60
StandardName: W. Europe Standard Time
StandardBias: 0
DaylightName: W. Europe Standard Time
DaylightBias: -60
GMT String: +0100


Hardstikke leuk, maar volgens de API zitten wij hier 's winters dus op GMT+0000 en 's zomers op GMT+0100. Volgens mij klopt dit niet (zit er nl. een uur naast :D). De API tijd is wel in UTC, maar GMT = UTC, toch?

Iemand een briljante ingeving?

  • BoomSmurf
  • Registratie: Maart 2003
  • Laatst online: 13-06-2025
Typisch gevalletje slecht lezen aan mijn kant... (net wakker heh)

's winters: Bias + StandardBias
's zomers: Bias + DaylightBias

Ik dacht dat Bias de correcte waarde voor nu teruggaf... Foutje! Sorry voor de overlast |:(

[ Voor 7% gewijzigd door BoomSmurf op 30-03-2005 14:47 ]


  • _Thanatos_
  • Registratie: Januari 2001
  • Laatst online: 06-03 20:19

_Thanatos_

Ja, en kaal

Ga je er nu niet hard-coded van uit dat er daylight savings gehandhaafd worden? In verschillende landen kennen ze dat nml niet ;)

日本!🎌


  • BoomSmurf
  • Registratie: Maart 2003
  • Laatst online: 13-06-2025
Ik ga er van uit dat Windows dat wel weet. Als er geen daylight saving time is daaro, zal of DaylightBias 0 zijn of zal de functie altijd TIME_ZONE_ID_STANDARD teruggeven.

Maar ik ga er idd wel van uit dat de gebruiker EN zijn timezone EN zijn tijd goed ingesteld heeft :+

Zie de uiteindelijke functie voor de zgn 'GMT Offset' (sHHMM):
(ja mooi is anders maar het werkt wel :))

Delphi:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
function GetGMTOffset: String;
var TZI: _TIME_ZONE_INFORMATION;
    Res: DWORD;
    S: String;
    IsPos: Boolean;
    Bias: Integer;
begin
  Res := GetTimeZoneInformation(TZI);

  Bias := TZI.Bias;
  if Res = TIME_ZONE_ID_STANDARD then
    Bias := Bias + TZI.StandardBias
  else if Res = TIME_ZONE_ID_DAYLIGHT then
    Bias := Bias + TZI.DaylightBias;
  IsPos := Bias < 0; // Bias is negative -> GMT offset is positive
  Bias := Abs(Bias);
  S := IntToStr(Bias mod 60);
  while Length(S) < 2 do S := '0' + S;
  S := IntToStr(Bias div 60) + S;
  while Length(S) < 4 do S := '0' + S;
  if IsPos then
    S := '+' + S
  else
    S := '-' + S;
  Result := S; // eg +0100 of -1200
end;

[ Voor 85% gewijzigd door BoomSmurf op 30-03-2005 17:56 ]