focus-follows-mouse: ignore events generated when reshaping the stage

* Export meta_display_add_ignored_crossing_serial()
* Add the serial for reshaping the stage
* Increase the size of the "ignored_serials" array a bit to
  try to avoid the possibility of losing serials from multiple
  reshapes happening close together.

https://bugzilla.gnome.org/show_bug.cgi?id=597190
This commit is contained in:
Owen W. Taylor 2011-09-07 11:19:15 -04:00
parent bf4f3a8a99
commit 1ab6abc044
4 changed files with 29 additions and 7 deletions

View File

@ -279,6 +279,12 @@ do_set_stage_input_region (MetaScreen *screen,
Window xstage = clutter_x11_get_stage_window (CLUTTER_STAGE (info->stage)); Window xstage = clutter_x11_get_stage_window (CLUTTER_STAGE (info->stage));
XFixesSetWindowShapeRegion (xdpy, xstage, ShapeInput, 0, 0, region); XFixesSetWindowShapeRegion (xdpy, xstage, ShapeInput, 0, 0, region);
/* It's generally a good heuristic that when a crossing event is generated because
* we reshape the overlay, we don't want it to affect focus-follows-mouse focus -
* it's not the user doing something, it's the environment changing under the user.
*/
meta_display_add_ignored_crossing_serial (display, XNextRequest (xdpy));
XFixesSetWindowShapeRegion (xdpy, info->output, ShapeInput, 0, 0, region); XFixesSetWindowShapeRegion (xdpy, info->output, ShapeInput, 0, 0, region);
} }

View File

@ -73,9 +73,11 @@ typedef enum {
/* This is basically a bogus number, just has to be large enough /* This is basically a bogus number, just has to be large enough
* to handle the expected case of the alt+tab operation, where * to handle the expected case of the alt+tab operation, where
* we want to ignore serials from UnmapNotify on the tab popup, * we want to ignore serials from UnmapNotify on the tab popup,
* and the LeaveNotify/EnterNotify from the pointer ungrab * and the LeaveNotify/EnterNotify from the pointer ungrab. It
* also has to be big enough to hold ignored serials from the point
* where we reshape the stage to the point where we get events back.
*/ */
#define N_IGNORED_SERIALS 4 #define N_IGNORED_SERIALS 10
typedef enum { typedef enum {
META_TILE_NONE, META_TILE_NONE,

View File

@ -1383,8 +1383,19 @@ meta_display_get_current_time_roundtrip (MetaDisplay *display)
return timestamp; return timestamp;
} }
static void /**
add_ignored_serial (MetaDisplay *display, * meta_display_add_ignored_crossing_serial:
* @display: a #MetaDisplay
* @serial: the serial to ignore
*
* Save the specified serial and ignore crossing events with that
* serial for the purpose of focus-follows-mouse. This can be used
* for certain changes to the window hierarchy that we don't want
* to change the focus window, even if they cause the pointer to
* end up in a new window.
*/
void
meta_display_add_ignored_crossing_serial (MetaDisplay *display,
unsigned long serial) unsigned long serial)
{ {
int i; int i;
@ -1603,7 +1614,7 @@ event_callback (XEvent *event,
if (meta_ui_window_should_not_cause_focus (display->xdisplay, if (meta_ui_window_should_not_cause_focus (display->xdisplay,
modified)) modified))
{ {
add_ignored_serial (display, event->xany.serial); meta_display_add_ignored_crossing_serial (display, event->xany.serial);
meta_topic (META_DEBUG_FOCUS, meta_topic (META_DEBUG_FOCUS,
"Adding EnterNotify serial %lu to ignored focus serials\n", "Adding EnterNotify serial %lu to ignored focus serials\n",
event->xany.serial); event->xany.serial);
@ -1613,7 +1624,7 @@ event_callback (XEvent *event,
event->xcrossing.mode == NotifyUngrab && event->xcrossing.mode == NotifyUngrab &&
modified == display->ungrab_should_not_cause_focus_window) modified == display->ungrab_should_not_cause_focus_window)
{ {
add_ignored_serial (display, event->xany.serial); meta_display_add_ignored_crossing_serial (display, event->xany.serial);
meta_topic (META_DEBUG_FOCUS, meta_topic (META_DEBUG_FOCUS,
"Adding LeaveNotify serial %lu to ignored focus serials\n", "Adding LeaveNotify serial %lu to ignored focus serials\n",
event->xany.serial); event->xany.serial);

View File

@ -155,4 +155,7 @@ GSList *meta_display_sort_windows_by_stacking (MetaDisplay *display,
Window meta_display_get_leader_window (MetaDisplay *display); Window meta_display_get_leader_window (MetaDisplay *display);
void meta_display_add_ignored_crossing_serial (MetaDisplay *display,
unsigned long serial);
#endif #endif