X-Git-Url: http://git.hungrycats.org/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=hacks%2Frd-bomb.c;h=dd5253bc259974f74f6cb4dcee38824b12328b5c;hb=3f438031d610c7e15fd33876a879b97e290e05fb;hp=0a7cee75a1ab7949adbb4a294aa55b44d04b6409;hpb=6bb727f03bff0389fbb1349d7df4c9d8d7532959;p=xscreensaver diff --git a/hacks/rd-bomb.c b/hacks/rd-bomb.c index 0a7cee75..dd5253bc 100644 --- a/hacks/rd-bomb.c +++ b/hacks/rd-bomb.c @@ -1,5 +1,5 @@ -/* xscreensaver, Copyright (c) 1992, 1995, 1997 - * Jamie Zawinski +/* xscreensaver, Copyright (c) 1992, 1995, 1997, 1998, 1999, 2003 + * Jamie Zawinski * * reaction/diffusion textures * Copyright (c) 1997 Scott Draves spot@transmeta.com @@ -21,23 +21,28 @@ #include #include "screenhack.h" +#include + +#ifdef HAVE_XSHM_EXTENSION +# include "xshm.h" +#endif /* HAVE_XSHM_EXTENSION */ /* costs ~6% speed */ #define dither_when_mapped 1 -int verbose; -int ncolors = 0; -XColor *colors = 0; -Display *display; -Visual *visual; +static int verbose; +static int ncolors = 0; +static XColor *colors = 0; +static Display *display; +static Visual *visual; #if dither_when_mapped -unsigned char *mc = 0; +static unsigned char *mc = 0; #endif -Colormap cmap = 0; -Window window; -int mapped; -int pdepth; -void random_colors(void); +static Colormap cmap = 0; +static Window window; +static int mapped; +static int pdepth; +static void random_colors(void); /* ----------------------------------------------------------- pixel hack, 8-bit pixel grid, first/next frame interface @@ -58,22 +63,29 @@ void random_colors(void); /* why strip bit? */ #define R (ya_random()&((1<<30)-1)) -int frame = 0, epoch_time; -ushort *r1, *r2, *r1b, *r2b; -int width, height, npix; -int radius; -int reaction = 0; -int diffusion = 0; +static int frame = 0, epoch_time; +static ushort *r1, *r2, *r1b, *r2b; +static int width, height, npix; +static int radius; +static int reaction = 0; +static int diffusion = 0; /* returns number of pixels that the pixack produces. called once. */ -void -pixack_init(int *size_h, int *size_v) { +static void +pixack_init(int *size_h, int *size_v) +{ int sz_base; width = get_integer_resource ("width", "Integer"); height = get_integer_resource ("height", "Integer"); sz_base = 80 + (R%40); if (width <= 0) width = (R%20) ? sz_base : (28 + R%10); if (height <= 0) height = (R%20) ? sz_base : (28 + R%10); + + /* jwz: when (and only when) XSHM is in use on an SGI 8-bit visual, + we get shear unless width is a multiple of 4. I don't understand + why. This is undoubtedly the wrong fix... */ + width &= ~0x7; + /* don't go there */ if (width < 10) width = 10; if (height < 10) height = 10; @@ -97,8 +109,9 @@ pixack_init(int *size_h, int *size_v) { /* returns the pixels. called many times. */ -void -pixack_frame(char *pix_buf) { +static void +pixack_frame(char *pix_buf) +{ int i, j; int w2 = width + 2; ushort *t; @@ -126,10 +139,10 @@ pixack_frame(char *pix_buf) { if (!(frame%epoch_time)) { int s; if (0 != frame) { - int t = epoch_time / 500; - if (t > 15) - t = 15; - sleep(t); + int tt = epoch_time / 500; + if (tt > 15) + tt = 15; + sleep(tt); } for (i = 0; i < npix; i++) { @@ -185,7 +198,8 @@ pixack_frame(char *pix_buf) { int ii = i + 1; char *q = pix_buf + width * i; short *qq = ((short *) pix_buf) + width * i; - long *qqq = ((long *) pix_buf) + width * i; +/* long *qqq = ((long *) pix_buf) + width * i; -- crashes on Alpha */ + int *qqq = ((int *) pix_buf) + width * i; ushort *i1 = r1 + 1 + w2 * ii; ushort *i2 = r2 + 1 + w2 * ii; ushort *o1 = r1b + 1 + w2 * ii; @@ -282,8 +296,8 @@ char *progclass = "RD"; char *defaults [] = { - "RD.background: black", /* to placate SGI */ - "RD.foreground: white", + ".background: black", + ".foreground: white", "*width: 0", /* tried to use -1 but it complained */ "*height: 0", "*epoch: 40000", @@ -292,9 +306,12 @@ char *defaults [] = { "*verbose: off", "*radius: -1", "*speed: 0.0", - "*size: 0.66", + "*size: 1.0", "*delay: 1", "*colors: -1", +#ifdef HAVE_XSHM_EXTENSION + "*useSHM: True", +#endif /* HAVE_XSHM_EXTENSION */ 0 }; @@ -310,22 +327,17 @@ XrmOptionDescRec options [] = { { "-size", ".size", XrmoptionSepArg, 0 }, { "-delay", ".delay", XrmoptionSepArg, 0 }, { "-ncolors", ".colors", XrmoptionSepArg, 0 }, +#ifdef HAVE_XSHM_EXTENSION + { "-shm", ".useSHM", XrmoptionNoArg, "True" }, + { "-no-shm", ".useSHM", XrmoptionNoArg, "False" }, +#endif /* HAVE_XSHM_EXTENSION */ { 0, 0, 0, 0 } }; -/* why doesn't this work??? and more importantly, do i really still have - to do this in X? */ - -#ifdef HAVE_XSHM_EXTENSION -#include -#include -#include -#endif - - -void -random_colors() { +static void +random_colors(void) +{ memset(colors, 0, ncolors*sizeof(*colors)); make_smooth_colormap (display, visual, cmap, colors, &ncolors, True, 0, True); @@ -368,12 +380,11 @@ screenhack (Display *dpy, Window win) double array_x, array_y; double array_dx, array_dy; int w2; - char *p; + char *pd; int vdepth; int npix; - int *m = 0; #ifdef HAVE_XSHM_EXTENSION - int use_shm = 0; + Bool use_shm = get_boolean_resource("useSHM", "Boolean"); XShmSegmentInfo shm_info; #endif @@ -404,6 +415,11 @@ screenhack (Display *dpy, Window win) array_y = (xgwa.height - array_height)/2; array_dx = p; array_dy = .31415926 * p; + + /* start in a random direction */ + if (random() & 1) array_dx = -array_dx; + if (random() & 1) array_dy = -array_dy; + } verbose = get_boolean_resource ("verbose", "Boolean"); npix = (width + 2) * (height + 2); @@ -421,6 +437,40 @@ screenhack (Display *dpy, Window win) vdepth <= 16 ? 16 : 32); + /* Ok, this like, sucks and stuff. There are some XFree86 systems + that have depth-24 visuals, that do not accept depth-32 XImages! + Which if you ask me is just absurd, since all it would take is + for the server to truncate the bits in that case. So, this crap + here detects the specific case of: we have chosen depth 32; + and the server does not support depth 32. In that case, we + try and use depth 16 instead. + + The real fix would be to rewrite this program to deal with + depth 24 directly (or even better, arbitrary depths, but that + would mean going through the XImage routines instead of messing + with the XImage->data directly.) + + jwz, 18-Mar-99: well, the X servers I have access to these days do + support 32-deep images on deep visuals, so I no longer have the + ability to test this code -- but it was causing problems on the + visuals that I do have, and I think that's because I mistakenly + wrote `pfv[i].depth' when I meant to write `pfv[i].bits_per_pixel'. + The symptom I was seeing was that the grid was 64x64, but the + images were being drawn 32x32 -- so there was a black stripe on + every other row. Wow, this code sucks so much. + */ + if (pdepth == 32) + { + int i, pfvc = 0; + Bool ok = False; + XPixmapFormatValues *pfv = XListPixmapFormats (dpy, &pfvc); + for (i = 0; i < pfvc; i++) + if (pfv[i].bits_per_pixel == pdepth) + ok = True; + if (!ok) + pdepth = 16; + } + cmap = xgwa.colormap; ncolors = get_integer_resource ("colors", "Integer"); @@ -442,72 +492,91 @@ screenhack (Display *dpy, Window win) int i, di; mc = (unsigned char *) malloc(1<<16); for (i = 0; i < (1<<16); i++) { - di = (i + (ya_random()&255))>>8; + di = (i + (random()&255))>>8; if (di > 255) di = 255; mc[i] = di; } } - p = malloc(npix * (pdepth == 1 ? 1 : (pdepth / 8))); - if (!p) { + pd = malloc(npix * (pdepth == 1 ? 1 : (pdepth / 8))); + if (!pd) { fprintf(stderr, "not enough memory for %d pixels.\n", npix); exit(1); } + image = 0; + #ifdef HAVE_XSHM_EXTENSION - if (use_shm) { - printf("p=%X\n", p); - free(p); - image = XShmCreateImage(dpy, xgwa.visual, vdepth, - ZPixmap, 0, &shm_info, width, height); - shm_info.shmid = shmget(IPC_PRIVATE, - image->bytes_per_line * image->height, - IPC_CREAT | 0777); - if (shm_info.shmid == -1) - printf ("shmget failed!"); - shm_info.readOnly = False; - p = shmat(shm_info.shmid, 0, 0); - printf("p=%X %d\n", p, image->bytes_per_line); - XShmAttach(dpy, &shm_info); - XSync(dpy, False); - } else -#endif - image = XCreateImage(dpy, xgwa.visual, vdepth, - ZPixmap, 0, p, - width, height, 8, 0); + if (use_shm) + { + image = create_xshm_image(dpy, xgwa.visual, vdepth, + ZPixmap, 0, &shm_info, width, height); + if (!image) + use_shm = False; + else + { + free(pd); + pd = image->data; + } + } +#endif /* HAVE_XSHM_EXTENSION */ + + if (!image) + { + image = XCreateImage(dpy, xgwa.visual, vdepth, + ZPixmap, 0, pd, + width, height, 8, 0); + } while (1) { + Bool bump = False; + int i, j; - pixack_frame(p); + pixack_frame(pd); for (i = 0; i < array_width; i += width) for (j = 0; j < array_height; j += height) #ifdef HAVE_XSHM_EXTENSION if (use_shm) - XShmPutImage(dpy, win, gc, image, 0, 0, i, j, + XShmPutImage(dpy, win, gc, image, 0, 0, i+array_x, j+array_y, width, height, False); else #endif - XPutImage(dpy, win, gc, image, 0, 0, i+array_x, j+array_y, width, height); + XPutImage(dpy, win, gc, image, 0, 0, i+array_x, j+array_y, + width, height); array_x += array_dx; array_y += array_dy; if (array_x < 0) { array_x = 0; array_dx = -array_dx; + bump = True; } else if (array_x > (xgwa.width - array_width)) { array_x = (xgwa.width - array_width); array_dx = -array_dx; + bump = True; } if (array_y < 0) { array_y = 0; array_dy = -array_dy; + bump = True; } else if (array_y > (xgwa.height - array_height)) { array_y = (xgwa.height - array_height); array_dy = -array_dy; + bump = True; } + + if (bump) { + if (random() & 1) { + double swap = array_dx; + array_dx = array_dy; + array_dy = swap; + } + } + frame++; XSync(dpy, False); + screenhack_handle_events (dpy); if (delay > 0) usleep(1000 * delay); }