Add GNU LGPL headers to all .c .C and .h files
[oweals/cde.git] / cde / programs / dtwm / examples / wsinfo / wsinfo.c
1 /*
2  * CDE - Common Desktop Environment
3  *
4  * Copyright (c) 1993-2012, The Open Group. All rights reserved.
5  *
6  * These libraries and programs are free software; you can
7  * redistribute them and/or modify them under the terms of the GNU
8  * Lesser General Public License as published by the Free Software
9  * Foundation; either version 2 of the License, or (at your option)
10  * any later version.
11  *
12  * These libraries and programs are distributed in the hope that
13  * they will be useful, but WITHOUT ANY WARRANTY; without even the
14  * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15  * PURPOSE. See the GNU Lesser General Public License for more
16  * details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with these librararies and programs; if not, write
20  * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
21  * Floor, Boston, MA 02110-1301 USA
22  */
23 /* $XConsortium: wsinfo.c /main/3 1996/11/05 12:17:59 mustafa $ */
24 /***********************************************************************
25  *  CDE Developer's Conference Sample Program
26  *
27  *  File: wsinfo.c
28  *
29  *  Purpose:
30  *      Demonstrate the CDE Workspace API. This file uses:
31  *
32  *          DtWsmGetWorkspaceInfo
33  *          DtWsmFreeWorkspaceInfo
34  *          DtWsmGetCurrentWorkspace
35  *          DtWsmAddCurrentWorkspaceCallback 
36  *          DtWsmOccupyAllWorkspaces 
37  *
38  *  (c) Copyright 1993, 1994 Hewlett-Packard Company    
39  *  (c) Copyright 1993, 1994 International Business Machines Corp.
40  *  (c) Copyright 1993, 1994 Sun Microsystems, Inc.
41  *  (c) Copyright 1993, 1994 Unix System Labs, Inc., a subsidiary of
42  *      Novell, Inc.
43  ***********************************************************************/
44
45 /*  
46  * include files  
47  */
48
49 #include <stdio.h>
50 #include <X11/Intrinsic.h>
51 #include <Xm/Xm.h>
52 #include <Xm/AtomMgr.h>
53 #include <Xm/Form.h>
54 #include <Xm/PushB.h>
55 #include <Xm/Label.h>
56
57 #include <Dt/Wsm.h>
58
59
60 /*  
61  * functions defined in this program  
62  */
63 void main();
64 void quitCB(); 
65 void updateCB(); 
66 void ShowCurrentWorkspaceInfo ();
67 DtWsmWsChangeProc wschangecb();
68 void InstallXErrorHandler();
69
70 /*  
71  * global variables  
72  */
73 Widget  toplevel; /*  Shell widget      */
74 Widget wChildren [20];
75
76 /* 
77  * button assignments 
78  */
79 #define QUIT_BUTTON     (wChildren[0])
80 #define UPDATE_BUTTON   (wChildren[1])
81 #define SEPARATOR       (wChildren[2])
82 #define WS_LABEL        (wChildren[3])
83 #define WS_VALUE        (wChildren[4])
84 #define TITLE_LABEL     (wChildren[5])
85 #define TITLE_VALUE     (wChildren[6])
86 #define BACKDROP_LABEL  (wChildren[7])
87 #define BACKDROP_VALUE  (wChildren[8])
88 #define COLORSET_LABEL  (wChildren[9])
89 #define COLORSET_VALUE  (wChildren[10])
90 #define SEPARATOR2      (wChildren[11])
91 #define NUM_CHILDREN    12
92
93 /*-------------------------------------------------------------
94  *      main - main logic for program
95  */
96 void main (argc,argv)
97 int argc;
98 char **argv;
99 {
100     Widget      form;
101     Widget  top;
102     XtAppContext app_context;
103     Arg args[10];
104     register int n;
105     register int i;
106     XmString xms, xmsBlank;
107
108     /*  
109      * initialize toolkit  
110      */
111     n = 0;
112     XtSetArg (args[n], XmNallowShellResize, True);  n++;
113     toplevel = XtAppInitialize (&app_context, "XMDemos", NULL, 0, 
114             &argc, argv, NULL, args, n);
115
116     /* 
117      * Set up X error handling
118      */
119     InstallXErrorHandler ();
120
121     /*  
122      * manager widget 
123      */
124     n = 0;
125     form = XmCreateForm (toplevel, "form", args, n);
126     XtManageChild (form);
127
128     /*  
129      * create compound string for blank labels
130      */
131     xmsBlank = XmStringCreateLocalized("   ");
132
133     /*******************************************
134      * QUIT BUTTON
135      ******************************************/
136
137     /*  
138      * create compound string for the button text  
139      */
140     xms = XmStringCreateLocalized("Quit");
141
142     /*  
143      * set up arglist  
144      */
145     n = 0;
146     XtSetArg (args[n], XmNlabelType, XmSTRING);  n++;
147     XtSetArg (args[n], XmNlabelString, xms);  n++;
148     XtSetArg (args[n], XmNleftAttachment, XmATTACH_FORM); n++;
149     XtSetArg (args[n], XmNtopAttachment, XmATTACH_FORM); n++;
150     /*  
151      * create button  
152      */
153     top = QUIT_BUTTON = XtCreateWidget ("button", xmPushButtonWidgetClass,
154           form, args, n);
155     XmStringFree (xms);
156
157     /*  
158      * add callback  
159      */
160     XtAddCallback (QUIT_BUTTON, XmNactivateCallback, quitCB, NULL);
161
162     /*******************************************
163      * UPDATE WORKSPACE INFO BUTTON
164      ******************************************/
165
166     /*  
167      * create compound string for the button text  
168      */
169     xms = XmStringCreateLocalized("Get workspace info");
170
171     /*  
172      * set up arglist  
173      */
174     n = 0;
175     XtSetArg (args[n], XmNlabelType, XmSTRING);  n++;
176     XtSetArg (args[n], XmNlabelString, xms);  n++;
177     XtSetArg (args[n], XmNleftAttachment, XmATTACH_FORM); n++;
178     XtSetArg (args[n], XmNtopAttachment, XmATTACH_WIDGET); n++;
179     XtSetArg (args[n], XmNtopWidget, top); n++;
180     /*  
181      * create button  
182      */
183     top = UPDATE_BUTTON = XtCreateWidget ("button", xmPushButtonWidgetClass,
184           form, args, n);
185     XmStringFree (xms);
186
187     /*  
188      * add callback  
189      */
190     XtAddCallback (UPDATE_BUTTON, XmNactivateCallback, updateCB, NULL);
191
192     /*******************************************
193      * SEPARATOR
194      ******************************************/
195
196     /*  
197      * set up arglist  
198      */
199     n = 0;
200     XtSetArg (args[n], XmNleftAttachment, XmATTACH_FORM); n++;
201     XtSetArg (args[n], XmNrightAttachment, XmATTACH_FORM); n++;
202     XtSetArg (args[n], XmNtopAttachment, XmATTACH_WIDGET); n++;
203     XtSetArg (args[n], XmNtopWidget, top); n++;
204     /*  
205      * create separator  
206      */
207     top = SEPARATOR = (Widget) 
208             XmCreateSeparatorGadget (form, "separator", args, n);
209
210     /*******************************************
211      * LABEL FOR CURRENT WORKSPACE
212      ******************************************/
213
214     /*
215      * NOTE: We assume this is the longest label and lay out the
216      *       other fields based on this assumption.
217      */
218
219     /*  
220      * create compound string for the label text  
221      */
222     xms = XmStringCreateLocalized("Current workspace: ");
223
224     /*  
225      * set up arglist  
226      */
227     n = 0;
228     XtSetArg (args[n], XmNlabelType, XmSTRING);  n++;
229     XtSetArg (args[n], XmNlabelString, xms);  n++;
230     XtSetArg (args[n], XmNleftAttachment, XmATTACH_FORM); n++;
231     XtSetArg (args[n], XmNtopAttachment, XmATTACH_WIDGET); n++;
232     XtSetArg (args[n], XmNtopWidget, top); n++;
233     /*  
234      * create label  
235      */
236     WS_LABEL = XtCreateWidget ("label", xmLabelWidgetClass,
237           form, args, n);
238     XmStringFree (xms);
239
240     /*******************************************
241      * VALUE FOR CURRENT WORKSPACE
242      ******************************************/
243
244     /*  
245      * set up arglist  
246      */
247     n = 0;
248     XtSetArg (args[n], XmNlabelType, XmSTRING);  n++;
249     XtSetArg (args[n], XmNlabelString, xmsBlank);  n++;
250     XtSetArg (args[n], XmNleftAttachment, XmATTACH_WIDGET); n++;
251     XtSetArg (args[n], XmNleftWidget, WS_LABEL); n++;
252     XtSetArg (args[n], XmNtopAttachment, XmATTACH_WIDGET); n++;
253     XtSetArg (args[n], XmNtopWidget, top); n++;
254     /*  
255      * create value
256      */
257     top = WS_VALUE = XtCreateWidget ("label", xmLabelWidgetClass,
258           form, args, n);
259
260     /*******************************************
261      * LABEL FOR WORKSPACE TITLE
262      ******************************************/
263
264     /*  
265      * create compound string for the label text  
266      */
267     xms = XmStringCreateLocalized("    title: ");
268
269     /*  
270      * set up arglist  
271      */
272     n = 0;
273     XtSetArg (args[n], XmNlabelType, XmSTRING);  n++;
274     XtSetArg (args[n], XmNlabelString, xms);  n++;
275     XtSetArg (args[n], XmNrightAttachment, XmATTACH_OPPOSITE_WIDGET); n++;
276     XtSetArg (args[n], XmNrightWidget, WS_LABEL); n++;
277     XtSetArg (args[n], XmNtopAttachment, XmATTACH_WIDGET); n++;
278     XtSetArg (args[n], XmNtopWidget, top); n++;
279     /*  
280      * create label  
281      */
282     TITLE_LABEL = XtCreateWidget ("label", xmLabelWidgetClass,
283           form, args, n);
284     XmStringFree (xms);
285
286     /*******************************************
287      * VALUE FOR WORKSPACE TITLE
288      ******************************************/
289
290     /*  
291      * set up arglist  
292      */
293     n = 0;
294     XtSetArg (args[n], XmNlabelType, XmSTRING);  n++;
295     XtSetArg (args[n], XmNlabelString, xmsBlank);  n++;
296     XtSetArg (args[n], XmNleftAttachment, XmATTACH_WIDGET); n++;
297     XtSetArg (args[n], XmNleftWidget, TITLE_LABEL); n++;
298     XtSetArg (args[n], XmNtopAttachment, XmATTACH_WIDGET); n++;
299     XtSetArg (args[n], XmNtopWidget, top); n++;
300     /*  
301      * create value
302      */
303     top = TITLE_VALUE = XtCreateWidget ("label", xmLabelWidgetClass,
304           form, args, n);
305
306     /*******************************************
307      * LABEL FOR WORKSPACE BACKDROP
308      ******************************************/
309
310     /*  
311      * create compound string for the label text  
312      */
313     xms = XmStringCreateLocalized("    backdrop: ");
314
315     /*  
316      * set up arglist  
317      */
318     n = 0;
319     XtSetArg (args[n], XmNlabelType, XmSTRING);  n++;
320     XtSetArg (args[n], XmNlabelString, xms);  n++;
321     XtSetArg (args[n], XmNrightAttachment, XmATTACH_OPPOSITE_WIDGET); n++;
322     XtSetArg (args[n], XmNrightWidget, WS_LABEL); n++;
323     XtSetArg (args[n], XmNtopAttachment, XmATTACH_WIDGET); n++;
324     XtSetArg (args[n], XmNtopWidget, top); n++;
325     /*  
326      * create label  
327      */
328     BACKDROP_LABEL = XtCreateWidget ("label", xmLabelWidgetClass,
329           form, args, n);
330     XmStringFree (xms);
331
332     /*******************************************
333      * VALUE FOR WORKSPACE BACKDROP
334      ******************************************/
335
336     /*  
337      * set up arglist  
338      */
339     n = 0;
340     XtSetArg (args[n], XmNlabelType, XmSTRING);  n++;
341     XtSetArg (args[n], XmNlabelString, xmsBlank);  n++;
342     XtSetArg (args[n], XmNleftAttachment, XmATTACH_WIDGET); n++;
343     XtSetArg (args[n], XmNleftWidget, BACKDROP_LABEL); n++;
344     XtSetArg (args[n], XmNtopAttachment, XmATTACH_WIDGET); n++;
345     XtSetArg (args[n], XmNtopWidget, top); n++;
346     /*  
347      * create value
348      */
349     top = BACKDROP_VALUE = XtCreateWidget ("label", xmLabelWidgetClass,
350           form, args, n);
351
352     /*******************************************
353      * LABEL FOR WORKSPACE COLORSET ID
354      ******************************************/
355
356     /*  
357      * create compound string for the label text  
358      */
359     xms = XmStringCreateLocalized("    color set id: ");
360
361     /*  
362      * set up arglist  
363      */
364     n = 0;
365     XtSetArg (args[n], XmNlabelType, XmSTRING);  n++;
366     XtSetArg (args[n], XmNlabelString, xms);  n++;
367     XtSetArg (args[n], XmNrightAttachment, XmATTACH_OPPOSITE_WIDGET); n++;
368     XtSetArg (args[n], XmNrightWidget, WS_LABEL); n++;
369     XtSetArg (args[n], XmNtopAttachment, XmATTACH_WIDGET); n++;
370     XtSetArg (args[n], XmNtopWidget, top); n++;
371     /*  
372      * create label  
373      */
374     COLORSET_LABEL = XtCreateWidget ("label", xmLabelWidgetClass,
375           form, args, n);
376     XmStringFree (xms);
377
378     /*******************************************
379      * VALUE FOR WORKSPACE COLORSET ID
380      ******************************************/
381
382     /*  
383      * set up arglist  
384      */
385     n = 0;
386     XtSetArg (args[n], XmNlabelType, XmSTRING);  n++;
387     XtSetArg (args[n], XmNlabelString, xmsBlank);  n++;
388     XtSetArg (args[n], XmNleftAttachment, XmATTACH_WIDGET); n++;
389     XtSetArg (args[n], XmNleftWidget, COLORSET_LABEL); n++;
390     XtSetArg (args[n], XmNtopAttachment, XmATTACH_WIDGET); n++;
391     XtSetArg (args[n], XmNtopWidget, top); n++;
392     /*  
393      * create value
394      */
395     top = COLORSET_VALUE = XtCreateWidget ("label", xmLabelWidgetClass,
396           form, args, n);
397
398     /*******************************************
399      * SEPARATOR
400      ******************************************/
401
402     /*  
403      * set up arglist  
404      */
405     n = 0;
406     XtSetArg (args[n], XmNleftAttachment, XmATTACH_FORM); n++;
407     XtSetArg (args[n], XmNrightAttachment, XmATTACH_FORM); n++;
408     XtSetArg (args[n], XmNtopAttachment, XmATTACH_WIDGET); n++;
409     XtSetArg (args[n], XmNtopWidget, top); n++;
410     /*  
411      * create separator  
412      */
413     top = SEPARATOR2 = (Widget) 
414             XmCreateSeparatorGadget (form, "separator", args, n);
415
416     /*  
417      * manage children
418      */
419     XtManageChildren (wChildren, NUM_CHILDREN);
420
421     /* 
422      * Show info on current workspace
423      */
424     ShowCurrentWorkspaceInfo ();
425
426     /*  
427      * realize widgets  
428      */
429     XtRealizeWidget (toplevel);
430
431     /*
432      * Do these calls after the shell is realized.  
433      * They need a window created for the top level shell.
434      *
435      * HINT: See XtSetMappedWhenManaged(1) if you want to 
436      *       realize a widget to get a window, but need to
437      *       control when the map of the window occurs.
438      */
439     (void) DtWsmAddCurrentWorkspaceCallback (toplevel,
440                 (DtWsmWsChangeProc) wschangecb, NULL);
441
442     DtWsmOccupyAllWorkspaces (XtDisplay(toplevel), XtWindow(toplevel));
443
444     /*  
445      * process events  
446      */
447     XtAppMainLoop (app_context);
448 }
449
450
451 /*-------------------------------------------------------------
452  *      Update the information for the current workspace
453  */
454 void ShowCurrentWorkspaceInfo ()
455 {
456     Arg args[10]; /*  arg list          */
457     register int n;     /*  arg count           */
458     Atom aWs;
459     int rval;
460     Display *dpy;
461     Window root;
462     DtWsmWorkspaceInfo *pWsInfo;
463     XmString xms;
464     char pch[512];
465     char *pchName;
466
467     dpy = XtDisplay(toplevel);
468     root = XDefaultRootWindow(dpy);
469
470     rval = DtWsmGetCurrentWorkspace(dpy, root, &aWs);
471
472     if (rval == Success)
473     {
474         rval = DtWsmGetWorkspaceInfo (dpy, root, aWs, &pWsInfo);
475
476         if (rval == Success)
477         {
478             /* workspace name */
479             pchName = XmGetAtomName (dpy, pWsInfo->workspace);
480             xms = XmStringCreateLocalized(pchName);
481
482             n = 0;
483             XtSetArg (args[n], XmNlabelString, xms);  n++;
484             XtSetValues (WS_VALUE, args, n);
485
486             XmStringFree (xms);
487             XtFree (pchName);
488
489             /* workspace title */
490             xms = XmStringCreateLocalized(pWsInfo->pchTitle);
491
492             n = 0;
493             XtSetArg (args[n], XmNlabelString, xms);  n++;
494             XtSetValues (TITLE_VALUE, args, n);
495
496             XmStringFree (xms);
497
498             /* workspace backdrop name */
499             if (pWsInfo->backdropName != None)
500                 pchName = XmGetAtomName (dpy, pWsInfo->backdropName);
501             else
502                 pchName = "<failed to load!>";
503             xms = XmStringCreateLocalized(pchName);
504
505             n = 0;
506             XtSetArg (args[n], XmNlabelString, xms);  n++;
507             XtSetValues (BACKDROP_VALUE, args, n);
508
509             XmStringFree (xms);
510             if (pWsInfo->backdropName != None)
511                 XtFree (pchName);
512
513             /* workspace colorset id */
514             sprintf (pch, "%d", pWsInfo->colorSetId);
515             xms = XmStringCreateLocalized(pch);
516
517             n = 0;
518             XtSetArg (args[n], XmNlabelString, xms);  n++;
519             XtSetValues (COLORSET_VALUE, args, n);
520
521             XmStringFree (xms);
522
523             DtWsmFreeWorkspaceInfo (pWsInfo);
524         }
525     }
526
527     if (rval != Success)
528     {
529         fprintf (stderr, "Failed to get workspace information.\n");
530         fprintf (stderr, "Is dtwm running?\n");
531         exit (1);
532     }
533 }
534
535 /*-------------------------------------------------------------
536  *      quitCB - callback for button
537  */
538 void quitCB (w, client_data, call_data) 
539 Widget  w;              /*  widget id           */
540 caddr_t client_data;    /*  data from application   */
541 caddr_t call_data;      /*  data from widget class  */
542 {
543     exit (0);
544 }
545
546
547 /*-------------------------------------------------------------
548  *      updateCB - callback for show current workspace info
549  */
550 void updateCB (w, client_data, call_data) 
551 Widget  w;              /*  widget id           */
552 caddr_t client_data;    /*  data from application   */
553 caddr_t call_data;      /*  data from widget class  */
554 {
555
556     ShowCurrentWorkspaceInfo ();
557
558 }
559
560 /*-------------------------------------------------------------
561 **      wschangecb - callback for workspace switch
562 */
563 DtWsmWsChangeProc
564 wschangecb (w, atom, client_data)
565 Widget  w;
566 Atom    atom;
567 XtPointer client_data;
568 {
569     ShowCurrentWorkspaceInfo ();
570 }
571
572
573
574 /*-------------------------------------------------------------
575 **      data for X error handler
576 */
577 #define E_MAJOR_CODE            0
578 #define E_MINOR_CODE            1
579 #define E_RESOURCE_ID           2
580 #define E_ERROR_SERIAL          3
581 #define E_CURRENT_SERIAL        4
582
583 #define NUM_E_STRINGS           5
584
585 static char *pchErrorFormatNames [NUM_E_STRINGS] = {
586     "MajorCode",
587     "MinorCode",
588     "ResourceID",
589     "ErrorSerial",
590     "CurrentSerial"
591 };
592
593 static char *pchErrorFormat [NUM_E_STRINGS];
594
595
596 /*-------------------------------------------------------------
597 **      HandleXErrors - catch X protocol errors
598 */
599 static int
600 _HandleXErrors (display, errorEvent)
601 Display  *display;
602 XErrorEvent *errorEvent;
603 {
604     char buffer[BUFSIZ];
605     char message[BUFSIZ];
606
607     XGetErrorText (display, errorEvent->error_code, buffer, BUFSIZ);
608     fprintf (stderr, "\n*** X error occurred ***\n");
609     fprintf (stderr, "Description = '%s'\n  ", buffer);
610
611     fprintf (stderr, pchErrorFormat[E_MAJOR_CODE], errorEvent->request_code);
612     sprintf(message, "%d", errorEvent->request_code);
613     XGetErrorDatabaseText (display, "XRequest", message, " ", buffer, BUFSIZ);
614     fprintf (stderr, " (%s)\n  ", buffer);
615     fprintf (stderr, pchErrorFormat[E_MINOR_CODE], errorEvent->minor_code);
616     fprintf (stderr, "\n  ");
617     fprintf (stderr, pchErrorFormat[E_RESOURCE_ID], errorEvent->resourceid);
618     fprintf (stderr, "\n  ");
619     fprintf (stderr, pchErrorFormat[E_ERROR_SERIAL], errorEvent->serial);
620     fprintf (stderr, "\n  ");
621     fprintf (stderr, pchErrorFormat[E_CURRENT_SERIAL],
622                         LastKnownRequestProcessed(display));
623     fprintf (stderr, "\n");
624
625     return (0);
626 }
627
628 /*-------------------------------------------------------------
629 **      Setup the X error handler
630 */
631 void
632 InstallXErrorHandler ( display )
633 Display *display;
634 {
635     char buffer[BUFSIZ];
636     int i;
637
638     /*
639      * Fetch the X error format strings from XErrorDB
640      */
641     for (i = 0; i< NUM_E_STRINGS; i++)
642     {
643         XGetErrorDatabaseText (display, "XlibMessage",
644                     pchErrorFormatNames[i], " %d ", buffer, BUFSIZ);
645
646         pchErrorFormat[i] = (char *) XtMalloc (1+strlen(buffer));
647
648         strcpy(pchErrorFormat[i], buffer);
649     }
650
651     XSetErrorHandler (_HandleXErrors);
652 }