272
XGetWindowAttributes (display, window, &xgwa);
274
originalcolors = get_boolean_resource ("originalcolors", "Boolean");
276
count = get_integer_resource ("count", "Integer");
277
if (count < 2) count = 2;
280
XGetWindowAttributes (st->dpy, st->window, &xgwa);
282
st->originalcolors = get_boolean_resource (st->dpy, "originalcolors", "Boolean");
284
st->count = get_integer_resource (st->dpy, "count", "Integer");
285
if (st->count < 2) st->count = 2;
279
287
/* number of colors can't be greater than the half depth of the screen. */
280
if (count > (1L << (xgwa.depth-1)))
281
count = (1L << (xgwa.depth-1));
288
if (st->count > (unsigned int) (1L << (xgwa.depth-1)))
289
st->count = (unsigned int) (1L << (xgwa.depth-1));
283
291
/* Actually, since cell->col is of type char, this has to be small. */
284
if (count >= (1L << ((sizeof(arr[0].col) * 8) - 1)))
285
count = (1L << ((sizeof(arr[0].col) * 8) - 1));
288
if (originalcolors && (count > 8))
293
coloredGCs = (GC *) calloc (sizeof(GC), count * 2);
295
diaglim = get_float_resource ("diaglim", "Float");
300
else if (diaglim > 2.0)
306
anychan = get_float_resource ("anychan", "Float");
311
else if (anychan > 1.0)
316
minorchan = get_float_resource ("minorchan","Float");
321
else if (minorchan > 1.0)
326
instantdeathchan = get_float_resource ("instantdeathchan","Float");
327
if (instantdeathchan < 0.0)
329
instantdeathchan = 0.0;
331
else if (instantdeathchan > 1.0)
333
instantdeathchan = 1.0;
336
minlifespan = get_integer_resource ("minlifespan", "Integer");
342
maxlifespan = get_integer_resource ("maxlifespan", "Integer");
343
if (maxlifespan < minlifespan)
345
maxlifespan = minlifespan;
348
minlifespeed = get_float_resource ("minlifespeed", "Float");
349
if (minlifespeed < 0.0)
353
else if (minlifespeed > 1.0)
358
maxlifespeed = get_float_resource ("maxlifespeed", "Float");
359
if (maxlifespeed < minlifespeed)
361
maxlifespeed = minlifespeed;
363
else if (maxlifespeed > 1.0)
368
mindeathspeed = get_float_resource ("mindeathspeed", "Float");
369
if (mindeathspeed < 0.0)
373
else if (mindeathspeed > 1.0)
378
maxdeathspeed = get_float_resource ("maxdeathspeed", "Float");
379
if (maxdeathspeed < mindeathspeed)
381
maxdeathspeed = mindeathspeed;
383
else if (maxdeathspeed > 1.0)
388
minlifespeed *= diaglim;
389
maxlifespeed *= diaglim;
390
mindeathspeed *= diaglim;
391
maxdeathspeed *= diaglim;
292
if (st->count >= (unsigned int) (1L << ((sizeof(st->arr[0].col) * 8) - 1)))
293
st->count = (unsigned int) (1L << ((sizeof(st->arr[0].col) * 8) - 1));
296
if (st->originalcolors && (st->count > 8))
301
st->coloredGCs = (GC *) calloc (sizeof(GC), st->count * 2);
303
st->diaglim = get_float_resource (st->dpy, "diaglim", "Float");
304
if (st->diaglim < 1.0)
308
else if (st->diaglim > 2.0)
312
st->diaglim *= st->orthlim;
314
st->anychan = get_float_resource (st->dpy, "anychan", "Float");
315
if (st->anychan < 0.0)
319
else if (st->anychan > 1.0)
324
st->minorchan = get_float_resource (st->dpy, "minorchan","Float");
325
if (st->minorchan < 0.0)
329
else if (st->minorchan > 1.0)
334
st->instantdeathchan = get_float_resource (st->dpy, "instantdeathchan","Float");
335
if (st->instantdeathchan < 0.0)
337
st->instantdeathchan = 0.0;
339
else if (st->instantdeathchan > 1.0)
341
st->instantdeathchan = 1.0;
344
st->minlifespan = get_integer_resource (st->dpy, "minlifespan", "Integer");
345
if (st->minlifespan < 1)
350
st->maxlifespan = get_integer_resource (st->dpy, "maxlifespan", "Integer");
351
if (st->maxlifespan < st->minlifespan)
353
st->maxlifespan = st->minlifespan;
356
st->minlifespeed = get_float_resource (st->dpy, "minlifespeed", "Float");
357
if (st->minlifespeed < 0.0)
359
st->minlifespeed = 0.0;
361
else if (st->minlifespeed > 1.0)
363
st->minlifespeed = 1.0;
366
st->maxlifespeed = get_float_resource (st->dpy, "maxlifespeed", "Float");
367
if (st->maxlifespeed < st->minlifespeed)
369
st->maxlifespeed = st->minlifespeed;
371
else if (st->maxlifespeed > 1.0)
373
st->maxlifespeed = 1.0;
376
st->mindeathspeed = get_float_resource (st->dpy, "mindeathspeed", "Float");
377
if (st->mindeathspeed < 0.0)
379
st->mindeathspeed = 0.0;
381
else if (st->mindeathspeed > 1.0)
383
st->mindeathspeed = 1.0;
386
st->maxdeathspeed = get_float_resource (st->dpy, "maxdeathspeed", "Float");
387
if (st->maxdeathspeed < st->mindeathspeed)
389
st->maxdeathspeed = st->mindeathspeed;
391
else if (st->maxdeathspeed > 1.0)
393
st->maxdeathspeed = 1.0;
396
st->minlifespeed *= st->diaglim;
397
st->maxlifespeed *= st->diaglim;
398
st->mindeathspeed *= st->diaglim;
399
st->maxdeathspeed *= st->diaglim;
393
401
cmap = xgwa.colormap;
395
windowWidth = xgwa.width;
396
windowHeight = xgwa.height;
403
st->windowWidth = xgwa.width;
404
st->windowHeight = xgwa.height;
398
arr_width = windowWidth / cell_size;
399
arr_height = windowHeight / cell_size;
406
st->arr_width = st->windowWidth / cell_size;
407
st->arr_height = st->windowHeight / cell_size;
401
alloc_size = sizeof(cell) * arr_width * arr_height;
409
alloc_size = sizeof(cell) * st->arr_width * st->arr_height;
402
410
oalloc = alloc_size;
404
412
if (mem_throttle > 0)
405
while (cell_size < windowWidth/10 &&
406
cell_size < windowHeight/10 &&
413
while (cell_size < st->windowWidth/10 &&
414
cell_size < st->windowHeight/10 &&
407
415
alloc_size > mem_throttle)
410
arr_width = windowWidth / cell_size;
411
arr_height = windowHeight / cell_size;
412
alloc_size = sizeof(cell) * arr_width * arr_height;
418
st->arr_width = st->windowWidth / cell_size;
419
st->arr_height = st->windowHeight / cell_size;
420
alloc_size = sizeof(cell) * st->arr_width * st->arr_height;
415
423
if (osize != cell_size)
417
static int warned = 0;
421
428
"%s: throttling cell size from %d to %d because of %dM limit.\n",
422
429
progname, osize, cell_size, mem_throttle / (1 << 20));
423
430
fprintf (stderr, "%s: %dx%dx%d = %.1fM, %dx%dx%d = %.1fM.\n",
425
windowWidth, windowHeight, osize,
432
st->windowWidth, st->windowHeight, osize,
426
433
((float) oalloc) / (1 << 20),
427
windowWidth, windowHeight, cell_size,
434
st->windowWidth, st->windowHeight, cell_size,
428
435
((float) alloc_size) / (1 << 20));
433
xSize = windowWidth / arr_width;
434
ySize = windowHeight / arr_height;
440
st->xSize = st->arr_width ? st->windowWidth / st->arr_width : 0;
441
st->ySize = st->arr_height ? st->windowHeight / st->arr_height : 0;
442
if (st->xSize > st->ySize)
444
st->xSize = st->ySize;
448
st->ySize = st->xSize;
444
xOffset = (windowWidth - (arr_width * xSize)) / 2;
445
yOffset = (windowHeight - (arr_height * ySize)) / 2;
451
st->xOffset = (st->windowWidth - (st->arr_width * st->xSize)) / 2;
452
st->yOffset = (st->windowHeight - (st->arr_height * st->ySize)) / 2;
454
if (st->originalcolors)
449
setup_original_colormap (&xgwa);
456
setup_original_colormap (st, &xgwa);
453
setup_random_colormap (&xgwa);
460
setup_random_colormap (st, &xgwa);
457
static void drawblock (int x, int y, unsigned char c)
464
static void drawblock (struct state *st, int x, int y, unsigned char c)
459
if (xSize == 1 && ySize == 1)
460
XDrawPoint (display, window, coloredGCs[c], x + xOffset, y + yOffset);
466
if (st->xSize == 1 && st->ySize == 1)
467
XDrawPoint (st->dpy, st->window, st->coloredGCs[c], x + st->xOffset, y + st->yOffset);
462
XFillRectangle (display, window, coloredGCs[c],
463
x * xSize + xOffset, y * ySize + yOffset,
469
XFillRectangle (st->dpy, st->window, st->coloredGCs[c],
470
x * st->xSize + st->xOffset, y * st->ySize + st->yOffset,
471
st->xSize, st->ySize);
467
static void setup_arr (void)
474
static void setup_arr (struct state *st)
476
XFillRectangle (display, window, coloredGCs[0], 0, 0,
477
windowWidth, windowHeight);
483
XFillRectangle (st->dpy, st->window, st->coloredGCs[0], 0, 0,
484
st->windowWidth, st->windowHeight);
486
if (!st->arr_width) st->arr_width = 1;
487
if (!st->arr_height) st->arr_height = 1;
479
arr = (cell *) calloc (sizeof(cell), arr_width * arr_height);
489
st->arr = (cell *) calloc (sizeof(cell), st->arr_width * st->arr_height);
482
492
fprintf (stderr, "%s: out of memory allocating %dx%d grid\n",
483
progname, arr_width, arr_height);
493
progname, st->arr_width, st->arr_height);
487
for (y = 0; y < arr_height; y++)
497
for (y = 0; y < st->arr_height; y++)
489
int row = y * arr_width;
490
for (x = 0; x < arr_width; x++)
499
int row = y * st->arr_width;
500
for (x = 0; x < st->arr_width; x++)
492
arr[row+x].speed = 0.0;
493
arr[row+x].growth = 0.0;
495
arr[row+x].isnext = 0;
502
st->arr[row+x].speed = 0.0;
503
st->arr[row+x].growth = 0.0;
504
st->arr[row+x].col = 0;
505
st->arr[row+x].isnext = 0;
506
st->arr[row+x].next = 0;
507
st->arr[row+x].prev = 0;
511
if (st->head == NULL)
503
head = (cell *) malloc (sizeof (cell));
513
st->head = (cell *) malloc (sizeof (cell));
516
if (st->tail == NULL)
508
tail = (cell *) malloc (sizeof (cell));
518
st->tail = (cell *) malloc (sizeof (cell));
521
st->head->next = st->tail;
522
st->head->prev = st->head;
523
st->tail->next = st->tail;
524
st->tail->prev = st->head;
516
blastcount = random_life_value ();
526
st->blastcount = random_life_value (st);
519
static void newcell (cell *c, unsigned char col, FLOAT sp)
529
static void newcell (struct state *st, cell *c, unsigned char col, FLOAT sp)
582
int x = random () % arr_width;
583
int y = random () % arr_height;
592
int x = st->arr_width ? random () % st->arr_width : 0;
593
int y = st->arr_height ? random () % st->arr_height : 0;
589
s = RAND_FLOAT * (maxdeathspeed - mindeathspeed) + mindeathspeed;
599
s = RAND_FLOAT * (st->maxdeathspeed - st->mindeathspeed) + st->mindeathspeed;
593
c = (random () % (count-1)) + 1;
594
s = RAND_FLOAT * (maxlifespeed - minlifespeed) + minlifespeed;
603
c = ((st->count - 1) ? random () % (st->count-1) : 0) + 1;
604
s = RAND_FLOAT * (st->maxlifespeed - st->minlifespeed) + st->minlifespeed;
596
newcell (&arr[y * arr_width + x], c, s);
606
newcell (st, &st->arr[y * st->arr_width + x], c, s);
600
static void update (void)
610
static void update (struct state *st)
604
for (a = head->next; a != tail; a = a->next)
614
for (a = st->head->next; a != st->tail; a = a->next)
606
static XPoint all_coords[] = {{-1, -1}, {-1, 1}, {1, -1}, {1, 1},
607
{-1, 0}, { 1, 0}, {0, -1}, {0, 1},
616
static const XPoint all_coords[] = {{-1, -1}, {-1, 1}, {1, -1}, {1, 1},
617
{-1, 0}, { 1, 0}, {0, -1}, {0, 1},
620
const XPoint *coords = 0;
612
622
if (a->speed == 0) continue;
613
623
a->growth += a->speed;
615
if (a->growth >= diaglim)
625
if (a->growth >= st->diaglim)
617
627
coords = all_coords;
619
else if (a->growth >= orthlim)
629
else if (a->growth >= st->orthlim)
621
631
coords = &all_coords[4];