Accaparation du pointer : grab

/* grab1.c */

/* accaparation (grab) de la souris */

#include <stdio.h>
#include <X11/Xlib.h>
#include <X11/Xutil.h>
#include <X11/cursorfont.h>

GC      gc; 
Display *display; 
int     screen, presse=0; 
Window  win, root, subwin; 
unsigned long white_pixel, black_pixel;
Cursor curs;

main() { 
  if ((display = XOpenDisplay ("")) == NULL) { 
    fprintf (stderr, "Can't open Display\n"); 
    exit (1); 
  } 
  gc = DefaultGC (display, screen); 
  screen = DefaultScreen (display); 
  root = RootWindow (display, screen); 
  white_pixel = WhitePixel (display, screen); 
  black_pixel = BlackPixel (display, screen); 
  curs = XCreateFontCursor(display, XC_man);
  win = XCreateSimpleWindow (display, root,  
			     0, 0, 200, 200, 5, black_pixel, white_pixel); 
  XSelectInput (display, win, PointerMotionMask | ButtonPressMask |
		ButtonReleaseMask); 
  XStoreName (display, win, "grab1"); 
  XMapWindow (display, win); 
  subwin = XCreateSimpleWindow (display, win,  
			     70, 70, 60, 60, 2, black_pixel, white_pixel); 
  XSelectInput (display, subwin, PointerMotionMask | ButtonPressMask |
		ButtonReleaseMask); 
  XMapWindow (display, subwin); 
  XDefineCursor(display, subwin, curs);
 
  for (;;) { 
    XEvent ev;
    XNextEvent (display, &ev);
    switch (ev.type) {
    case MotionNotify :
      if (presse) {
	if (ev.xmotion.window == win)
	  write(1, "je suis accapare par win\n", 25);
	else if (ev.xmotion.window == subwin)
	  write(1, "je suis accapare par subwin\n", 28);
      } else
	write(1, "je me ballade\n", 14);
      break ;
    case ButtonPress  : 
      presse=1;
      if (ev.xbutton.window == win)
	write(1, "accaparation par win\n", 21);
      else if (ev.xbutton.window == subwin)
	write(1, "accaparation par subwin\n", 24);
      break ;
    case ButtonRelease  : 
      presse=0;
      write(1, "fin d'accaparation\n", 19);
      break ; 
    default :
      break;
    } 
  } 
}

Execution :

Appuyez sur un des boutons de souris dans la fenêtre ou sa sous-fenêtre, puis balladez la souris en maintenant le bouton enfoncé, enfin relachez. Regardez ce qui est affiché au fer et à mesure dans la fenêtre Xterm.

Fonctionnement de ce programme :

Accaparation, Monopolisation, saisie, Grab de la souris par une fenêtre :
- Par défaut (saisie automatique), entre l'enfoncement et le ralachement d'un bouton, seule la fenêtre accaparante (celle où s'est produit l'enfoncement) recoit les évênements souris. Par conséquent, en analisant les informations de l'événement, la fenêtre du pointer peut être différente de la fenêtre recevant l'événement.
- La requête XGrabPointer (...) définit aussi la fenêtre qui accapare le pointeur. XUngrabPointer annule cette monopolisation.

programme suivant index général fonctions de la XLib événements types dans XLib