Split X11 event dispatching into a function
This commit is contained in:
parent
f51a05b2dc
commit
bd9590506a
1 changed files with 143 additions and 139 deletions
|
@ -2962,11 +2962,151 @@ void check_new_wayland_res( void )
|
|||
}
|
||||
}
|
||||
|
||||
static void
|
||||
dispatch_x11( Display *dpy, MouseCursor *cursor, bool *vblank )
|
||||
{
|
||||
do {
|
||||
XEvent ev;
|
||||
XNextEvent (dpy, &ev);
|
||||
if ((ev.type & 0x7f) != KeymapNotify)
|
||||
discard_ignore (dpy, ev.xany.serial);
|
||||
if (debugEvents)
|
||||
{
|
||||
gpuvis_trace_printf ("event %d", ev.type);
|
||||
printf ("event %d\n", ev.type);
|
||||
}
|
||||
switch (ev.type) {
|
||||
case CreateNotify:
|
||||
if (ev.xcreatewindow.parent == root)
|
||||
add_win (dpy, ev.xcreatewindow.window, 0, ev.xcreatewindow.serial);
|
||||
break;
|
||||
case ConfigureNotify:
|
||||
configure_win (dpy, &ev.xconfigure);
|
||||
break;
|
||||
case DestroyNotify:
|
||||
{
|
||||
win * w = find_win(dpy, ev.xdestroywindow.window);
|
||||
|
||||
if (w && w->id == ev.xdestroywindow.window)
|
||||
destroy_win (dpy, ev.xdestroywindow.window, True, True);
|
||||
break;
|
||||
}
|
||||
case MapNotify:
|
||||
{
|
||||
win * w = find_win(dpy, ev.xmap.window);
|
||||
|
||||
if (w && w->id == ev.xmap.window)
|
||||
map_win (dpy, ev.xmap.window, ev.xmap.serial);
|
||||
break;
|
||||
}
|
||||
case UnmapNotify:
|
||||
{
|
||||
win * w = find_win(dpy, ev.xunmap.window);
|
||||
|
||||
if (w && w->id == ev.xunmap.window)
|
||||
unmap_win (dpy, ev.xunmap.window, True);
|
||||
break;
|
||||
}
|
||||
case ReparentNotify:
|
||||
if (ev.xreparent.parent == root)
|
||||
add_win (dpy, ev.xreparent.window, 0, ev.xreparent.serial);
|
||||
else
|
||||
{
|
||||
win * w = find_win(dpy, ev.xreparent.window);
|
||||
|
||||
if (w && w->id == ev.xreparent.window)
|
||||
{
|
||||
destroy_win (dpy, ev.xreparent.window, False, True);
|
||||
}
|
||||
else
|
||||
{
|
||||
// If something got reparented _to_ a toplevel window,
|
||||
// go check for the fullscreen workaround again.
|
||||
w = find_win(dpy, ev.xreparent.parent);
|
||||
if (w)
|
||||
{
|
||||
get_size_hints(dpy, w);
|
||||
focusDirty = True;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
case CirculateNotify:
|
||||
circulate_win(dpy, &ev.xcirculate);
|
||||
break;
|
||||
case MapRequest:
|
||||
map_request(dpy, &ev.xmaprequest);
|
||||
break;
|
||||
case ConfigureRequest:
|
||||
configure_request(dpy, &ev.xconfigurerequest);
|
||||
break;
|
||||
case CirculateRequest:
|
||||
circulate_request(dpy, &ev.xcirculaterequest);
|
||||
break;
|
||||
case Expose:
|
||||
break;
|
||||
case PropertyNotify:
|
||||
handle_property_notify(dpy, &ev.xproperty);
|
||||
break;
|
||||
case ClientMessage:
|
||||
handle_client_message(dpy, &ev.xclient);
|
||||
|
||||
if ( ev.xclient.data.l[0] == 24 && ev.xclient.data.l[1] == 8 )
|
||||
{
|
||||
// Decode the split up vblanktime... Sign-extend nonsense...
|
||||
uint64_t vblanktime = (uint64_t(uint32_t(ev.xclient.data.l[2])) << 32) |
|
||||
uint64_t(uint32_t(ev.xclient.data.l[3]));
|
||||
uint64_t vblankreceived = get_time_in_nanos();
|
||||
uint64_t diff = vblankreceived - vblanktime;
|
||||
|
||||
// give it 1 ms of slack.. maybe too long
|
||||
if ( diff > 1'000'000ul )
|
||||
{
|
||||
gpuvis_trace_printf( "ignored stale vblank" );
|
||||
}
|
||||
else
|
||||
{
|
||||
gpuvis_trace_printf( "got vblank" );
|
||||
*vblank = true;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case LeaveNotify:
|
||||
if (ev.xcrossing.window == currentInputFocusWindow)
|
||||
{
|
||||
// This shouldn't happen due to our pointer barriers,
|
||||
// but there is a known X server bug; warp to last good
|
||||
// position.
|
||||
cursor->resetPosition();
|
||||
}
|
||||
break;
|
||||
case MotionNotify:
|
||||
{
|
||||
win * w = find_win(dpy, ev.xmotion.window);
|
||||
if (w && w->id == currentInputFocusWindow)
|
||||
{
|
||||
cursor->move(ev.xmotion.x, ev.xmotion.y);
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
if (ev.type == damage_event + XDamageNotify)
|
||||
{
|
||||
damage_win (dpy, (XDamageNotifyEvent *) &ev);
|
||||
}
|
||||
else if (ev.type == xfixes_event + XFixesCursorNotify)
|
||||
{
|
||||
cursor->setDirty();
|
||||
}
|
||||
break;
|
||||
}
|
||||
} while (QLength (dpy));
|
||||
}
|
||||
|
||||
void
|
||||
steamcompmgr_main (int argc, char **argv)
|
||||
{
|
||||
Display *dpy;
|
||||
XEvent ev;
|
||||
Window root_return, parent_return;
|
||||
Window *children;
|
||||
unsigned int nchildren;
|
||||
|
@ -3309,147 +3449,11 @@ steamcompmgr_main (int argc, char **argv)
|
|||
break;
|
||||
}
|
||||
|
||||
if ( !( x11_pollfd.revents & POLLIN ) )
|
||||
if ( x11_pollfd.revents & POLLIN )
|
||||
{
|
||||
continue;
|
||||
dispatch_x11( dpy, cursor.get(), &vblank );
|
||||
}
|
||||
|
||||
do {
|
||||
XNextEvent (dpy, &ev);
|
||||
if ((ev.type & 0x7f) != KeymapNotify)
|
||||
discard_ignore (dpy, ev.xany.serial);
|
||||
if (debugEvents)
|
||||
{
|
||||
gpuvis_trace_printf ("event %d", ev.type);
|
||||
printf ("event %d\n", ev.type);
|
||||
}
|
||||
switch (ev.type) {
|
||||
case CreateNotify:
|
||||
if (ev.xcreatewindow.parent == root)
|
||||
add_win (dpy, ev.xcreatewindow.window, 0, ev.xcreatewindow.serial);
|
||||
break;
|
||||
case ConfigureNotify:
|
||||
configure_win (dpy, &ev.xconfigure);
|
||||
break;
|
||||
case DestroyNotify:
|
||||
{
|
||||
win * w = find_win(dpy, ev.xdestroywindow.window);
|
||||
|
||||
if (w && w->id == ev.xdestroywindow.window)
|
||||
destroy_win (dpy, ev.xdestroywindow.window, True, True);
|
||||
break;
|
||||
}
|
||||
case MapNotify:
|
||||
{
|
||||
win * w = find_win(dpy, ev.xmap.window);
|
||||
|
||||
if (w && w->id == ev.xmap.window)
|
||||
map_win (dpy, ev.xmap.window, ev.xmap.serial);
|
||||
break;
|
||||
}
|
||||
case UnmapNotify:
|
||||
{
|
||||
win * w = find_win(dpy, ev.xunmap.window);
|
||||
|
||||
if (w && w->id == ev.xunmap.window)
|
||||
unmap_win (dpy, ev.xunmap.window, True);
|
||||
break;
|
||||
}
|
||||
case ReparentNotify:
|
||||
if (ev.xreparent.parent == root)
|
||||
add_win (dpy, ev.xreparent.window, 0, ev.xreparent.serial);
|
||||
else
|
||||
{
|
||||
win * w = find_win(dpy, ev.xreparent.window);
|
||||
|
||||
if (w && w->id == ev.xreparent.window)
|
||||
{
|
||||
destroy_win (dpy, ev.xreparent.window, False, True);
|
||||
}
|
||||
else
|
||||
{
|
||||
// If something got reparented _to_ a toplevel window,
|
||||
// go check for the fullscreen workaround again.
|
||||
w = find_win(dpy, ev.xreparent.parent);
|
||||
if (w)
|
||||
{
|
||||
get_size_hints(dpy, w);
|
||||
focusDirty = True;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
case CirculateNotify:
|
||||
circulate_win(dpy, &ev.xcirculate);
|
||||
break;
|
||||
case MapRequest:
|
||||
map_request(dpy, &ev.xmaprequest);
|
||||
break;
|
||||
case ConfigureRequest:
|
||||
configure_request(dpy, &ev.xconfigurerequest);
|
||||
break;
|
||||
case CirculateRequest:
|
||||
circulate_request(dpy, &ev.xcirculaterequest);
|
||||
break;
|
||||
case Expose:
|
||||
break;
|
||||
case PropertyNotify:
|
||||
handle_property_notify(dpy, &ev.xproperty);
|
||||
break;
|
||||
case ClientMessage:
|
||||
handle_client_message(dpy, &ev.xclient);
|
||||
|
||||
if ( ev.xclient.data.l[0] == 24 && ev.xclient.data.l[1] == 8 )
|
||||
{
|
||||
// Decode the split up vblanktime... Sign-extend nonsense...
|
||||
uint64_t vblanktime = (uint64_t(uint32_t(ev.xclient.data.l[2])) << 32) |
|
||||
uint64_t(uint32_t(ev.xclient.data.l[3]));
|
||||
uint64_t vblankreceived = get_time_in_nanos();
|
||||
uint64_t diff = vblankreceived - vblanktime;
|
||||
|
||||
// give it 1 ms of slack.. maybe too long
|
||||
if ( diff > 1'000'000ul )
|
||||
{
|
||||
gpuvis_trace_printf( "ignored stale vblank" );
|
||||
}
|
||||
else
|
||||
{
|
||||
gpuvis_trace_printf( "got vblank" );
|
||||
vblank = true;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case LeaveNotify:
|
||||
if (ev.xcrossing.window == currentInputFocusWindow)
|
||||
{
|
||||
// This shouldn't happen due to our pointer barriers,
|
||||
// but there is a known X server bug; warp to last good
|
||||
// position.
|
||||
cursor->resetPosition();
|
||||
}
|
||||
break;
|
||||
case MotionNotify:
|
||||
{
|
||||
win * w = find_win(dpy, ev.xmotion.window);
|
||||
if (w && w->id == currentInputFocusWindow)
|
||||
{
|
||||
cursor->move(ev.xmotion.x, ev.xmotion.y);
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
if (ev.type == damage_event + XDamageNotify)
|
||||
{
|
||||
damage_win (dpy, (XDamageNotifyEvent *) &ev);
|
||||
}
|
||||
else if (ev.type == xfixes_event + XFixesCursorNotify)
|
||||
{
|
||||
cursor->setDirty();
|
||||
}
|
||||
break;
|
||||
}
|
||||
} while (QLength (dpy));
|
||||
|
||||
if ( run == false )
|
||||
{
|
||||
break;
|
||||
|
|
Loading…
Reference in a new issue