# # scrot_paint_mouse.diff # # author: mathias gumz # purpose: # # add a new flag to 'scrot': -M, this would paint a "mousepointer" into the # grabbed image at the correct position. # # this is done by grabbing the area underneath the mousepointer and render # a glyph of the "cursor"-font at that position with 'white' as fgcolor and # 'black' as bgcolor # # limitations: # # - shape and color of the painted mousepointer is fixed and is not in sync # with current x11-cursor # - multiple screens are not supported # diff -abBpur scrot-0.8/src/imlib.c scrot-0.8.akira/src/imlib.c --- scrot-0.8/src/imlib.c 2003-03-12 14:16:16.000000000 +0100 +++ scrot-0.8.akira/src/imlib.c 2005-05-30 14:34:34.083961464 +0200 @@ -33,6 +33,9 @@ Colormap cm; int depth; Window root = 0; +int mouse_x = 0; +int mouse_y = 0; + void init_x_and_imlib(char *dispstr, int screen_num) { diff -abBpur scrot-0.8/src/main.c scrot-0.8.akira/src/main.c --- scrot-0.8/src/main.c 2003-06-23 14:05:48.000000000 +0200 +++ scrot-0.8.akira/src/main.c 2005-05-30 15:05:35.757944000 +0200 @@ -47,6 +47,8 @@ main(int argc, opt.thumb_file = gib_estrdup("%Y-%m-%d-%H%M%S_$wx$h_scrot-thumb.png"); } + if (opt.mouse) + scrot_update_mouse_position(); if (opt.select) image = scrot_sel_and_grab_image(); @@ -156,6 +158,21 @@ scrot_grab_shot(void) im = gib_imlib_create_image_from_drawable(root, 0, 0, 0, scr->width, scr->height, 1); + + if (opt.mouse && im) { + Imlib_Image cim = scrot_create_cursor_image(); + if (cim) { + unsigned int w = gib_imlib_image_get_width(cim); + unsigned int h = gib_imlib_image_get_height(cim); + gib_imlib_blend_image_onto_image(im, cim, 1, + 0, 0, w, h, + mouse_x, mouse_y, w, h, + 0, 0, 0); + imlib_context_set_image(cim); + imlib_free_image(); + } + } + return im; } @@ -367,6 +384,21 @@ scrot_sel_and_grab_image(void) XBell(disp, 0); im = gib_imlib_create_image_from_drawable(root, 0, rx, ry, rw, rh, 1); + if (opt.mouse) { + Imlib_Image cim = scrot_create_cursor_image(); + if (mouse_x >= rx && mouse_x <= rx + rw && + mouse_y >= ry && mouse_y <= ry + rh && + cim) { + unsigned int w = gib_imlib_image_get_width(cim); + unsigned int h = gib_imlib_image_get_height(cim); + gib_imlib_blend_image_onto_image(im, cim, 1, + 0, 0, w, h, + mouse_x - rx, mouse_y - ry, w, h, + 0, 0, 0); + imlib_context_set_image(cim); + imlib_free_image(); + } + } } return im; } @@ -630,3 +662,51 @@ stalk_image_concat(gib_list * images) } return ret; } + +void scrot_update_mouse_position(void) +{ + Window tmp_win; + int tmp_ignore; + unsigned int tmp_ignore2; + XQueryPointer(disp, root, &tmp_win, &tmp_win, + &mouse_x, &mouse_y, + &tmp_ignore, &tmp_ignore, &tmp_ignore2); +} + +Imlib_Image +scrot_create_cursor_image(void) +{ + Imlib_Image ret; + unsigned int cw = 0; + unsigned int ch = 0; + XImage* ti = NULL; + Pixmap cpm = None; + GC cgc = None; + unsigned char text[2]; + + XFontStruct* cf = XLoadQueryFont(disp, "cursor"); + + text[0] = 0x45; + text[1] = 0; + cw = XTextWidth(cf, text, 1); + cw = mouse_x + cw > scr->width ? scr->width - mouse_x: cw; + ch = cf->ascent + cf->descent; + ch = mouse_y + ch > scr->height ? scr->height - mouse_y : ch; + cpm = XCreatePixmap(disp, scr->root, cw, ch, scr->root_depth); + cgc = XCreateGC(disp, cpm, 0, NULL); + ti = XGetImage(disp, root, mouse_x, mouse_y, cw, ch, AllPlanes, ZPixmap); + XPutImage(disp, cpm, cgc, ti, 0, 0, 0, 0, cw, ch); + XSetFont(disp, cgc, cf->fid); + XSetForeground(disp, cgc, scr->black_pixel); + XDrawString(disp, cpm, cgc, 0, 0, text, 1); + text[0] = 0x44; + XSetForeground(disp, cgc, scr->white_pixel); + XDrawString(disp, cpm, cgc, 0, 0, text, 1); + ret = gib_imlib_create_image_from_drawable(cpm, 0, 0, 0, cw, ch, 1); + XDestroyImage(ti); + XFreePixmap(disp, cpm); + XFreeGC(disp, cgc); + XFreeFont(disp, cf); + + return ret; +} Nur in scrot-0.8.akira/src: Makefile. diff -abBpur scrot-0.8/src/options.c scrot-0.8.akira/src/options.c --- scrot-0.8/src/options.c 2003-06-23 14:09:08.000000000 +0200 +++ scrot-0.8.akira/src/options.c 2005-05-30 13:10:28.644984776 +0200 @@ -44,7 +44,7 @@ init_parse_options(int argc, char **argv static void scrot_parse_option_array(int argc, char **argv) { - static char stropts[] = "bcd:e:hmq:st:v+:"; + static char stropts[] = "bcd:e:hmMq:st:v+:"; static struct option lopts[] = { /* actions */ {"help", 0, 0, 'h'}, /* okay */ @@ -52,6 +52,7 @@ scrot_parse_option_array(int argc, char {"count", 0, 0, 'c'}, {"select", 0, 0, 's'}, {"border", 0, 0, 'b'}, + {"mouse", 0, 0, 'M'}, {"multidisp", 0, 0, 'm'}, /* toggles */ {"thumb", 1, 0, 't'}, @@ -104,6 +105,8 @@ scrot_parse_option_array(int argc, char case 't': options_parse_thumbnail(optarg); break; + case 'M': + opt.mouse = 1; default: break; } @@ -220,6 +223,7 @@ show_usage(void) " -h, --help display this help and exit\n" " -v, --version output version information and exit\n" " -b, --border When selecting a window, grab wm border too\n" + " -M, --mouse Include mousepointer in screenshot\n" " -c, --count show a countdown before taking the shot\n" " -d, --delay NUM wait NUM seconds before taking a shot\n" " -e, --exec APP run APP on the resulting screenshot\n" diff -abBpur scrot-0.8/src/options.h scrot-0.8.akira/src/options.h --- scrot-0.8/src/options.h 2003-06-23 14:05:50.000000000 +0200 +++ scrot-0.8.akira/src/options.h 2005-05-30 12:59:08.238422296 +0200 @@ -38,6 +38,7 @@ struct __scrotoptions int thumb; int thumb_width; int thumb_height; + int mouse; char *output_file; char *thumb_file; char *exec; diff -abBpur scrot-0.8/src/scrot.h scrot-0.8.akira/src/scrot.h --- scrot-0.8/src/scrot.h 2003-06-23 14:05:51.000000000 +0200 +++ scrot-0.8.akira/src/scrot.h 2005-05-30 15:04:16.938926312 +0200 @@ -82,6 +82,8 @@ char *im_printf(char *str, struct tm *tm Imlib_Image im); Imlib_Image scrot_grab_shot_multi(void); Imlib_Image stalk_image_concat(gib_list *images); +void scrot_update_mouse_position(void); +Imlib_Image scrot_create_cursor_image(void); /* Imlib stuff */ extern Display *disp; @@ -93,4 +95,6 @@ extern int depth; extern Window root; extern Screen *scr; +extern int mouse_x; +extern int mouse_y; #endif