PDA

Ver la Versión Completa : bloquear movimiento del cursor


dragon_maldito
11-07-2010, 01:45:38
Saludos.

Estoy en busca de ayuda. Estoy haciendo una aplicacion en Delphi que escucha los eventos del ratón a nivel global, esto utilizando una DLL. Ya tengo la parte donde muestro que evento fue el que ocurrió, ahora lo que me interesa es que, cuando ocurra el evento WM_MOUSEMOVE o WM_NCMOUSEMOVE, mi aplicacion si detecte el evento pero el cursor no se mueva, es decir, necesito cambiar los datos de DX y DY para que los incrementos sean "0" y el cursor simplemente no se mueva.

No tengo idea de como hacer esto. Hice algo similar pero para el botón derecho, poniendo una condicion IF haciendo como si nunca hubiera ocurrido ese evento. Este es el código que me funcionó.

begin
if (WParam = WM_RBUTTONDOWN) then
begin
Result := 1;
exit;
end;
if (WParam = WM_RBUTTONUP) then
begin
Result := 1;
exit;
end;

end;

Pero al intentar hacer esto para bloquear el movimiento en X y Y, no se que debo hacer. Alguien me podría ayudar.

Gracias.

escafandra
11-07-2010, 02:47:53
No entiendo el sentido que le quieres dar a que el cursos del ratón no se mueva, eso te bloqueará las aplicaciones.

La forma mas sencilla de bloquear el ratón cuando detectas movimiento en mediante un Hook de bajo nivel rompiendo la cadena de hooks:

function MouseEvent(nCode, wParam, lParam: Integer): Integer; stdcall;
begin
if nCode>=0 then
begin
if wParam = WM_MOUSEMOVE then
begin
Result := -1;
exit;
end;
end;
Result:= CallNextHookEx(hMouseHook, nCode, wParam, lParam);
end;


El problema es que te quedas bloqueado si no colocas una bandera de desbloqueo. He preparado un ejemplo sencillo en el que el bloqeuo es controlado con un Timer. Pasado el tiempo prefijado se desbloquea el ratón:

unit Unit1;

interface

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

type
TForm1 = class(TForm)
Timer1: TTimer;
procedure Timer1Timer(Sender: TObject);
procedure FormCreate(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;

const
WH_MOUSE_LL = 14;


var
Form1: TForm1;
hMouseHook: HHOOK = 0;
tt: boolean = true;
implementation

{$R *.dfm}
function MouseEvent(nCode, wParam, lParam: Integer): Integer; stdcall;
begin
if nCode>=0 then
begin
if wParam = WM_MOUSEMOVE then
begin
Result := -1;
if tt then exit;
end;
end;
Result:= CallNextHookEx(hMouseHook, nCode, wParam, lParam);
end;
procedure TForm1.Timer1Timer(Sender: TObject);
begin
tt:= false;
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
hMouseHook:= SetWindowsHookEx(WH_MOUSE_LL, @MouseEvent, HInstance, 0);
end;

end.

Saludos.

dragon_maldito
11-07-2010, 02:58:22
Lo que pasa es que quiero bloquear el evento de movimiento con los datos que le introdujo el raton, para posteriormente posicionar el cursor con nuevos datos.

Por ejemplo, el ratón le inyecta un dx=4 y dy=8 , esto haria "normalmente" que el cursor se moviera hacia la derecha 4 y hacia abajo 8. Bloqueo el movimiento con esos datos. ntercambio los valores ahora dx=8 y dy=4 y utilizo esos valores intercambiados para posicionar el cursor. El programa intercambia los ejes.

Es por eso que quiero IGNORAR el evento de movimiento del cursor.

Neftali [Germán.Estévez]
12-07-2010, 11:21:08
...haciendo una aplicacion en Delphi que escucha los eventos del ratón a nivel global,

El problema, es que tu aplicación sólo recibirá (con este sistema) los mensajes que se produzcan sobre ella, no sobre el resto de aplicaciones.
Para eso no se si tendrías que definir un Hook a nivel global.

dragon_maldito
12-07-2010, 16:43:56
Si, de hecho el código que puse es parte de la DLL. El hook lo tengo a nivel global.

Estuve tratando de probar el primer código que me pusiste pero lo único que hacia era omitir el mensaje del evento, pero el cursor sigue moviéndose. Investigué y leí que el evento WM_MOUSEMOVE solo es un mensaje de notificacion pero que no pueden controlar el cursor.

El código que ando utilizando de base es el que se encuentra en la pagina de trucomania.org, en el índice de trucos, es el truco numero 414.

Lo que necesito hacer para mi proyecto es:

1.- Estar listo para escuchar el evento del movimiento del ratón.
2.- Adquirir el incremento de movimiento en x y y. (necesito el movimiento relativo a la posición anterior del cursor)
3.- Omitir ese evento de movimiento.
4.- Los valores adquiridos de movimiento utilizarlos para pasarlos a un filtro digital, esto es, utilizar una ecuación donde incluya los valores de X y Y que adquirí previamente.
5.- El resultado de esta ecuacion serán 2 posiciones, X y Y nuevos. Esos datos utilizarlos para posicionar el cursor.
6.- Reiniciar el proceso

Sin embargo, desde el principio tengo problemas ya que todavía no se como adquirir los incrementos. Lo que si adquiere es la posicion del cursor, sin embargo estas son coordenadas absolutas respecto a la pantalla, pero yo lo que necesito son los incrementos de posicion.

Y una vez adquiridos los incrementos, necesitaría omitir, ignorar o bloquear ese evento de tal modo que el cursor no responda al evento de movimiento.

Tendrás alguna idea de por donde debo buscar, es que ya llevo como 1 semana sin obtener resultados y no creo que no se pueda hacer. Hay un proyecto llamado SteadyMouse que hace algo como lo que quiero hacer. Pero no tengo idea de como lo hizo y yo creo que tengo que utilizar los Hooks.

Gracias por tu ayuda y espero tu respuesta haber si puedes orientarme con esto. =)