Foros Club Delphi

Foros Club Delphi (https://www.clubdelphi.com/foros/index.php)
-   Varios (https://www.clubdelphi.com/foros/forumdisplay.php?f=11)
-   -   Calcular tiempo transcurrido (https://www.clubdelphi.com/foros/showthread.php?t=84071)

dtomeysoto 04-09-2013 20:21:24

Calcular tiempo transcurrido
 
Hola a todos, he desarrollando una aplicación en Delphi XE que me registra la hora en que se encienden y se apagan los PC y Servidores en la red. También se registran la hora y la fecha en que los usuarios inician sesión y la hora en la que se finaliza. Los datos los guardo en una tabla de una base de datos MS SQL 2005.

Hasta aquí todo bien, pero a la hora de mostrar los resultados almacenados desde otra aplicación me gustaría mostrar además de la hora de inicio de sesión y la de cierre (en el caso de la información registrada para los usuarios) y la de encendido y apagado (en el caso de los PC y Servidores) mostrar además la duración de la sesión, es decir cuanto tiempo estuvo abierta la sesión (horas, minutos, segundos y milisegundos). Teniendo en cuenta que una sesión puede estar abierta más de 24 horas lo que equivaldría a mostrar también los días.

Me gustaría si alguno de ustedes ya tiene hecho algo similar que me mostrara como hacerlo, porque he intentado restar los dos campos que son de tipo TDateTime y luego con DecodeDateTime pero no consigo lo que quiero.

Gracias.

ecfisa 04-09-2013 21:07:57

Hola dtomeysoto.

Para mostrar los datos de inicio y fin de sesión y el tiempo transcurrido entre ellos, podrías hacer:
Código Delphi [-]
(* 
  Para el ejemplo uso variables, y los eventos OnClick de dos Buttons,
  en tu caso los tiempos de incio y cierre se obtendrían de los campos 
  de la tabla donde almacenas esos datos. 
*)
uses DateUtils;

war
  InicioSesion,
  FinSesion : TDateTime;

procedure TForm1.btnInicioClick(Sender: TObject);
begin
  InicioSesion := Now;
end;

procedure TForm1.btnFinClick(Sender: TObject);
begin
  FinSesion  := Now;

  Memo1.Font.Name := 'Courier';
  with Memo1.Lines do
  begin
    Clear;
    Add('Inicio sesión: ' + DateTimeToStr(InicioSesion));
    Add('Fin sesión   : ' + DateTimeToStr(FinSesion));
    Add('');
    Add('Tiempo transcurrido');
    Add('-------------------');
    Add('Dias     : ' + IntToStr(DaysBetween(FinSesion, InicioSesion)));
    Add('Horas    : ' + IntToStr(HoursBetween(FinSesion, InicioSesion)));
    Add('Minutos  : ' + IntToStr(MinutesBetween(FinSesion, InicioSesion)));
    Add('Segundos : ' + IntToStr(SecondsBetween(FinSesion, InicioSesion)));
    Add('Miliseg. : ' + IntToStr(MilliSecondsBetween(FinSesion, InicioSesion)));
  end;
end;

Saludos :)

dtomeysoto 04-09-2013 22:09:28

Ya había probado algo como lo que me recomiendas pero no estoy conforme con el resultado que obtengo, por ejemplo para los siguientes valores:

sesion_ini = 04/09/2013 07:04:11 am
sesion_fin = 04/09/2013 11:01:06 am

Obtengo:

Duración = D:0, H:3, M:236, S:14215

No quiero que los minutos se pasen de 60 al igual que los segundos.

Casimiro Notevi 04-09-2013 23:11:34

¿Has probado en hacer una búsqueda? es un tema muy repetido y seguro que encuentras la solución.

nlsgarcia 05-09-2013 01:55:40

dtomeysoto,

Cita:

Empezado por dtomeysoto
...me gustaría mostrar...la duración de la sesión, es decir cuanto tiempo estuvo abierta la sesión (horas, minutos, segundos y milisegundos)...

Revisa este código basado en la solución sugerida en el Msg #2:
Código Delphi [-]
unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, DateUtils;

type
  TForm1 = class(TForm)
    Button1: TButton;
    Button2: TButton;
    Memo1: TMemo;
    procedure Button1Click(Sender: TObject);
    procedure Button2Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;
  InicioSesion, FinSesion : TDateTime;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
begin
   InicioSesion := Now;
end;

procedure TForm1.Button2Click(Sender: TObject);
var
   YYI, MMI, DDI, HHI, NNI, SSI, MSI : Word;
   YYF, MMF, DDF, HHF, NNF, SSF, MSF : Word;
   YYT, MMT, DDT, HHT, NNT, SST, MST : Word;
   FinalSesion : String;

begin

   FinSesion  := Now;

   ShortDateFormat := 'dd/mm/yyyy';
   ShortTimeFormat := 'hh:nn:ss:zzz';
   DateSeparator := '/';
   TimeSeparator := ':';

   DecodeDateTime(InicioSesion,YYI,MMI,DDI,HHI,NNI,SSI,MSI);
   DecodeDateTime(FinSesion,YYF,MMF,DDF,HHF,NNF,SSF,MSF);

   YYT := YYF - YYI;

   if MMF >= MMI then
   begin
      MMT := MMF - MMI
   end
   else
   begin
      YYF := YYF - 1;
      MMF := MMF + 12 - MMI;
   end;

   if DDF >= DDI then
   begin
      DDT := DDF - DDI
   end
   else
   begin
      MMT := MMT - 1;
      DDT := DDF + MonthDays[IsLeapYear(YYF),MMF] - DDI;
   end;

   if MMT < 0 then
   begin
      YYT := YYT - 1;
      MMT := 12 + MMT;
   end;

   if HHF >= HHI then
   begin
      HHT := HHF - HHI;
   end
   else
   begin
      DDT := DDT - 1;
      HHT := HHF + 24 - HHI;
   end;

   if NNF >= NNI then
   begin
      NNT := NNF - NNI;
   end
   else
   begin
      HHT := HHT - 1;
      NNT := NNF + 60 - NNI;
   end;

   if HHT < 0 then
   begin
      DDT := DDT - 1;
      HHT := HHT + 24
   end;

   if SSF >= SSI then
   begin
      SST := SSF - SSI;
   end
   else
   begin
      NNT := NNT - 1;
      SST := SSF + 60 - SSI;
   end;

   if MSF >= MSI then
   begin
      MST := MSF - MSI;
   end
   else
   begin
      SST := SST - 1;
      MST := MSF + 1000 - MSI;
   end;

   if SST < 0 then
   begin
      NNT := NNT - 1;
      SST := SST + 60;
   end;

   Memo1.Font.Name := 'Courier';
   with Memo1.Lines do
   begin
      Clear;
      Add('Inicio sesión : ' + DateTimeToStr(InicioSesion));
      Add('Fin sesión    : ' + DateTimeToStr(FinSesion));
      Add('');
      Add('Tiempo transcurrido');
      Add('-------------------');
      Add('Años     : ' + IntToStr(YYT));
      Add('Meses    : ' + IntToStr(MMT));
      Add('Dias     : ' + IntToStr(DDT));
      Add('Horas    : ' + IntToStr(HHT));
      Add('Minutos  : ' + IntToStr(NNT));
      Add('Segundos : ' + IntToStr(SST));
      Add('Miliseg. : ' + IntToStr(MST));
   end;

end;

end.
El código anterior permite mostrar en un componente TMemo el lapso de tiempo transcurridos entre dos variables TDateTime.

Nota: Variable TDateTime Inicial deber ser menor o igual a Variable TDateTime Final.

Espero sea útil :)

Nelson.

dtomeysoto 05-09-2013 20:55:02

Hola Nelson, gracias por la colaboración. Lo ajusté a lo que necesito y parece trabajar bien.
Solo una cosa, cuando compilo me da 4 advertencias,

En estas líneas me dice: Comparison always evaluates to False

if MMT < 0 then
if HHT < 0 then
if SST < 0 then

Y esta línea: Variable 'MMT' might not have been initialized

if MMT < 0 then

Todo sobre Delphi XE.

nlsgarcia 05-09-2013 23:10:46

dtomeysoto,

Cita:

Empezado por dtomeysoto
...ajusté a lo que necesito y parece trabajar bien...cuando compilo me da 4 advertencias...sobre Delphi XE...

El código del Msg #5 fue desarrollado en Delphi 7 y en dicho ambiente se generan las mismas advertencias del compilador que en Delphi XE, sin afectar el funcionamiento del código.

Espero sea útil :)

