1 /* GNOME Window Manager Compliance support for amiwm
2    by Peter Bortas february 2000 */
3 
4 #include <stdio.h>
5 #include <X11/Xlib.h>
6 #include <X11/Xproto.h>
7 #include <X11/Xatom.h>
8 
9 #include <X11/Xutil.h>
10 
11 
gnome_setup()12 extern void gnome_setup()
13 {
14   /* Section 1 - Detection of a GNOME compliant Window Manager
15 
16      There is a single unambiguous way to detect if there currently is
17      a GNOME compliant Window Manager running. It is the job of the
18      Window Manager to set up a few things to make this
19      possible. Using the following method it is also possible for
20      applications to detect compliance by receiving an event when the
21      Window Manager exits.
22 
23      To do this the Window Manager should create a Window, that is a
24      child of the root window. There is no need to map it, just create
25      it. The Window Manager may reuse ANY window it has for this
26      purpose - even if it is mapped, just as long as the window is
27      never destroyed while the Window Manager is running.
28 
29      Once the Window is created the Window Manager should set a
30      property on the root window of the name _WIN_SUPPORTING_WM_CHECK,
31      and type CARDINAL. The atom's data would be a CARDINAL that is
32      the Window ID of the window that was created above. The window
33      that was created would ALSO have this property set on it with the
34      same values and type.*/
35 
36   Display            *disp;
37   Window              root_window;
38   Atom                atom_set;
39   CARD32              val;
40   Window              win;
41 
42   Atom                list[10];
43 
44   atom_set = XInternAtom(disp, "_WIN_SUPPORTING_WM_CHECK", False);
45   win = XCreateSimpleWindow(disp, root_window, -200, -200, 5, 5, 0, 0, 0);
46   val = win;
47   XChangeProperty(disp, root_window, atom_set, XA_CARDINAL, 32,
48 		  PropModeReplace, (unsigned char *)&val, 1);
49   XChangeProperty(disp, win, atom_set, XA_CARDINAL, 32, PropModeReplace,
50 		  (unsigned char *)&val, 1);
51 
52   /* Section 2 - Listing GNOME Window Manager Compliance
53 
54      It is important to list which parts of GNOME Window Manager
55      compliance are supported. This is done fairly easily by doing the
56      following:
57 
58      Create a property on the root window of the atom name
59      _WIN_PROTOCOLS. This property contains a list(array)of atoms that
60      are all the properties the Window Manager supports. These atoms
61      are any number of the following:
62 
63      _WIN_LAYER
64      _WIN_STATE
65      _WIN_HINTS
66      _WIN_APP_STATE
67      _WIN_EXPANDED_SIZE
68      _WIN_ICONS
69      _WIN_WORKSPACE
70      _WIN_WORKSPACE_COUNT
71      _WIN_WORKSPACE_NAMES
72      _WIN_CLIENT_LIST
73 
74      If you list one of these properties then you support it and
75      applications can expect information provided by, or accepted by
76      the Window Manager to work. */
77 
78   atom_set = XInternAtom(disp, "_WIN_PROTOCOLS", False);
79   list[0] = XInternAtom(disp, "_WIN_LAYER", False);
80   list[1] = XInternAtom(disp, "_WIN_STATE", False);
81   list[2] = XInternAtom(disp, "_WIN_HINTS", False);
82   list[3] = XInternAtom(disp, "_WIN_APP_STATE", False);
83   list[4] = XInternAtom(disp, "_WIN_EXPANDED_SIZE", False);
84   list[5] = XInternAtom(disp, "_WIN_ICONS", False);
85   list[6] = XInternAtom(disp, "_WIN_WORKSPACE", False);
86   list[7] = XInternAtom(disp, "_WIN_WORKSPACE_COUNT", False);
87   list[8] = XInternAtom(disp, "_WIN_WORKSPACE_NAMES", False);
88   list[9] = XInternAtom(disp, "_WIN_CLIENT_LIST", False);
89   XChangeProperty(disp, root_window, atom_set, XA_ATOM, 32, PropModeReplace,
90 		  (unsigned char *)list, 10);
91 }
92 
gnome_managed_clients()93 extern void gnome_managed_clients()
94 {
95   /* Section 3 - Providing Shortcuts Managed Clients
96 
97      As an aide in having external applications be able to list and
98      access clients being managed by the Window Manager, a property
99      should be set on the root window of the name _WIN_CLIENT_LIST
100      which is an array of type CARDINAL. Each entry is the Window ID
101      of a managed client. If the list of managed clients changes,
102      clients are added or deleted, this list should be updated. */
103 
104   Display            *disp;
105   Window              root_window;
106   Atom                atom_set;
107   Window             *wl;
108   int                 num;
109 
110   fprintf(stderr, "FIXME: snome_managed_clients is a stub\n");
111 
112   atom_set = XInternAtom(disp, "_WIN_CLIENT_LIST", False);
113   num = 0;  /* FIXME: number of clients goes here */
114   wl = malloc(sizeof(Window) * num);
115   /* FIXME: Fill in array of window ID's */
116   XChangeProperty(disp, root_window, atom_set, XA_CARDINAL, 32,
117 		  PropModeReplace, (unsigned char *)wl, num);
118   if (wl)
119     free(wl);
120 }
121 
gnome_multiple_desktops()122 extern void gnome_multiple_desktops()
123 {
124   /* Section 3 - Providing Multiple/Virtual Desktop Information.
125 
126      If your Window Manager supports the concept of Multiple/Virtual
127      Desktops or Workspaces then you will definitely want to include
128      it. This involves your Window Manager setting several properties
129      on the root window.
130 
131      First you should advertise how many Desktops your Window Manager
132      supports. This is done by setting a property on the root window
133      with the atom name _WIN_WORKSPACE_COUNT of type CARDINAL. The
134      properties data is a 32-bit integer that is the number of
135      Desktops your Window Manager currently supports. If you can add
136      and delete desktops while running, you may change this property
137      and its value whenever required. You should also set a property
138      of the atom _WIN_WORKSPACE of type CARDINAL that contains the
139      number of the currently active desktop (which is a number between
140      0 and the number advertised by _WIN_WORKSPACE_COUNT -
141      1). Whenever the active desktop changes, change this property.
142 
143      Lastly you should set a property that is a list of strings called
144      _WIN_WORKSPACE_NAMES that contains names for the desktops (the
145      first string is the name of the first desktop, the second string
146      is the second desktop, etc.). This will allow applications toq
147      know what the name of the desktop is too, possibly to display it. */
148 
149   Display            *disp;
150   Window              root_window;
151   Atom                atom_set;
152   XTextProperty       text;
153   int                 i, current_desk, number_of_desks;
154   char              **names, s[1024];
155   CARD32              val;
156 
157   /* FIXME: set current_desk, number_of_desks  names */
158 
159   atom_set = XInternAtom(disp, "_WIN_WORKSPACE", False);
160   val = (CARD32) current_desk;
161   XChangeProperty(disp, root_window, atom_set, XA_CARDINAL, 32,
162 		  PropModeReplace, (unsigned char *)&val, 1);
163   atom_set = XInternAtom(disp, "_WIN_WORKSPACE_COUNT", False);
164 
165   val = (CARD32) number_of_desks;
166   XChangeProperty(disp, root_window, atom_set, XA_CARDINAL, 32,
167 		  PropModeReplace, (unsigned char *)&val, 1);
168   atom_set = XInternAtom(disp, "_WIN_WORKSPACE_NAMES", False);
169   names = malloc(sizeof(char *) * number_of_desks);
170   for (i = 0; i < number_of_desks; i++)
171   {
172     snprintf(s, sizeof(s), "Desktop %i", i);
173     names[i] = malloc(strlen(s) + 1);
174     strcpy(names[i], s);
175   }
176   if (XStringListToTextProperty(names, mode.numdesktops,  ))
177   {
178     XSetTextProperty(disp, root_window, &val, atom_set);
179     XFree(text.value);
180   }
181   for (i = 0; i < number_of_desks; i++)
182     free(names[i]);
183   free(names);
184 }
185