void SetClientWMState (ClientData *pCD, int wmState, int mwmState) { ClientData *pNext; #ifdef WSM Boolean bToUnseen; bToUnseen = (mwmState & UNSEEN_STATE) != 0; mwmState &= ~UNSEEN_STATE; #endif /* WSM */ #ifdef WSM SetClientWsIndex (pCD); #endif /* WSM */ pNext = pCD->transientChildren; while (pNext) { if (pNext->transientChildren) { SetClientWMState (pNext, wmState, mwmState); } #ifdef WSM SetClientWsIndex (pNext); #endif /* WSM */ SetWMState (pNext->client, wmState, ICON_FRAME_WIN(pNext)); if (pNext->maxConfig && mwmState == NORMAL_STATE) { pNext->clientState = MAXIMIZED_STATE; } #ifdef WSM else if (!pNext->maxConfig && mwmState == MAXIMIZED_STATE) { pNext->clientState = NORMAL_STATE; } #endif /* WSM */ else { pNext->clientState = mwmState; } #ifdef WSM if (bToUnseen) pNext->clientState |= UNSEEN_STATE; #endif /* WSM */ pNext = pNext->transientSiblings; } SetWMState (pCD->client, wmState, ICON_FRAME_WIN(pCD)); pCD->clientState = mwmState; #ifdef WSM if (bToUnseen) pCD->clientState |= UNSEEN_STATE; #endif /* WSM */ } /* END OF FUNCTION SetClientWMState */
bool X11Helper::SetWMFullscreenMonitors( const DisplaySpec &target ) { int num_screens = 0; XineramaScreenInfo *screens = XineramaQueryScreens( Dpy, &num_screens ); if (screens == nullptr) { return false; } XineramaScreenInfo *end = screens + num_screens; Rage::RectI monitors{}; bool found_bounds = false; if (target.isVirtual()) { auto topmost = std::min_element( screens, end, []( XineramaScreenInfo &a, XineramaScreenInfo &b ) { return a.y_org < b.y_org; } ); monitors.top = topmost->screen_number; auto bottommost = std::max_element( screens, end, []( XineramaScreenInfo &a, XineramaScreenInfo &b ) { return a.y_org < b.y_org; } ); monitors.bottom = bottommost->screen_number; auto leftmost = std::min_element( screens, end, []( XineramaScreenInfo &a, XineramaScreenInfo &b ) { return a.x_org < b.x_org; } ); monitors.left = leftmost->screen_number; auto rightmost = std::max_element( screens, end, []( XineramaScreenInfo &a, XineramaScreenInfo &b ) { return a.x_org < b.x_org; } ); monitors.right = rightmost->screen_number; found_bounds = true; } else if (target.currentMode() != nullptr) { auto mon = std::find_if( screens, end, [&]( XineramaScreenInfo &screen ) { return screen.x_org == target.currentBounds().left && screen.y_org == target.currentBounds().top && screen.width == target.currentMode()->width && screen.height == target.currentMode()->height; } ); if (mon != end) { monitors.left = monitors.right = monitors.top = monitors.bottom = mon->screen_number; found_bounds = true; } } XFree( screens ); XWindowAttributes attr = {0}; if (!found_bounds || !XGetWindowAttributes( Dpy, Win, &attr )) { return false; } SetWMState( attr.root, Win, 1, XInternAtom( Dpy, "_NET_WM_STATE_FULLSCREEN", False )); XClientMessageEvent xclient = {0}; xclient.type = ClientMessage; xclient.window = Win; xclient.message_type = XInternAtom( Dpy, "_NET_WM_FULLSCREEN_MONITORS", False ); xclient.format = 32; xclient.data.l[0] = monitors.top; xclient.data.l[1] = monitors.bottom; xclient.data.l[2] = monitors.left; xclient.data.l[3] = monitors.right; xclient.data.l[4] = 1; XSendEvent( Dpy, attr.root, False, SubstructureRedirectMask | SubstructureNotifyMask, reinterpret_cast<XEvent *> (&xclient)); XFlush( Dpy ); return true; }