X-Git-Url: http://git.hungrycats.org/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=hacks%2Fcompass.c;h=5b9ba4990ec51febf325ae04183ec366d5bc14cf;hb=49f5b54f312fe4ac2e9bc47581a72451bd0e8439;hp=ed765a987c0bdeba36373344e09cf2af7445d6c2;hpb=3c58fb6311db49c46f1670922933b27c6ea0c065;p=xscreensaver diff --git a/hacks/compass.c b/hacks/compass.c index ed765a98..5b9ba499 100644 --- a/hacks/compass.c +++ b/hacks/compass.c @@ -23,19 +23,38 @@ #define RAND(n) ((long) ((random() & 0x7fffffff) % ((long) (n)))) #define RANDSIGN() ((random() & 1) ? 1 : -1) +struct state { + Display *dpy; + Window window; + + int delay; + Bool dbuf; + struct disc *discs[4]; + int x, y, size, size2; + GC ptr_gc; + GC erase_gc; + XWindowAttributes xgwa; + Pixmap b, ba, bb; /* double-buffer to reduce flicker */ +#ifdef HAVE_DOUBLE_BUFFER_EXTENSION + XdbeBackBuffer backb; +#endif /* HAVE_DOUBLE_BUFFER_EXTENSION */ +}; + + + struct disc { int theta; /* 0 - 360*64 */ int velocity; int acceleration; int limit; GC gc; - void (*draw) (Display *, Drawable, struct disc *, + void (*draw) (struct state *, Drawable, struct disc *, int x, int y, int radius); }; static void -draw_letters (Display *dpy, Drawable d, struct disc *disc, +draw_letters (struct state *st, Drawable d, struct disc *disc, int x, int y, int radius) { XPoint points[50]; @@ -61,7 +80,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[4].x = x + radius * 0.8 * cos(th + 0.07); points[4].y = y + radius * 0.8 * sin(th + 0.07); - XDrawLines (dpy, d, disc->gc, points, 5, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 5, CoordModeOrigin); /* 30 (1) */ @@ -94,7 +113,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[8].x = x + radius * 0.72 * cos(th - 0.13); points[8].y = y + radius * 0.72 * sin(th - 0.13); - XDrawLines (dpy, d, disc->gc, points, 9, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 9, CoordModeOrigin); /* 30 (2) */ @@ -118,7 +137,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[6] = points[0]; - XDrawLines (dpy, d, disc->gc, points, 7, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 7, CoordModeOrigin); /* 33 (1) */ @@ -151,7 +170,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[8].x = x + radius * 0.72 * cos(th - 0.13); points[8].y = y + radius * 0.72 * sin(th - 0.13); - XDrawLines (dpy, d, disc->gc, points, 9, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 9, CoordModeOrigin); /* 33 (2) */ @@ -182,7 +201,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[8].x = x + radius * 0.72 * cos(th + 0.03); points[8].y = y + radius * 0.72 * sin(th + 0.03); - XDrawLines (dpy, d, disc->gc, points, 9, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 9, CoordModeOrigin); /* N */ @@ -200,7 +219,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[3].x = x + radius * 0.8 * cos(th + 0.05); points[3].y = y + radius * 0.8 * sin(th + 0.05); - XDrawLines (dpy, d, disc->gc, points, 4, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 4, CoordModeOrigin); /* 3 */ @@ -233,7 +252,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[8].x = x + radius * 0.72 * cos(th - 0.05); points[8].y = y + radius * 0.72 * sin(th - 0.05); - XDrawLines (dpy, d, disc->gc, points, 9, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 9, CoordModeOrigin); /* 6 */ @@ -266,7 +285,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[8].x = x + radius * 0.74 * cos(th - 0.05); points[8].y = y + radius * 0.74 * sin(th - 0.05); - XDrawLines (dpy, d, disc->gc, points, 9, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 9, CoordModeOrigin); /* E */ @@ -294,7 +313,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[6].x = x + radius * 0.7 * cos(th + 0.05); points[6].y = y + radius * 0.7 * sin(th + 0.05); - XDrawLines (dpy, d, disc->gc, points, 7, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 7, CoordModeOrigin); /* 12 (1) */ @@ -309,7 +328,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[2].x = x + radius * 0.7 * cos(th - 0.03); points[2].y = y + radius * 0.7 * sin(th - 0.03); - XDrawLines (dpy, d, disc->gc, points, 3, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 3, CoordModeOrigin); /* 12 (2) */ @@ -337,7 +356,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[7].x = x + radius * 0.7 * cos(th + 0.13); points[7].y = y + radius * 0.7 * sin(th + 0.13); - XDrawLines (dpy, d, disc->gc, points, 8, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 8, CoordModeOrigin); /* 15 (1) */ @@ -352,7 +371,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[2].x = x + radius * 0.7 * cos(th - 0.03); points[2].y = y + radius * 0.7 * sin(th - 0.03); - XDrawLines (dpy, d, disc->gc, points, 3, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 3, CoordModeOrigin); /* 15 (2) */ @@ -383,7 +402,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[8].x = x + radius * 0.72 * cos(th + 0.02); points[8].y = y + radius * 0.72 * sin(th + 0.02); - XDrawLines (dpy, d, disc->gc, points, 9, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 9, CoordModeOrigin); /* S */ @@ -413,7 +432,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[7].x = x + radius * 0.72 * cos(th - 0.05); points[7].y = y + radius * 0.72 * sin(th - 0.05); - XDrawLines (dpy, d, disc->gc, points, 8, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 8, CoordModeOrigin); /* 21 (1) */ @@ -443,7 +462,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[7].x = x + radius * 0.7 * cos(th - 0.02); points[7].y = y + radius * 0.7 * sin(th - 0.02); - XDrawLines (dpy, d, disc->gc, points, 8, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 8, CoordModeOrigin); /* 21 (2) */ @@ -456,7 +475,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[2].x = x + radius * 0.7 * cos(th + 0.06); points[2].y = y + radius * 0.7 * sin(th + 0.06); - XDrawLines (dpy, d, disc->gc, points, 3, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 3, CoordModeOrigin); /* 24 (1) */ @@ -486,7 +505,7 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[7].x = x + radius * 0.7 * cos(th - 0.02); points[7].y = y + radius * 0.7 * sin(th - 0.02); - XDrawLines (dpy, d, disc->gc, points, 8, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 8, CoordModeOrigin); /* 24 (2) */ @@ -502,12 +521,12 @@ draw_letters (Display *dpy, Drawable d, struct disc *disc, points[3].x = x + radius * 0.72 * cos(th + 0.13); points[3].y = y + radius * 0.72 * sin(th + 0.13); - XDrawLines (dpy, d, disc->gc, points, 4, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 4, CoordModeOrigin); } static void -draw_ticks (Display *dpy, Drawable d, struct disc *disc, +draw_ticks (struct state *st, Drawable d, struct disc *disc, int x, int y, int radius) { XSegment segs[72]; @@ -529,14 +548,14 @@ draw_ticks (Display *dpy, Drawable d, struct disc *disc, segs[i].x2 = x + radius2 * cos(th); segs[i].y2 = y + radius2 * sin(th); } - XDrawSegments (dpy, d, disc->gc, segs, countof(segs)); + XDrawSegments (st->dpy, d, disc->gc, segs, countof(segs)); - draw_letters (dpy, d, disc, x, y, radius); + draw_letters (st, d, disc, x, y, radius); } static void -draw_thin_arrow (Display *dpy, Drawable d, struct disc *disc, +draw_thin_arrow (struct state *st, Drawable d, struct disc *disc, int x, int y, int radius) { XPoint points[3]; @@ -558,18 +577,18 @@ draw_thin_arrow (Display *dpy, Drawable d, struct disc *disc, points[2].x = x + radius2 * cos(th + tick); /* tip right */ points[2].y = y + radius2 * sin(th + tick); - XDrawLine (dpy, d, disc->gc, + XDrawLine (st->dpy, d, disc->gc, (int) (x + radius2 * cos(th)), (int) (y + radius2 * sin(th)), (int) (x + -radius * cos(th)), (int) (y + -radius * sin(th))); - XFillPolygon (dpy, d, disc->gc, points, 3, Convex, CoordModeOrigin); + XFillPolygon (st->dpy, d, disc->gc, points, 3, Convex, CoordModeOrigin); } static void -draw_thick_arrow (Display *dpy, Drawable d, struct disc *disc, +draw_thick_arrow (struct state *st, Drawable d, struct disc *disc, int x, int y, int radius) { XPoint points[10]; @@ -593,7 +612,7 @@ draw_thick_arrow (Display *dpy, Drawable d, struct disc *disc, points[3] = points[0]; - XDrawLines (dpy, d, disc->gc, points, 4, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 4, CoordModeOrigin); points[0].x = x + radius2 * cos(th - tick/2); /* top left */ points[0].y = y + radius2 * sin(th - tick/2); @@ -615,7 +634,7 @@ draw_thick_arrow (Display *dpy, Drawable d, struct disc *disc, points[6].x = x + radius2 * cos(th + tick/2); /* top right */ points[6].y = y + radius2 * sin(th + tick/2); - XDrawLines (dpy, d, disc->gc, points, 7, CoordModeOrigin); + XDrawLines (st->dpy, d, disc->gc, points, 7, CoordModeOrigin); } @@ -668,268 +687,287 @@ init_spin (struct disc *disc) static void -draw_compass (Display *dpy, Drawable d, struct disc **discs, - int x, int y, int radius) +draw_compass (struct state *st) { int i = 0; - while (discs[i]) + while (st->discs[i]) { - discs[i]->draw (dpy, d, discs[i], x, y, radius); - roll_disc (discs[i]); + st->discs[i]->draw (st, st->b, st->discs[i], st->x, st->y, st->size); + roll_disc (st->discs[i]); i++; } } static void -draw_pointer (Display *dpy, Drawable d, GC ptr_gc, GC dot_gc, - int x, int y, int radius) +draw_pointer (struct state *st) { + int radius = st->size; + GC dot_gc = st->discs[0]->gc; XPoint points[3]; int size = radius * 0.1; /* top */ - points[0].x = x - size; - points[0].y = y - radius - size; + points[0].x = st->x - size; + points[0].y = st->y - radius - size; - points[1].x = x + size; - points[1].y = y - radius - size; + points[1].x = st->x + size; + points[1].y = st->y - radius - size; - points[2].x = x; - points[2].y = y - radius; + points[2].x = st->x; + points[2].y = st->y - radius; - XFillPolygon (dpy, d, ptr_gc, points, 3, Convex, CoordModeOrigin); + XFillPolygon (st->dpy, st->b, st->ptr_gc, points, 3, Convex, CoordModeOrigin); /* top right */ - points[0].x = x - (radius * 0.85); - points[0].y = y - (radius * 0.8); + points[0].x = st->x - (radius * 0.85); + points[0].y = st->y - (radius * 0.8); - points[1].x = x - (radius * 1.1); - points[1].y = y - (radius * 0.55); + points[1].x = st->x - (radius * 1.1); + points[1].y = st->y - (radius * 0.55); - points[2].x = x - (radius * 0.6); - points[2].y = y - (radius * 0.65); + points[2].x = st->x - (radius * 0.6); + points[2].y = st->y - (radius * 0.65); - XFillPolygon (dpy, d, ptr_gc, points, 3, Convex, CoordModeOrigin); + XFillPolygon (st->dpy, st->b, st->ptr_gc, points, 3, Convex, CoordModeOrigin); /* left */ - points[0].x = x - (radius * 1.05); - points[0].y = y; + points[0].x = st->x - (radius * 1.05); + points[0].y = st->y; - points[1].x = x - (radius * 1.1); - points[1].y = y - (radius * 0.025); + points[1].x = st->x - (radius * 1.1); + points[1].y = st->y - (radius * 0.025); - points[2].x = x - (radius * 1.1); - points[2].y = y + (radius * 0.025); + points[2].x = st->x - (radius * 1.1); + points[2].y = st->y + (radius * 0.025); - XFillPolygon (dpy, d, dot_gc, points, 3, Convex, CoordModeOrigin); + XFillPolygon (st->dpy, st->b, dot_gc, points, 3, Convex, CoordModeOrigin); /* right */ - points[0].x = x + (radius * 1.05); - points[0].y = y; + points[0].x = st->x + (radius * 1.05); + points[0].y = st->y; - points[1].x = x + (radius * 1.1); - points[1].y = y - (radius * 0.025); + points[1].x = st->x + (radius * 1.1); + points[1].y = st->y - (radius * 0.025); - points[2].x = x + (radius * 1.1); - points[2].y = y + (radius * 0.025); + points[2].x = st->x + (radius * 1.1); + points[2].y = st->y + (radius * 0.025); - XFillPolygon (dpy, d, dot_gc, points, 3, Convex, CoordModeOrigin); + XFillPolygon (st->dpy, st->b, dot_gc, points, 3, Convex, CoordModeOrigin); /* bottom */ - points[0].x = x; - points[0].y = y + (radius * 1.05); + points[0].x = st->x; + points[0].y = st->y + (radius * 1.05); - points[1].x = x - (radius * 0.025); - points[1].y = y + (radius * 1.1); + points[1].x = st->x - (radius * 0.025); + points[1].y = st->y + (radius * 1.1); - points[2].x = x + (radius * 0.025); - points[2].y = y + (radius * 1.1); + points[2].x = st->x + (radius * 0.025); + points[2].y = st->y + (radius * 1.1); - XFillPolygon (dpy, d, dot_gc, points, 3, Convex, CoordModeOrigin); + XFillPolygon (st->dpy, st->b, dot_gc, points, 3, Convex, CoordModeOrigin); /* bottom left */ - points[0].x = x + (radius * 0.74); - points[0].y = y + (radius * 0.74); + points[0].x = st->x + (radius * 0.74); + points[0].y = st->y + (radius * 0.74); - points[1].x = x + (radius * 0.78); - points[1].y = y + (radius * 0.75); + points[1].x = st->x + (radius * 0.78); + points[1].y = st->y + (radius * 0.75); - points[2].x = x + (radius * 0.75); - points[2].y = y + (radius * 0.78); + points[2].x = st->x + (radius * 0.75); + points[2].y = st->y + (radius * 0.78); - XFillPolygon (dpy, d, dot_gc, points, 3, Convex, CoordModeOrigin); + XFillPolygon (st->dpy, st->b, dot_gc, points, 3, Convex, CoordModeOrigin); /* top left */ - points[0].x = x + (radius * 0.74); - points[0].y = y - (radius * 0.74); + points[0].x = st->x + (radius * 0.74); + points[0].y = st->y - (radius * 0.74); - points[1].x = x + (radius * 0.78); - points[1].y = y - (radius * 0.75); + points[1].x = st->x + (radius * 0.78); + points[1].y = st->y - (radius * 0.75); - points[2].x = x + (radius * 0.75); - points[2].y = y - (radius * 0.78); + points[2].x = st->x + (radius * 0.75); + points[2].y = st->y - (radius * 0.78); - XFillPolygon (dpy, d, dot_gc, points, 3, Convex, CoordModeOrigin); + XFillPolygon (st->dpy, st->b, dot_gc, points, 3, Convex, CoordModeOrigin); /* bottom right */ - points[0].x = x - (radius * 0.74); - points[0].y = y + (radius * 0.74); + points[0].x = st->x - (radius * 0.74); + points[0].y = st->y + (radius * 0.74); - points[1].x = x - (radius * 0.78); - points[1].y = y + (radius * 0.75); + points[1].x = st->x - (radius * 0.78); + points[1].y = st->y + (radius * 0.75); - points[2].x = x - (radius * 0.75); - points[2].y = y + (radius * 0.78); + points[2].x = st->x - (radius * 0.75); + points[2].y = st->y + (radius * 0.78); - XFillPolygon (dpy, d, dot_gc, points, 3, Convex, CoordModeOrigin); + XFillPolygon (st->dpy, st->b, dot_gc, points, 3, Convex, CoordModeOrigin); } - -char *progclass = "Compass"; -char *defaults [] = { - ".background: #000000", - ".foreground: #DDFFFF", - "*arrow1Foreground: #FFF66A", - "*arrow2Foreground: #F7D64A", - "*pointerForeground: #FF0000", - "*delay: 20000", - "*doubleBuffer: True", -#ifdef HAVE_DOUBLE_BUFFER_EXTENSION - "*useDBE: True", -#endif /* HAVE_DOUBLE_BUFFER_EXTENSION */ - 0 -}; - -XrmOptionDescRec options [] = { - { "-delay", ".delay", XrmoptionSepArg, 0 }, - { "-db", ".doubleBuffer", XrmoptionNoArg, "True" }, - { "-no-db", ".doubleBuffer", XrmoptionNoArg, "False" }, - { 0, 0, 0, 0 } -}; - -void -screenhack (Display *dpy, Window window) +static void * +compass_init (Display *dpy, Window window) { + struct state *st = (struct state *) calloc (1, sizeof(*st)); XGCValues gcv; - int delay = get_integer_resource ("delay", "Integer"); - Bool dbuf = get_boolean_resource ("doubleBuffer", "Boolean"); - struct disc *discs[4]; - int x, y, size, size2; - GC ptr_gc; - GC erase_gc = 0; - XWindowAttributes xgwa; - Pixmap b=0, ba=0, bb=0; /* double-buffer to reduce flicker */ -#ifdef HAVE_DOUBLE_BUFFER_EXTENSION - XdbeBackBuffer backb = 0; -#endif /* HAVE_DOUBLE_BUFFER_EXTENSION */ + st->dpy = dpy; + st->window = window; + st->delay = get_integer_resource (st->dpy, "delay", "Integer"); + st->dbuf = get_boolean_resource (st->dpy, "doubleBuffer", "Boolean"); + +# ifdef HAVE_COCOA /* Don't second-guess Quartz's double-buffering */ + st->dbuf = False; +# endif - XGetWindowAttributes (dpy, window, &xgwa); - size2 = MIN(xgwa.width, xgwa.height); + XGetWindowAttributes (st->dpy, st->window, &st->xgwa); + st->size2 = MIN(st->xgwa.width, st->xgwa.height); - if (size2 > 600) size2 = 600; + if (st->size2 > 600) st->size2 = 600; - size = (size2 / 2) * 0.8; + st->size = (st->size2 / 2) * 0.8; - x = xgwa.width/2; - y = xgwa.height/2; + st->x = st->xgwa.width/2; + st->y = st->xgwa.height/2; - if (dbuf) + if (st->dbuf) { #ifdef HAVE_DOUBLE_BUFFER_EXTENSION - b = backb = xdbe_get_backbuffer (dpy, window, XdbeUndefined); + st->b = st->backb = xdbe_get_backbuffer (st->dpy, st->window, XdbeUndefined); #endif /* HAVE_DOUBLE_BUFFER_EXTENSION */ - if (!b) + if (!st->b) { - x = size2/2; - y = size2/2; - ba = XCreatePixmap (dpy, window, size2, size2, xgwa.depth); - bb = XCreatePixmap (dpy, window, size2, size2, xgwa.depth); - b = ba; + st->x = st->size2/2; + st->y = st->size2/2; + st->ba = XCreatePixmap (st->dpy, st->window, st->size2, st->size2, st->xgwa.depth); + st->bb = XCreatePixmap (st->dpy, st->window, st->size2, st->size2, st->xgwa.depth); + st->b = st->ba; } } else { - b = window; + st->b = st->window; } - discs[0] = (struct disc *) calloc (1, sizeof (struct disc)); - discs[1] = (struct disc *) calloc (1, sizeof (struct disc)); - discs[2] = (struct disc *) calloc (1, sizeof (struct disc)); - discs[3] = 0; + st->discs[0] = (struct disc *) calloc (1, sizeof (struct disc)); + st->discs[1] = (struct disc *) calloc (1, sizeof (struct disc)); + st->discs[2] = (struct disc *) calloc (1, sizeof (struct disc)); + st->discs[3] = 0; - gcv.foreground = get_pixel_resource ("foreground", "Foreground", - dpy, xgwa.colormap); - gcv.line_width = MAX(2, (size/60)); + gcv.foreground = get_pixel_resource (st->dpy, st->xgwa.colormap, + "foreground", "Foreground"); + gcv.line_width = MAX(2, (st->size/60)); gcv.join_style = JoinBevel; - discs[0]->draw = draw_ticks; - discs[0]->gc = XCreateGC (dpy, b, GCForeground|GCLineWidth|GCJoinStyle, + st->discs[0]->draw = draw_ticks; + st->discs[0]->gc = XCreateGC (st->dpy, st->b, GCForeground|GCLineWidth|GCJoinStyle, &gcv); - init_spin (discs[0]); - - gcv.foreground = get_pixel_resource ("arrow2Foreground", "Foreground", - dpy, xgwa.colormap); - gcv.line_width = MAX(4, (size / 30)); - discs[1]->draw = draw_thick_arrow; - discs[1]->gc = XCreateGC (dpy, b, GCForeground|GCLineWidth, &gcv); - init_spin (discs[1]); - - gcv.foreground = get_pixel_resource ("arrow1Foreground", "Foreground", - dpy, xgwa.colormap); - gcv.line_width = MAX(4, (size / 30)); - discs[2]->draw = draw_thin_arrow; - discs[2]->gc = XCreateGC (dpy, b, GCForeground|GCLineWidth, &gcv); - init_spin (discs[2]); - - gcv.foreground = get_pixel_resource ("pointerForeground", "Foreground", - dpy, xgwa.colormap); - ptr_gc = XCreateGC (dpy, b, GCForeground|GCLineWidth, &gcv); - - gcv.foreground = get_pixel_resource ("background", "Background", - dpy, xgwa.colormap); - erase_gc = XCreateGC (dpy, b, GCForeground, &gcv); - - if (ba) XFillRectangle (dpy, ba, erase_gc, 0, 0, size2, size2); - if (bb) XFillRectangle (dpy, bb, erase_gc, 0, 0, size2, size2); - - while (1) - { - XFillRectangle (dpy, b, erase_gc, 0, 0, xgwa.width, xgwa.height); + init_spin (st->discs[0]); + + gcv.foreground = get_pixel_resource (st->dpy, st->xgwa.colormap, + "arrow2Foreground", "Foreground"); + gcv.line_width = MAX(4, (st->size / 30)); + st->discs[1]->draw = draw_thick_arrow; + st->discs[1]->gc = XCreateGC (st->dpy, st->b, GCForeground|GCLineWidth, &gcv); + init_spin (st->discs[1]); + + gcv.foreground = get_pixel_resource (st->dpy, st->xgwa.colormap, + "arrow1Foreground", "Foreground"); + gcv.line_width = MAX(4, (st->size / 30)); + st->discs[2]->draw = draw_thin_arrow; + st->discs[2]->gc = XCreateGC (st->dpy, st->b, GCForeground|GCLineWidth, &gcv); + init_spin (st->discs[2]); + + gcv.foreground = get_pixel_resource (st->dpy, st->xgwa.colormap, + "pointerForeground", "Foreground"); + st->ptr_gc = XCreateGC (st->dpy, st->b, GCForeground|GCLineWidth, &gcv); + + gcv.foreground = get_pixel_resource (st->dpy, st->xgwa.colormap, + "background", "Background"); + st->erase_gc = XCreateGC (st->dpy, st->b, GCForeground, &gcv); + + if (st->ba) XFillRectangle (st->dpy, st->ba, st->erase_gc, 0, 0, st->size2, st->size2); + if (st->bb) XFillRectangle (st->dpy, st->bb, st->erase_gc, 0, 0, st->size2, st->size2); + + return st; +} + +static unsigned long +compass_draw (Display *dpy, Window window, void *closure) +{ + struct state *st = (struct state *) closure; + XFillRectangle (st->dpy, st->b, st->erase_gc, 0, 0, st->xgwa.width, st->xgwa.height); - draw_compass (dpy, b, discs, x, y, size); - draw_pointer (dpy, b, ptr_gc, discs[0]->gc, x, y, size); + draw_compass (st); + draw_pointer (st); #ifdef HAVE_DOUBLE_BUFFER_EXTENSION - if (backb) - { - XdbeSwapInfo info[1]; - info[0].swap_window = window; - info[0].swap_action = XdbeUndefined; - XdbeSwapBuffers (dpy, info, 1); - } - else + if (st->backb) + { + XdbeSwapInfo info[1]; + info[0].swap_window = st->window; + info[0].swap_action = XdbeUndefined; + XdbeSwapBuffers (st->dpy, info, 1); + } + else #endif /* HAVE_DOUBLE_BUFFER_EXTENSION */ - if (dbuf) - { - XCopyArea (dpy, b, window, erase_gc, 0, 0, - size2, size2, - xgwa.width/2 - x, - xgwa.height/2 - y); - b = (b == ba ? bb : ba); - } + if (st->dbuf) + { + XCopyArea (st->dpy, st->b, st->window, st->erase_gc, 0, 0, + st->size2, st->size2, + st->xgwa.width/2 - st->x, + st->xgwa.height/2 - st->y); + st->b = (st->b == st->ba ? st->bb : st->ba); + } + + return st->delay; +} - XSync (dpy, False); - screenhack_handle_events (dpy); - if (delay) - usleep (delay); - } +static void +compass_reshape (Display *dpy, Window window, void *closure, + unsigned int w, unsigned int h) +{ +} + +static Bool +compass_event (Display *dpy, Window window, void *closure, XEvent *event) +{ + return False; } + +static void +compass_free (Display *dpy, Window window, void *closure) +{ +} + + + +static const char *compass_defaults [] = { + ".background: #000000", + ".foreground: #DDFFFF", + "*arrow1Foreground: #FFF66A", + "*arrow2Foreground: #F7D64A", + "*pointerForeground: #FF0000", + "*delay: 20000", + "*doubleBuffer: True", +#ifdef HAVE_DOUBLE_BUFFER_EXTENSION + "*useDBE: True", +#endif /* HAVE_DOUBLE_BUFFER_EXTENSION */ + 0 +}; + +static XrmOptionDescRec compass_options [] = { + { "-delay", ".delay", XrmoptionSepArg, 0 }, + { "-db", ".doubleBuffer", XrmoptionNoArg, "True" }, + { "-no-db", ".doubleBuffer", XrmoptionNoArg, "False" }, + { 0, 0, 0, 0 } +}; + + +XSCREENSAVER_MODULE ("Compass", compass)