diff options
author | Arnaud Fontaine <arnau@debian.org> | 2011-10-30 16:47:08 +0900 |
---|---|---|
committer | Arnaud Fontaine <arnau@debian.org> | 2011-10-30 16:47:08 +0900 |
commit | 6da6193021802ba1455a953e6e21707e88f18985 (patch) | |
tree | 4325e732173f32da144df1e4d8bd794125fc18c3 | |
parent | 705d787a5b35a8409c482526b5c2955aa5371b1e (diff) | |
parent | c63bf55e69fc50e08b9bf500e9b05cf36ce48680 (diff) |
Merge branch 'transset-df'
-rw-r--r-- | README | 37 | ||||
-rw-r--r-- | dsimple.c | 102 | ||||
-rw-r--r-- | dsimple.h | 7 | ||||
-rw-r--r-- | transSet.c | 298 |
4 files changed, 400 insertions, 44 deletions
@@ -0,0 +1,37 @@ +This is a patched version of xorg's transset +I wanted to integrate transset into my windowmanager and to +be able to set and unset transparency by just pressing a key. +To make that possible I added several different 'select methods'. +The first one was 'select by point' and lets the user run transset +directly on the window curently under the cursor without bringing +up the crosshair. Later select by name and id was added after insperation +from other transset patches. + +In the future I guess it's ment for the windowmanagers to handle +transparency. Then we will hopefully see these functions and many other +now imposible function. This will however require you to wait untill this is +implementet in your favorite wm. This patch is a way of "scratching where it +itches", by creating a usefull integration with every windowmanager without +changing any wm-code. And it's a very "unix way" of doing things too :) + +Features + *select window by clicking (as transset) + *select actual focused X11 window + *select window by pointing + *select by window name or id + *force toggle + *increase or decrease opacity + +Instalation + type: + make + make install + +Homepage: http://www.forchheimer.se/transset-df/ + +Any questions/sugestions or if you just want to say hello don't fear to send +me a email + +Cheers +Daniel Forchheimer (upiom) +n04df@student.lth.se @@ -35,6 +35,9 @@ from The Open Group. #include <stdio.h> #include <stdlib.h> #include <stdarg.h> + +#include <sys/types.h> +#include <regex.h> /* * Other_stuff.h: Definitions of routines in other_stuff. * @@ -450,6 +453,41 @@ Window Select_Window(dpy) return(target_win); } +/* + * Routine that returns the window currently under the cursor + * Added by Daniel Forchheimer. Last updated 19/12/04 + */ + +Window Get_Window_Under_Cursor(dpy) + Display *dpy; +{ + int status; + Cursor cursor; + //XEvent event; + Window target_win = None, root = RootWindow(dpy,screen); + //int buttons = 0; + Window tmp; + int rx,ry,cx,cy; + unsigned int mask; + + /* Make the target cursor */ + cursor = XCreateFontCursor(dpy, XC_crosshair); + + /* Grab the pointer using target cursor, letting it room all over */ + status = XGrabPointer(dpy, root, False, + ButtonPressMask|ButtonReleaseMask, GrabModeSync, + GrabModeAsync, root, cursor, CurrentTime); + if (status != GrabSuccess) Fatal_Error("Can't grab the mouse."); + + /* get the window under the cursor */ + XQueryPointer(dpy, root, &tmp, &target_win, &rx, &ry, + &cx, &cy, &mask); + + XUngrabPointer(dpy, CurrentTime); /* Done with pointer */ + + return(target_win); +} + /* * Window_With_Name: routine to locate a window with a given name on a display. @@ -468,7 +506,7 @@ Window Window_With_Name(dpy, top, name) int i; Window w=0; char *window_name; - + if (XFetchName(dpy, top, &window_name) && !strcmp(window_name, name)) return(top); @@ -485,6 +523,68 @@ Window Window_With_Name(dpy, top, name) } /* + * Window_With_Name_Regex: Same as above but use regular expressions + * to match a window name. Only returns the first + * result. + * Window_With_Name_Regex_Recurse: Takes regex_t struct as argument + * instead of char* + * Written by Daniel Forchheimer 2005 + * */ +Window Window_With_Name_Regex_Recurse(dpy, top, reg_name) + Display *dpy; + Window top; + regex_t *reg_name; +{ + Window *children, dummy; + unsigned int nchildren; + int i; + Window w=0; + char *window_name; + + if (XFetchName(dpy, top, &window_name) && !regexec(reg_name,window_name,0,NULL,0)) + return(top); + + if (!XQueryTree(dpy, top, &dummy, &dummy, &children, &nchildren)) + return(0); + + for (i=0; i<nchildren; i++) { + w = Window_With_Name_Regex_Recurse(dpy, children[i], reg_name); + if (w) + break; + } + if (children) XFree ((char *)children); + return(w); +} +/* prepare the reg-exp for use with above function */ +Window Window_With_Name_Regex(dpy,top,name) + Display *dpy; + Window top; + char *name; +{ + int err_no=0; + regex_t *regexp_name; + Window target_win; + regexp_name = (regex_t *) malloc(sizeof(regex_t)); + if((err_no=regcomp(regexp_name, name, 0))!=0) + { + size_t length; + char *buffer; + length = regerror (err_no, regexp_name, NULL, 0); + buffer = malloc(length); + regerror (err_no, regexp_name, buffer, length); + fprintf(stderr, "%s\n", buffer); + free(buffer); + regfree(regexp_name); + exit(1); + } + target_win = Window_With_Name_Regex_Recurse(dpy, RootWindow(dpy, screen),regexp_name); + + regfree(regexp_name); + free(regexp_name); + return target_win; +} + +/* * outl: a debugging routine. Flushes stdout then prints a message on stderr * and flushes stderr. Used to print messages when past certain points * in code so we can tell where we are. Outl may be invoked like @@ -39,6 +39,7 @@ from The Open Group. * Send bugs, etc. to chariot@athena.mit.edu. */ +#include <regex.h> /* Global variables used by routines in just_display.c */ extern char *program_name; /* Name of this program */ @@ -91,14 +92,20 @@ void usage(); unsigned long Resolve_Color(Window, char *); Pixmap Bitmap_To_Pixmap(Display *, Drawable, GC, Pixmap, int, int); Window Select_Window(Display *); +Window Get_Window_Under_Cursor(Display *); /*added by Daniel Forchheimer for transset-df*/ void blip(void); Window Window_With_Name(Display *, Window, char *); +Window Window_With_Name_Regex(Display *, Window, char *); /*added by Daniel Forchheimer for transset-df*/ +Window Window_With_Name_Regex_Recurse(Display *, Window, regex_t *); /*added by Daniel Forchheimer for transset-df*/ #else unsigned long Resolve_Color(); Pixmap Bitmap_To_Pixmap(); Window Select_Window(); +Window Get_Window_Under_Cursor(); /*added by Daniel Forchheimer for transset-df*/ void blip(); Window Window_With_Name(); +Window Window_With_Name_Regex(); /*added by Daniel Forchheimer for transset-df*/ +Window Window_With_Name_Regex_Recurse(); /*added by Daniel Forchheimer for transset-df*/ #endif #ifdef __GNUC__ void Fatal_Error(char *, ...) __attribute__((__noreturn__)); @@ -1,19 +1,28 @@ -/* Simple program to toggle Translucency property on next window clicked - Uses dsimple.h and dsimple.c from xlsfonts. - Based on xprops and xwininfo +/* Simple program to toggle Translucency property + Based on 'transset' by Matthew Hawn + With some additional features to make it more automatic and integrated + The purpos is to bind it from your wm to a key or mouse-button - By Matthew Hawn - Use however you want. I can't stop you. + License: Use however you want. + Authors: + Matthew Hawn + Daniel Forchheimer + Andreas Kohn + Roman Divacky */ - +#define VERSIONSTR "6" +#define RELEASEDATESTR "2007-09-21" #include <stdio.h> #include <X11/Xlib.h> #include <X11/Xatom.h> #include "dsimple.h" #include <stdlib.h> - +#include <getopt.h> +#include <string.h> +#include <sys/types.h> +#include <regex.h> Window target_win; @@ -21,76 +30,279 @@ Window target_win; void usage() { - fprintf(stderr, "Bad arguments\n"); + fprintf(stderr,"usage: transset-df [-options ...] [opacity]\n"); + fprintf(stderr,"options:\n"); + + fprintf(stderr, + " -h, --help display this message\n"); + fprintf(stderr, + " -t, --toggle force toggle of opacity\n"); + fprintf(stderr, + " -c, --click select by clicking on window (default)\n"); + fprintf(stderr, + " -p, --point select the window currently under the cursor\n"); + fprintf(stderr, + " -a, --actual select the actual window\n"); + fprintf(stderr, + " -n, --name NAME select by name, NAME is matched as regular expression\n"); + fprintf(stderr, + " --no-regex don't use regular expression for matching name\n"); + fprintf(stderr, + " -i, --id select by window id\n"); + fprintf(stderr, + " --inc increase by the given opacity\n"); + fprintf(stderr, + " --dec decrease by given opacity\n"); + fprintf(stderr, + " -m, --min OPACITY minimum possible opacity (default = 0)\n"); + fprintf(stderr, + " -x, --max OPACITY maximum possible opacity (default = 1)\n"); + fprintf(stderr, + " -v, --verbose print some debug info\n"); + fprintf(stderr, + " -V, --version print version number\n"); + + exit(1); } #define OPAQUE 0xffffffff #define OPACITY "_NET_WM_WINDOW_OPACITY" +/* returns the highest parent of child that is not the root-window */ +Window get_top_window(Display *dpy,Window child) { + Window parent; + Window root; + Window *child_list; + unsigned int num_children; + + if (!XQueryTree(dpy, child, &root, &parent, &child_list, + &num_children)) + Fatal_Error("Can't query window tree."); + if(parent==root) return child; + + while(parent!=root) { + child = parent; + if (!XQueryTree(dpy, child, &root, &parent, &child_list, + &num_children)) + Fatal_Error("Can't query window tree."); + + } + return child; +} + +/* returns the actual window */ +Window get_actual_window(Display *dpy) +{ + int i; + Window w; + + XGetInputFocus(dpy, &w, &i); + return get_top_window(dpy, w); +} + /* nothing fancy */ int main(int argc, char **argv) { int gotd = 0; double d; unsigned int opacity; + unsigned int current_opacity; + int select_method = 0; // 0 = click, 1 = point, 2 = id, 3 = name + int flag_toggle=0; + int flag_increase=0; + int flag_decrease=0; + int flag_verbose=0; + int flag_no_regex=0; + int o; + float min=0,max=1; + char *idstr,*namestr; + char *windowname=NULL; + + int options_index=0; + static struct option long_options[] = { + {"toggle",0,NULL,'t'}, + {"help",0,NULL,'h'}, + {"point",0,NULL,'p'}, + {"actual",0,NULL,'a'}, + {"click",0,NULL,'c'}, + {"id",1,NULL,'i'}, + {"name",1,NULL,'n'}, + {"inc",0,NULL,'1'}, + {"dec",0,NULL,'2'}, + {"min",1,NULL,'m'}, + {"max",1,NULL,'x'}, + {"no-regex",0,NULL,'4'}, + {"version",0,NULL,'V'}, + {"verbose",0,NULL,'v'}, + {0,0,0,0} + }; + unsigned char *data; + + Atom actual; + int format; + unsigned long n, left; /* wonderful utility */ Setup_Display_And_Screen(&argc, argv); - if (argv[1]) + /* parse arguments */ + while ((o = getopt_long(argc, argv, "thapci:n:vVm:x:123",long_options,&options_index)) != -1) + { + switch (o) { + case 't': + flag_toggle=1; + break; + case 'h': + usage(); + break; + case 'c': + select_method=0; + break; + case 'p': + select_method=1; + break; + case 'i': + idstr = malloc(strlen(optarg)+1); + idstr = optarg; + select_method=2; + break; + case 'n': + namestr = malloc(strlen(optarg)+1); + namestr = optarg; + select_method=3; + break; + case 'a': + select_method=4; + break; + case '1': + flag_increase=1; + break; + case '2': + flag_decrease=1; + break; + case 'v': + flag_verbose=1; + break; + case '4': + flag_no_regex=1; + break; + case 'm': + min = atof(optarg); + break; + case 'x': + max = atof(optarg); + break; + case 'V': + fprintf(stderr,"version: %s\nreleased: %s\n",VERSIONSTR,RELEASEDATESTR); + exit(1); + break; + default: + usage(); + } + } + + if(optind<argc) { - printf ("got arg %s\n", argv[1]); - d = atof (argv[1]); - printf ("d is %g\n", d); + d = atof (argv[optind]); gotd = 1; } - /* grab mouse and return window that is next clicked */ - target_win = Select_Window(dpy); + /* select the window to make transparent */ + if(select_method==1) { + /* don't wait for click */ + if(flag_verbose) printf("Selecting window by click\n"); + target_win = Get_Window_Under_Cursor(dpy); + } else if(select_method==2) { + /* select by id, pretty much ripped from dsimple.c */ + if(flag_verbose) printf("Selecting window by id\n"); + sscanf(idstr, "0x%lx", &target_win); + if (!target_win) + sscanf(idstr, "%ld", &target_win); + if (!target_win) { + fprintf(stderr,"Invalid window id format: %s.\n", idstr); + exit(0); + } + if(flag_verbose) printf("Selected 0x%x, trying to get top parent ... ",(unsigned int)target_win); + target_win = get_top_window(dpy,target_win); + if(flag_verbose) printf("found 0x%x\n",(unsigned int)target_win); + + } else if(select_method==3) { + /* select by name, pretty much ripped from dsimple.c */ + if(flag_verbose) printf("Selecting window by name\n"); - unsigned char *data; + if(flag_no_regex) + target_win = Window_With_Name(dpy, RootWindow(dpy, screen),namestr); + else + target_win = Window_With_Name_Regex(dpy, RootWindow(dpy, screen),namestr); + + if (!target_win) { + fprintf(stderr,"No window matching %s exists!\n",namestr); + exit(0); + } + /* store the matched window name*/ + XFetchName(dpy,target_win,&windowname); - Atom actual; - int format; - unsigned long n, left; + if(flag_verbose) printf("Selected 0x%x, trying to get top parent ... ",(unsigned int)target_win); + target_win = get_top_window(dpy,target_win); + if(flag_verbose) printf("found 0x%x\n",(unsigned int)target_win); + + } else if(select_method==4) { + target_win = get_actual_window(dpy); + } else { + /* grab mouse and return window that is next clicked */ + target_win = Select_Window(dpy); + } + + if (!gotd) d=0.75; - if (gotd) - opacity = (unsigned int) (d * OPAQUE); + /* get property */ + XGetWindowProperty(dpy, target_win, XInternAtom(dpy, OPACITY, False), + 0L, 1L, False, XA_CARDINAL, &actual, &format, &n, &left, + (unsigned char **) &data); + + if (data != None) + { + memcpy (¤t_opacity, data, sizeof (unsigned int)); + XFree(( void *) data ); + if(flag_verbose) printf("Found transparency: %g\n", (double) opacity / OPAQUE); + } else - { - /* get property */ - XGetWindowProperty(dpy, target_win, XInternAtom(dpy, OPACITY, False), - 0L, 1L, False, XA_CARDINAL, &actual, &format, &n, &left, - (unsigned char **) &data); + current_opacity = OPAQUE; - if (data != None) - { - memcpy (&opacity, data, sizeof (unsigned int)); - XFree(( void *) data ); - printf("Found property: %g\n", (double) opacity / OPAQUE); - } - else - opacity = OPAQUE; + if(flag_increase) { + d = (double)current_opacity/OPAQUE + d; + } else if(flag_decrease) { + d = (double)current_opacity/OPAQUE - d; + } + //printf("%f\n",d); + /* check min and max */ + if(d<min) d=min; + if(d>max) d=max; + + opacity = (unsigned int) (d * OPAQUE); + + /* for user-compability with transset */ + if(!gotd) flag_toggle=1; - /* toggle */ - if (opacity != OPAQUE) + /* toggle */ + if(flag_toggle) + if (current_opacity != OPAQUE) opacity = OPAQUE; - else - opacity = 0xc0000000; - } - printf ("opacity 0x%x\n", opacity); + // printf ("opacity 0x%x\n", opacity); if (opacity == OPAQUE) - XDeleteProperty (dpy, target_win, XInternAtom(dpy, OPACITY, False)); + XDeleteProperty (dpy, target_win, XInternAtom(dpy, OPACITY, False)); /* set it */ - else + else XChangeProperty(dpy, target_win, XInternAtom(dpy, OPACITY, False), XA_CARDINAL, 32, PropModeReplace, (unsigned char *) &opacity, 1L); XSync(dpy, False); - printf("Set Property to %g\n", (double) opacity / OPAQUE); - + printf("Set Property to %g", (double) opacity / OPAQUE); + if(windowname) printf(" on \n%s\n",windowname); + else printf("\n"); + if(flag_verbose) printf("Propery set on: 0x%x\n",(unsigned int)target_win); /* all done, wasn't that simple */ return 0; } |