Foros Club Delphi

Foros Club Delphi (https://www.clubdelphi.com/foros/index.php)
-   Varios (https://www.clubdelphi.com/foros/forumdisplay.php?f=11)
-   -   Buscar archivos con horario de verano activado (https://www.clubdelphi.com/foros/showthread.php?t=78783)

ehdez82 16-05-2012 22:42:01

Buscar archivos con horario de verano activado
 
1 Archivos Adjunto(s)
Estoy realizando una aplicación con Delphi 2010 que entre sus funciones busca en una carpeta los archivos modificados después de una fecha y hora. Estoy utilizando para esto el componente JvSearchFiles del paquete Jedi.
El problema es que cuando el sistema aplica automáticamente el horario de verano la hora de modificación de los archivos se adelanta una hora afectando la comparación.

He separado un pequeño ejemplo para explicar el problema, aqui está el código:

Código Delphi [-]
procedure TForm1.Button1Click(Sender: TObject);
var
  D: TDateTime;
begin
  with JvSearchFiles do
  begin
    RootDirectory := ExtractFilePath(Application.ExeName) + '\Logs';
    D := EncodeDateTime(2011, 12, 5, 21, 30, 0, 0);
    MFiles.Lines.Add('Searching files modified after ' + DateTimeToStr(D));
    FileParams.SearchTypes := FileParams.SearchTypes + [stLastChangeAfter];
    FileParams.LastChangeAfter := D;
    Search;
  end;
end;

procedure TForm1.JvSearchFilesFindFile(Sender: TObject; const AName: string);
var
  S: String;
begin
  with JvSearchFiles do
  begin
    S := S + AName;
    S := S + '      Modified Time: ' + DateTimeToStr
      (FileTimeToDateTime(FindData.ftLastWriteTime));
    S := S + '      Creation Time: ' + DateTimeToStr
      (FileTimeToDateTime(FindData.ftCreationTime));
  end;
  MFiles.Lines.Add(S);
end;

Lo que me muestra en el memo es:

Searching files modified after 05/12/2011 02:00:00 PM
Log (1).log Modified Time: 05/12/2011 02:54:03 PM Creation Time: 12/05/2012 02:13:46 AM
Log (2).log Modified Time: 05/12/2011 08:57:16 PM Creation Time: 15/05/2012 01:32:04 PM
Log (3).log Modified Time: 05/12/2011 10:05:00 PM Creation Time: 15/05/2012 01:32:05 PM
Log (4).log Modified Time: 05/12/2011 10:59:27 PM Creation Time: 15/05/2012 01:32:05 PM

Lo que dice el explorador de windows 7 es:

Log (1).log Modified Time: 05/12/2011 01:54:03 PM Creation Time: 12/05/2012 02:13:46 AM
Log (2).log Modified Time: 05/12/2011 07:57:16 PM Creation Time: 15/05/2012 01:32:04 PM
Log (3).log Modified Time: 05/12/2011 09:05:00 PM Creation Time: 15/05/2012 01:32:05 PM
Log (4).log Modified Time: 05/12/2011 09:59:27 PM Creation Time: 15/05/2012 01:32:05 PM


El componente JvSearchFiles utiliza principalmente estos dos procedimientos:

Código Delphi [-]
procedure TJvSearchParams.SetLastChangeAfter(const Value: TDateTime);
var
  DosFileTime: Longint;
  LocalFileTime: TFileTime;
begin
  { Value must be >= 1-1-1980 }
  DosFileTime := DateTimeToDosDateTime(Value);
  if not Windows.DosDateTimeToFileTime(LongRec(DosFileTime).Hi,
    LongRec(DosFileTime).Lo, LocalFileTime) or
    not Windows.LocalFileTimeToFileTime(LocalFileTime, FLastChangeAfterFT) then
    RaiseLastOSError;

  FLastChangeAfter := Value;
end;

function TJvSearchParams.Check(const AFindData: TWin32FindData): Boolean;
begin
    ...
   
    if stLastChangeAfter in FSearchTypes then
      if CompareFileTime(ftLastWriteTime, FLastChangeAfterFT) < 0 then
        Exit;
    ...
end;

En el procedimiento SetLastChangeAfter se utilizan las funciones DateTimeToDosDateTime, DosDateTimeToFileTime y LocalFileTimeToFileTime los cuales por lo visto no logran que se le aplique a la fecha el horario de verano.

Cuando desactivo aplicar automáticamente el horario de verano todo funciona perfectamente y coincide la hora de modificación que muestra la aplicación con la del explorador de windows 7. Sin embargo no creo que la aplicación deba forzar al usuario a cambiar su configuración personal. Entonces lo que necesito es alguna forma de convertir mi fecha a la configuración local incluyendo el horario de verano.

Gracias de antemano.
Saludos.

Casimiro Notevi 17-05-2012 00:05:40

Con la hora UTC creo que solventas el problema:

Código Delphi [-]
procedure TMainForm.TimeZoneClick(Sender: TObject);
var
  MyTime : TDateTime;
  UTC: TSystemTime;
begin
  MyTime := Time;
  GetSystemTime(UTC);
  with Memo1.Lines do
  begin
    Add('PC time: '+TimeToStr(MyTime));
    Add('UTC: '+IntToStr(UTC.wHour)+':'+IntToStr(UTC.wMinute)+':'+IntToStr(UTC.wSecond));
    Add('Date: '+IntToStr(UTC.wYear)+':'+IntToStr(UTC.wMonth)+':'+IntToStr(UTC.wDay));
  end;
end;

Mira aquí.

Casimiro Notevi 17-05-2012 00:15:27

También puede ser GMT:
Código Delphi [-]
function GMTToLocalTime(GMTTime: TDateTime): TDateTime; 
var   
  GMTST: Windows.TSystemTime;   
  LocalST: Windows.TSystemTime; 
begin    
  SysUtils.DateTimeToSystemTime(GMTTime, GMTST);    
  SysUtils.Win32Check(Windows.SystemTimeToTzSpecificLocalTime(nil, GMTST, LocalST));    
  Result := SysUtils.SystemTimeToDateTime(LocalST); 
end;

Aquí.


La franja horaria es GMT +2. Ahora son las 14:01:01.

Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi