2 * ion/ioncore/property.c
4 * Copyright (c) Tuomo Valkonen 1999-2007.
6 * Ion is free software; you can redistribute it and/or modify it under
7 * the terms of the GNU Lesser General Public License as published by
8 * the Free Software Foundation; either version 2.1 of the License, or
9 * (at your option) any later version.
23 static ulong xwindow_get_property_(Window win, Atom atom, Atom type,
24 ulong n32expected, bool more, uchar **p,
32 status=XGetWindowProperty(ioncore_g.dpy, win, atom, 0L, n32expected,
33 False, type, &real_type, format, &n,
36 if(status!=Success || *p==NULL)
43 n32expected+=(extra+4)/4;
57 ulong xwindow_get_property(Window win, Atom atom, Atom type,
58 ulong n32expected, bool more, uchar **p)
61 return xwindow_get_property_(win, atom, type, n32expected, more, p,
69 /*{{{ String property stuff */
72 char *xwindow_get_string_property(Window win, Atom a, int *nret)
77 n=xwindow_get_property(win, a, XA_STRING, 64L, TRUE, (uchar**)&p);
82 return (n<=0 ? NULL : p);
86 void xwindow_set_string_property(Window win, Atom a, const char *value)
89 XDeleteProperty(ioncore_g.dpy, win, a);
91 XChangeProperty(ioncore_g.dpy, win, a, XA_STRING,
92 8, PropModeReplace, (uchar*)value, strlen(value));
100 /*{{{ Integer property stuff */
103 bool xwindow_get_integer_property(Window win, Atom a, int *vret)
108 n=xwindow_get_property(win, a, XA_INTEGER, 1L, FALSE, (uchar**)&p);
120 void xwindow_set_integer_property(Window win, Atom a, int value)
126 XChangeProperty(ioncore_g.dpy, win, a, XA_INTEGER,
127 32, PropModeReplace, (uchar*)data, 1);
134 bool xwindow_get_state_property(Window win, int *state)
138 if(xwindow_get_property(win, ioncore_g.atom_wm_state,
139 ioncore_g.atom_wm_state,
140 2L, FALSE, (uchar**)&p)<=0)
151 void xwindow_set_state_property(Window win, int state)
158 XChangeProperty(ioncore_g.dpy, win,
159 ioncore_g.atom_wm_state, ioncore_g.atom_wm_state,
160 32, PropModeReplace, (uchar*)data, 2);
167 /*{{{ Text property stuff */
170 char **xwindow_get_text_property(Window win, Atom a, int *nret)
177 st=XGetTextProperty(ioncore_g.dpy, win, &prop, a);
180 *nret=(!st ? 0 : -1);
185 #ifdef CF_XFREE86_TEXTPROP_BUG_WORKAROUND
186 while(prop.nitems>0){
187 if(prop.value[prop.nitems-1]=='\0')
194 if(!ioncore_g.use_mb){
195 st=XTextPropertyToStringList(&prop, &list, &n);
197 st=XmbTextPropertyToTextList(ioncore_g.dpy, &prop, &list, &n);
203 if(!st || n==0 || list==NULL)
213 void xwindow_set_text_property(Window win, Atom a, const char **ptr, int n)
218 if(!ioncore_g.use_mb){
219 st=XStringListToTextProperty((char **)&ptr, n, &prop);
221 #ifdef X_HAVE_UTF8_STRING
222 st=XmbTextListToTextProperty(ioncore_g.dpy, (char **)ptr, n,
223 XUTF8StringStyle, &prop);
225 st=XmbTextListToTextProperty(ioncore_g.dpy, (char **)ptr, n,
234 XSetTextProperty(ioncore_g.dpy, win, &prop, a);
246 * Create a new atom. See \code{XInternAtom}(3) manual page for details.
249 int ioncore_x_intern_atom(const char *name, bool only_if_exists)
251 return XInternAtom(ioncore_g.dpy, name, only_if_exists);
256 * Get the name of an atom. See \code{XGetAtomName}(3) manual page for
260 char *ioncore_x_get_atom_name(int atom)
262 return XGetAtomName(ioncore_g.dpy, atom);
269 for(i=0; i<n; i++) extl_table_seti_i(tab, i+1, d[i]); \
274 * Get a property \var{atom} of type \var{atom_type} for window \var{win}.
275 * The \var{n32expected} parameter indicates the expected number of 32bit
276 * words, and \var{more} indicates whether all or just this amount of data
277 * should be fetched. Each 8, 16 or 32bit element of the property, as
278 * deciphered from \var{atom_type} is a field in the returned table.
279 * See \code{XGetWindowProperty}(3) manual page for more information.
283 ExtlTab ioncore_x_get_window_property(int win, int atom, int atom_type,
284 int n32expected, bool more)
291 n=xwindow_get_property_(win, atom, atom_type, n32expected, more, &p,
295 return extl_table_none();
297 if(n<=0 || (format!=8 && format!=16 && format!=32)){
299 return extl_table_none();
302 tab=extl_create_table();
305 case 8: CP(char); break;
306 case 16: CP(short); break;
307 case 32: CP(long); break;
316 TYPE *d=ALLOC_N(TYPE, n); \
317 if(d==NULL) return; \
318 for(i=0; i<n; i++) { \
319 if(!extl_table_geti_i(tab, i+1, &tmp)) return; \
326 static bool get_mode(const char *mode, int *m)
328 if(strcmp(mode, "replace")==0)
330 else if(strcmp(mode, "prepend")==0)
332 else if(strcmp(mode, "append")==0)
342 * Modify a window property. The \var{mode} is one of
343 * \code{"replace"}, \code{"prepend"} or \code{"append"}, and format
344 * is either 8, 16 or 32. Also see \fnref{ioncore.x_get_window_property}
345 * and the \code{XChangeProperty}(3) manual page.
348 void ioncore_x_change_property(int win, int atom, int atom_type,
349 int format, const char *mode, ExtlTab tab)
351 int tmp, m, i, n=extl_table_get_n(tab);
354 if(n<0 || !get_mode(mode, &m)){
355 warn(TR("Invalid arguments."));
360 case 8: GET(char); break;
361 case 16: GET(short); break;
362 case 32: GET(long); break;
364 warn(TR("Invalid arguments."));
368 XChangeProperty(ioncore_g.dpy, win, atom, atom_type, format, m, p, n);
375 * Delete a window property.
378 void ioncore_x_delete_property(int win, int atom)
380 XDeleteProperty(ioncore_g.dpy, win, atom);
385 * Get a text property for a window (\code{STRING}, \code{COMPOUND_TEXT},
386 * or \code{UTF8_STRING} property converted). The fields in the returned
387 * table (starting from 1) are the null-separated parts of the property.
388 * See the \code{XGetTextProperty}(3) manual page for more information.
392 ExtlTab ioncore_x_get_text_property(int win, int atom)
396 ExtlTab tab=extl_table_none();
398 list=xwindow_get_text_property(win, atom, &n);
402 tab=extl_create_table();
404 extl_table_seti_s(tab, i+1, list[i]);
406 XFreeStringList(list);
414 * Set a text property for a window. The fields of \var{tab} starting from
415 * 1 should be the different null-separated parts of the property.
416 * See the \code{XSetTextProperty}(3) manual page for more information.
419 void ioncore_x_set_text_property(int win, int atom, ExtlTab tab)
422 int i, n=extl_table_get_n(tab);
424 list=ALLOC_N(char*, n);
431 extl_table_geti_s(tab, i+1, &(list[i]));
434 xwindow_set_text_property(win, atom, (const char **)list, n);
436 XFreeStringList(list);