X-Git-Url: http://git.hungrycats.org/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=hacks%2Fripples.c;h=fac61995060e103740a8c5212a1ce64237189925;hb=c1b9b55ad8d59dc05ef55e316aebf5863e7dfa56;hp=1fd3831f927267c2ffc52dae54c3ef1ce0e109c8;hpb=49f5b54f312fe4ac2e9bc47581a72451bd0e8439;p=xscreensaver diff --git a/hacks/ripples.c b/hacks/ripples.c index 1fd3831f..fac61995 100644 --- a/hacks/ripples.c +++ b/hacks/ripples.c @@ -90,6 +90,8 @@ struct state { int draw_count; int iterations, delay, rate, box, oily, stir, fluidity; + int duration; + time_t start_time; void (*draw_transparent) (struct state *st, short *src); @@ -529,6 +531,7 @@ setup_X(struct state *st) st->img_loader = load_image_async_simple (0, xgwa.screen, st->window, st->window, 0, 0); + st->start_time = time ((time_t) 0); } else { XGCValues gcv; @@ -715,19 +718,21 @@ sinc(struct state *st, double x) static void add_circle_drop(struct state *st, int x, int y, int radius, int dheight) { - int i, r2, cx, cy; + int r, r2, cx, cy; short *buf = (random()&1) ? st->bufferA : st->bufferB; - i = y * st->width + x; r2 = radius * radius; + for (cy = -radius; cy <= radius; cy++) for (cx = -radius; cx <= radius; cx++) { - int r = cx*cx + cy*cy; - if (r <= r2) { - buf[i + cx + cy*st->width] = - (short)(dheight * sinc(st, sqrt(r)/radius)); - } + int xx = x+cx; + int yy = y+cy; + if (xx < 0 || yy < 0 || xx >= st->width || yy >= st->height) {break;} + r = cx*cx + cy*cy; + if (r > r2) break; + buf[xx + yy*st->width] = + (short)(dheight * sinc(st, sqrt(r)/radius)); } } @@ -757,10 +762,13 @@ add_drop(struct state *st, ripple_mode mode, int drop) case ripple_blob: { double power; + int tmp_i, tmp_j; power = drop_dist[random() % (sizeof(drop_dist)/sizeof(drop_dist[0]))]; /* clumsy */ dheight = (int)(drop * (power + 0.01)); - newx = radius + border + (random() % (int)(st->width - 2*border - 2*radius*power)); - newy = radius + border + (random() % (int)(st->height - 2*border - 2*radius*power)); + tmp_i = (int)(st->width - 2*border - 2*radius*power); + tmp_j = (int)(st->height - 2*border - 2*radius*power); + newx = radius + border + ((tmp_i > 0) ? random() % tmp_i : 0); + newy = radius + border + ((tmp_j > 0) ? random() % tmp_j : 0); add_circle_drop(st, newx, newy, radius, dheight); } break; @@ -770,12 +778,15 @@ add_drop(struct state *st, ripple_mode mode, int drop) int x; int cx, cy; short *buf = (random()&1) ? st->bufferA : st->bufferB; + int tmp_i, tmp_j; radius = (1 + (random() % 5)) * (1 + (random() % 5)); dheight = drop / 128; if (random() & 1) dheight = -dheight; - newx = radius + border + (random() % (st->width - 2*border - 2*radius)); - newy = radius + border + (random() % (st->height - 2*border - 2*radius)); + tmp_i = st->width - 2*border - 2*radius; + tmp_j = st->height - 2*border - 2*radius; + newx = radius + border + ((tmp_i > 0) ? random() % tmp_i : 0); + newy = radius + border + ((tmp_j > 0) ? random() % tmp_j : 0); x = newy * st->width + newx; for (cy = -radius; cy <= radius; cy++) for (cx = -radius; cx <= radius; cx++) @@ -945,6 +956,7 @@ ripples_init (Display *disp, Window win) st->window = win; st->iterations = 0; st->delay = get_integer_resource(disp, "delay", "Integer"); + st->duration = get_integer_resource (st->dpy, "duration", "Seconds"); st->rate = get_integer_resource(disp, "rate", "Integer"); st->box = get_integer_resource(disp, "box", "Integer"); st->oily = get_boolean_resource(disp, "oily", "Boolean"); @@ -957,6 +969,8 @@ ripples_init (Display *disp, Window win) #endif /* HAVE_XSHM_EXTENSION */ st->light = get_integer_resource(disp, "light", "Integer"); + if (st->delay < 0) st->delay = 0; + if (st->duration < 1) st->duration = 1; if (st->fluidity <= 1) st->fluidity = 1; if (st->fluidity > 16) st->fluidity = 16; /* 16 = sizeof(short) */ if (st->light < 0) st->light = 0; @@ -1015,6 +1029,7 @@ ripples_draw (Display *dpy, Window window, void *closure) if (! st->img_loader) { /* just finished */ XWindowAttributes xgwa; XGetWindowAttributes(st->dpy, st->window, &xgwa); + st->start_time = time ((time_t) 0); st->orig_map = XGetImage (st->dpy, st->window, 0, 0, xgwa.width, xgwa.height, ~0L, ZPixmap); @@ -1023,6 +1038,16 @@ ripples_draw (Display *dpy, Window window, void *closure) return st->delay; } + if (!st->img_loader && + st->start_time + st->duration < time ((time_t) 0)) { + XWindowAttributes xgwa; + XGetWindowAttributes(st->dpy, st->window, &xgwa); + st->img_loader = load_image_async_simple (0, xgwa.screen, st->window, + st->window, 0, 0); + st->start_time = time ((time_t) 0); + return st->delay; + } + if (st->rate > 0 && (st->iterations % st->rate) == 0) add_drop(st, ripple_blob, -SPLASH); if (st->stir) @@ -1065,13 +1090,14 @@ static const char *ripples_defaults[] = "*colors: 200", "*dontClearRoot: True", "*delay: 50000", + "*duration: 120", "*rate: 5", "*box: 0", - "*water: False", + "*water: True", "*oily: False", "*stir: False", "*fluidity: 6", - "*light: 0", + "*light: 4", "*grayscale: False", #ifdef HAVE_XSHM_EXTENSION "*useSHM: True", @@ -1086,6 +1112,7 @@ static XrmOptionDescRec ripples_options[] = { "-colors", ".colors", XrmoptionSepArg, 0}, { "-colours", ".colors", XrmoptionSepArg, 0}, {"-delay", ".delay", XrmoptionSepArg, 0}, + {"-duration", ".duration", XrmoptionSepArg, 0 }, {"-rate", ".rate", XrmoptionSepArg, 0}, {"-box", ".box", XrmoptionSepArg, 0}, {"-water", ".water", XrmoptionNoArg, "True"},