Ver Mensaje Individual
  #2  
Antiguo 11-08-2005
Avatar de roman
roman roman is offline
Moderador
 
Registrado: may 2003
Ubicación: Ciudad de México
Posts: 20.269
Reputación: 10
roman Es un diamante en brutoroman Es un diamante en brutoroman Es un diamante en bruto
No cabe duda que Peter Below (autor del código que pones) es genial.

No entiendo bien del todo su código pero vamos a intentarlo.

Toda aplicación consiste básicamente de un ciclo:

Código:
repeat
  obtener_mensaje(msg)
  procesar_mensaje(msg)
end
Los mensajes, sean del ratón, del teclado, etc. se van colocando en una cola de mensajes para la aplicación y se van procesando conforme llegan a esta cola.

Según lo que explica Peter Below, procesar_mensaje() lo primero que hace (en una aplicación MDI) es llamar a la función IsMDIMsg que determina si el mensaje es especial para ventanas MDI. En el caso de Ctrl-Tab así es y el mensaje se transforma para hacer el cambio de ventana hija de manera que el mensaje original nunca llega al formulario activo. (Si el mensaje no es MDI entonces el mensaje se redirige al formulario activo)

Tal como él dice, hay un único punto donde se puede interceptar esto y es en el evento OnMessage de una componente TApplicationEvents. Dependiendo de la versión que uses de Delphi, es posible que no dispongas de tal componente. En tal caso procedes como él lo hace asignando el evento al objeto Application en el constructor del formulario principal.

En este evento, él detecta cuando el mensaje corresponde a Ctrl-Tab.

Ahora bien, el parámetro Handled del evento se usa para indicar a la VCL si ha de dejar que el mensaje siga su ruta normal o no. Prueba poniendo Handled := true sin más y verás que el efecto del Ctrl-Tab se deshabilita por completo.

Claro que esto no es lo que quieres pues no sólo evitas que se cambie la ventana activa sino que también inhabilitas el cambio de pestaña.

Lo que Peter Below hace es redirigir el mensaje al evento OnShortCut del formulario activo (la llamada a IsShortCut genera dicho evento).

Si no hay evento asignado IsShortCut devolverá false por lo que el valor de Handled en el evento OnMessage será false y el mensaje proseguirá su ruta normal. De esta forma logra que si se está en cualquier otro formulario, el cambio de ventana activa aún sea posible.

En el formulario con el PageControl debes colocar el evento OnShortcut. En este evento, Peter Below determina si estás parado sobre el PageControl (función IsOnTabSheet). Si no lo estás pone el valor de Handled en false. Aquí Handled es similar al del evento OnMessage y será lo que devuelva la función IsShortCut llamada allá de manera que el Handled de OnMessage será false indicando que se siga la ruta normal y se cambia la ventana activa.

Pero si sí estás parado sobre el PageControl, el código de Peter Below hace el cambio de pestaña (Perform(CM_DIALOGKEY...)) y pone Handled en true que a su vez hará que IsShortCut regrese true y por tanto el Handled de OnMessage sea true indicando que se deje de procesar el mensaje y evitando así el cambio de ventana activa.

// Saludos

Última edición por roman fecha: 11-08-2005 a las 07:54:39.
Responder Con Cita