Esempio n. 1
0
ENTRYPOINT void init_antmaze(ModeInfo * mi) 
{
  double rot_speed = 0.3;
  int i;

  antmazestruct *mp;
  
  if (antmaze == NULL) {
	if ((antmaze = (antmazestruct *) calloc(MI_NUM_SCREENS(mi),
						sizeof (antmazestruct))) == NULL)
	  return;
  }
  mp = &antmaze[MI_SCREEN(mi)];
  mp->step = NRAND(90);
  mp->ant_position = NRAND(90);


  mp->antdirection[0] = PI/2.0;
  mp->antdirection[1] = PI/2.0;
  mp->antdirection[2] = 0;
  mp->antdirection[3] = PI/2.0;
  mp->antdirection[4] = PI/2.0;

  mp->antposition[0][0] = -4.0;
  mp->antposition[0][1] =  5.0;
  mp->antposition[0][1] =  0.15;

  mp->antposition[1][0] = -4.0;
  mp->antposition[1][1] =  3.0;
  mp->antposition[1][1] =  0.15;

  mp->antposition[2][0] = -1.0;
  mp->antposition[2][1] = -2.0;
  mp->antposition[2][1] =  0.15;

  mp->antposition[3][0] = -3.9;
  mp->antposition[3][1] =  6.0;
  mp->antposition[3][1] =  0.15;

  mp->antposition[4][0] =  2.0;
  mp->antposition[4][1] = -2.0;
  mp->antposition[4][1] =  0.15;

  

  for (i = 0; i < ANTCOUNT; i++) {
    mp->antvelocity[i] = 0.02;
    mp->antsize[i] = 1.0;
    mp->anton[i] = 0;
  }

  mp->bposition[0][0] = 0;
  mp->bposition[0][1] = 8;

  mp->bposition[1][0] = 9;
  mp->bposition[1][1] = 1;

  mp->bposition[2][0] = 1;
  mp->bposition[2][1] = 1;

  mp->bposition[3][0] = 4;
  mp->bposition[3][1] = 8;

  mp->bposition[4][0] = 2;
  mp->bposition[4][1] = 1;

  mp->part[0] = 0;
  mp->part[1] = 1;
  mp->part[2] = 5;
  mp->part[3] = 1;
  mp->part[4] = 3;

  mp->introduced = 0;
  mp->entroducing = 12;
  mp->fadeout = 1.0;
  mp->mag = 4.0;

  mp->rot = make_rotator (rot_speed, rot_speed, rot_speed, 1, 0, True);
  mp->trackball = gltrackball_init ();
  
  if ((mp->glx_context = init_GL(mi)) != NULL) {
    reshape_antmaze(mi, MI_WIDTH(mi), MI_HEIGHT(mi));
    glDrawBuffer(GL_BACK);
    pinit(mp);
  } 
  else
    MI_CLEARWINDOW(mi);
}
Esempio n. 2
0
ENTRYPOINT void
init_rotor (ModeInfo * mi)
{
	int         x;
	elem       *pelem;
	unsigned char wasiconified;
	rotorstruct *rp;

	if (rotors == NULL) {
		if ((rotors = (rotorstruct *) calloc(MI_NUM_SCREENS(mi),
					      sizeof (rotorstruct))) == NULL)
			return;
	}
	rp = &rotors[MI_SCREEN(mi)];

#ifdef HAVE_COCOA
    jwxyz_XSetAntiAliasing (MI_DISPLAY(mi), MI_GC(mi),  False);
#endif

	rp->prevcenterx = rp->centerx;
	rp->prevcentery = rp->centery;

	rp->centerx = MI_WIDTH(mi) / 2;
	rp->centery = MI_HEIGHT(mi) / 2;

	rp->redrawing = 0;
	/*
	 * sometimes, you go into iconified view, only to see a really whizzy pattern
	 * that you would like to look more closely at. Normally, clicking in the
	 * icon reinitializes everything - but I don't, cuz I'm that kind of guy.
	 * HENCE, the wasiconified stuff you see here.
	 */

	wasiconified = rp->iconifiedscreen;
	rp->iconifiedscreen = MI_IS_ICONIC(mi);

	if (wasiconified && !rp->iconifiedscreen)
		rp->firsttime = True;
	else {

		/* This is a fudge is needed since prevcenter may not be set when it comes
		   from the the random mode and return is pressed (and its not the first
		   mode that was running). This assumes that the size of the lock screen
		   window / size of the icon window = 12 */
		if (!rp->prevcenterx)
			rp->prevcenterx = rp->centerx * 12;
		if (!rp->prevcentery)
			rp->prevcentery = rp->centery * 12;

		rp->num = MI_COUNT(mi);
		if (rp->num < 0) {
			rp->num = NRAND(-rp->num) + 1;
			if (rp->elements != NULL) {
				(void) free((void *) rp->elements);
				rp->elements = (elem *) NULL;
			}
		}
		if (rp->elements == NULL)
			if ((rp->elements = (elem *) calloc(rp->num,
					sizeof (elem))) == NULL) {
				free_rotor(rp);
				return;
			}
		rp->nsave = MI_CYCLES(mi);
		if (rp->nsave <= 1)
			rp->nsave = 2;
		if (rp->save == NULL)
			if ((rp->save = (XPoint *) malloc(rp->nsave *
					sizeof (XPoint))) == NULL) {
				free_rotor(rp);
				return;
			}
		for (x = 0; x < rp->nsave; x++) {
			rp->save[x].x = rp->centerx;
			rp->save[x].y = rp->centery;
		}

		pelem = rp->elements;

		for (x = rp->num; --x >= 0; pelem++) {
			pelem->radius_drift_max = 1.0;
			pelem->radius_drift_now = 1.0;

			pelem->end_radius = 100.0;

			pelem->ratio_drift_max = 1.0;
			pelem->ratio_drift_now = 1.0;
			pelem->end_ratio = 10.0;
		}
		if (MI_NPIXELS(mi) > 2)
			rp->pix = NRAND(MI_NPIXELS(mi));

		rp->rotor = 0;
		rp->prev = 1;
		rp->lastx = rp->centerx;
		rp->lasty = rp->centery;
		rp->angle = (float) NRAND((long) MAXANGLE) / 3.0;
		rp->forward = rp->firsttime = True;
	}
	rp->linewidth = MI_SIZE(mi);

	if (rp->linewidth == 0)
		rp->linewidth = 1;
	if (rp->linewidth < 0)
		rp->linewidth = NRAND(-rp->linewidth) + 1;

	MI_CLEARWINDOW(mi);
}
Esempio n. 3
0
ENTRYPOINT void
init_flow (ModeInfo * mi)
{
    flowstruct *sp;
    char       *name;

    if (flows == NULL) {
        if ((flows = (flowstruct *) calloc(MI_NUM_SCREENS(mi),
                                           sizeof (flowstruct))) == NULL)
            return;
    }
    sp = &flows[MI_SCREEN(mi)];

    sp->count2 = 0;

    sp->taillen = MI_SIZE(mi);
    if (sp->taillen < -MINTRAIL) {
        /* Change by sqrt so it seems more variable */
        sp->taillen = NRAND((int)sqrt((double) (-sp->taillen - MINTRAIL + 1)));
        sp->taillen = sp->taillen * sp->taillen + MINTRAIL;
    } else if (sp->taillen < MINTRAIL) {
        sp->taillen = MINTRAIL;
    }

    if(!rotatep && !ridep) rotatep = True; /* We need at least one viewpoint */

    /* Start camera at Orbit or Bee */
    if(rotatep) {
        sp->chaseto = ORBIT;
    } else {
        sp->chaseto = BEE;
    }
    sp->chasetime = 1; /* Go directly to target */

    sp->lyap = 0;
    sp->yperiod = 0;
    sp->step2 = INITIALSTEP;

    /* Zero parameter set */
    memset(sp->par2, 0, N_PARS * sizeof(dvector));

    /* Set up standard examples */
    switch (NRAND((periodicp) ? 5 : 3)) {
    case 0:
        /*
          x' = a(y - x)
          y' = x(b - z) - y
          z' = xy - cz
         */
        name = "Lorentz";
        sp->par2[Y].x = 10 + balance_rand(5*0); /* a */
        sp->par2[X].x = - sp->par2[Y].x;        /* -a */
        sp->par2[X].y = 28 + balance_rand(5*0); /* b */
        sp->par2[XZ].y = -1;
        sp->par2[Y].y = -1;
        sp->par2[XY].z = 1;
        sp->par2[Z].z = - 2 + balance_rand(1*0); /* -c */
        break;
    case 1:
        /*
          x' = -(y + az)
          y' = x + by
          z' = c + z(x - 5.7)
         */
        name = "Rossler";
        sp->par2[Y].x = -1;
        sp->par2[Z].x = -2 + balance_rand(1); /* a */
        sp->par2[X].y = 1;
        sp->par2[Y].y = 0.2 + balance_rand(0.1); /* b */
        sp->par2[C].z = 0.2 + balance_rand(0.1); /* c */
        sp->par2[XZ].z = 1;
        sp->par2[Z].z = -5.7;
        break;
    case 2:
        /*
          x' = -(y + az)
          y' = x + by - cz^2
          z' = 0.2 + z(x - 5.7)
         */
        name = "RosslerCone";
        sp->par2[Y].x = -1;
        sp->par2[Z].x = -2; /* a */
        sp->par2[X].y = 1;
        sp->par2[Y].y = 0.2; /* b */
        sp->par2[ZZ].y = -0.331 + balance_rand(0.01); /* c */
        sp->par2[C].z = 0.2;
        sp->par2[XZ].z = 1;
        sp->par2[Z].z = -5.7;
        break;
    case 3:
        /*
          x' = -z + b sin(y)
          y' = c
          z' = 0.7x + az(0.1 - x^2)
         */
        name = "Birkhoff";
        sp->par2[Z].x = -1;
        sp->par2[SINY].x = 0.35 + balance_rand(0.25); /* b */
        sp->par2[C].y = 1.57; /* c */
        sp->par2[X].z = 0.7;
        sp->par2[Z].z = 1 + balance_rand(0.5); /* a/10 */
        sp->par2[XXZ].z = -10 * sp->par2[Z].z; /* -a */
        sp->yperiod = 2 * M_PI;
        break;
    default:
        /*
          x' = -ax - z/2 - z^3/8 + b sin(y)
          y' = c
          z' = 2x
         */
        name = "Duffing";
        sp->par2[X].x = -0.2 + balance_rand(0.1); /* a */
        sp->par2[Z].x = -0.5;
        sp->par2[ZZZ].x = -0.125;
        sp->par2[SINY].x = 27.0 + balance_rand(3.0); /* b */
        sp->par2[C].y = 1.33; /* c */
        sp->par2[X].z = 2;
        sp->yperiod = 2 * M_PI;
        break;

    }

    sp->range.x = 5;
    sp->range.z = 5;

    if(sp->yperiod > 0) {
        sp->ODE = Periodic;
        /* periodic flows show either uniform distribution or a
           snapshot on the 'time' axis */
        sp->range.y = NRAND(2)? sp->yperiod : 0;
    } else {
        sp->range.y = 5;
        sp->ODE = Cubic;
    }

    /* Run discoverer to set up bounding box, etc.  Lyapunov will
       probably be innaccurate, since we're only running it once, but
       we're using known strange attractors so it should be ok. */
    discover(mi);
    if(MI_IS_VERBOSE(mi))
        fprintf(stdout,
                "flow: Lyapunov exponent: %g, step: %g, size: %g (%s)\n",
                sp->lyap2, sp->step2, sp->size2, name);
    /* Install new params */
    sp->lyap = sp->lyap2;
    sp->size = sp->size2;
    sp->mid = sp->mid2;
    sp->step = sp->step2;
    memcpy(sp->par, sp->par2, sizeof(sp->par2));

    sp->count2 = 0; /* Reset search */

    free_flow(sp);
    sp->beecount = MI_COUNT(mi);
    if (sp->beecount < 0) {	/* random variations */
        sp->beecount = NRAND(-sp->beecount) + 1; /* Minimum 1 */
    }

# ifdef HAVE_COCOA	/* Don't second-guess Quartz's double-buffering */
    dbufp = False;
# endif

    if(dbufp) { /* Set up double buffer */
        if (sp->buffer != None)
            XFreePixmap(MI_DISPLAY(mi), sp->buffer);
        sp->buffer = XCreatePixmap(MI_DISPLAY(mi), MI_WINDOW(mi),
                                   MI_WIDTH(mi), MI_HEIGHT(mi), MI_DEPTH(mi));
    } else {
        sp->buffer = MI_WINDOW(mi);
    }
    /* no "NoExpose" events from XCopyArea wanted */
    XSetGraphicsExposures(MI_DISPLAY(mi), MI_GC(mi), False);

    /* Make sure we're using 'thin' lines */
    XSetLineAttributes(MI_DISPLAY(mi), MI_GC(mi), 0, LineSolid, CapNotLast,
                       JoinMiter);

    /* Clear the background (may be slow depending on user prefs). */
    MI_CLEARWINDOW(mi);

    /* Allocate memory. */
    if (sp->csegs == NULL) {
        allocate(sp->csegs, XSegment,
                 (sp->beecount + BOX_L) * MI_NPIXELS(mi) * sp->taillen);
        allocate(sp->cnsegs, int, MI_NPIXELS(mi));
        allocate(sp->old_segs, XSegment, sp->beecount * sp->taillen);
        allocate(sp->p, dvector, sp->beecount * sp->taillen);
    }
Esempio n. 4
0
void
init_tik_tak(ModeInfo * mi)
{
	Display    *display = MI_DISPLAY(mi);
	Window      window = MI_WINDOW(mi);
	int         i, max_objects, size_object;
	tik_takstruct *tiktak;

/* initialize */
	if (tik_taks == NULL) {
		if ((tik_taks = (tik_takstruct *) calloc(MI_NUM_SCREENS(mi),
				sizeof (tik_takstruct))) == NULL)
			return;
	}
	tiktak = &tik_taks[MI_SCREEN(mi)];
	tiktak->mi = mi;

	if (tiktak->gc == None) {
		if (MI_IS_INSTALL(mi) && MI_NPIXELS(mi) > 2) {
			XColor      color;

#ifndef STANDALONE
			tiktak->fg = MI_FG_PIXEL(mi);
			tiktak->bg = MI_BG_PIXEL(mi);
#endif
			tiktak->blackpixel = MI_BLACK_PIXEL(mi);
			tiktak->whitepixel = MI_WHITE_PIXEL(mi);
			if ((tiktak->cmap = XCreateColormap(display, window,
					MI_VISUAL(mi), AllocNone)) == None) {
				free_tik_tak(display, tiktak);
				return;
			}
			XSetWindowColormap(display, window, tiktak->cmap);
			(void) XParseColor(display, tiktak->cmap, "black", &color);
			(void) XAllocColor(display, tiktak->cmap, &color);
			MI_BLACK_PIXEL(mi) = color.pixel;
			(void) XParseColor(display, tiktak->cmap, "white", &color);
			(void) XAllocColor(display, tiktak->cmap, &color);
			MI_WHITE_PIXEL(mi) = color.pixel;
#ifndef STANDALONE
			(void) XParseColor(display, tiktak->cmap, background, &color);
			(void) XAllocColor(display, tiktak->cmap, &color);
			MI_BG_PIXEL(mi) = color.pixel;
			(void) XParseColor(display, tiktak->cmap, foreground, &color);
			(void) XAllocColor(display, tiktak->cmap, &color);
			MI_FG_PIXEL(mi) = color.pixel;
#endif
			tiktak->colors = (XColor *) NULL;
			tiktak->ncolors = 0;
		}
		if ((tiktak->gc = XCreateGC(display, MI_WINDOW(mi),
			     (unsigned long) 0, (XGCValues *) NULL)) == None) {
			free_tik_tak(display, tiktak);
			return;
		}
	}
/* Clear Display */
	MI_CLEARWINDOW(mi);
	tiktak->painted = False;
	XSetFunction(display, tiktak->gc, GXxor);


/*Set up tik_tak data */
	tiktak->direction = (LRAND() & 1) ? 1 : -1;
	tiktak->win_width = MI_WIDTH(mi);
	tiktak->win_height = MI_HEIGHT(mi);
	tiktak->num_object = MI_COUNT(mi);
        tiktak->x0 = tiktak->win_width / 2;
        tiktak->y0 = tiktak->win_height / 2;
	max_objects = MI_COUNT(mi);
	if (tiktak->num_object == 0) {
		tiktak->num_object = DEF_NUM_OBJECT;
		max_objects = DEF_NUM_OBJECT;
	} else if (tiktak->num_object < 0) {
		max_objects = -tiktak->num_object;
		tiktak->num_object = NRAND(-tiktak->num_object) + 1;
	}
	if (tiktak->object == NULL)
		if ((tiktak->object = (tik_takobject *) calloc(max_objects,
				sizeof (tik_takobject))) == NULL) {
			free_tik_tak(display, tiktak);
			return;
		}
	size_object = MIN( tiktak->win_width , tiktak->win_height) / 3;
	if ( abs( MI_SIZE(mi) ) > size_object) {
	   if ( MI_SIZE( mi ) < 0 )
	     {
		size_object = -size_object;
	     }
	}
   else
     {
	size_object = MI_SIZE(mi);
     }
	if (MI_IS_INSTALL(mi) && MI_NPIXELS(mi) > 2) {
/* Set up colour map */
		if (tiktak->colors != NULL) {
			if (tiktak->ncolors && !tiktak->no_colors)
				free_colors(display, tiktak->cmap, tiktak->colors, tiktak->ncolors);
			free(tiktak->colors);
			tiktak->colors = (XColor *) NULL;
		}
		tiktak->ncolors = MI_NCOLORS(mi);
		if (tiktak->ncolors < 2)
			tiktak->ncolors = 2;
		if (tiktak->ncolors <= 2)
			tiktak->mono_p = True;
		else
			tiktak->mono_p = False;

		if (tiktak->mono_p)
			tiktak->colors = (XColor *) NULL;
		else
			if ((tiktak->colors = (XColor *) malloc(sizeof (*tiktak->colors) *
					(tiktak->ncolors + 1))) == NULL) {
				free_tik_tak(display, tiktak);
				return;
			}
		tiktak->cycle_p = has_writable_cells(mi);
		if (tiktak->cycle_p) {
			if (MI_IS_FULLRANDOM(mi)) {
				if (!NRAND(8))
					tiktak->cycle_p = False;
				else
					tiktak->cycle_p = True;
			} else {
				tiktak->cycle_p = cycle_p;
			}
		}
		if (!tiktak->mono_p) {
			if (!(LRAND() % 10))
				make_random_colormap(
#ifdef STANDALONE
						MI_DISPLAY(mi), MI_WINDOW(mi),
#else
            mi,
#endif
						tiktak->cmap, tiktak->colors, &tiktak->ncolors,
						True, True, &tiktak->cycle_p);
			else if (!(LRAND() % 2))
				make_uniform_colormap(
#ifdef STANDALONE
						MI_DISPLAY(mi), MI_WINDOW(mi),
#else
            mi,
#endif
                  tiktak->cmap, tiktak->colors, &tiktak->ncolors,
						      True, &tiktak->cycle_p);
			else
				make_smooth_colormap(
#ifdef STANDALONE
						MI_DISPLAY(mi), MI_WINDOW(mi),
#else
            mi,
#endif
                 tiktak->cmap, tiktak->colors, &tiktak->ncolors,
						     True, &tiktak->cycle_p);
		}
		XInstallColormap(display, tiktak->cmap);
		if (tiktak->ncolors < 2) {
			tiktak->ncolors = 2;
			tiktak->no_colors = True;
		} else
			tiktak->no_colors = False;
		if (tiktak->ncolors <= 2)
			tiktak->mono_p = True;

		if (tiktak->mono_p)
			tiktak->cycle_p = False;

	}
	for (i = 0; i < tiktak->num_object; i++) {
		tik_takobject *object0;

		object0 = &tiktak->object[i];
		if (MI_IS_INSTALL(mi) && MI_NPIXELS(mi) > 2) {
			if (tiktak->ncolors > 2)
				object0->colour = NRAND(tiktak->ncolors - 2) + 2;
			else
				object0->colour = 1;	/* Just in case */
			XSetForeground(display, tiktak->gc, tiktak->colors[object0->colour].pixel);
		} else {
			if (MI_NPIXELS(mi) > 2)
				object0->colour = MI_PIXEL(mi, NRAND(MI_NPIXELS(mi)));
			else
				object0->colour = 1;	/*Xor'red so WHITE may not be appropriate */
			XSetForeground(display, tiktak->gc, object0->colour);
		}
		object0->angle = NRAND(90) * PI_RAD;
		object0->angle1 = NRAND(90) * PI_RAD;
		object0->velocity_a = (NRAND(7) - 3) * PI_RAD;
		object0->velocity_a1 = (NRAND(7) - 3) * PI_RAD;
		if (size_object == 0)
			object0->size_ob = 9;
		else if (size_object > 0)
			object0->size_ob = size_object;
		else
			object0->size_ob = NRAND(-size_object) + 1;
		object0->size_ob++;
		object0->num_point = NRAND(6)+3;
	   if (LRAND() & 1)
	     object0->size_mult = 1.0;
	   else
	     {
		object0->num_point *= 2;
		object0->size_mult = 1.0 - ( 1.0 / (float) ((LRAND() & 1) +
							    2 ) );
	     }
	   if (object0->xy != NULL)
			free(object0->xy);
	   if ((object0->xy = (XPoint *) malloc(sizeof( XPoint ) *
				(2 * object0->num_point + 2))) == NULL) {
			free_tik_tak(display, tiktak);
			return;
		}
	   if ((LRAND() & 1) || object0->size_ob < 10 )
	     {
		object0->inner = False;
		if ( object0->xy1 != NULL ) free( object0->xy1 );
		object0->xy1 = (XPoint *) NULL;
	     }
	   else
	     {
		object0->inner = True;
	        object0->size_ob1 = object0->size_ob -
		  NRAND( object0->size_ob / 5 ) - 1;
		object0->num_point1 = NRAND(6)+3;
		if (LRAND() & 1)
		  object0->size_mult1 = 1.0;
		else
		  {
		     object0->num_point1 *= 2;
		     object0->size_mult1 = 1.0 -
		        ( 1.0 / (float) ((LRAND() & 1) + 2 ) );
		  }
		if (object0->xy1 != NULL)
			free(object0->xy1);
		if ((object0->xy1 = (XPoint *) malloc(sizeof( XPoint ) *
				(2 * object0->num_point1 + 2))) == NULL) {
			free_tik_tak(display, tiktak);
			return;
		}
		object0->size_mult1 = 1.0;
	     }
		tik_tak_setupobject( mi , object0);
		tik_tak_reset_object( object0);
		tik_tak_drawobject(mi, object0 );
	}
	XFlush(display);
	XSetFunction(display, tiktak->gc, GXcopy);
}
Esempio n. 5
0
ENTRYPOINT void
init_planet (ModeInfo * mi)
{
  planetstruct *gp;
  int screen = MI_SCREEN(mi);
  Bool wire = MI_IS_WIREFRAME(mi);

  if (planets == NULL) {
	if ((planets = (planetstruct *) calloc(MI_NUM_SCREENS(mi),
										  sizeof (planetstruct))) == NULL)
	  return;
  }
  gp = &planets[screen];

  if ((gp->glx_context = init_GL(mi)) != NULL) {
	reshape_planet(mi, MI_WIDTH(mi), MI_HEIGHT(mi));
  }

  {
	//char *f = get_string_resource(mi->dpy, "imageForeground", "Foreground");
	//char *b = get_string_resource(mi->dpy, "imageBackground", "Background");
	char *f = _strdup(imageForeground);
	char *b = _strdup(imageBackground);
	char *s;
	if (!f) f = _strdup("white");
	if (!b) b = _strdup("black");
	
	for (s = f + strlen(f)-1; s > f; s--)
	  if (*s == ' ' || *s == '\t')
		*s = 0;
	for (s = b + strlen(b)-1; s > b; s--)
	  if (*s == ' ' || *s == '\t')
		*s = 0;

    if (!XParseColor(mi->dpy, mi->xgwa.colormap, f, &gp->fg))
      {
		fprintf(stderr, "%s: unparsable color: \"%s\"\n", progname, f);
		exit(1);
      }
    if (!XParseColor(mi->dpy, mi->xgwa.colormap, b, &gp->bg))
      {
		fprintf(stderr, "%s: unparsable color: \"%s\"\n", progname, f);
		exit(1);
      }

	free (f);
	free (b);
  }

  {
    double spin_speed   = 0.5;
    double wander_speed = 0.02;
    gp->rot = make_rotator (do_roll ? spin_speed : 0,
                            do_roll ? spin_speed : 0,
                            0, 1,
                            do_wander ? wander_speed : 0,
                            True);
    gp->z = frand (1.0);
    gp->trackball = gltrackball_init ();
  }

  if (wire)
    {
      do_texture = False;
      do_light = False;
    }

  if (do_texture)
    setup_texture (mi);

  if (do_light)
	init_sun (mi);

  if (do_stars)
    init_stars (mi);

  if (random() & 1)
    star_spin = -star_spin;

  /* construct the polygons of the planet
   */
  gp->platelist = glGenLists(1);
  glNewList (gp->platelist, GL_COMPILE);
  glColor3f (1,1,1);
  glPushMatrix ();
  glScalef (RADIUS, RADIUS, RADIUS);
  glRotatef (90, 1, 0, 0);
  glFrontFace(GL_CCW);
  unit_sphere (resolution, resolution, wire);
  glPopMatrix ();
  glEndList();

  /* construct the polygons of the latitude/longitude/axis lines.
   */
  gp->latlonglist = glGenLists(1);
  glNewList (gp->latlonglist, GL_COMPILE);
  glPushMatrix ();
  glDisable (GL_TEXTURE_2D);
  glDisable (GL_LIGHTING);
  glDisable (GL_LINE_SMOOTH);
  glColor3f (0.1, 0.3, 0.1);
  glScalef (RADIUS, RADIUS, RADIUS);
  glScalef (1.01, 1.01, 1.01);
  glRotatef (90, 1, 0, 0);
  unit_sphere (12, 24, 1);
  glBegin(GL_LINES);
  glVertex3f(0, -2, 0);
  glVertex3f(0,  2, 0);
  glEnd();
  glPopMatrix ();
  glEndList();
}
Esempio n. 6
0
ENTRYPOINT void
init_laser(ModeInfo * mi)
{
    Display *display = MI_DISPLAY(mi);
    int         i, c = 0;
    lasersstruct *lp;

    if (lasers == NULL) {
        if ((lasers = (lasersstruct *) calloc(MI_NUM_SCREENS(mi),
                                              sizeof (lasersstruct))) == NULL)
            return;
    }
    lp = &lasers[MI_SCREEN(mi)];

    lp->width = MI_WIDTH(mi);
    lp->height = MI_HEIGHT(mi);
    lp->time = 0;

    lp->ln = MI_COUNT(mi);
    if (lp->ln < -MINLASER) {
        /* if lp->ln is random ... the size can change */
        if (lp->laser != NULL) {
            (void) free((void *) lp->laser);
            lp->laser = (laserstruct *) NULL;
        }
        lp->ln = NRAND(-lp->ln - MINLASER + 1) + MINLASER;
    } else if (lp->ln < MINLASER)
        lp->ln = MINLASER;

    if (lp->laser == NULL) {
        if ((lp->laser = (laserstruct *) malloc(lp->ln *
                                                sizeof (laserstruct))) == NULL) {
            free_laser(display, lp);
            return;
        }
    }
    if (lp->stippledGC == None) {
        XGCValues   gcv;

        gcv.foreground = MI_WHITE_PIXEL(mi);
        gcv.background = MI_BLACK_PIXEL(mi);
        lp->gcv_black.foreground = MI_BLACK_PIXEL(mi);
        if ((lp->stippledGC = XCreateGC(display, MI_WINDOW(mi),
                                        GCForeground | GCBackground, &gcv)) == None) {
            free_laser(display, lp);
            return;
        }
# ifdef HAVE_JWXYZ
        jwxyz_XSetAntiAliasing (MI_DISPLAY(mi), lp->stippledGC, False);
# endif
    }
    MI_CLEARWINDOW(mi);

    if (MINDIST < lp->width - MINDIST)
        lp->cx = RANGE_RAND(MINDIST, lp->width - MINDIST);
    else
        lp->cx = RANGE_RAND(0, lp->width);
    if (MINDIST < lp->height - MINDIST)
        lp->cy = RANGE_RAND(MINDIST, lp->height - MINDIST);
    else
        lp->cy = RANGE_RAND(0, lp->height);
    lp->lw = RANGE_RAND(MINWIDTH, MAXWIDTH);
    lp->lr = RANGE_RAND(MINREDRAW, MAXREDRAW);
    lp->sw = 0;
    lp->so = 0;

    if (MI_NPIXELS(mi) > 2)
        c = NRAND(MI_NPIXELS(mi));

    for (i = 0; i < lp->ln; i++) {
        laserstruct *l = &lp->laser[i];

        l->bn = (border) NRAND(4);

        switch (l->bn) {
        case TOP:
            l->bx = NRAND(lp->width);
            l->by = 0;
            break;
        case RIGHT:
            l->bx = lp->width;
            l->by = NRAND(lp->height);
            break;
        case BOTTOM:
            l->bx = NRAND(lp->width);
            l->by = lp->height;
            break;
        case LEFT:
            l->bx = 0;
            l->by = NRAND(lp->height);
        }

        l->dir = (int) (LRAND() & 1);
        l->speed = ((RANGE_RAND(MINSPEED, MAXSPEED) * lp->width) / 1000) + 1;
        if (MI_NPIXELS(mi) > 2) {
            l->gcv.foreground = MI_PIXEL(mi, c);
            c = (c + COLORSTEP) % MI_NPIXELS(mi);
        } else
            l->gcv.foreground = MI_WHITE_PIXEL(mi);
    }
}
ENTRYPOINT void init_blocktube (ModeInfo *mi)
{
    int loop;
    GLfloat fogColor[4] = {0,0,0,1};
    blocktube_configuration *lp;
    int wire = MI_IS_WIREFRAME(mi);

    if (!lps) {
        lps = (blocktube_configuration *)
              calloc (MI_NUM_SCREENS(mi), sizeof (blocktube_configuration));
        if (!lps) {
            fprintf(stderr, "%s: out of memory\n", progname);
            exit(1);
        }
        lp = &lps[MI_SCREEN(mi)];
    }

    lp = &lps[MI_SCREEN(mi)];
    lp->glx_context = init_GL(mi);

    lp->zoom = 30;
    lp->tilt = 4.5;
    lp->tunnelLength = 200;
    lp->tunnelWidth = 5;

    if (wire) {
        do_fog = False;
        do_texture = False;
        glLineWidth(2);
    }

    lp->block_dlist = glGenLists (1);
    glNewList (lp->block_dlist, GL_COMPILE);
    lp->polys = cube_vertices(0.15, 1.2, 5.25, wire);
    glEndList ();

#if defined( I_HAVE_XPM )
    if (do_texture) {
        if (!LoadGLTextures(mi)) {
            fprintf(stderr, "%s: can't load textures!\n", progname);
            exit(1);
        }
        glEnable(GL_TEXTURE_2D);
    }
#endif

    /* kick on the fog machine */
    if (do_fog) {
        glEnable(GL_FOG);
        glFogi(GL_FOG_MODE, GL_LINEAR);
        glHint(GL_FOG_HINT, GL_NICEST);
        glFogf(GL_FOG_START, 0);
        glFogf(GL_FOG_END, lp->tunnelLength/1.8);
        glFogfv(GL_FOG_COLOR, fogColor);
        glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
    }
    glShadeModel(GL_SMOOTH);
    glEnable(GL_DEPTH_TEST);
    glEnable(GL_CULL_FACE);
    glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
    glClearDepth(1.0f);

    if (!do_texture && !wire) {
        /* If there is no texture, the boxes don't show up without a light.
           Though I don't understand why all the blocks come out gray.
         */
        GLfloat pos[4] = {0.0, 1.0, 1.0, 0.0};
        GLfloat amb[4] = {0.2, 0.2, 0.2, 1.0};
        GLfloat dif[4] = {1.0, 1.0, 1.0, 1.0};
        GLfloat spc[4] = {1.0, 1.0, 1.0, 1.0};
        glLightfv(GL_LIGHT0, GL_POSITION, pos);
        glLightfv(GL_LIGHT0, GL_AMBIENT,  amb);
        glLightfv(GL_LIGHT0, GL_DIFFUSE,  dif);
        glLightfv(GL_LIGHT0, GL_SPECULAR, spc);
        glEnable(GL_LIGHTING);
        glEnable(GL_LIGHT0);
    }

    lp->counter = holdtime;
    lp->currentR = random() % 256;
    lp->currentG = random() % 256;
    lp->currentB = random() % 256;
    newTargetColor(lp);
    for (loop = 0; loop < MAX_ENTITIES; loop++)
    {
        randomize_entity(lp, &lp->entities[loop]);
    }
    reshape_blocktube(mi, MI_WIDTH(mi), MI_HEIGHT(mi));
    glFlush();
}
Esempio n. 8
0
ENTRYPOINT void 
init_knot (ModeInfo *mi)
{
  knot_configuration *bp;
  int wire = MI_IS_WIREFRAME(mi);

  if (!bps) {
    bps = (knot_configuration *)
      calloc (MI_NUM_SCREENS(mi), sizeof (knot_configuration));
    if (!bps) {
      fprintf(stderr, "%s: out of memory\n", progname);
      exit(1);
    }

    bp = &bps[MI_SCREEN(mi)];
  }

  bp = &bps[MI_SCREEN(mi)];

  bp->glx_context = init_GL(mi);

  if (thickness <= 0) thickness = 0.001;
  else if (thickness > 1) thickness = 1;

  if (segments < 10) segments = 10;

  reshape_knot (mi, MI_WIDTH(mi), MI_HEIGHT(mi));

  if (!wire)
    {
      GLfloat pos[4] = {1.0, 1.0, 1.0, 0.0};
      GLfloat amb[4] = {0.0, 0.0, 0.0, 1.0};
      GLfloat dif[4] = {1.0, 1.0, 1.0, 1.0};
      GLfloat spc[4] = {0.0, 1.0, 1.0, 1.0};

      glEnable(GL_LIGHTING);
      glEnable(GL_LIGHT0);
      glEnable(GL_DEPTH_TEST);
      glEnable(GL_CULL_FACE);

      glLightfv(GL_LIGHT0, GL_POSITION, pos);
      glLightfv(GL_LIGHT0, GL_AMBIENT,  amb);
      glLightfv(GL_LIGHT0, GL_DIFFUSE,  dif);
      glLightfv(GL_LIGHT0, GL_SPECULAR, spc);
    }

  {
    Bool spinx=False, spiny=False, spinz=False;
    double spin_speed   = 2.0;
    double wander_speed = 0.05;
    double spin_accel   = 0.2;

    char *s = do_spin;
    while (*s)
      {
        if      (*s == 'x' || *s == 'X') spinx = True;
        else if (*s == 'y' || *s == 'Y') spiny = True;
        else if (*s == 'z' || *s == 'Z') spinz = True;
        else if (*s == '0') ;
        else
          {
            fprintf (stderr,
         "%s: spin must contain only the characters X, Y, or Z (not \"%s\")\n",
                     progname, do_spin);
            exit (1);
          }
        s++;
      }

    bp->rot = make_rotator (spinx ? spin_speed : 0,
                            spiny ? spin_speed : 0,
                            spinz ? spin_speed : 0,
                            spin_accel,
                            do_wander ? wander_speed : 0,
                            (spinx && spiny && spinz));
    bp->trackball = gltrackball_init ();
  }

  bp->knot_list = glGenLists (1);
  new_knot(mi);

  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
}
Esempio n. 9
0
ENTRYPOINT void 
init_ball (ModeInfo *mi)
{
  ball_configuration *bp;
  int wire = MI_IS_WIREFRAME(mi);

  if (!bps) {
    bps = (ball_configuration *)
      calloc (MI_NUM_SCREENS(mi), sizeof (ball_configuration));
    if (!bps) {
      fprintf(stderr, "%s: out of memory\n", progname);
      exit(1);
    }
  }

  bp = &bps[MI_SCREEN(mi)];

  bp->glx_context = init_GL(mi);

  reshape_ball (mi, MI_WIDTH(mi), MI_HEIGHT(mi));

  if (!wire)
    {
      GLfloat pos[4] = {1.0, 1.0, 1.0, 0.0};
      GLfloat amb[4] = {0.0, 0.0, 0.0, 1.0};
      GLfloat dif[4] = {1.0, 1.0, 1.0, 1.0};
      GLfloat spc[4] = {0.0, 1.0, 1.0, 1.0};

      glEnable(GL_LIGHTING);
      glEnable(GL_LIGHT0);
      glEnable(GL_DEPTH_TEST);
      glEnable(GL_CULL_FACE);

      glLightfv(GL_LIGHT0, GL_POSITION, pos);
      glLightfv(GL_LIGHT0, GL_AMBIENT,  amb);
      glLightfv(GL_LIGHT0, GL_DIFFUSE,  dif);
      glLightfv(GL_LIGHT0, GL_SPECULAR, spc);
    }

  {
    double spin_speed   = 10.0;
    double wander_speed = 0.12;
    double spin_accel   = 2.0;

    bp->rot = make_rotator (do_spin ? spin_speed : 0,
                            do_spin ? spin_speed : 0,
                            do_spin ? spin_speed : 0,
                            spin_accel,
                            do_wander ? wander_speed : 0,
                            True);
    bp->trackball = gltrackball_init ();
  }

  bp->ncolors = 128;
  bp->colors = (XColor *) calloc(bp->ncolors, sizeof(XColor));
  make_smooth_colormap (0, 0, 0,
                        bp->colors, &bp->ncolors,
                        False, 0, False);

  bp->spikes = (int *) calloc(MI_COUNT(mi), sizeof(*bp->spikes) * 2);

  bp->ball_list = glGenLists (1);
  bp->spike_list = glGenLists (1);

  glNewList (bp->ball_list, GL_COMPILE);
  unit_sphere (SPHERE_STACKS, SPHERE_SLICES, wire);
  glEndList ();

  glNewList (bp->spike_list, GL_COMPILE);
  cone (0, 0, 0,
        0, 1, 0,
        1, 0, SPIKE_FACES, SMOOTH_SPIKES, False, wire);
  glEndList ();

  randomize_spikes (mi);
}
Esempio n. 10
0
void
init_molecule (ModeInfo *mi)
{
  molecule_configuration *mc;
  int wire;

#ifndef STANDALONE
  timeout = MI_CYCLES(mi);
#endif
  if (!mcs) {
    mcs = (molecule_configuration *)
      calloc (MI_NUM_SCREENS(mi), sizeof (molecule_configuration));
    if (!mcs) {
       return;
    }
  }

  mc = &mcs[MI_SCREEN(mi)];
  if (mc->glx_context) {
	/* Free font stuff */
	free_fonts (mi);
  }

  if ((mc->glx_context = init_GL(mi)) != NULL) {
    glDrawBuffer(GL_BACK);
    gl_init();
    last = 0;
    reshape_molecule (mi, MI_WIDTH(mi), MI_HEIGHT(mi));
  }

  if (!load_fonts (mi)) {
	release_molecule(mi);
	return;
  }
  if (firstcall)
  startup_blurb (mi);
  cur_wire = MI_IS_WIREFRAME(mi);
  wire = cur_wire;

  mc->rotx = FLOATRAND(1.0) * RANDSIGN();
  mc->roty = FLOATRAND(1.0) * RANDSIGN();
  mc->rotz = FLOATRAND(1.0) * RANDSIGN();

  /* bell curve from 0-6 degrees, avg 3 */
  mc->dx = (FLOATRAND(0.1) + FLOATRAND(0.1) + FLOATRAND(0.1)) / (360/2);
  mc->dy = (FLOATRAND(0.1) + FLOATRAND(0.1) + FLOATRAND(0.1)) / (360/2);
  mc->dz = (FLOATRAND(0.1) + FLOATRAND(0.1) + FLOATRAND(0.1)) / (360/2);

  mc->d_max = mc->dx * 8;

  mc->ddx = 0.00006 + FLOATRAND(0.00003);
  mc->ddy = 0.00006 + FLOATRAND(0.00003);
  mc->ddz = 0.00006 + FLOATRAND(0.00003);

  {
    char *s = do_spin;
    while (*s)
      {
        if      (*s == 'x' || *s == 'X') mc->spin_x = 1;
        else if (*s == 'y' || *s == 'Y') mc->spin_y = 1;
        else if (*s == 'z' || *s == 'Z') mc->spin_z = 1;
        else
          {
            (void) fprintf (stderr,
         "molecule: spin must contain only the characters X, Y, or Z (not \"%s\")\n",
                     do_spin);
            /* exit (1); */
          }
        s++;
      }
  }

  mc->molecule_dlist = glGenLists(1);

  load_molecules (mi);
  mc->which =  NRAND(mc->nmolecules);

#ifdef STANDALONE
  mc->no_label_threshold = get_float_resource ("noLabelThreshold",
                                               "NoLabelThreshold");
  mc->wireframe_threshold = get_float_resource ("wireframeThreshold",
                                                "WireframeThreshold");
#else
  mc->no_label_threshold = 30;
  mc->wireframe_threshold = 150;
#endif

  if (wire)
    do_bonds = 1;
}
Esempio n. 11
0
/* Constructs the GL shapes of the current molecule
 */
static void
build_molecule (ModeInfo *mi)
{
  molecule_configuration *mc = &mcs[MI_SCREEN(mi)];
  int wire = cur_wire;
  int i;

  molecule *m = &mc->molecules[mc->which];

  if (wire)
    {
      glDisable(GL_CULL_FACE);
      glDisable(GL_LIGHTING);
      glDisable(GL_LIGHT0);
      glDisable(GL_DEPTH_TEST);
      glDisable(GL_NORMALIZE);
      glDisable(GL_CULL_FACE);
    }
  else
    {
      glEnable(GL_CULL_FACE);
      glEnable(GL_LIGHTING);
      glEnable(GL_LIGHT0);
      glEnable(GL_DEPTH_TEST);
      glEnable(GL_NORMALIZE);
      glEnable(GL_CULL_FACE);
    }

  if (!wire)
    set_atom_color (mi, 0, False);

  if (do_bonds)
    for (i = 0; i < m->nbonds; i++)
      {
        molecule_bond *b = &m->bonds[i];
        molecule_atom *from = get_atom(m->atoms, m->natoms, b->from,
		MI_IS_VERBOSE(mi));
        molecule_atom *to   = get_atom(m->atoms, m->natoms, b->to,
		MI_IS_VERBOSE(mi));

        if (wire)
          {
            glBegin(GL_LINES);
            glVertex3f(from->x, from->y, from->z);
            glVertex3f(to->x,   to->y,   to->z);
            glEnd();
          }
        else
          {
            int faces = (scale_down ? TUBE_FACES_2 : TUBE_FACES);
# ifdef SMOOTH_TUBE
            int smooth = True;
# else
            int smooth = False;
# endif
            GLfloat thickness = 0.07 * b->strength;
            GLfloat cap_size = 0.03;
            if (thickness > 0.3)
              thickness = 0.3;

            tube (from->x, from->y, from->z,
                  to->x,   to->y,   to->z,
                  thickness, cap_size,
                  faces, smooth, !do_atoms, wire);
          }
      }

  for (i = 0; i < m->natoms; i++)
    {
      molecule_atom *a = &m->atoms[i];
      int i;

      if (!wire && do_atoms)
        {
          GLfloat size = atom_size (a);
          set_atom_color (mi, a, False);
          sphere (a->x, a->y, a->z, size, wire);
        }

      if (do_labels)
        {
          glPushAttrib (GL_LIGHTING_BIT | GL_DEPTH_BUFFER_BIT);
          glDisable (GL_LIGHTING);
          glDisable (GL_DEPTH_TEST);

          if (!wire)
            set_atom_color (mi, a, True);

          glRasterPos3f (a->x, a->y, a->z);

          {
            GLdouble mm[17], pm[17];
            GLint vp[5];
            GLdouble wx=-1, wy=-1, wz=-1;
            glGetDoublev (GL_MODELVIEW_MATRIX, mm);
            glGetDoublev (GL_PROJECTION_MATRIX, pm);
            glGetIntegerv (GL_VIEWPORT, vp);

            /* Convert 3D coordinates to window coordinates */
            gluProject (a->x, a->y, a->z, mm, pm, vp, &wx, &wy, &wz);

            /* Fudge the window coordinates to center the string */
            wx -= string_width (mc->xfont1, a->label) / 2;
            wy -= mc->xfont1->descent;

            /* Convert new window coordinates back to 3D coordinates */
            gluUnProject (wx, wy, wz, mm, pm, vp, &wx, &wy, &wz);
            glRasterPos3f (wx, wy, wz);
          }

          for (i = 0; i < (int) strlen(a->label); i++)
            glCallList (mc->font1_dlist + (int)(a->label[i]));

          glPopAttrib();
        }
    }

  if (do_bbox)
    draw_bounding_box (mi);

  if (do_titles && m->label && *m->label)
    print_title_string (mi, m->label,
                        10, MI_HEIGHT(mi) - 10,
                        mc->xfont2->ascent + mc->xfont2->descent);
}
Esempio n. 12
0
/* Pick random starting and ending positions for the given sprite.
 */
static void
randomize_sprite (ModeInfo *mi, sprite *sp)
{
  int vp_w = MI_WIDTH(mi);
  int vp_h = MI_HEIGHT(mi);
  int img_w = sp->img->geom.width;
  int img_h = sp->img->geom.height;
  int min_w, max_w;
  double ratio = (double) img_h / img_w;

  if (letterbox_p)
    {
      min_w = img_w;
    }
  else
    {
      if (img_w < vp_w)
        min_w = vp_w;
      else
        min_w = img_w * (float) vp_h / img_h;
    }

  max_w = min_w * 100 / zoom;

  sp->from.w = min_w + frand ((max_w - min_w) * 0.4);
  sp->to.w   = max_w - frand ((max_w - min_w) * 0.4);
  sp->from.h = sp->from.w * ratio;
  sp->to.h   = sp->to.w   * ratio;

  if (zoom == 100)	/* only one box, and it is centered */
    {
      sp->from.x = (sp->from.w > vp_w
                    ? -(sp->from.w - vp_w) / 2
                    :  (vp_w - sp->from.w) / 2);
      sp->from.y = (sp->from.h > vp_h
                    ? -(sp->from.h - vp_h) / 2
                    :  (vp_h - sp->from.h) / 2);
      sp->to = sp->from;
    }
  else			/* position both boxes randomly */
    {
      sp->from.x = (sp->from.w > vp_w
                    ? -frand (sp->from.w - vp_w)
                    :  frand (vp_w - sp->from.w));
      sp->from.y = (sp->from.h > vp_h
                    ? -frand (sp->from.h - vp_h)
                    :  frand (vp_h - sp->from.h));
      sp->to.x   = (sp->to.w > vp_w
                    ? -frand (sp->to.w - vp_w)
                    :  frand (vp_w - sp->to.w));
      sp->to.y   = (sp->to.h > vp_h
                    ? -frand (sp->to.h - vp_h)
                    :  frand (vp_h - sp->to.h));
    }

  if (random() & 1)
    {
      rect swap = sp->to;
      sp->to = sp->from;
      sp->from = swap;
    }

  /* Make sure the aspect ratios are within 0.001 of each other.
   */
  {
    int r1 = 0.5 + (sp->from.w * 1000 / sp->from.h);
    int r2 = 0.5 + (sp->to.w   * 1000 / sp->to.h);
    if (r1 < r2-1 || r1 > r2+1)
      {
        fprintf (stderr,
                 "%s: botched aspect: %f x %f (%d) vs  %f x %f (%d): %s\n",
                 progname, 
                 sp->from.w, sp->from.h, r1,
                 sp->to.w, sp->to.h, r2,
                 (sp->img->title ? sp->img->title : "[null]"));
        abort();
      }
  }

  sp->from.x /= vp_w;
  sp->from.y /= vp_h;
  sp->from.w /= vp_w;
  sp->from.h /= vp_h;
  sp->to.x   /= vp_w;
  sp->to.y   /= vp_h;
  sp->to.w   /= vp_w;
  sp->to.h   /= vp_h;
}
Esempio n. 13
0
/* Callback that tells us that the texture has been loaded.
 */
static void
image_loaded_cb (const char *filename, XRectangle *geom,
                 int image_width, int image_height,
                 int texture_width, int texture_height,
                 void *closure)
{
  image *img = (image *) closure;
  ModeInfo *mi = img->mi;
  /* slideshow_state *ss = &sss[MI_SCREEN(mi)]; */

  int wire = MI_IS_WIREFRAME(mi);

  if (wire)
    {
      img->w = MI_WIDTH (mi) * (0.5 + frand (1.0));
      img->h = MI_HEIGHT (mi);
      img->geom.width  = img->w;
      img->geom.height = img->h;
      goto DONE;
    }

  if (image_width == 0 || image_height == 0)
    exit (1);

  glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
  glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
                   mipmap_p ? GL_LINEAR_MIPMAP_LINEAR : GL_LINEAR);

  glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
  glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);

  img->w  = image_width;
  img->h  = image_height;
  img->tw = texture_width;
  img->th = texture_height;
  img->geom = *geom;
  img->title = (filename ? strdup (filename) : 0);

  /* If the image's width doesn't come back as the width of the screen,
     then the image must have been scaled down (due to insufficient
     texture memory.)  Scale up the coordinates to stretch the image
     to fill the window.
   */
  if (img->w != MI_WIDTH(mi))
    {
      double scale = (double) MI_WIDTH(mi) / img->w;
      img->w  *= scale;
      img->h  *= scale;
      img->tw *= scale;
      img->th *= scale;
      img->geom.x      *= scale;
      img->geom.y      *= scale;
      img->geom.width  *= scale;
      img->geom.height *= scale;
    }

  /* xscreensaver-getimage returns paths relative to the image directory
     now, so leave the sub-directory part in.  Unless it's an absolute path.
  */
  if (img->title && img->title[0] == '/')
    {
      /* strip filename to part between last "/" and last ".". */
      char *s = strrchr (img->title, '/');
      if (s) strcpy (img->title, s+1);
      s = strrchr (img->title, '.');
      if (s) *s = 0;
    }

  if (debug_p)
    fprintf (stderr, "%s: loaded   img %2d: \"%s\"\n",
             blurb(), img->id, (img->title ? img->title : "(null)"));
 DONE:

  img->loaded_p = True;
}
Esempio n. 14
0
ENTRYPOINT void draw_antmaze(ModeInfo * mi) 
{
  double h = (GLfloat) MI_HEIGHT(mi) / (GLfloat) MI_WIDTH(mi);

  antmazestruct *mp;
  
  Display    *display = MI_DISPLAY(mi);
  Window      window = MI_WINDOW(mi);
  
  if(!antmaze)
	return;
  mp = &antmaze[MI_SCREEN(mi)];
  
  MI_IS_DRAWN(mi) = True;
  
  if(!mp->glx_context)
	return;
  
  mi->polygon_count = 0;
  glXMakeCurrent(display, window, *(mp->glx_context));

  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

  /* first panel */
  glPushMatrix();
/*   h = ((GLfloat) MI_HEIGHT(mi)/2) / (3*(GLfloat)MI_WIDTH(mi)/4); */
  glViewport(MI_WIDTH(mi)/32, MI_HEIGHT(mi)/8, (9*MI_WIDTH(mi))/16, 3*MI_HEIGHT(mi)/4);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();

/*   h = (3*MI_HEIGHT(mi)/4) / (3*MI_WIDTH(mi)/4); */
  gluPerspective(45, 1/h, 1, 25.0);

  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
  device_rotate(mi);

  glPushMatrix();

  /* follow focused ant */
  glTranslatef(0.0, 0.0, -mp->mag - 5.0);
  glRotatef(20.0+5.0*sin(mp->ant_step/40.0), 1.0, 0.0, 0.0);
/*   glTranslatef(0.0,  */
/* 	       started ? -mag : -8.0 + 4.0*fabs(sin(ant_step/10.0)),  */
/* 	       started ? -mag : -8.0 + 4.0*fabs(sin(ant_step/10.0))); */

  gltrackball_rotate(mp->trackball);

  glRotatef(mp->ant_step*0.6, 0.0, 1.0, 0.0);

/*   glRotatef(90.0, 0.0, 0.0, 1.0); */

/*   glTranslatef(-antposition[0][0]-0.5, 0.0, -antposition[focus][1]); */
  /*-elevator*/

  /* sync */
  if(!draw_antmaze_strip(mi)) {
    release_antmaze(mi);
    return;
  }

  glPopMatrix();
  glPopMatrix();

  h = (GLfloat) (3*MI_HEIGHT(mi)/8) / (GLfloat) (MI_WIDTH(mi)/2);

  /* draw overhead */
  glPushMatrix();
  glViewport((17*MI_WIDTH(mi))/32, MI_HEIGHT(mi)/2, MI_WIDTH(mi)/2, 3*MI_HEIGHT(mi)/8);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  device_rotate(mi);
  gluPerspective(45, 1/h, 1, 25.0);
  glMatrixMode(GL_MODELVIEW);
    
  /* twist scene */
  glTranslatef(0.0, 0.0, -16.0);
  glRotatef(60.0, 1.0, 0.0, 0.0);
  glRotatef(-15.0 + mp->ant_step/10.0, 0.0, 1.0, 0.0);
  gltrackball_rotate(mp->trackball);

  /* sync */
  if(!draw_antmaze_strip(mi)) {
    release_antmaze(mi);
    return;
  }

  glPopMatrix();

  /* draw ant display */
  glPushMatrix();
  glViewport((5*MI_WIDTH(mi))/8, MI_HEIGHT(mi)/8, (11*MI_WIDTH(mi))/32, 3*MI_HEIGHT(mi)/8);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  device_rotate(mi);
  gluPerspective(45, 1/h, 1, 25.0);
  glMatrixMode(GL_MODELVIEW);
    
  /* twist scene */
  glTranslatef(0.0, 0.0, -1.6);
  glRotatef(30.0, 1.0, 0.0, 0.0);
  glRotatef(mp->ant_step, 0.0, 1.0, 0.0);
  glRotatef(90.0, 0.0, 0.0, 1.0);
  
/*   /\* draw ant shadow *\/ */
/*   glPushMatrix(); */
/*   glScalef(1.0, 0.01, 1.0); */
/*   glRotatef(90.0, 0.0, 0.0, 1.0); */
/*   glRotatef(90.0, 0.0, 1.0, 0.0); */
/*   glDisable(GL_LIGHTING); */
/*   glColor4fv(MaterialGray6); */
  
/*   /\* slow down first ant *\/ */
/*   draw_ant(MaterialGrayB, 0, 1, first_ant_step, mySphere, myCone); */
/*   glPopMatrix(); */

  /* draw ant body */
  glEnable(GL_TEXTURE_2D);
  glLightfv(GL_LIGHT0, GL_DIFFUSE, diffuse);
  glLightfv(GL_LIGHT1, GL_DIFFUSE, diffuse);
  glBindTexture(GL_TEXTURE_2D, mp->brushedtexture);
  draw_ant(mi, mp, MaterialGray35, 0, 1, mp->ant_step/2.0, mySphereTex, myCone2);
  glDisable(GL_TEXTURE_2D);

  glPopMatrix();

/*   /\* draw overlay *\/ */
/*   glPushMatrix(); */

/*   /\* go to ortho mode *\/ */
/*   glViewport(MI_WIDTH(mi)/2, MI_HEIGHT(mi)/8, MI_WIDTH(mi)/2, 3*MI_HEIGHT(mi)/8); */

/*   glMatrixMode(GL_PROJECTION); */
/*   glLoadIdentity(); */

/*   glPushMatrix (); */
/*   glOrtho(-4.0, 4.0, -3.0, 3.0, -100.0, 100.0); */

/*   glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, MaterialGrayB); */
/*   glColor4fv(MaterialGrayB); */

/*   glDisable(GL_LIGHTING); */
/*   glEnable(GL_BLEND); */

/*   glBegin(GL_QUADS); */
/*   glNormal3f(0.0, 0.0, 1.0); */
/*   glVertex3f(4.0, 3.0, 0.0); */
/*   glVertex3f(2.0, 3.0, 0.0); */
/*   glVertex3f(2.0, -3.0, 0.0); */
/*   glVertex3f(4.0, -3.0, 0.0); */
/*   mi->polygon_count++; */
/*   glEnd(); */

/*   glEnable(GL_LIGHTING); */
/*   glDisable(GL_BLEND); */

/*   glPopMatrix(); */
/*   glPopMatrix(); */
  
  if (MI_IS_FPS(mi)) {
    glViewport(0, 0, MI_WIDTH(mi), MI_HEIGHT(mi));
    do_fps (mi);
  }
  glFlush();
  
  glXSwapBuffers(display, window);
  
  update_ants(mp);

  mp->step += 0.025;
}
Esempio n. 15
0
/* Standard reshape function */
ENTRYPOINT void
reshape_pulsar(ModeInfo *mi, int width, int height)
{
  glViewport( 0, 0, MI_WIDTH(mi), MI_HEIGHT(mi) );
  resetProjection();
}
Esempio n. 16
0
ENTRYPOINT void 
init_quasicrystal (ModeInfo *mi)
{
  quasicrystal_configuration *bp;
  int wire = MI_IS_WIREFRAME(mi);
  unsigned char *tex_data = 0;
  int tex_width;
  int i;

  if (!bps) {
    bps = (quasicrystal_configuration *)
      calloc (MI_NUM_SCREENS(mi), sizeof (quasicrystal_configuration));
    if (!bps) {
      fprintf(stderr, "%s: out of memory\n", progname);
      exit(1);
    }
  }

  bp = &bps[MI_SCREEN(mi)];

  bp->glx_context = init_GL(mi);

  reshape_quasicrystal (mi, MI_WIDTH(mi), MI_HEIGHT(mi));

  glDisable (GL_DEPTH_TEST);
  glEnable (GL_CULL_FACE);

  bp->count = MI_COUNT(mi);
  if (bp->count < 1) bp->count = 1;

  if (! wire)
    {
      unsigned char *o;
      tex_width = 4096;
      tex_data = (unsigned char *) calloc (4, tex_width);
      o = tex_data;
      for (i = 0; i < tex_width; i++)
        {
          unsigned char y = 255 * (1 + sin (i * M_PI * 2 / tex_width)) / 2;
          *o++ = y;
          *o++ = y;
          *o++ = y;
          *o++ = 255;
        }
    }

  bp->symmetric_p =
    get_boolean_resource (MI_DISPLAY (mi), "symmetry", "Symmetry");

  bp->contrast = get_float_resource (MI_DISPLAY (mi), "contrast", "Contrast");
  if (bp->contrast < 0 || bp->contrast > 100) 
    {
      fprintf (stderr, "%s: contrast must be between 0 and 100%%.\n", progname);
      bp->contrast = 0;
    }

  {
    Bool spinp   = get_boolean_resource (MI_DISPLAY (mi), "spin", "Spin");
    Bool wanderp = get_boolean_resource (MI_DISPLAY (mi), "wander", "Wander");
    double spin_speed   = 0.01;
    double wander_speed = 0.0001;
    double spin_accel   = 10.0;
    double scale_speed  = 0.005;

    bp->planes = (plane *) calloc (sizeof (*bp->planes), bp->count);

    bp->ncolors = 256;  /* ncolors affects color-cycling speed */
    bp->colors = (XColor *) calloc (bp->ncolors, sizeof(XColor));
    make_smooth_colormap (0, 0, 0, bp->colors, &bp->ncolors,
                          False, 0, False);
    bp->ccolor = 0;

    for (i = 0;  i < bp->count; i++)
      {
        plane *p = &bp->planes[i];
        p->rot = make_rotator (0, 0,
                               spinp ? spin_speed : 0,
                               spin_accel,
                               wanderp ? wander_speed : 0,
                               True);
        p->rot2 = make_rotator (0, 0,
                                0, 0,
                               scale_speed,
                               True);
        if (! wire)
          {
            clear_gl_error();

            glGenTextures (1, &p->texid);
            glBindTexture (GL_TEXTURE_1D, p->texid);
            glPixelStorei (GL_UNPACK_ALIGNMENT, 1);
            glTexImage1D (GL_TEXTURE_1D, 0, GL_RGBA,
                          tex_width, 0,
                          GL_RGBA,
                          /* GL_UNSIGNED_BYTE, */
                          GL_UNSIGNED_INT_8_8_8_8_REV,
                          tex_data);
            check_gl_error("texture");

            glTexParameterf(GL_TEXTURE_1D, GL_TEXTURE_WRAP_S, GL_REPEAT);
            glTexParameterf(GL_TEXTURE_1D, GL_TEXTURE_WRAP_T, GL_REPEAT);

            glTexParameteri(GL_TEXTURE_1D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
            glTexParameteri(GL_TEXTURE_1D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);

            glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
          }
      }
  }

  if (tex_data) free (tex_data);

  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
}
Esempio n. 17
0
ENTRYPOINT void
draw_stairs (ModeInfo * mi)
{
	stairsstruct *sp = &stairs[MI_SCREEN(mi)];
    GLfloat rot = current_device_rotation();

	Display    *display = MI_DISPLAY(mi);
	Window      window = MI_WINDOW(mi);

	if (!sp->glx_context)
		return;

	glXMakeCurrent(display, window, *sp->glx_context);

	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

	glPushMatrix();

    glRotatef(rot, 0, 0, 1);

	glTranslatef(0.0, 0.0, -10.0);

	if (!MI_IS_ICONIC(mi)) {
		glScalef(Scale4Window * sp->WindH / sp->WindW, Scale4Window, Scale4Window);
	} else {
		glScalef(Scale4Iconic * sp->WindH / sp->WindW, Scale4Iconic, Scale4Iconic);
	}

# ifdef HAVE_MOBILE	/* Keep it the same relative size when rotated. */
  {
    GLfloat h = MI_HEIGHT(mi) / (GLfloat) MI_WIDTH(mi);
    if (rot != 0 && rot != 180 && rot != -180)
      glScalef (1/h, 1/h, 1/h);
  }
# endif

    gltrackball_rotate (sp->trackball);

    glTranslatef(0, 0.5, 0);
	glRotatef(44.5, 1, 0, 0);
    glRotatef(50, 0, 1, 0);

    if (!sp->rotating) {
      if ((LRAND() % 500) == 0)
        sp->rotating = (LRAND() & 1) ? 1 : -1;
    }

    if (sp->rotating) {
      glRotatef(sp->rotating * sp->step, 0, 1, 0);
      if (sp->step >= 360) {
        sp->rotating = 0;
		sp->step = 0;
      }

# ifndef DEBUG
      if (!sp->button_down_p)
        sp->step += 2;
# endif /* DEBUG */
    }

	draw_stairs_internal(mi);


# ifdef DEBUG
    {
      int i, j;
#  ifdef DEBUG_PATH
      glDisable(GL_LIGHTING);
      glDisable(GL_TEXTURE_2D);
      glBegin (GL_LINE_LOOP);
#  endif /* DEBUG_PATH */
      for (i = 0; i < NPOSITIONS; i ++)
        for (j = 0; j < SPHERE_TICKS; j++)
          mi->polygon_count += draw_sphere(i, j);
#  ifdef DEBUG_PATH
      glEnd();
      glEnable(GL_LIGHTING);
      glEnable(GL_TEXTURE_2D);
#  endif /* DEBUG_PATH */
    }
#else  /* !DEBUG */
    mi->polygon_count += draw_sphere(sp->sphere_position, sp->sphere_tick);
#endif /* !DEBUG */

    if (sp->button_down_p)
      ;
    else if (++sp->sphere_tick >= SPHERE_TICKS)
      {
        sp->sphere_tick = 0;
        if (++sp->sphere_position >= NPOSITIONS)
          sp->sphere_position = 0;
      }

	glPopMatrix();

    if (mi->fps_p) do_fps (mi);
	glFlush();

	glXSwapBuffers(display, window);
}
Esempio n. 18
0
/* Create and return a new gear sized for placement next to or on top of
   the given parent gear (if any.)  Returns 0 if out of memory.
   [Mostly lifted from pinion.c]
 */
static gear *
new_gear (ModeInfo *mi, gear *parent)
{
  gears_configuration *bp = &bps[MI_SCREEN(mi)];
  gear *g = (gear *) calloc (1, sizeof (*g));
  static unsigned long id = 0;  /* only used in debugging output */

  if (!g) return 0;
  g->id = ++id;

  /* Pick the size of the teeth.
   */
  if (parent) /* adjascent gears need matching teeth */
    {
      g->tooth_w = parent->tooth_w;
      g->tooth_h = parent->tooth_h;
      g->tooth_slope = -parent->tooth_slope;
    }
  else                 /* gears that begin trains get any size they want */
    {
      g->tooth_w = 0.007 * (1.0 + BELLRAND(4.0));
      g->tooth_h = 0.005 * (1.0 + BELLRAND(8.0));
/*
      g->tooth_slope = ((random() % 8)
                        ? 0
                        : 0.5 + BELLRAND(1));
 */
    }

  /* Pick the number of teeth, and thus, the radius.
   */
  {
    double c;

    if (!parent || bp->ngears > 4)
      g->nteeth = 5 + BELLRAND (20);
    else
      g->nteeth = parent->nteeth * (0.5 + BELLRAND(2));

    c = g->nteeth * g->tooth_w * 2;     /* circumference = teeth + gaps */
    g->r = c / (M_PI * 2);              /* c = 2 pi r  */
  }

  g->thickness  = g->tooth_w + frand (g->r);
  g->thickness2 = g->thickness * 0.7;
  g->thickness3 = g->thickness;

  /* Colorize
   */
  g->color[0] = 0.5 + frand(0.5);
  g->color[1] = 0.5 + frand(0.5);
  g->color[2] = 0.5 + frand(0.5);
  g->color[3] = 1.0;

  g->color2[0] = g->color[0] * 0.85;
  g->color2[1] = g->color[1] * 0.85;
  g->color2[2] = g->color[2] * 0.85;
  g->color2[3] = g->color[3];


  /* Decide on shape of gear interior:
     - just a ring with teeth;
     - that, plus a thinner in-set "plate" in the middle;
     - that, plus a thin raised "lip" on the inner plate;
     - or, a wide lip (really, a thicker third inner plate.)
   */
  if ((random() % 10) == 0)
    {
      /* inner_r can go all the way in; there's no inset disc. */
      g->inner_r = (g->r * 0.1) + frand((g->r - g->tooth_h/2) * 0.8);
      g->inner_r2 = 0;
      g->inner_r3 = 0;
    }
  else
    {
      /* inner_r doesn't go in very far; inner_r2 is an inset disc. */
      g->inner_r  = (g->r * 0.5)  + frand((g->r - g->tooth_h) * 0.4);
      g->inner_r2 = (g->r * 0.1) + frand(g->inner_r * 0.5);
      g->inner_r3 = 0;

      if (g->inner_r2 > (g->r * 0.2))
        {
          int nn = (random() % 10);
          if (nn <= 2)
            g->inner_r3 = (g->r * 0.1) + frand(g->inner_r2 * 0.2);
          else if (nn <= 7 && g->inner_r2 >= 0.1)
            g->inner_r3 = g->inner_r2 - 0.01;
        }
    }

  /* If we have three discs, sometimes make the middle disc be spokes.
   */
  if (g->inner_r3 && ((random() % 5) == 0))
    {
      g->spokes = 2 + BELLRAND (5);
      g->spoke_thickness = 1 + frand(7.0);
      if (g->spokes == 2 && g->spoke_thickness < 2)
        g->spoke_thickness += 1;
    }

  /* Sometimes add little nubbly bits, if there is room.
   */
  if (g->nteeth > 5)
    {
      double size = 0;
      involute_biggest_ring (g, 0, &size, 0);
      if (size > g->r * 0.2 && (random() % 5) == 0)
        {
          g->nubs = 1 + (random() % 16);
          if (g->nubs > 8) g->nubs = 1;
        }
    }

  if (g->inner_r3 > g->inner_r2) abort();
  if (g->inner_r2 > g->inner_r) abort();
  if (g->inner_r  > g->r) abort();

  /* Decide how complex the polygon model should be.
   */
  {
    double pix = g->tooth_h * MI_HEIGHT(mi); /* approx. tooth size in pixels */
    if (pix <= 2.5)      g->size = INVOLUTE_SMALL;
    else if (pix <= 3.5) g->size = INVOLUTE_MEDIUM;
    else                 g->size = INVOLUTE_LARGE;
  }

  g->base_p = !parent;

  return g;
}
Esempio n. 19
0
ENTRYPOINT void
init_ball (ModeInfo *mi)
{
  int wire = MI_IS_WIREFRAME(mi);
  blinkboxstruct *bp;
  
  MI_INIT (mi, blinkbox);
  bp = &blinkbox[MI_SCREEN(mi)];

  if ((bp->glx_context = init_GL(mi)) != NULL) {
    reshape_ball(mi, MI_WIDTH(mi), MI_HEIGHT(mi));
    glDrawBuffer(GL_BACK);
  }
  else
    MI_CLEARWINDOW(mi);

  bp->ball.d = 1;
  bp->bscale.wh = bscale_wh;
  bp->bscale.d = 0.25;

  bp->mo.x = 1;
  bp->mo.y = 1;
  bp->mo.z = 1;

  bp->moh.x = -1.0;
  bp->moh.y = -1.5;
  bp->moh.z = -1.5;

  bp->bpos.x = 1;
  bp->bpos.y = 1;
  bp->bpos.z = 1;

  bp->des_amt = 1;

  bp->lside.counter = MAX_COUNT;
  bp->rside.counter = MAX_COUNT;
  bp->tside.counter = MAX_COUNT;
  bp->bside.counter = MAX_COUNT;
  bp->fside.counter = MAX_COUNT;
  bp->aside.counter = MAX_COUNT;

  bp->lside.color[0] = 1;
  bp->rside.color[1] = 1;
  bp->tside.color[2] = 1;

  bp->bside.color[0] = 1;
  bp->bside.color[1] = 0.5;

  bp->fside.color[0] = 1;
  bp->fside.color[1] = 1;

  bp->aside.color[0] = 0.5;
  bp->aside.color[2] = 1;

  bp->lside.rot[0] = 90;
  bp->rside.rot[0] = 90;
  bp->tside.rot[0] = 90;
  bp->bside.rot[0] = 90;
  bp->fside.rot[0] = 90;
  bp->aside.rot[0] = 90;

  bp->lside.rot[2] = 1;
  bp->rside.rot[2] = 1;
  bp->tside.rot[1] = 1;
  bp->bside.rot[1] = 1;
  bp->fside.rot[3] = 1;
  bp->aside.rot[3] = 1;

  bp->lside.des_count = 1;
  bp->rside.des_count = 1;
  bp->tside.des_count = 1;
  bp->bside.des_count = 1;
  bp->fside.des_count = 1;
  bp->aside.des_count = 1;

  bp->lside.alpha_count = 1;
  bp->rside.alpha_count = 1;
  bp->tside.alpha_count = 1;
  bp->bside.alpha_count = 1;
  bp->fside.alpha_count = 1;
  bp->aside.alpha_count = 1;


#define SPHERE_SLICES 12  /* how densely to render spheres */
#define SPHERE_STACKS 16

  bp->sp = malloc(sizeof(*bp->sp));
  if(bp->sp == NULL){
    fprintf(stderr,"Could not allocate memory\n");
    exit(1);
  }
  if( (bp->bscale.wh < 1) ||
      (bp->bscale.wh > 8) ) {
    fprintf(stderr,"Boxsize out of range. Using default\n");
    bp->bscale.wh = 2;
  }
  if (do_dissolve){
    bp->des_amt = bp->bscale.wh / MAX_COUNT;
  }

  reshape_ball(mi, MI_WIDTH(mi), MI_HEIGHT(mi));
  bp->ballList = glGenLists(1);
  glNewList(bp->ballList, GL_COMPILE);
  unit_sphere (SPHERE_STACKS, SPHERE_SLICES, wire);
  glEndList ();

  bp->boxList = glGenLists(1);
  glNewList(bp->boxList, GL_COMPILE);
  unit_cube(wire);
  glEndList();

  if (wire) return;

  glEnable(GL_COLOR_MATERIAL);
  glShadeModel(GL_SMOOTH);
  glClearDepth(1.0f);
  glEnable(GL_DEPTH_TEST);
  glDepthFunc(GL_LEQUAL);
  glEnable(GL_LIGHTING);
  glClearDepth(1);
  glLightfv(GL_LIGHT1, GL_DIFFUSE, LightDiffuse);
  glLightfv(GL_LIGHT1, GL_POSITION,LightPosition);
  glEnable(GL_LIGHT1);
  if (do_fade || do_blur) {
    glEnable(GL_BLEND);
    glDisable(GL_DEPTH_TEST);
  }
}
Esempio n. 20
0
ENTRYPOINT void 
init_gears (ModeInfo *mi)
{
  gears_configuration *bp;
  int wire = MI_IS_WIREFRAME(mi);
  int i;

  if (!bps) {
    bps = (gears_configuration *)
      calloc (MI_NUM_SCREENS(mi), sizeof (gears_configuration));
    if (!bps) {
      fprintf(stderr, "%s: out of memory\n", progname);
      exit(1);
    }
  }

  bp = &bps[MI_SCREEN(mi)];

  bp->glx_context = init_GL(mi);

  reshape_gears (mi, MI_WIDTH(mi), MI_HEIGHT(mi));

  if (!wire)
    {
      GLfloat pos[4] = {1.0, 1.0, 1.0, 0.0};
      GLfloat amb[4] = {0.0, 0.0, 0.0, 1.0};
      GLfloat dif[4] = {1.0, 1.0, 1.0, 1.0};
      GLfloat spc[4] = {0.0, 1.0, 1.0, 1.0};

      glEnable(GL_LIGHTING);
      glEnable(GL_LIGHT0);
      glEnable(GL_DEPTH_TEST);
      glEnable(GL_CULL_FACE);

      glLightfv(GL_LIGHT0, GL_POSITION, pos);
      glLightfv(GL_LIGHT0, GL_AMBIENT,  amb);
      glLightfv(GL_LIGHT0, GL_DIFFUSE,  dif);
      glLightfv(GL_LIGHT0, GL_SPECULAR, spc);
    }

  {
    double spin_speed   = 0.5;
    double wander_speed = 0.01;
    double spin_accel   = 0.25;

    bp->rot = make_rotator (do_spin ? spin_speed : 0,
                            do_spin ? spin_speed : 0,
                            do_spin ? spin_speed : 0,
                            spin_accel,
                            do_wander ? wander_speed : 0,
                            True
                            );
    bp->trackball = gltrackball_init ();
  }

  if (!(random() % 8))
    {
      planetary_gears (mi);
    }
  else
    {
      gear *g = 0;
      int total_gears = MI_COUNT (mi);
      int i;
      if (total_gears <= 0)
        total_gears = 3 + abs (BELLRAND (8) - 4);  /* 3 - 7, mostly 3. */

      bp->gears = (gear **) calloc (total_gears+2, sizeof(**bp->gears));
      bp->ngears = 0;

      for (i = 0; i < total_gears; i++)
        g = place_new_gear (mi, g);
    }


  /* Center gears in scene. */
  {
    GLfloat minx=99999, miny=99999, maxx=-99999, maxy=-99999;
    int i;
    for (i = 0; i < bp->ngears; i++)
      {
        gear *g = bp->gears[i];
        if (g->x - g->r < minx) minx = g->x - g->r;
        if (g->x + g->r > maxx) maxx = g->x + g->r;
        if (g->y - g->r < miny) miny = g->y - g->r;
        if (g->y + g->r > maxy) maxy = g->y + g->r;
      }
    bp->bbox.x1 = minx;
    bp->bbox.y1 = miny;
    bp->bbox.x2 = maxx;
    bp->bbox.y2 = maxy;
  }

  /* Now render each gear into its display list.
   */
  for (i = 0; i < bp->ngears; i++)
    {
      gear *g = bp->gears[i];
      g->dlist = glGenLists (1);
      if (! g->dlist)
        {
          check_gl_error ("glGenLists");
          abort();
        }

      glNewList (g->dlist, GL_COMPILE);
      g->polygons += draw_involute_gear (g, wire);
      glEndList ();
    }
  if (bp->planetary_p)
    armature (mi);
}
Esempio n. 21
0
ENTRYPOINT void
init_spiral(ModeInfo * mi)
{
	spiralstruct *sp;
	int         i;

	if (spirals == NULL) {
		if ((spirals = (spiralstruct *) calloc(MI_NUM_SCREENS(mi),
					     sizeof (spiralstruct))) == NULL)
			return;
	}
	sp = &spirals[MI_SCREEN(mi)];

#ifdef HAVE_COCOA
    jwxyz_XSetAntiAliasing (MI_DISPLAY(mi), MI_GC(mi),  False);
#endif

	sp->width = MI_WIDTH(mi);
	sp->height = MI_HEIGHT(mi);

	MI_CLEARWINDOW(mi);

	/* Init */
	sp->nlength = MI_CYCLES(mi);

	if (!sp->traildots)
		if ((sp->traildots = (Traildots *) malloc(sp->nlength *
				sizeof (Traildots))) == NULL) {
			return;
		}

	/* initialize the allocated array */
	for (i = 0; i < sp->nlength; i++) {
		sp->traildots[i].hx = 0.0;
		sp->traildots[i].hy = 0.0;
		sp->traildots[i].ha = 0.0;
		sp->traildots[i].hr = 0.0;
	}
	sp->redrawing = 0;

	/* keep the window parameters proportional */
	sp->top = 10000.0;
	sp->bottom = 0;
	sp->right = (float) (sp->width) / (float) (sp->height) * (10000.0);
	sp->left = 0;

	/* assign the initial values */
	sp->cx = (float) (5000.0 - NRAND(2000)) / 10000.0 * sp->right;
	sp->cy = (float) (5000.0 - NRAND(2000));
	sp->radius = (float) (NRAND(200) + 200);
	sp->angle = 0.0;
	sp->dx = (float) (10 - NRAND(20)) * SPEED;
	sp->dy = (float) (10 - NRAND(20)) * SPEED;
	sp->dr = (float) ((NRAND(10) + 4) * (1 - (LRAND() & 1) * 2));
	sp->da = (float) NRAND(360) / 7200.0 + 0.01;
	if (MI_NPIXELS(mi) > 2)
		sp->colors = (float) NRAND(MI_NPIXELS(mi));
	sp->erase = 0;
	sp->inc = 0;
	sp->traildots[sp->inc].hx = sp->cx;
	sp->traildots[sp->inc].hy = sp->cy;
	sp->traildots[sp->inc].ha = sp->angle;
	sp->traildots[sp->inc].hr = sp->radius;
	sp->inc++;

	sp->dots = MI_COUNT(mi);
	if (sp->dots < -MINDOTS)
		sp->dots = NRAND(sp->dots - MINDOTS + 1) + MINDOTS;
	/* Absolute minimum */
	if (sp->dots < MINDOTS)
		sp->dots = MINDOTS;
}
Esempio n. 22
0
ENTRYPOINT Bool
klein_handle_event (ModeInfo *mi, XEvent *event)
{
    kleinstruct *kp = &klein[MI_SCREEN(mi)];

    if (event->xany.type == ButtonPress && event->xbutton.button == Button1) {
        kp->button_down_p = True;
        gltrackball_start (kp->trackball, event->xbutton.x, event->xbutton.y, MI_WIDTH (mi), MI_HEIGHT (mi));
        return True;
    } else if (event->xany.type == ButtonRelease && event->xbutton.button == Button1) {
        kp->button_down_p = False;
        return True;
    } else if (event->xany.type == ButtonPress &&
               (event->xbutton.button == Button4 ||
                event->xbutton.button == Button5 ||
                event->xbutton.button == Button6 ||
                event->xbutton.button == Button7)) {
        gltrackball_mousewheel (kp->trackball, event->xbutton.button, 10,
                                !!event->xbutton.state);
        return True;
    } else if (event->xany.type == MotionNotify && kp->button_down_p) {
        gltrackball_track (kp->trackball, event->xmotion.x, event->xmotion.y, MI_WIDTH (mi), MI_HEIGHT (mi));
        return True;
    }

    return False;
}
Esempio n. 23
0
ENTRYPOINT void 
init_sponge (ModeInfo *mi)
{
  sponge_configuration *sp;
  int wire = MI_IS_WIREFRAME(mi);

  if (!sps) {
    sps = (sponge_configuration *)
      calloc (MI_NUM_SCREENS(mi), sizeof (sponge_configuration));
    if (!sps) {
      fprintf(stderr, "%s: out of memory\n", progname);
      exit(1);
    }
  }

  sp = &sps[MI_SCREEN(mi)];

  if ((sp->glx_context = init_GL(mi)) != NULL) {
    reshape_sponge (mi, MI_WIDTH(mi), MI_HEIGHT(mi));
  }

  if (!wire)
    {
      static const GLfloat pos0[4] = {-1.0, -1.0, 1.0, 0.1};
      static const GLfloat pos1[4] = { 1.0, -0.2, 0.2, 0.1};
      static const GLfloat dif0[4] = {1.0, 1.0, 1.0, 1.0};
      static const GLfloat dif1[4] = {1.0, 1.0, 1.0, 1.0};

      glLightfv(GL_LIGHT0, GL_POSITION, pos0);
      glLightfv(GL_LIGHT1, GL_POSITION, pos1);
      glLightfv(GL_LIGHT0, GL_DIFFUSE, dif0);
      glLightfv(GL_LIGHT1, GL_DIFFUSE, dif1);

      glEnable(GL_LIGHTING);
      glEnable(GL_LIGHT0);
      glEnable(GL_LIGHT1);

      glEnable(GL_DEPTH_TEST);
      glEnable(GL_NORMALIZE);

      glShadeModel(GL_SMOOTH);
    }

  {
    double spin_speed   = 1.0;
    double wander_speed = 0.03;
    sp->rot = make_rotator (do_spin ? spin_speed : 0,
                            do_spin ? spin_speed : 0,
                            do_spin ? spin_speed : 0,
                            1.0,
                            do_wander ? wander_speed : 0,
                            True);
    sp->trackball = gltrackball_init (True);
  }

  sp->ncolors = 128;
  sp->colors = (XColor *) calloc(sp->ncolors, sizeof(XColor));
  make_smooth_colormap (0, 0, 0,
                        sp->colors, &sp->ncolors,
                        False, 0, False);
  sp->ccolor0 = 0;
  sp->ccolor1 = sp->ncolors / 3;
  sp->ccolor2 = sp->ccolor1 * 2;

  sp->sponge_list0 = glGenLists (1);
  sp->sponge_list1 = glGenLists (1);
  sp->sponge_list2 = glGenLists (1);

  sp->draw_tick = 9999999;
}
Esempio n. 24
0
ENTRYPOINT void
init_klein(ModeInfo *mi)
{
    int	 screen = MI_SCREEN(mi);
    kleinstruct *kp;

    if (klein == NULL) {
        if ((klein = (kleinstruct *) calloc(MI_NUM_SCREENS(mi), sizeof (kleinstruct))) == NULL)
            return;
    }
    kp = &klein[screen];

    kp->window = MI_WINDOW(mi);

    {
        double spin_speed	 = 1.0;
        double wander_speed = 0.03;
        kp->rot = make_rotator (do_spin ? spin_speed : 0,
                                do_spin ? spin_speed : 0,
                                do_spin ? spin_speed : 0,
                                1.0,
                                do_wander ? wander_speed : 0,
                                True);
        kp->trackball = gltrackball_init ();
    }

    if(rand) {
        render = random() % MY_PRIM_LAST;
        kp->surface = random() % SURFACE_LAST;
    } else {
        render = MY_LINE_LOOP;
        kp->surface = KLEIN;
    }

    switch (render) {
    case MY_POINTS:
        kp->render = GL_POINTS;
        break;
    case MY_LINES:
        kp->render = GL_LINES;
        break;
    case MY_LINE_LOOP:
        kp->render = GL_LINE_LOOP;
        break;
    default:
        kp->render = GL_LINE_LOOP;
    }
    /*kp->render=GL_TRIANGLE_FAN;*/
    /*kp->render=GL_POLYGON;*/

    kp->du = 0.07;
    kp->dv = 0.07;
    kp->a = kp->b = 1;
    kp->c = 0.1;


    if ((kp->glx_context = init_GL(mi)) != NULL) {
        reshape_klein(mi, MI_WIDTH(mi), MI_HEIGHT(mi));
    } else {
        MI_CLEARWINDOW(mi);
    }
}
Esempio n. 25
0
ENTRYPOINT void 
init_fliptext (ModeInfo *mi)
{
  int wire = MI_IS_WIREFRAME(mi);

  fliptext_configuration *sc;

  MI_INIT(mi, scs);

  sc = &scs[MI_SCREEN(mi)];
  sc->lines = (line **) calloc (max_lines+1, sizeof(char *));

  sc->dpy = MI_DISPLAY(mi);

  if ((sc->glx_context = init_GL(mi)) != NULL) {
    reshape_fliptext (mi, MI_WIDTH(mi), MI_HEIGHT(mi));
    clear_gl_error(); /* WTF? sometimes "invalid op" from glViewport! */
  }

  {
    XCharStruct e;
    int cw, lh, ascent, descent;
    sc->texfont = load_texture_font (MI_DISPLAY(mi), "font");
    check_gl_error ("loading font");
    texture_string_metrics (sc->texfont, "n", &e, &ascent, &descent);
    cw = e.width;
    lh = ascent + descent;
    sc->char_width = cw;
    sc->line_height = lh;
  }

  if (!wire)
    {
      glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); 
      glEnable (GL_BLEND);
      glEnable (GL_ALPHA_TEST);
      glEnable (GL_TEXTURE_2D);

      /* "Anistropic filtering helps for quadrilateral-angled textures.
         A sharper image is accomplished by interpolating and filtering
         multiple samples from one or more mipmaps to better approximate
         very distorted textures.  This is the next level of filtering
         after trilinear filtering." */
      if (strstr ((char *) glGetString(GL_EXTENSIONS),
                  "GL_EXT_texture_filter_anisotropic"))
      {
        GLfloat anisotropic = 0.0;
        glGetFloatv (GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &anisotropic);
        if (anisotropic >= 1.0)
          glTexParameterf (GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT, 
                           anisotropic);
      }
    }
  
  /* The default font is (by fiat) "18 points".
     Interpret the user's font size request relative to that.
   */
  sc->font_scale = 3 * (font_size / 18.0);

  if (target_columns <= 2) target_columns = 2;

  /* Figure out what the wrap column should be, in font-coordinate pixels.
     Compute it from the given -columns value, but don't let it be wider
     than the screen.
   */
  {
    GLfloat maxw = 110 * sc->line_height / sc->font_scale;  /* magic... */
    sc->font_wrap_pixels = target_columns * sc->char_width;
    if (sc->font_wrap_pixels > maxw ||
        sc->font_wrap_pixels <= 0)
      sc->font_wrap_pixels = maxw;
  }

  sc->buf_size = target_columns * max_lines;
  sc->buf = (char *) calloc (1, sc->buf_size);

  alignment_random_p = False;
  if (!alignment_str || !*alignment_str ||
      !strcasecmp(alignment_str, "left"))
    sc->alignment = -1;
  else if (!strcasecmp(alignment_str, "center") ||
           !strcasecmp(alignment_str, "middle"))
    sc->alignment = 0;
  else if (!strcasecmp(alignment_str, "right"))
    sc->alignment = 1;
  else if (!strcasecmp(alignment_str, "random"))
    sc->alignment = -1, alignment_random_p = True;

  else
    {
      fprintf (stderr,
               "%s: alignment must be left/center/right/random, not \"%s\"\n",
               progname, alignment_str);
      exit (1);
    }

  sc->tc = textclient_open (sc->dpy);

  if (max_lines < 1) max_lines = 1;
  min_lines = max_lines * 0.66;
  if (min_lines > max_lines - 3) min_lines = max_lines - 4;
  if (min_lines < 1) min_lines = 1;

  parse_color (mi, "foreground",
               get_string_resource(mi->dpy, "foreground", "Foreground"),
               sc->color);

  sc->top_margin = (sc->char_width * 100);
  sc->bottom_margin = -sc->top_margin;
  reshape_fliptext (mi, MI_WIDTH(mi), MI_HEIGHT(mi));  /* compute left/right */
}
Esempio n. 26
0
ENTRYPOINT Bool
hydrostat_handle_event (ModeInfo *mi, XEvent *event)
{
  hydrostat_configuration *bp = &bps[MI_SCREEN(mi)];
  int w = MI_WIDTH(mi);
  int h = MI_HEIGHT(mi);
  int x, y;

# ifdef USE_TRACKBALL
  if (gltrackball_event_handler (event, bp->trackball,
                                 MI_WIDTH (mi), MI_HEIGHT (mi),
                                 &bp->button_down_p))
    return True;
# endif

  switch (event->xany.type) {
  case ButtonPress: case ButtonRelease:
    x = event->xbutton.x;
    y = event->xbutton.y;
    break;
  case MotionNotify:
    x = event->xmotion.x;
    y = event->xmotion.y;
    break;
  default:
    x = y = 0;
  }

  x -= w/2;
  y -= h/2;
  x *= 0.7;
  y *= 0.7;

  if (event->xany.type == ButtonPress)
    {
      int i;
      GLfloat D0 = 999999;

      /* This is pretty halfassed hit detection, but it works ok... */
      for (i = 0; i < MI_COUNT(mi); i++)
        {
          squid *s = bp->squids[i];
          GLfloat X = s->pos.x - x;
          GLfloat Y = s->pos.z - y;
          GLfloat D = sqrt(X*X + Y*Y);
          if (D < D0)
            {
              bp->dragging = i;
              D0 = D;
            }
        }

      if (D0 > 300)	/* Too far away, missed hit */
        {
          bp->dragging = -1;
          return False;
        }

      bp->squids[bp->dragging]->ratio = -3;
      bp->button_down_p = True;

      return True;
    }
  else if (event->xany.type == ButtonRelease && bp->dragging >= 0)
    {
      bp->button_down_p = False;
      bp->dragging = -1;
      return True;
    }
  else if (event->xany.type == MotionNotify && bp->dragging >= 0)
    {
      squid *s = bp->squids[bp->dragging];
      s->from.x = s->to.x = s->pos.x = x;
      s->from.z = s->to.z = s->pos.z = y;
      s->from.y = s->to.y = s->pos.y;
      return True;
    }

  return False;
}
Esempio n. 27
0
ENTRYPOINT void init_jigglypuff(ModeInfo *mi)
{
    jigglystruct *js;
    int subdivs;

    if(!jss) {
	jss = (jigglystruct*)
	    calloc(MI_NUM_SCREENS(mi), sizeof(jigglystruct));
	if(!jss) {
	    fprintf(stderr, "%s: No..memory...must...abort..\n", progname);
	    exit(1);
	}
    }

    js = &jss[MI_SCREEN(mi)];

    js->do_wireframe = MI_IS_WIREFRAME(mi);
# ifdef HAVE_JWZGLES
    js->do_wireframe = 0; /* GL_LINE unimplemented */
# endif

    js->shininess = shininess;

    subdivs = (complexity==1) ? 4 : (complexity==2) ? 5
	: (complexity==3) ? 6 : 5;

    js->spooky = spooky << (subdivs-3);

    if(!parse_color(js)) {
	fprintf(stderr, "%s: Bad color specification: '%s'.\n", progname, color);
	exit(-1);
    }
    
    if(random_parms)
	randomize_parameters(js);

    js->angle = frand(180);
    js->axis  = frand(M_PI);

    js->shape = tesselated_tetrahedron(1, subdivs, js);

    if(!do_tetrahedron)
	solid_spherify(js->shape, 1);

    if(js->color_style == COLOR_STYLE_CLOWNBARF)
	clownbarf_colorize(js->shape);

    calculate_parameters(js, subdivs);

    if((js->glx_context = init_GL(mi)) != NULL) {
	glXMakeCurrent(MI_DISPLAY(mi), MI_WINDOW(mi), *(js->glx_context));
	setup_opengl(mi, js);
	reshape_jigglypuff(mi, MI_WIDTH(mi), MI_HEIGHT(mi));
    }
    else {
	MI_CLEARWINDOW(mi);
    }
    js->trackball = gltrackball_init();
/*    _DEBUG("distance : %f\nhold : %f\nspherify : %f\ndamping : %f\ndfact : %f\n",
	   js->stable_distance, js->hold_strength, js->spherify_strength,
	   js->damping_velocity, js->damping_factor);
    _DEBUG("wire : %d\nspooky : %d\nstyle : %d\nshininess : %d\n",
	   js->do_wireframe, js->spooky, js->color_style, js->shininess);*/
}
Esempio n. 28
0
ENTRYPOINT void 
init_hydrostat (ModeInfo *mi)
{
  int wire = MI_IS_WIREFRAME(mi);
  hydrostat_configuration *bp;
  int i;

  MI_INIT (mi, bps, free_hydrostat);

  bp = &bps[MI_SCREEN(mi)];

  bp->glx_context = init_GL(mi);

  reshape_hydrostat (mi, MI_WIDTH(mi), MI_HEIGHT(mi));

  if (!wire)
    {
      GLfloat pos[4] = {1.0, 1.0, 1.0, 0.0};
      GLfloat amb[4] = {0.0, 0.0, 0.0, 1.0};
      GLfloat dif[4] = {1.0, 1.0, 1.0, 1.0};
      GLfloat spc[4] = {0.0, 1.0, 1.0, 1.0};

      glEnable(GL_LIGHTING);
      glEnable(GL_LIGHT0);
      glEnable(GL_DEPTH_TEST);
      glEnable(GL_CULL_FACE);

      glLightfv(GL_LIGHT0, GL_POSITION, pos);
      glLightfv(GL_LIGHT0, GL_AMBIENT,  amb);
      glLightfv(GL_LIGHT0, GL_DIFFUSE,  dif);
      glLightfv(GL_LIGHT0, GL_SPECULAR, spc);
    }

  glShadeModel(GL_SMOOTH);

  glEnable(GL_DEPTH_TEST);
  glEnable(GL_NORMALIZE);

  if (MI_COUNT(mi) <= 0)
    MI_COUNT(mi) = 1;

  if (random() & 1)
    current_arg = -current_arg;

  if (MI_COUNT(mi) == 1 || wire)
    opacity_arg = 1.0;
  if (opacity_arg < 0.1) opacity_arg = 0.1;
  if (opacity_arg > 1.0) opacity_arg = 1.0;

  bp->squids = (squid **) calloc (MI_COUNT(mi), sizeof(*bp->squids));
  for (i = 0; i < MI_COUNT(mi); i++)
    bp->squids[i] = make_squid (mi, i);

  bp->dragging = -1;

  if (opacity_arg < 1.0)
    {
      glEnable (GL_BLEND);
      glBlendFunc (GL_SRC_ALPHA, GL_ONE);
    }

# ifdef USE_TRACKBALL
  bp->trackball = gltrackball_init (True);
# endif
}
Esempio n. 29
0
static void
move_fly(ModeInfo * mi, Fly * f)
{
	int         win_width = MI_WIDTH(mi);
	int         win_height = MI_HEIGHT(mi);
	int         left = (f->side == FLY_SIDE_LEFT) ? -(f->width) : 0;
	int         right = (f->side == FLY_SIDE_RIGHT) ? win_width :
	win_width - f->width;
	Bool        track_p = trackmouse;
	int         cx, cy;


	f->oldx = f->x;		/* remember position before moving, */
	f->oldy = f->y;		/* for unpainting previous image */

	if (track_p) {
		Window      r, c;
		int         rx, ry;
		unsigned int m;

		(void) XQueryPointer(MI_DISPLAY(mi), MI_WINDOW(mi),
				     &r, &c, &rx, &ry, &cx, &cy, &m);
		if (cx <= 0 || cy <= 0 ||
		    cx >= MI_WIDTH(mi) - f->width - 1 ||
		    cy >= MI_HEIGHT(mi) - f->width - 1) {
			track_p = False;
		}
	}
	if (track_p) {
		f->x = cx;
		f->y = cy;
		return;
	}
	f->x += f->vx;		/* apply x velocity */

	if (f->x > right) {
		if (f->side == FLY_SIDE_RIGHT) {
			unpaint_fly(mi, f);	/* went off the edge, reset */
			init_fly(mi, f);
		} else {
			/* Bounce off the right edge */
			f->x = 2 * (win_width - f->width) - f->x;
			f->vx = -f->vx + f->vx / FRICTION;
		}
	} else if (f->x < left) {
		if (f->side == FLY_SIDE_LEFT) {
			unpaint_fly(mi, f);	/* went off the edge, reset */
			init_fly(mi, f);
		} else {
			/* Bounce off the left edge */
			f->x = -f->x;
			f->vx = -f->vx + f->vx / FRICTION;
		}
	}
	f->vy++;		/* gravity, accelerate in y direction */
	f->y += f->vy;		/* apply y velocity */

	if (f->y >= (win_height - f->height)) {
		/* Bounce off the bottom edge */
		f->y = (win_height - f->height);
		f->vy = -f->vy + f->vy / FRICTION;
		/* every once in a while, go apeshit to clean "high lurkers" */
		if (NRAND(50) == 0) {
			f->vy *= 4;
		}
	} else if (f->y < 0) {
		/* Bounce off the top edge */
		f->y = -f->y;
		f->vy = -f->vy + f->vy / FRICTION;
	}
	/* if he settles to the bottom, move him off quick */
	if (abs(f->vy) < 2) {
		if ((f->zero_y++) > 10) {
			f->vx += (f->side == FLY_SIDE_LEFT) ? -1 : 1;
		}
	} else {
		f->zero_y = 0;	/* still bouncing */
	}
}
Esempio n. 30
0
/* Create and return a new gear sized for placement next to or on top of
   the given parent gear (if any.)  Returns 0 if out of memory.
 */
