static void meta_backend_x11_select_stage_events (MetaBackend *backend) { MetaBackendX11 *x11 = META_BACKEND_X11 (backend); MetaBackendX11Private *priv = meta_backend_x11_get_instance_private (x11); Window xwin = meta_backend_x11_get_xwindow (x11); unsigned char mask_bits[XIMaskLen (XI_LASTEVENT)] = { 0 }; XIEventMask mask = { XIAllMasterDevices, sizeof (mask_bits), mask_bits }; XISetMask (mask.mask, XI_KeyPress); XISetMask (mask.mask, XI_KeyRelease); XISetMask (mask.mask, XI_ButtonPress); XISetMask (mask.mask, XI_ButtonRelease); XISetMask (mask.mask, XI_Enter); XISetMask (mask.mask, XI_Leave); XISetMask (mask.mask, XI_FocusIn); XISetMask (mask.mask, XI_FocusOut); XISetMask (mask.mask, XI_Motion); XIClearMask (mask.mask, XI_TouchBegin); XIClearMask (mask.mask, XI_TouchEnd); XIClearMask (mask.mask, XI_TouchUpdate); XISelectEvents (priv->xdisplay, xwin, &mask, 1); }
static void unset_hierarchy_mask(::Display *display, XIEventMask *masks, int nmasks, bool was_set, bool was_created) { if (was_set || was_created) { if (was_set) { for (int i = 0; i < nmasks; i++) { if (masks[i].deviceid == XIAllDevices) XIClearMask(masks[i].mask, XI_HierarchyChanged); } } else if (was_created) masks[nmasks - 1].mask_len = 0; XISelectEvents(display, DefaultRootWindow(display), masks, nmasks); XFlush(display); } for (int i = 0; i < nmasks; i++) delete[] masks[i].mask; delete[] masks; }
static void test_convert_XIDeviceEvent(void) { DeviceEvent in; int i; memset(&in, 0, sizeof(in)); printf("Testing simple field values\n"); in.header = ET_Internal; in.type = ET_Motion; in.length = sizeof(DeviceEvent); in.time = 0; in.deviceid = 1; in.sourceid = 2; in.root = 3; in.root_x = 4; in.root_x_frac = 5; in.root_y = 6; in.root_y_frac = 7; in.detail.button = 8; in.mods.base = 9; in.mods.latched = 10; in.mods.locked = 11; in.mods.effective = 11; in.group.base = 12; in.group.latched = 13; in.group.locked = 14; in.group.effective = 15; test_XIDeviceEvent(&in); printf("Testing field ranges\n"); /* 32 bit */ in.detail.button = 1L; test_XIDeviceEvent(&in); in.detail.button = 1L << 8; test_XIDeviceEvent(&in); in.detail.button = 1L << 16; test_XIDeviceEvent(&in); in.detail.button = 1L << 24; test_XIDeviceEvent(&in); in.detail.button = ~0L; test_XIDeviceEvent(&in); /* 32 bit */ in.time = 1L; test_XIDeviceEvent(&in); in.time = 1L << 8; test_XIDeviceEvent(&in); in.time = 1L << 16; test_XIDeviceEvent(&in); in.time = 1L << 24; test_XIDeviceEvent(&in); in.time = ~0L; test_XIDeviceEvent(&in); /* 16 bit */ in.deviceid = 1; test_XIDeviceEvent(&in); in.deviceid = 1 << 8; test_XIDeviceEvent(&in); in.deviceid = ~0 & 0xFF; test_XIDeviceEvent(&in); /* 16 bit */ in.sourceid = 1; test_XIDeviceEvent(&in); in.deviceid = 1 << 8; test_XIDeviceEvent(&in); in.deviceid = ~0 & 0xFF; test_XIDeviceEvent(&in); /* 32 bit */ in.root = 1L; test_XIDeviceEvent(&in); in.root = 1L << 8; test_XIDeviceEvent(&in); in.root = 1L << 16; test_XIDeviceEvent(&in); in.root = 1L << 24; test_XIDeviceEvent(&in); in.root = ~0L; test_XIDeviceEvent(&in); /* 16 bit */ in.root_x = 1; test_XIDeviceEvent(&in); in.root_x = 1 << 8; test_XIDeviceEvent(&in); in.root_x = ~0 & 0xFF; test_XIDeviceEvent(&in); in.root_x_frac = 1; test_XIDeviceEvent(&in); in.root_x_frac = 1 << 8; test_XIDeviceEvent(&in); in.root_x_frac = ~0 & 0xFF; test_XIDeviceEvent(&in); in.root_y = 1; test_XIDeviceEvent(&in); in.root_y = 1 << 8; test_XIDeviceEvent(&in); in.root_y = ~0 & 0xFF; test_XIDeviceEvent(&in); in.root_y_frac = 1; test_XIDeviceEvent(&in); in.root_y_frac = 1 << 8; test_XIDeviceEvent(&in); in.root_y_frac = ~0 & 0xFF; test_XIDeviceEvent(&in); /* 32 bit */ in.mods.base = 1L; test_XIDeviceEvent(&in); in.mods.base = 1L << 8; test_XIDeviceEvent(&in); in.mods.base = 1L << 16; test_XIDeviceEvent(&in); in.mods.base = 1L << 24; test_XIDeviceEvent(&in); in.mods.base = ~0L; test_XIDeviceEvent(&in); in.mods.latched = 1L; test_XIDeviceEvent(&in); in.mods.latched = 1L << 8; test_XIDeviceEvent(&in); in.mods.latched = 1L << 16; test_XIDeviceEvent(&in); in.mods.latched = 1L << 24; test_XIDeviceEvent(&in); in.mods.latched = ~0L; test_XIDeviceEvent(&in); in.mods.locked = 1L; test_XIDeviceEvent(&in); in.mods.locked = 1L << 8; test_XIDeviceEvent(&in); in.mods.locked = 1L << 16; test_XIDeviceEvent(&in); in.mods.locked = 1L << 24; test_XIDeviceEvent(&in); in.mods.locked = ~0L; test_XIDeviceEvent(&in); in.mods.effective = 1L; test_XIDeviceEvent(&in); in.mods.effective = 1L << 8; test_XIDeviceEvent(&in); in.mods.effective = 1L << 16; test_XIDeviceEvent(&in); in.mods.effective = 1L << 24; test_XIDeviceEvent(&in); in.mods.effective = ~0L; test_XIDeviceEvent(&in); /* 8 bit */ in.group.base = 1; test_XIDeviceEvent(&in); in.group.base = ~0 & 0xFF; test_XIDeviceEvent(&in); in.group.latched = 1; test_XIDeviceEvent(&in); in.group.latched = ~0 & 0xFF; test_XIDeviceEvent(&in); in.group.locked = 1; test_XIDeviceEvent(&in); in.group.locked = ~0 & 0xFF; test_XIDeviceEvent(&in); in.mods.effective = 1; test_XIDeviceEvent(&in); in.mods.effective = ~0 & 0xFF; test_XIDeviceEvent(&in); printf("Testing button masks\n"); for (i = 0; i < sizeof(in.buttons) * 8; i++) { XISetMask(in.buttons, i); test_XIDeviceEvent(&in); XIClearMask(in.buttons, i); } for (i = 0; i < sizeof(in.buttons) * 8; i++) { XISetMask(in.buttons, i); test_XIDeviceEvent(&in); } printf("Testing valuator masks\n"); for (i = 0; i < MAX_VALUATORS; i++) { XISetMask(in.valuators.mask, i); test_XIDeviceEvent(&in); XIClearMask(in.valuators.mask, i); } for (i = 0; i < MAX_VALUATORS; i++) { XISetMask(in.valuators.mask, i); in.valuators.data[i] = i + (i * 0.0020); test_XIDeviceEvent(&in); XIClearMask(in.valuators.mask, i); } for (i = 0; i < MAX_VALUATORS; i++) { XISetMask(in.valuators.mask, i); test_XIDeviceEvent(&in); } }
static void test_convert_XIRawEvent(void) { RawDeviceEvent in; int i; memset(&in, 0, sizeof(in)); printf("Testing all event types\n"); in.header = ET_Internal; in.type = ET_RawMotion; test_XIRawEvent(&in); in.header = ET_Internal; in.type = ET_RawKeyPress; test_XIRawEvent(&in); in.header = ET_Internal; in.type = ET_RawKeyRelease; test_XIRawEvent(&in); in.header = ET_Internal; in.type = ET_RawButtonPress; test_XIRawEvent(&in); in.header = ET_Internal; in.type = ET_RawButtonRelease; test_XIRawEvent(&in); printf("Testing details and other fields\n"); in.detail.button = 1L; test_XIRawEvent(&in); in.detail.button = 1L << 8; test_XIRawEvent(&in); in.detail.button = 1L << 16; test_XIRawEvent(&in); in.detail.button = 1L << 24; test_XIRawEvent(&in); in.detail.button = ~0L; test_XIRawEvent(&in); in.detail.button = 0; in.time = 1L; test_XIRawEvent(&in); in.time = 1L << 8; test_XIRawEvent(&in); in.time = 1L << 16; test_XIRawEvent(&in); in.time = 1L << 24; test_XIRawEvent(&in); in.time = ~0L; test_XIRawEvent(&in); in.deviceid = 1; test_XIRawEvent(&in); in.deviceid = 1 << 8; test_XIRawEvent(&in); in.deviceid = ~0 & 0xFF; test_XIRawEvent(&in); printf("Testing valuator masks\n"); for (i = 0; i < MAX_VALUATORS; i++) { XISetMask(in.valuators.mask, i); test_XIRawEvent(&in); XIClearMask(in.valuators.mask, i); } for (i = 0; i < MAX_VALUATORS; i++) { XISetMask(in.valuators.mask, i); in.valuators.data[i] = i + (i * 0.0010); in.valuators.data_raw[i] = (i + 10) + (i * 0.0030); test_XIRawEvent(&in); XIClearMask(in.valuators.mask, i); } for (i = 0; i < MAX_VALUATORS; i++) { XISetMask(in.valuators.mask, i); test_XIRawEvent(&in); } }
void meta_compositor_manage (MetaCompositor *compositor) { MetaDisplay *display = compositor->display; Display *xdisplay = display->xdisplay; MetaScreen *screen = display->screen; Window xwin = 0; gint width, height; meta_screen_set_cm_selection (display->screen); if (meta_is_wayland_compositor ()) { MetaWaylandCompositor *wayland_compositor = meta_wayland_compositor_get_default (); compositor->stage = meta_stage_new (); wayland_compositor->stage = compositor->stage; meta_screen_get_size (screen, &width, &height); clutter_actor_set_size (compositor->stage, width, height); clutter_actor_show (compositor->stage); } else { compositor->stage = clutter_stage_new (); meta_screen_get_size (screen, &width, &height); clutter_actor_realize (compositor->stage); xwin = clutter_x11_get_stage_window (CLUTTER_STAGE (compositor->stage)); XResizeWindow (xdisplay, xwin, width, height); { MetaBackendX11 *backend = META_BACKEND_X11 (meta_get_backend ()); Display *backend_xdisplay = meta_backend_x11_get_xdisplay (backend); unsigned char mask_bits[XIMaskLen (XI_LASTEVENT)] = { 0 }; XIEventMask mask = { XIAllMasterDevices, sizeof (mask_bits), mask_bits }; XISetMask (mask.mask, XI_KeyPress); XISetMask (mask.mask, XI_KeyRelease); XISetMask (mask.mask, XI_ButtonPress); XISetMask (mask.mask, XI_ButtonRelease); XISetMask (mask.mask, XI_Enter); XISetMask (mask.mask, XI_Leave); XISetMask (mask.mask, XI_FocusIn); XISetMask (mask.mask, XI_FocusOut); XISetMask (mask.mask, XI_Motion); XIClearMask (mask.mask, XI_TouchBegin); XIClearMask (mask.mask, XI_TouchEnd); XIClearMask (mask.mask, XI_TouchUpdate); XISelectEvents (backend_xdisplay, xwin, &mask, 1); } } /* We use connect_after() here to accomodate code in GNOME Shell that, * when benchmarking drawing performance, connects to ::after-paint * and calls glFinish(). The timing information from that will be * more accurate if we hold off until that completes before we signal * apps to begin drawing the next frame. If there are no other * connections to ::after-paint, connect() vs. connect_after() doesn't * matter. */ g_signal_connect_after (CLUTTER_STAGE (compositor->stage), "after-paint", G_CALLBACK (after_stage_paint), compositor); clutter_stage_set_sync_delay (CLUTTER_STAGE (compositor->stage), META_SYNC_DELAY); compositor->window_group = meta_window_group_new (screen); compositor->top_window_group = meta_window_group_new (screen); clutter_actor_add_child (compositor->stage, compositor->window_group); clutter_actor_add_child (compositor->stage, compositor->top_window_group); if (meta_is_wayland_compositor ()) { /* NB: When running as a wayland compositor we don't need an X * composite overlay window, and we don't need to play any input * region tricks to redirect events into clutter. */ compositor->output = None; } else { compositor->output = screen->composite_overlay_window; XReparentWindow (xdisplay, xwin, compositor->output, 0, 0); meta_empty_stage_input_region (screen); /* Make sure there isn't any left-over output shape on the * overlay window by setting the whole screen to be an * output region. * * Note: there doesn't seem to be any real chance of that * because the X server will destroy the overlay window * when the last client using it exits. */ XFixesSetWindowShapeRegion (xdisplay, compositor->output, ShapeBounding, 0, 0, None); /* Map overlay window before redirecting windows offscreen so we catch their * contents until we show the stage. */ XMapWindow (xdisplay, compositor->output); } redirect_windows (display->screen); compositor->plugin_mgr = meta_plugin_manager_new (compositor); }