PDA

Ver la Versión Completa : Como detectar en un OnClick q es un OnDblClick???


dmr1974
01-11-2004, 13:28:59
Hola:

Tengo un componente creado. Debe actuar de una forma cuando se le hace OnClick; de otra forma totalmente distinta cuando haces OnDblClick.
Hasta aquí todo correcto.
El problema es que cuando hago dobleclick se me activan los dos, y solo debería activarse el evento OnDblClick.
¿Es posible detectar en el OnClick que en verdad es un doble Click para que el evento no haga nada?¿Cómo?

Muchas Gracias

NeWNeO
01-11-2004, 14:06:58
podrias intentar esto...
Declaras 1 variable para contar clics

var
clics: smallint;

Ahora en el Onclic y OnDblClic de lo que quieras pones...

TForm1.Onclick(Sender: TObject);
begin
inc(clics,1);
if not Timer1.enabled then Timer.enabled := true;
end;

TForm1.OnDlbClic(Sender: TObject);
begin
if Timer1.enabled then Timer.enabled := false; // Pararemos el timer si haces doble clic;
DosClics; // Ejecutas tu proceso de doble clic
end;

Creas un timer en cuyo Evento se contabilize clics
[Delphi]
procedure TForm1.Timer1OnTimer(Sender: TObject);
begin
Timer1.enabled := false;
if clics = 1 then UnClic; // Si has hecho 1 clic... ejecutaras tu proceso de 1 clic
Clics := 0; // Reinicias clics
end;


Puede que te funcione correctamente, pero claro, el problema te vendrá cuando tengas que aplicarlo a muchos eventos... es una solución chapucerilla. Tal vez basandote en esto puedas encontrar alguna forma más rápida y ligera de alcanzar tu objetivo.

Lepe
01-11-2004, 14:43:41
Pon un label en un Form y un Memo, pega este código.

unit Unit1;

interface

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

type
TForm1 = class(TForm)
Label1: TLabel;
Memo1: TMemo;
procedure Label1Click(Sender: TObject);
procedure Label1DblClick(Sender: TObject);
procedure FormDblClick(Sender: TObject);
procedure FormClick(Sender: TObject);
private
{ Private declarations }
old,now:Int64;
public
{ Public declarations }
end;

var
Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.Label1Click(Sender: TObject);
begin
now := GetTickCount;
if now - old > GetDoubleClickTime then
begin
Memo1.lines.Add('uno');
end;
Memo1.lines.Add(IntToStr(now)+ ' ' +IntToStr(old)+' DIF ' +
IntToStr(now-old)+ ' gettick ' + IntToStr(GetDoubleClickTime));
old := GetTickCount;

end;

procedure TForm1.Label1DblClick(Sender: TObject);
begin
Memo1.lines.Add('dos');
old:= GetTickCount;
end;

procedure TForm1.FormDblClick(Sender: TObject);
begin
Memo1.Lines.Add('compuesto')
end;

procedure TForm1.FormClick(Sender: TObject);
begin
Memo1.Lines.Add('simple')
end;

end.

La verdad es que GetDoubleClickTime es de 500 por tanto, si tardas en hacer el doble clic más de 500 milisegundos, el evento Onclic tambien se activará.

El problema no es tuyo, es de la VCL o de windows, de hecho, si haces un Doble clic en el Form verás que sale 'Simple' y 'Compuesto' es decir, ha detectado el clic y el doble clic, cuando solo debería coger el doble clic.

Modificando en el panel de control de windows la rapidez del doble clic puedes variar desde 200 hasta 900 (muy poco márgen). Podrías usar en tu aplicación SetDoubleClickTime(intervalo en milisegundos) Pero afectaría a todo windows, y al ser un componente.... no lo creo conveniente.

Tambien puedes chequear cuando entra el foco en tu componente, modificar el tiempo de doble clic y al perder el foco ponerlo todo como estaba .... tú verás si es posible.


Conclusión rápida: No se puede
Conclusión Exhaustiva: Varios días de prueba y error y con suerte lo sacas ;)

Saludos

dmr1974
03-11-2004, 13:35:58
Gracias a ambos por la respuesta.

La solución de Lepe no era del todo válida, dado que un dobleclick inicial en una instancia del componente daba fallo...se activaban ambos.

Al final he arreglado la solución de NewNeo inicializando a 0 los clics en el dobleclick(q era el unico sitio donde fallaba-->tras hacer dobleclick no reconocía el primer click simple)....y funciona.

Un saludo
David

Lepe
03-11-2004, 19:43:59
No pretendía darte el código, solo la idea para que lo machacaras.

Por cierto, en cuanto al error que comentas.... Se puede solucionar facilmente no? ;)

dmr1974
03-11-2004, 21:24:03
Pues no sé Lepe. La verdad es q probé los dos métodos empezando por el tuyo pq se parecía más a las soluciones q yo había estado investigando, pero descubrí la pega esa...le dí dos vueltas y no ví solución rápida, así que probé la otra...le vi la pega, pero le encontré solución rápida.

Era un tema de presentación más que nada, así que no me calenté mucho...al final tendría que rehacerlo todo, que me sería más pesado. El problema es q con tu sistema el primer click no está controlado (o por lo menos no veo el sistema a bote pronto) y la creación y destrucción de instancias del componente es contínua durante toda la ejecución de la aplicación. Mejor no complicarlo mucho, que sino la depuración se vuelve insoportable.

Gracias de todos modos y un saludo.