123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333 |
- /*
- * CDE - Common Desktop Environment
- *
- * (c) Copyright 1993-2012 The Open Group
- * (c) Copyright 2012-2022 CDE Project contributors, see
- * CONTRIBUTORS for details
- *
- * These libraries and programs are free software; you can
- * redistribute them and/or modify them under the terms of the GNU
- * Lesser General Public License as published by the Free Software
- * Foundation; either version 2 of the License, or (at your option)
- * any later version.
- *
- * These libraries and programs are distributed in the hope that
- * they will be useful, but WITHOUT ANY WARRANTY; without even the
- * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
- * PURPOSE. See the GNU Lesser General Public License for more
- * details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with these libraries and programs; if not, write
- * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
- * Floor, Boston, MA 02110-1301 USA
- */
- #include <Xm/DialogS.h>
- #include <Xm/Form.h>
- #include <Xm/Text.h>
- #include <Xm/TextF.h>
- #include <Dt/DialogBox.h>
- #include <Dt/SharedProcs.h>
- #include "WmGlobal.h"
- #include "WmCDecor.h"
- #include "WmError.h"
- #include "WmHelp.h"
- #include "WmIDecor.h"
- #include "WmInstantTitle.h"
- #include "WmPanelP.h"
- #include "WmProperty.h"
- #include "WmWinList.h"
- #include "WmWrkspace.h"
- extern XtPointer _XmStringUngenerate(XmString, XmStringTag,
- XmTextType, XmTextType);
- static void InstantTitleGetTitle(PtrInstantTitleData pITD) {
- String value;
- Widget textFieldW = pITD->textFieldW;
- ClientData *pCD = pITD->pCDforClient;
- XmString title = pITD->contextForClient == F_CONTEXT_ICON ?
- ICON_DISPLAY_TITLE(pCD) : CLIENT_DISPLAY_TITLE(pCD);
- if (!title) return;
- value = _XmStringUngenerate(title, NULL, XmCHARSET_TEXT, XmCHARSET_TEXT);
- if (!value) return;
- XtVaSetValues(textFieldW, XmNvalue, value, NULL);
- XtFree(value);
- XtVaSetValues(textFieldW, XmNcursorPosition,
- XmTextFieldGetLastPosition(textFieldW), NULL);
- }
- static void InstantTitleSetTitle(PtrInstantTitleData pITD) {
- char *str = XmTextFieldGetString(pITD->textFieldW);
- ClientData *pCD = pITD->pCDforClient;
- Context context = pITD->contextForClient;
- XmString *title = &pCD->instantTitle;
- Window client = pCD->client;
- Atom name = wmGD.xa__NET_WM_VISIBLE_NAME;
- Atom iconName = wmGD.xa__NET_WM_VISIBLE_ICON_NAME;
- if (*title) XmStringFree(*title);
- _DtStripSpaces(str);
- if (str[0]) {
- *title = XmStringCreateLocalized(str);
- SetUtf8String (DISPLAY, client, name, str);
- SetUtf8String (DISPLAY, client, iconName, str);
- }
- else {
- *title = NULL;
- XDeleteProperty(DISPLAY, client, name);
- XDeleteProperty(DISPLAY, client, iconName);
- }
- XtFree(str);
- if (context == F_CONTEXT_ICON || pCD->pSD->useIconBox)
- RedisplayIconTitle(pCD);
- if (context != F_CONTEXT_ICON) DrawWindowTitle(pCD, True);
- }
- /**
- * @brief Hides the instant title dialog.
- *
- * @param pClientData
- */
- void InstantTitleHideDialog(ClientData *pClientData) {
- PtrInstantTitleData pITD = &pClientData->pSD->instantTitleData;
- if (pITD->widgetsInitialized && pITD->pCDforClient == pClientData)
- XtUnmanageChild(pITD->dialogBoxW);
- }
- static void InstantTitleButtonCB(Widget w, XtPointer client_data,
- XtPointer call_data)
- {
- PtrInstantTitleData pITD = client_data;
- DtDialogBoxCallbackStruct *cb = call_data;
- switch (cb->button_position) {
- case 1:
- InstantTitleSetTitle(pITD);
- case 2:
- InstantTitleHideDialog(pITD->pCDforClient);
- break;
- case 3:
- XtCallCallbacks(pITD->dialogBoxW, XmNhelpCallback, NULL);
- break;
- default:
- break;
- }
- }
- static void InstantTitleWorkspaceModifyCB(Widget w, Atom atom_name, int type,
- XtPointer client_data)
- {
- PtrInstantTitleData pITD = client_data;
- ClientData *pCD = pITD->pCDforClient;
- if (type == DtWSM_REASON_CURRENT &&
- pITD->contextForClient == F_CONTEXT_ICON &&
- XtIsManaged(pITD->dialogBoxW) && ClientInWorkspace(ACTIVE_WS, pCD))
- InstantTitleShowDialog(pCD);
- }
- static Boolean InstantTitleMakeDialog(PtrInstantTitleData pITD) {
- Cardinal n;
- Arg args[10];
- XmString buttonStrings[3];
- Widget dialogShellW, dialogBoxW, formW, cancelW, textFieldW;
- Boolean *widgetsInitialized = &pITD->widgetsInitialized;
- if (*widgetsInitialized) return True;
- n = 0;
- XtSetArg(args[n], XmNallowShellResize, True); ++n;
- XtSetArg(args[n], XmNmwmFunctions,
- MWM_FUNC_ALL | MWM_FUNC_MINIMIZE | MWM_FUNC_MAXIMIZE); ++n;
- dialogShellW = pITD->dialogShellW = XtCreatePopupShell(
- "instantTitleDialogShell", xmDialogShellWidgetClass,
- pITD->pCDforClient->pSD->screenTopLevelW1, args, n);
- if (!dialogShellW) goto err;
- if (!DtWsmAddWorkspaceModifiedCallback(dialogShellW,
- InstantTitleWorkspaceModifyCB, pITD)) goto err;
- buttonStrings[0] = XmStringCreateLocalized((char *)_DtOkString);
- buttonStrings[1] = XmStringCreateLocalized((char *)_DtCancelString);
- buttonStrings[2] = XmStringCreateLocalized((char *)_DtHelpString);
- n = 0;
- XtSetArg(args[n], XmNallowOverlap, False); ++n;
- XtSetArg(args[n], XmNdefaultPosition, False); ++n;
- XtSetArg(args[n], XmNbuttonCount, 3); ++n;
- XtSetArg(args[n], XmNbuttonLabelStrings, buttonStrings); ++n;
- dialogBoxW = pITD->dialogBoxW = _DtCreateDialogBox(dialogShellW,
- "instantTitleDialogBox", args, n);
- XmStringFree(buttonStrings[0]);
- XmStringFree(buttonStrings[1]);
- XmStringFree(buttonStrings[2]);
- if (!dialogBoxW) goto err;
- XtAddCallback(dialogBoxW, XmNcallback, InstantTitleButtonCB, pITD);
- XtAddCallback(dialogBoxW, XmNhelpCallback, WmDtWmTopicHelpCB,
- WM_DT_WINDOWRENAME_TOPIC);
- cancelW = _DtDialogBoxGetButton(dialogBoxW, 2);
- if (!cancelW) goto err;
- n = 0;
- XtSetArg(args[n], XmNautoUnmanage, False); ++n;
- XtSetArg(args[n], XmNcancelButton, cancelW); ++n;
- XtSetValues (dialogBoxW, args, n);
- formW = pITD->formW = XmCreateForm(dialogBoxW, "instantTitleForm", NULL, 0);
- if (!formW) goto err;
- n = 0;
- XtSetArg(args[n], XmNtopAttachment, XmATTACH_POSITION); ++n;
- XtSetArg(args[n], XmNleftAttachment, XmATTACH_FORM); ++n;
- XtSetArg(args[n], XmNrightAttachment, XmATTACH_FORM); ++n;
- XtSetArg(args[n], XmNbottomAttachment, XmATTACH_NONE); ++n;
- XtSetArg(args[n], XmNmaxLength, FILENAME_MAX); ++n;
- textFieldW = pITD->textFieldW = XmCreateTextField(formW,
- "instantTitleTextField", args, n);
- if (!textFieldW) goto err;
- XtManageChild(dialogShellW);
- XtManageChild(dialogBoxW);
- XtManageChild(formW);
- XtManageChild(cancelW);
- XtManageChild(textFieldW);
- DtWsmRemoveWorkspaceFunctions(DISPLAY1, XtWindow(dialogShellW));
- *widgetsInitialized = True;
- return True;
- err:
- if (dialogShellW) {
- XtDestroyWidget(dialogShellW);
- *widgetsInitialized = False;
- }
- Warning(GETMESSAGE(88, 1, "1 Unable to create instant title dialog."));
- return False;
- }
- static void InstantTitleSetPosition(PtrInstantTitleData pITD) {
- int x, y;
- Dimension height;
- Cardinal n;
- Arg args[10];
- XFontStruct *font;
- Window windowGroup;
- Widget dialogShellW = pITD->dialogShellW;
- Context context = pITD->contextForClient;
- ClientData *pCD = pITD->pCDforClient;
- WmScreenData *pSD = pCD->pSD;
- XtVaGetValues(dialogShellW, XmNheight, &height, NULL);
- if (wmGD.positionIsFrame) {
- if (pSD->decoupleTitleAppearance)
- font = pSD->clientTitleAppearance.font;
- else
- font = pSD->clientAppearance.font;
- height += TEXT_HEIGHT(font) + (2 * pSD->frameBorderWidth);
- }
- GetSystemMenuPosition(pCD, &x, &y, height, context);
- if (context == F_CONTEXT_ICON) {
- if (pSD->useIconBox && P_ICON_BOX(pCD))
- windowGroup = P_ICON_BOX(pCD)->pCD_iconBox->client;
- else
- windowGroup = XtUnspecifiedWindowGroup;
- }
- else {
- windowGroup = pCD->client;
- }
- n = 0;
- XtSetArg(args[n], XmNx, x); ++n;
- XtSetArg(args[n], XmNy, y); ++n;
- XtSetArg(args[n], XmNtransientFor, NULL); ++n;
- XtSetArg(args[n], XmNwindowGroup, windowGroup); ++n;
- XtSetValues(dialogShellW, args, n);
- }
- /**
- * @brief Shows the instant title dialog.
- *
- * @param pClientData
- * @param context
- */
- void InstantTitleShowDialog(ClientData *pClientData) {
- Widget dialogBoxW, textFieldW;
- Context context;
- ClientData *pCD = pClientData->transientLeader ?
- FindTransientTreeLeader(pClientData) : pClientData;
- WmScreenData *pSD = pCD->pSD;
- PtrInstantTitleData pITD = &pSD->instantTitleData;
- switch (pCD->clientState) {
- case MINIMIZED_STATE:
- context = F_CONTEXT_ICON;
- break;
- case NORMAL_STATE:
- case MAXIMIZED_STATE:
- context = F_CONTEXT_WINDOW;
- break;
- default:
- return;
- }
- pITD->pCDforClient = pCD;
- pITD->contextForClient = context;
- if (!InstantTitleMakeDialog(pITD)) return;
- InstantTitleGetTitle(pITD);
- InstantTitleSetPosition(pITD);
- dialogBoxW = pITD->dialogBoxW;
- XtUnmanageChild(dialogBoxW);
- XtManageChild(dialogBoxW);
- textFieldW = pITD->textFieldW;
- XmProcessTraversal(textFieldW, XmTRAVERSE_CURRENT);
- XmTextSetSelection(textFieldW, 0, XmTextGetLastPosition(textFieldW),
- CurrentTime);
- }
|