diff --git a/cde/programs/dtwm/WmCDInfo.c b/cde/programs/dtwm/WmCDInfo.c index dbe26d294..3027701f9 100644 --- a/cde/programs/dtwm/WmCDInfo.c +++ b/cde/programs/dtwm/WmCDInfo.c @@ -989,7 +989,8 @@ int IdentifyFramePart (ClientData *pCD, int x, int y) if (decor & MWM_DECOR_TITLE) { - if ( (x >= pCD->titleRectangle.x) && + if ( pCD->pTitleGadgets && + (x >= pCD->titleRectangle.x) && (x < (int)pCD->titleRectangle.x + (int)pCD->titleRectangle.width) && (y >= pCD->titleRectangle.y) && (y < (int)pCD->titleRectangle.y + (int)pCD->titleRectangle.height) ) @@ -1002,7 +1003,7 @@ int IdentifyFramePart (ClientData *pCD, int x, int y) /* try resize border */ - if (decor & MWM_DECOR_RESIZEH) + if (decor & MWM_DECOR_RESIZEH && pCD->pTitleGadgets) { rval = GadgetID(x, y, pCD->pResizeGadgets, STRETCH_COUNT); } diff --git a/cde/programs/dtwm/WmCDecor.c b/cde/programs/dtwm/WmCDecor.c index c8d6f3a79..8b731edf1 100644 --- a/cde/programs/dtwm/WmCDecor.c +++ b/cde/programs/dtwm/WmCDecor.c @@ -104,6 +104,91 @@ static Bevel_Count Bevels[] = + +/*************************************<->************************************* + * + * CreateTitleBarWindow (pcd) + * + * + * Description: + * ----------- + * Create title bar window. + * + * + * Inputs: + * ------ + * pcd - pointer to client data record + * + * Outputs: + * ------- + * pcd - modified + * + * + * Comments: + * -------- + * + *************************************<->***********************************/ + +static void CreateTitleBarWindow (ClientData *pcd) +{ + unsigned int wclass; /* window class */ + unsigned long attr_mask; + XSetWindowAttributes window_attribs; + + /* + * Create title bar window. If the title bar has its own appearance, + * or if there is no border around the client area, + * then we need to create an input/output window to draw in. Otherwise + * we can use an input-only window (to clip the corner resize windows). + */ + attr_mask = CWCursor; + window_attribs.cursor = wmGD.workspaceCursor; + + if (DECOUPLE_TITLE_APPEARANCE(pcd)) + { + /* title bar has a different appearance than rest of frame */ + wclass = InputOutput; + + /* need to handle exposure events */ + attr_mask |= CWEventMask; + window_attribs.event_mask = ExposureMask; + + /* + * Use background pixmap if one is specified, otherwise set the + * appropriate background color. + */ + + if (CLIENT_TITLE_APPEARANCE(pcd).backgroundPixmap) + { + attr_mask |= CWBackPixmap; + window_attribs.background_pixmap = + CLIENT_TITLE_APPEARANCE(pcd).backgroundPixmap; + } + else + { + attr_mask |= CWBackPixel; + window_attribs.background_pixel = + CLIENT_TITLE_APPEARANCE(pcd).background; + } + } + else + { + /* title bar has same appearance as rest of frame */ + wclass = InputOnly; + } + + pcd->clientTitleWin = XCreateWindow(DISPLAY, pcd->clientFrameWin, + (int) pcd->frameInfo.upperBorderWidth, + (int) pcd->frameInfo.upperBorderWidth, + pcd->frameInfo.width - + 2*pcd->frameInfo.upperBorderWidth, + pcd->frameInfo.titleBarHeight, + 0, + CopyFromParent,wclass,CopyFromParent, + attr_mask, &window_attribs); +} + + /*************************************<->************************************* * @@ -341,7 +426,6 @@ void BaseWinExposureProc (ClientData *pcd) Boolean ConstructFrame (ClientData *pcd) { unsigned long decoration = pcd->decor; - unsigned int wclass; /* window class */ unsigned long attr_mask; XSetWindowAttributes window_attribs; int frmX, frmY; @@ -414,60 +498,7 @@ Boolean ConstructFrame (ClientData *pcd) CreateStretcherWindows (pcd); } - /* - * Create title bar window. If the title bar has its own appearance, - * or if there is no border around the client area, - * then we need to create an input/output window to draw in. Otherwise - * we can use an input-only window (to clip the corner resize windows). - */ - if (decoration & MWM_DECOR_TITLE) { - - attr_mask = CWCursor; - window_attribs.cursor = wmGD.workspaceCursor; - - if (DECOUPLE_TITLE_APPEARANCE(pcd)) - { - /* title bar has a different appearance than rest of frame */ - wclass = InputOutput; - - /* need to handle exposure events */ - attr_mask |= CWEventMask; - window_attribs.event_mask = ExposureMask; - - /* - * Use background pixmap if one is specified, otherwise set the - * appropriate background color. - */ - - if (CLIENT_TITLE_APPEARANCE(pcd).backgroundPixmap) - { - attr_mask |= CWBackPixmap; - window_attribs.background_pixmap = - CLIENT_TITLE_APPEARANCE(pcd).backgroundPixmap; - } - else - { - attr_mask |= CWBackPixel; - window_attribs.background_pixel = - CLIENT_TITLE_APPEARANCE(pcd).background; - } - } - else - { - /* title bar has same appearance as rest of frame */ - wclass = InputOnly; - } - - pcd->clientTitleWin = XCreateWindow(DISPLAY, pcd->clientFrameWin, - (int) pcd->frameInfo.upperBorderWidth, - (int) pcd->frameInfo.upperBorderWidth, - pcd->frameInfo.width - - 2*pcd->frameInfo.upperBorderWidth, - pcd->frameInfo.titleBarHeight, - 0, - CopyFromParent,wclass,CopyFromParent, - attr_mask, &window_attribs); - } + if (decoration & MWM_DECOR_TITLE) CreateTitleBarWindow (pcd); /* generate gadget position search structure */ if (!AllocateGadgetRectangles (pcd)) @@ -1301,6 +1332,8 @@ void CreateStretcherWindows (ClientData *pcd) unsigned long attr_mask; for (iWin = 0; iWin < STRETCH_COUNT; iWin++) { + if (pcd->clientStretchWin[iWin]) continue; + switch (iWin) { case STRETCH_NORTH_WEST: GetFramePartInfo (pcd, FRAME_RESIZE_NW, @@ -2270,15 +2303,6 @@ void RegenerateClientFrame (ClientData *pcd) XMoveResizeWindow (DISPLAY, pcd->clientFrameWin, pcd->frameInfo.x, pcd->frameInfo.y, pcd->frameInfo.width, pcd->frameInfo.height); - - /* resize title bar window */ - if (decor & MWM_DECOR_TITLE) - { - XResizeWindow (DISPLAY, pcd->clientTitleWin, - pcd->frameInfo.width - 2*pcd->frameInfo.upperBorderWidth, - pcd->frameInfo.titleBarHeight); - } - /* resize base window */ XMoveResizeWindow (DISPLAY, pcd->clientBaseWin, BaseWindowX (pcd), BaseWindowY (pcd), @@ -2286,6 +2310,8 @@ void RegenerateClientFrame (ClientData *pcd) /* resize the stretcher windows */ if (SHOW_RESIZE_CURSORS(pcd) && (decor & MWM_DECOR_RESIZEH)) { + CreateStretcherWindows (pcd); + XMoveResizeWindow (DISPLAY, pcd->clientStretchWin[STRETCH_NORTH_WEST], 0, 0, pcd->frameInfo.cornerWidth, @@ -2334,7 +2360,17 @@ void RegenerateClientFrame (ClientData *pcd) pcd->frameInfo.height - 2*pcd->frameInfo.cornerHeight); } + /* resize title bar window */ + if (decor & MWM_DECOR_TITLE && !pcd->clientTitleWin) + { + CreateTitleBarWindow (pcd); + XResizeWindow (DISPLAY, pcd->clientTitleWin, + pcd->frameInfo.width - 2*pcd->frameInfo.upperBorderWidth, + pcd->frameInfo.titleBarHeight); + } + /* recreate gadget rectangles */ + AllocateGadgetRectangles (pcd); ComputeGadgetRectangles (pcd); /* regenerate the graphics */ @@ -2345,6 +2381,8 @@ void RegenerateClientFrame (ClientData *pcd) SetFrameShape (pcd); } + /* map all subwindows of client frame */ + XMapSubwindows(DISPLAY, pcd->clientFrameWin); } /* END OF FUNCTION RegenerateClientFrame */ diff --git a/cde/programs/dtwm/WmCEvent.c b/cde/programs/dtwm/WmCEvent.c index 9ce30f7ac..5b8d47fc6 100644 --- a/cde/programs/dtwm/WmCEvent.c +++ b/cde/programs/dtwm/WmCEvent.c @@ -611,8 +611,17 @@ Boolean HandleEventsOnSpecialWindows (XEvent *pEvent) case ClientMessage: { if (pCD = InitClientData (pEvent->xclient.window)) { - ProcessEwmh (pCD, (XClientMessageEvent *) pEvent); - dispatchEvent = False; + XClientMessageEvent *clientEvent = pEvent; + + if (clientEvent->message_type == + wmGD.xa__NET_WM_FULLSCREEN_MONITORS) + { + ProcessNetWmFullscreenMonitors (pCD, + clientEvent->data.l[0], clientEvent->data.l[1], + clientEvent->data.l[2], clientEvent->data.l[3]); + + dispatchEvent = False; + } } break; } @@ -840,7 +849,8 @@ void HandleCPropertyNotify (ClientData *pCD, XPropertyEvent *propertyEvent) ProcessColormapList (ACTIVE_PSD, pCD); } } - else if (propertyEvent->atom == wmGD.xa_MWM_HINTS) { + else if (propertyEvent->atom == wmGD.xa_MWM_HINTS) + { long suppliedReturn; XSizeHints hintsReturn = {0}; @@ -856,6 +866,14 @@ void HandleCPropertyNotify (ClientData *pCD, XPropertyEvent *propertyEvent) ProcessMwmHints (pCD); SetClientOffset (pCD); } + else if (propertyEvent->atom == wmGD.xa__NET_WM_NAME) + { + ProcessNetWmName (pCD); + } + else if (propertyEvent->atom == wmGD.xa__NET_WM_ICON_NAME) + { + ProcessNetWmIconName (pCD); + } break; } } @@ -2575,20 +2593,7 @@ void HandleClientMessage (ClientData *pCD, XClientMessageEvent *clientEvent) } else if (clientEvent->data.l[0] == NormalState) { - if (pCD->isFullscreen) - { - SetClientState (pCD, NORMAL_STATE, GetTimestamp ()); - newState = MAXIMIZED_STATE; - } - else - { - if (pCD->decorUpdated) - { - SetClientState (pCD, MAXIMIZED_STATE, GetTimestamp ()); - } - - newState = NORMAL_STATE; - } + newState = NORMAL_STATE; } if (!ClientInWorkspace (ACTIVE_WS, pCD)) { @@ -2598,9 +2603,16 @@ void HandleClientMessage (ClientData *pCD, XClientMessageEvent *clientEvent) SetClientState (pCD, newState, GetTimestamp ()); } - else + else if (clientEvent->message_type == wmGD.xa__NET_WM_FULLSCREEN_MONITORS) { - ProcessEwmh (pCD, clientEvent); + ProcessNetWmFullscreenMonitors (pCD, + clientEvent->data.l[0], clientEvent->data.l[1], + clientEvent->data.l[2], clientEvent->data.l[3]); + } + else if (clientEvent->message_type == wmGD.xa__NET_WM_STATE) + { + ProcessNetWmState (pCD, clientEvent->data.l[0], clientEvent->data.l[1], + clientEvent->data.l[2]); } } /* END OF FUNCTION HandleClientMessage */ diff --git a/cde/programs/dtwm/WmEwmh.c b/cde/programs/dtwm/WmEwmh.c index f77e8823b..12ef70255 100644 --- a/cde/programs/dtwm/WmEwmh.c +++ b/cde/programs/dtwm/WmEwmh.c @@ -25,50 +25,161 @@ #include -/* - * Included Files: - */ - #include "WmGlobal.h" +#include "WmEvent.h" #include "WmEwmh.h" - -/* - * include extern functions - */ - #include "WmMultiHead.h" #include "WmProperty.h" +#include "WmWinState.h" +#include "WmWrkspace.h" +static unsigned long GetWindowProperty (Window w, Atom property, Atom reqType, + unsigned char **propReturn) +{ + Atom actualType; + int actualFormat; + unsigned long nitems; + unsigned long leftover; - -/*************************************<->************************************* - * - * ProcessNetWmFullscreenMonitors (pCD, top, bottom, left, right) - * - * - * Description: - * ----------- - * This function retrieves the contents of the _NET_WM_FULLSCREEN_MONITORS - * message. - * - * - * - * Inputs: - * ------ - * pCD = pointer to client data - * top = the monitor whose top edge defines the top edge of the fullscreen - * window - * bottom = the monitor whose bottom edge defines the bottom edge of the - * fullscreen window - * left = the monitor whose left edge defines the left edge of the fullscreen - * window - * right = the monitor whose right edge defines the right edge of the - * fullscreen window - * - *************************************<->***********************************/ + if (XGetWindowProperty (DISPLAY, w, property, 0L, 1000000L, False, reqType, + &actualType, &actualFormat, &nitems, &leftover, + propReturn) != Success) goto err; -static void ProcessNetWmFullscreenMonitors (ClientData *pCD, - long top, long bottom, long left, long right) + if (actualType != reqType) goto err; + + return nitems; + +err: + XFree (*propReturn); + return 0; +} + +static void UpdateNetWmState (ClientData *pCD) +{ + unsigned long nitems; + unsigned long natoms = 0; + Atom *netWmState; + Atom *atoms; + + nitems = GetWindowProperty (pCD->client, wmGD.xa__NET_WM_STATE, XA_ATOM, + (unsigned char **) &netWmState); + + atoms = malloc ((nitems + 2) * sizeof (Atom)); if (!atoms) goto done; + + for (int i = 0; i < nitems; ++i) + if (netWmState[i] == wmGD.xa__NET_WM_STATE_FULLSCREEN || + netWmState[i] == wmGD.xa__NET_WM_STATE_MAXIMIZED_VERT || + netWmState[i] == wmGD.xa__NET_WM_STATE_MAXIMIZED_HORZ) + continue; + else + atoms[natoms++] = netWmState[i]; + + if (pCD->maxConfig) + { + if (pCD->isFullscreen) + { + atoms[natoms++] = wmGD.xa__NET_WM_STATE_FULLSCREEN; + } + else + { + atoms[natoms++] = wmGD.xa__NET_WM_STATE_MAXIMIZED_VERT; + atoms[natoms++] = wmGD.xa__NET_WM_STATE_MAXIMIZED_HORZ; + } + } + + XChangeProperty (DISPLAY, pCD->client, wmGD.xa__NET_WM_STATE, XA_ATOM, 32, + PropModeReplace, (unsigned char *) atoms, natoms); + +done: + XFree (netWmState); + XFree (atoms); +} + +static void ProcessNetWmStateFullscreen (ClientData *pCD, long action) +{ + switch (action) + { + case _NET_WM_STATE_REMOVE: + if (!pCD->isFullscreen) return; + pCD->isFullscreen = False; + break; + case _NET_WM_STATE_ADD: + if (pCD->isFullscreen) return; + pCD->isFullscreen = True; + break; + case _NET_WM_STATE_TOGGLE: + pCD->isFullscreen = !pCD->isFullscreen; + break; + default: + return; + } + + SetClientState (pCD, NORMAL_STATE, GetTimestamp ()); + + if (pCD->isFullscreen) + SetClientState (pCD, MAXIMIZED_STATE, GetTimestamp ()); +} + +static void ProcessNetWmStateMaximized (ClientData *pCD, long action) +{ + int newState; + + switch (action) + { + case _NET_WM_STATE_REMOVE: + if (pCD->clientState != MAXIMIZED_STATE) return; + newState = NORMAL_STATE; + break; + case _NET_WM_STATE_ADD: + if (pCD->clientState == MAXIMIZED_STATE) return; + newState = MAXIMIZED_STATE; + break; + case _NET_WM_STATE_TOGGLE: + newState = pCD->clientState == MAXIMIZED_STATE ? + NORMAL_STATE : MAXIMIZED_STATE; + break; + default: + return; + } + + SetClientState (pCD, newState, GetTimestamp ()); +} + +static void ProcessNetWmNameNetWmIconName (ClientData *pCD, Atom name) +{ + unsigned long nitems; + unsigned char *netNameProp; + XTextProperty nameProp = {0}; + + nitems = GetWindowProperty(pCD->client, name, wmGD.xa_UTF8_STRING, + &netNameProp); + + if (!nitems) goto done; + + if (Xutf8TextListToTextProperty (DISPLAY, (char **) &netNameProp, 1, + XUTF8StringStyle, &nameProp) != Success) goto done; + + if (name == wmGD.xa__NET_WM_NAME) + XSetWMName (DISPLAY, pCD->client, &nameProp); + else if (name == wmGD.xa__NET_WM_ICON_NAME) + XSetWMIconName (DISPLAY, pCD->client, &nameProp); + +done: + XFree (netNameProp); + XFree ((char*) nameProp.value); +} + +/** +* @brief Processes the _NET_WM_FULLSCREEN_MONITORS protocol. +* +* @param pCD +* @param top +* @param bottom +* @param left +* @param right +*/ +void ProcessNetWmFullscreenMonitors (ClientData *pCD, + long top, long bottom, long left, long right) { WmHeadInfo_t *pHeadInfo; @@ -105,171 +216,123 @@ static void ProcessNetWmFullscreenMonitors (ClientData *pCD, free(pHeadInfo); pCD->monitorSizeIsSet = True; -} /* END OF FUNCTION ProcessNetWmFullscreenMonitors */ +} - - -/*************************************<->************************************* - * - * ProcessNetWmStateFullscreen (pCD, en) - * - * - * Description: - * ----------- - * This function retrieves the contents of the _NET_WM_STATE_FULLSCREEN - * message. - * - * - * - * Inputs: - * ------ - * pCD = pointer to client data - * en = enable fullscreen - * - *************************************<->***********************************/ - -static void ProcessNetWmStateFullscreen (ClientData *pCD, Boolean en) +/** +* @brief Processes the _NET_WM_STATE client message. +* +* @param pCD +* @param action +* @param firstProperty +* @param secondProperty +*/ +void ProcessNetWmState (ClientData *pCD, long action, + long firstProperty, long secondProperty) { - PropMwmHints hints = {0}; - PropMwmHints *pHints = GetMwmHints (pCD); - XClientMessageEvent clientMsgEvent = { - .type = ClientMessage, - .window = pCD->client, - .message_type = wmGD.xa_WM_CHANGE_STATE, - .format = 32, - .data.l[0] = NormalState - }; + if (pCD->clientState & UNSEEN_STATE) return; - if (!pHints) pHints = &hints; + if (firstProperty == wmGD.xa__NET_WM_STATE_MAXIMIZED_VERT && + secondProperty == wmGD.xa__NET_WM_STATE_MAXIMIZED_HORZ || + firstProperty == wmGD.xa__NET_WM_STATE_MAXIMIZED_HORZ && + secondProperty == wmGD.xa__NET_WM_STATE_MAXIMIZED_VERT) + ProcessNetWmStateMaximized (pCD, action); + else if (firstProperty == wmGD.xa__NET_WM_STATE_FULLSCREEN || + secondProperty == wmGD.xa__NET_WM_STATE_FULLSCREEN) + ProcessNetWmStateFullscreen (pCD, action); - pHints->flags |= MWM_HINTS_DECORATIONS; - pHints->decorations = en ? WM_DECOR_NONE : WM_DECOR_DEFAULT; + if (!ClientInWorkspace (ACTIVE_WS, pCD)) + SetClientState (pCD, pCD->clientState | UNSEEN_STATE, GetTimestamp ()); - XChangeProperty (DISPLAY, pCD->client, wmGD.xa_MWM_HINTS, wmGD.xa_MWM_HINTS, - 32, PropModeReplace, (unsigned char *) pHints, - sizeof (PropMwmHints) / sizeof (long)); + UpdateNetWmState (pCD); +} - if (pHints != &hints) XFree (pHints); - - pCD->isFullscreen = en; - - XSendEvent (DISPLAY, ROOT_FOR_CLIENT (pCD), False, SubstructureRedirectMask, - (XEvent *) &clientMsgEvent); - - if (en) XChangeProperty (DISPLAY, pCD->client, wmGD.xa_NET_WM_STATE, - XA_ATOM, 32, PropModeReplace, - (unsigned char *) &wmGD.xa_NET_WM_STATE_FULLSCREEN, - 1); - else XDeleteProperty (DISPLAY, pCD->client, wmGD.xa_NET_WM_STATE); -} /* END OF FUNCTION ProcessNetWmStateFullscreen */ - - - -/*************************************<->************************************* - * - * ProcessEwmh (pCD, clientEvent) - * - * - * Description: - * ----------- - * This function retrieves the contents of the EWMH message. - * - * - * Inputs: - * ------ - * pCD = pointer to client data - * clientEvent = pointer to a client message event on the root window - * - *************************************<->***********************************/ - -void ProcessEwmh (ClientData *pCD, XClientMessageEvent *clientEvent) +/** +* @brief Processes the _NET_WM_NAME property. +* +* @param pCD +*/ +void ProcessNetWmName (ClientData *pCD) { - int i; + ProcessNetWmNameNetWmIconName (pCD, wmGD.xa__NET_WM_NAME); +} - if (clientEvent->message_type == wmGD.xa_NET_WM_FULLSCREEN_MONITORS) - { - ProcessNetWmFullscreenMonitors (pCD, - clientEvent->data.l[0], clientEvent->data.l[1], - clientEvent->data.l[2], clientEvent->data.l[3]); - } - else if (clientEvent->message_type == wmGD.xa_NET_WM_STATE) - { - for (i = 1; i < 3; ++i) - { - if (clientEvent->data.l[i] == wmGD.xa_NET_WM_STATE_FULLSCREEN) - { - ProcessNetWmStateFullscreen (pCD, clientEvent->data.l[0]); - } - } - } -} /* END OF FUNCTION ProcessEwmh */ - - - -/*************************************<->************************************* - * - * SetupWmEwmh () - * - * - * Description: - * ----------- - * This function sets up the window manager handling of the EWMH. - * - * - * Outputs: - * ------- - * (wmGD) = Atoms id's are setup. - * - *************************************<->***********************************/ +/** +* @brief Processes the _NET_WM_ICON_NAME property. +* +* @param pCD +*/ +void ProcessNetWmIconName (ClientData *pCD) +{ + ProcessNetWmNameNetWmIconName (pCD, wmGD.xa__NET_WM_ICON_NAME); +} +/** +* @brief Sets up the window manager handling of the EWMH. +*/ void SetupWmEwmh (void) { enum { - XA_NET_SUPPORTED, - XA_NET_WM_NAME, - XA_NET_SUPPORTING_WM_CHECK, - XA_NET_WM_FULLSCREEN_MONITORS, - XA_NET_WM_STATE, - XA_NET_WM_STATE_FULLSCREEN + XA_UTF8_STRING, + XA__NET_SUPPORTED, + XA__NET_SUPPORTING_WM_CHECK, + XA__NET_WM_NAME, + XA__NET_WM_ICON_NAME, + XA__NET_WM_FULLSCREEN_MONITORS, + XA__NET_WM_STATE, + XA__NET_WM_STATE_FULLSCREEN, + XA__NET_WM_STATE_MAXIMIZED_VERT, + XA__NET_WM_STATE_MAXIMIZED_HORZ }; static char *atom_names[] = { - _XA_NET_SUPPORTED, - _XA_NET_WM_NAME, - _XA_NET_SUPPORTING_WM_CHECK, - _XA_NET_WM_FULLSCREEN_MONITORS, - _XA_NET_WM_STATE, - _XA_NET_WM_STATE_FULLSCREEN + "UTF8_STRING", + _XA__NET_SUPPORTED, + _XA__NET_SUPPORTING_WM_CHECK, + _XA__NET_WM_NAME, + _XA__NET_WM_ICON_NAME, + _XA__NET_WM_FULLSCREEN_MONITORS, + _XA__NET_WM_STATE, + _XA__NET_WM_STATE_FULLSCREEN, + _XA__NET_WM_STATE_MAXIMIZED_VERT, + _XA__NET_WM_STATE_MAXIMIZED_HORZ }; - int scr; Window childWindow; Atom atoms[XtNumber(atom_names) + 1]; XInternAtoms(DISPLAY, atom_names, XtNumber(atom_names), False, atoms); - wmGD.xa_NET_WM_FULLSCREEN_MONITORS = atoms[XA_NET_WM_FULLSCREEN_MONITORS]; - wmGD.xa_NET_WM_STATE = atoms[XA_NET_WM_STATE]; - wmGD.xa_NET_WM_STATE_FULLSCREEN = atoms[XA_NET_WM_STATE_FULLSCREEN]; + wmGD.xa_UTF8_STRING = atoms[XA_UTF8_STRING]; + wmGD.xa__NET_WM_NAME = atoms[XA__NET_WM_NAME]; + wmGD.xa__NET_WM_ICON_NAME = atoms[XA__NET_WM_ICON_NAME]; + wmGD.xa__NET_WM_FULLSCREEN_MONITORS = atoms[XA__NET_WM_FULLSCREEN_MONITORS]; + wmGD.xa__NET_WM_STATE = atoms[XA__NET_WM_STATE]; + wmGD.xa__NET_WM_STATE_FULLSCREEN = atoms[XA__NET_WM_STATE_FULLSCREEN]; + wmGD.xa__NET_WM_STATE_MAXIMIZED_VERT = + atoms[XA__NET_WM_STATE_MAXIMIZED_VERT]; + wmGD.xa__NET_WM_STATE_MAXIMIZED_HORZ = + atoms[XA__NET_WM_STATE_MAXIMIZED_HORZ]; - for (scr = 0; scr < wmGD.numScreens; scr++) + for (int scr = 0; scr < wmGD.numScreens; ++scr) { childWindow = XCreateSimpleWindow(DISPLAY, wmGD.Screens[scr].rootWindow, -1, -1, 1, 1, 0, 0, 0); - XChangeProperty(DISPLAY, childWindow, atoms[XA_NET_WM_NAME], None, 32, - PropModeReplace, "DTWM", 5); + XChangeProperty(DISPLAY, childWindow, atoms[XA__NET_WM_NAME], + atoms[XA_UTF8_STRING], 8, PropModeReplace, + DT_WM_RESOURCE_NAME, 5); XChangeProperty(DISPLAY, childWindow, - atoms[XA_NET_SUPPORTING_WM_CHECK], XA_WINDOW, 32, + atoms[XA__NET_SUPPORTING_WM_CHECK], XA_WINDOW, 32, PropModeReplace, (unsigned char *)&childWindow, 1); XChangeProperty(DISPLAY, wmGD.Screens[scr].rootWindow, - atoms[XA_NET_SUPPORTING_WM_CHECK], XA_WINDOW, 32, + atoms[XA__NET_SUPPORTING_WM_CHECK], XA_WINDOW, 32, PropModeReplace, (unsigned char *)&childWindow, 1); XChangeProperty(DISPLAY, wmGD.Screens[scr].rootWindow, - atoms[XA_NET_SUPPORTED], XA_ATOM, 32, PropModeReplace, - (unsigned char *)&atoms[XA_NET_SUPPORTING_WM_CHECK], 4); + atoms[XA__NET_SUPPORTED], XA_ATOM, 32, PropModeReplace, + (unsigned char *)&atoms[XA__NET_SUPPORTING_WM_CHECK], + 8); } -} /* END OF FUNCTION SetupWmEwmh */ +} diff --git a/cde/programs/dtwm/WmEwmh.h b/cde/programs/dtwm/WmEwmh.h index 5dd7d9480..804b2aef2 100644 --- a/cde/programs/dtwm/WmEwmh.h +++ b/cde/programs/dtwm/WmEwmh.h @@ -26,18 +26,26 @@ #ifndef _Dt_WmEwmh_h_ #define _Dt_WmEwmh_h_ -#define _NET_WM_STATE_REMOVE 0 -#define _NET_WM_STATE_ADD 1 -#define _NET_WM_STATE_TOGGLE 2 +#define _NET_WM_STATE_REMOVE 0 +#define _NET_WM_STATE_ADD 1 +#define _NET_WM_STATE_TOGGLE 2 -#define _XA_NET_SUPPORTED "_NET_SUPPORTED" -#define _XA_NET_WM_NAME "_NET_WM_NAME" -#define _XA_NET_SUPPORTING_WM_CHECK "_NET_SUPPORTING_WM_CHECK" -#define _XA_NET_WM_FULLSCREEN_MONITORS "_NET_WM_FULLSCREEN_MONITORS" -#define _XA_NET_WM_STATE "_NET_WM_STATE" -#define _XA_NET_WM_STATE_FULLSCREEN "_NET_WM_STATE_FULLSCREEN" +#define _XA__NET_SUPPORTED "_NET_SUPPORTED" +#define _XA__NET_SUPPORTING_WM_CHECK "_NET_SUPPORTING_WM_CHECK" +#define _XA__NET_WM_NAME "_NET_WM_NAME" +#define _XA__NET_WM_ICON_NAME "_NET_WM_ICON_NAME" +#define _XA__NET_WM_FULLSCREEN_MONITORS "_NET_WM_FULLSCREEN_MONITORS" +#define _XA__NET_WM_STATE "_NET_WM_STATE" +#define _XA__NET_WM_STATE_FULLSCREEN "_NET_WM_STATE_FULLSCREEN" +#define _XA__NET_WM_STATE_MAXIMIZED_VERT "_NET_WM_STATE_MAXIMIZED_VERT" +#define _XA__NET_WM_STATE_MAXIMIZED_HORZ "_NET_WM_STATE_MAXIMIZED_HORZ" -void ProcessEwmh (ClientData *pCD, XClientMessageEvent *clientEvent); +void ProcessNetWmFullscreenMonitors (ClientData *pCD, + long top, long bottom, long left, long right); +void ProcessNetWmState (ClientData *pCD, long action, + long firstProperty, long secondProperty); +void ProcessNetWmName (ClientData *pCD); +void ProcessNetWmIconName (ClientData *pCD); void SetupWmEwmh (void); #endif /* _Dt_WmEwmh_h_ */ diff --git a/cde/programs/dtwm/WmGlobal.h b/cde/programs/dtwm/WmGlobal.h index 891c4fb2e..3d06f4b3f 100644 --- a/cde/programs/dtwm/WmGlobal.h +++ b/cde/programs/dtwm/WmGlobal.h @@ -1628,7 +1628,6 @@ typedef struct _ClientData Window clientBaseWin; /* for matte & reparenting */ int xBorderWidth; /* original X border width */ FrameInfo frameInfo; /* frame geometry data */ - Boolean decorUpdated; /* True => decoration updated */ Boolean isFullscreen; /* True => fullscreen */ Boolean monitorSizeIsSet; /* True => X, Y, W, H is set */ int monitorX; /* monitor X loc */ @@ -1935,9 +1934,14 @@ typedef struct _WmGlobalData Atom xa_SM_CLIENT_ID; Atom xa_WMSAVE_HINT; - Atom xa_NET_WM_FULLSCREEN_MONITORS; - Atom xa_NET_WM_STATE; - Atom xa_NET_WM_STATE_FULLSCREEN; + Atom xa_UTF8_STRING; + Atom xa__NET_WM_NAME; + Atom xa__NET_WM_ICON_NAME; + Atom xa__NET_WM_FULLSCREEN_MONITORS; + Atom xa__NET_WM_STATE; + Atom xa__NET_WM_STATE_FULLSCREEN; + Atom xa__NET_WM_STATE_MAXIMIZED_VERT; + Atom xa__NET_WM_STATE_MAXIMIZED_HORZ; /* atoms used for workspace management: */ diff --git a/cde/programs/dtwm/WmManage.c b/cde/programs/dtwm/WmManage.c index a2347f5c3..60aab5657 100644 --- a/cde/programs/dtwm/WmManage.c +++ b/cde/programs/dtwm/WmManage.c @@ -1008,6 +1008,7 @@ void WithdrawWindow (ClientData *pCD) } } + XDeleteProperty (DISPLAY, pCD->client, wmGD.xa__NET_WM_STATE); XUnmapWindow (DISPLAY, pCD->client); XReparentWindow (DISPLAY, pCD->client, ROOT_FOR_CLIENT(pCD), x, y); diff --git a/cde/programs/dtwm/WmWinConf.c b/cde/programs/dtwm/WmWinConf.c index 397a7c785..c3dd6aa81 100644 --- a/cde/programs/dtwm/WmWinConf.c +++ b/cde/programs/dtwm/WmWinConf.c @@ -1934,12 +1934,6 @@ void ProcessNewConfiguration (ClientData *pCD, int x, int y, unsigned int width, newMax = True; } - if (pCD->decorUpdated) - { - changedValues = CWWidth | CWHeight; - pCD->decorUpdated = False; - } - /* * If the configuration has changed, update client data * diff --git a/cde/programs/dtwm/WmWinInfo.c b/cde/programs/dtwm/WmWinInfo.c index f1dc6d185..cfde984bd 100644 --- a/cde/programs/dtwm/WmWinInfo.c +++ b/cde/programs/dtwm/WmWinInfo.c @@ -56,6 +56,7 @@ #include "WmCDecor.h" #include "WmCPlace.h" #include "WmError.h" +#include "WmEwmh.h" #include "WmIDecor.h" #include "WmIPlace.h" #include "WmIconBox.h" @@ -113,6 +114,7 @@ WmWorkspaceData *pIconBoxInitialWS; ClientData * InitClientData (Window clientWindow) { + int i; ClientData *pCD; if (!XFindContext (DISPLAY, clientWindow, wmGD.windowContextType, @@ -217,10 +219,11 @@ InitClientData (Window clientWindow) pCD->smClientID = (String)NULL; - pCD->decorUpdated = False; pCD->isFullscreen = False; pCD->monitorSizeIsSet = False; + for (i = 0; i < STRETCH_COUNT; ++i) pCD->clientStretchWin[i] = (Window)0L; + return (pCD); } /* END OF FUNCTION InitClientData */ @@ -417,6 +420,7 @@ GetClientInfo (WmScreenData *pSD, Window clientWindow, long manageFlags) */ ProcessWmWindowTitle (pCD, TRUE); + ProcessNetWmName (pCD); /* @@ -424,6 +428,7 @@ GetClientInfo (WmScreenData *pSD, Window clientWindow, long manageFlags) */ ProcessWmIconTitle (pCD, TRUE); + ProcessNetWmIconName (pCD); /* @@ -3853,7 +3858,11 @@ ProcessMwmHints (ClientData *pCD) { if (pHints->flags & MWM_HINTS_FUNCTIONS) { - if (pHints->functions == WM_FUNC_DEFAULT) + if (pHints->functions == WM_FUNC_NONE) + { + pCD->clientFunctions = WM_FUNC_NONE; + } + else if (pHints->functions == WM_FUNC_DEFAULT) { pCD->clientFunctions = WM_FUNC_ALL; } @@ -3865,7 +3874,7 @@ ProcessMwmHints (ClientData *pCD) else { /* client indicating applicable functions */ - pCD->clientFunctions &= pHints->functions; + pCD->clientFunctions |= pHints->functions; } #if 0 if (!(pCD->clientFlags & GOT_DT_WM_HINTS) && @@ -3886,7 +3895,11 @@ ProcessMwmHints (ClientData *pCD) if (pHints->flags & MWM_HINTS_DECORATIONS) { - if (pHints->decorations == WM_DECOR_DEFAULT) + if (pHints->decorations == WM_DECOR_NONE) + { + pCD->clientDecoration = WM_DECOR_NONE; + } + else if (pHints->decorations == WM_DECOR_DEFAULT) { pCD->clientDecoration = WM_DECOR_ALL; } @@ -3898,7 +3911,7 @@ ProcessMwmHints (ClientData *pCD) else { /* client indicating decorations to be added */ - pCD->clientDecoration &= pHints->decorations; + pCD->clientDecoration |= pHints->decorations; } /* @@ -3999,6 +4012,5 @@ ProcessMwmHints (ClientData *pCD) pCD->decor = pCD->clientDecoration; /* !!! combine decor ... !!! */ - pCD->decorUpdated = True; } /* END OF ProcessMwmHints */ diff --git a/cde/programs/dtwm/WmWinState.c b/cde/programs/dtwm/WmWinState.c index 22ab205c0..b70ca7ff9 100644 --- a/cde/programs/dtwm/WmWinState.c +++ b/cde/programs/dtwm/WmWinState.c @@ -181,7 +181,6 @@ void SetClientStateWithEventMask (ClientData *pCD, int newState, Time setTime, u * WM_STATE property is set in WithdrawWindow. */ - XDeleteProperty (DISPLAY, pCD->client, wmGD.xa_NET_WM_STATE); UnManageWindow (pCD); break; } @@ -605,9 +604,7 @@ static void SetupWindowStateWithEventMask (ClientData *pCD, int newState, void ConfigureNewState (ClientData *pcd) { - WmHeadInfo_t *WmHI = NULL; - - if (pcd->maxConfig) + if (pcd->maxConfig && !pcd->isFullscreen) { pcd->maxConfig = FALSE; RegenerateClientFrame(pcd); @@ -617,6 +614,16 @@ void ConfigureNewState (ClientData *pcd) } else { + long decor; + WmHeadInfo_t *WmHI; + + if (pcd->isFullscreen) + { + decor = pcd->decor; + pcd->decor = WM_DECOR_NONE; + SetClientOffset (pcd); + } + if (pcd->isFullscreen && pcd->monitorSizeIsSet) { pcd->maxX = pcd->monitorX; @@ -646,7 +653,14 @@ void ConfigureNewState (ClientData *pcd) (unsigned int) pcd->maxHeight); pcd->maxConfig = TRUE; RegenerateClientFrame(pcd); + + if (pcd->isFullscreen) + { + pcd->decor = decor; + SetClientOffset (pcd); + } } + SendConfigureNotify (pcd); /*