Nelson.

dtomeysoto 06-09-2013 18:24:47

Cita:

Empezado por nlsgarcia (Mensaje 466486)
dtomeysoto,



El código del Msg #5 fue desarrollado en Delphi 7 y en dicho ambiente se generan las mismas advertencias del compilador que en Delphi XE, sin afectar el funcionamiento del código.

Espero sea útil :)

Nelson.

Mas que útil, me ha venido como una joya.

josydasalone 15-09-2016 22:36:00

Tal vez le sirva a lguien
 
Cita:

Empezado por dtomeysoto (Mensaje 466437)
Ya había probado algo como lo que me recomiendas pero no estoy conforme con el resultado que obtengo, por ejemplo para los siguientes valores:

sesion_ini = 04/09/2013 07:04:11 am
sesion_fin = 04/09/2013 11:01:06 am

Obtengo:

Duración = D:0, H:3, M:236, S:14215

No quiero que los minutos se pasen de 60 al igual que los segundos.

Creo q lo mejor seria sacar el mod en los minutos y segundos.
Osea M := M mod 60;
S := S mod 60;

Casimiro Notevi 15-09-2016 22:56:57

Bienvenido a clubdelphi, como siempre aconsejamos a los nuevos, no olvides leer nuestra guía de estilo, gracias por tu colaboración :)


Y recuerda poner los tags al código fuente, ejemplo:



Gracias :)

josydasalone 16-09-2016 00:19:19

Cita:

Empezado por dtomeysoto (Mensaje 466437)
Ya había probado algo como lo que me recomiendas pero no estoy conforme con el resultado que obtengo, por ejemplo para los siguientes valores:

sesion_ini = 04/09/2013 07:04:11 am
sesion_fin = 04/09/2013 11:01:06 am

Obtengo:

Duración = D:0, H:3, M:236, S:14215

No quiero que los minutos se pasen de 60 al igual que los segundos.

Creo q lo mejor seria sacar el mod en los minutos y segundos.
Osea
Código Delphi [-]
M := M mod 60;
S := S mod 60;
Asi solo te daran resultados debajo de 60.


La franja horaria es GMT +2. Ahora son las 20:10:07.

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