static gear *
new_gear (ModeInfo *mi, gear *parent, Bool coaxial_p)
{
  pinion_configuration *pp = &pps[MI_SCREEN(mi)];
  gear *g = (gear *) calloc (1, sizeof (*g));
  int loop_count = 0;
  static unsigned long id = 0;  /* only used in debugging output */

  if (!g) return 0;
  if (coaxial_p && !parent) abort();
  g->id = ++id;

  g->coax_displacement = pp->plane_displacement;

  while (1)
    {
      loop_count++;
      if (loop_count > 1000)
        /* The only time we loop in here is when making a coaxial gear, and
           trying to pick a radius that is either significantly larger or
           smaller than its parent.  That shouldn't be hard, so something
           must be really wrong if we can't do that in only a few tries.
         */
        abort();

      /* Pick the size of the teeth.
       */
      if (parent && !coaxial_p) /* adjascent gears need matching teeth */
        {
          g->tooth_w = parent->tooth_w;
          g->tooth_h = parent->tooth_h;
          g->thickness  = parent->thickness;
          g->thickness2 = parent->thickness2;
          g->thickness3 = parent->thickness3;
        }
      else                 /* gears that begin trains get any size they want */
        {
          double scale = (1.0 + BELLRAND(4.0)) * gear_size;
          g->tooth_w = 0.007 * scale;
          g->tooth_h = 0.005 * scale;
          g->thickness  = g->tooth_h * (0.1 + BELLRAND(1.5));
          g->thickness2 = g->thickness / 4;
          g->thickness3 = g->thickness;
        }

      /* Pick the number of teeth, and thus, the radius.
       */
      {
        double c;

      AGAIN:
        g->nteeth = 3 + (random() % 97);    /* from 3 to 100 teeth */

        if (g->nteeth < 7 && (random() % 5) != 0)
          goto AGAIN;   /* Let's make very small tooth-counts more rare */

        c = g->nteeth * g->tooth_w * 2;     /* circumference = teeth + gaps */
        g->r = c / (M_PI * 2);              /* c = 2 pi r  */
      }


      /* Are we done now?
       */
      if (! coaxial_p) break;   /* yes */
      if (g->nteeth == parent->nteeth) continue; /* ugly */
      if (g->r  < parent->r * 0.6) break;  /* g much smaller than parent */
      if (parent->r < g->r  * 0.6) break;  /* g much larger than parent  */
    }

  /* g->tooth_slope = (parent ? -parent->tooth_slope : 4); */

  /* Colorize
   */
  g->color[0] = 0.5 + frand(0.5);
  g->color[1] = 0.5 + frand(0.5);
  g->color[2] = 0.5 + frand(0.5);
  g->color[3] = 1.0;

  g->color2[0] = g->color[0] * 0.85;
  g->color2[1] = g->color[1] * 0.85;
  g->color2[2] = g->color[2] * 0.85;
  g->color2[3] = g->color[3];


  /* Decide on shape of gear interior:
     - just a ring with teeth;
     - that, plus a thinner in-set "plate" in the middle;
     - that, plus a thin raised "lip" on the inner plate;
     - or, a wide lip (really, a thicker third inner plate.)
   */
  if ((random() % 10) == 0)
    {
      /* inner_r can go all the way in; there's no inset disc. */
      g->inner_r = (g->r * 0.1) + frand((g->r - g->tooth_h/2) * 0.8);
      g->inner_r2 = 0;
      g->inner_r3 = 0;
    }
  else
    {
      /* inner_r doesn't go in very far; inner_r2 is an inset disc. */
      g->inner_r  = (g->r * 0.5)  + frand((g->r - g->tooth_h) * 0.4);
      g->inner_r2 = (g->r * 0.1) + frand(g->inner_r * 0.5);
      g->inner_r3 = 0;

      if (g->inner_r2 > (g->r * 0.2))
        {
          int nn = (random() % 10);
          if (nn <= 2)
            g->inner_r3 = (g->r * 0.1) + frand(g->inner_r2 * 0.2);
          else if (nn <= 7 && g->inner_r2 >= 0.1)
            g->inner_r3 = g->inner_r2 - 0.01;
        }
    }

  /* Coaxial gears need to have the same innermost hole size (for the axle.)
     Use whichever of the two is smaller.  (Modifies parent.)
   */
  if (coaxial_p)
    {
      double hole1 = (g->inner_r3 ? g->inner_r3 :
                      g->inner_r2 ? g->inner_r2 :
                      g->inner_r);
      double hole2 = (parent->inner_r3 ? parent->inner_r3 :
                      parent->inner_r2 ? parent->inner_r2 :
                      parent->inner_r);
      double hole = (hole1 < hole2 ? hole1 : hole2);
      if (hole <= 0) abort();

      if      (g->inner_r3) g->inner_r3 = hole;
      else if (g->inner_r2) g->inner_r2 = hole;
      else                  g->inner_r  = hole;

      if      (parent->inner_r3) parent->inner_r3 = hole;
      else if (parent->inner_r2) parent->inner_r2 = hole;
      else                       parent->inner_r  = hole;
    }

  /* If we have three discs, sometimes make the middle disc be spokes.
   */
  if (g->inner_r3 && ((random() % 5) == 0))
    {
      g->spokes = 2 + BELLRAND (5);
      g->spoke_thickness = 1 + frand(7.0);
      if (g->spokes == 2 && g->spoke_thickness < 2)
        g->spoke_thickness += 1;
    }

  /* Sometimes add little nubbly bits, if there is room.
   */
  if (g->nteeth > 5)
    {
      double size = 0;
      involute_biggest_ring (g, 0, &size, 0);
      if (size > g->r * 0.2 && (random() % 5) == 0)
        {
          g->nubs = 1 + (random() % 16);
          if (g->nubs > 8) g->nubs = 1;
        }
    }

  if (g->inner_r3 > g->inner_r2) abort();
  if (g->inner_r2 > g->inner_r) abort();
  if (g->inner_r  > g->r) abort();

  /* Decide how complex the polygon model should be.
   */
  {
    double pix = g->tooth_h * MI_HEIGHT(mi); /* approx. tooth size in pixels */
    if (pix <= 2.5)      g->size = INVOLUTE_SMALL;
    else if (pix <= 3.5) g->size = INVOLUTE_MEDIUM;
    else                 g->size = INVOLUTE_LARGE;
  }

  g->base_p = !parent;

  return g;
}