home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Encyclopedia of Graphics File Formats Companion
/
GFF_CD.ISO
/
formats
/
ttddd
/
code
/
bumpit.c
< prev
next >
Wrap
C/C++ Source or Header
|
1994-06-20
|
6KB
|
205 lines
/* bumpit.c - Read in an Imagine object, bump the puppy, then spit it back out
* - Written by Glenn M. Lewis - 8/6/92
* - Modified by Charles Congdon to use public domain noise calls
* - Reads from stdin, writes to stdout.
* - Inspiration by Steve Worley:
Heres a cool idea! And TRIVIAL to implement! It's an object perturber.
It loads in a TDDD object. It calls fractal noise three times for three
displacements for each vertex. It dispaces the vertex that amount. It
then saves the object back out as a new object.
Want an asteroid? Make a primative sphere in Imagine. Use "bumpit" and
displace the points. Load the new object! BAM, bumpy sphere! You
could even add features like craters before bumping.
Or take a flat plane, bump only in the +Z direction. Boom, a mountain
range!
bumpit max_X max_Y max_Z Initial_scale #_of_scales Scale_ratio Amp_ratio
time_ratio time
or "turbit" with the same parameters. You make 3 calls to "fractalval3"
for the X Y and Z displacements. See?
Cool, useful, eh? Make that Cyberware head pulse with animated displacements!
I figure about 15 minutes to write, too. Want to give it a whirl?
-Steve
----------------------------------------------------------------------------
Here's another (option?) for bumpit. Make RADIAL perturbations. So the
perfect sphere won't "fold over" on itself: it will always be radial. So
DX DY DZ DR as 4 options? They can all be summed together, the fact
that DR is a 3 vector is no biggie.
-Steve
*/
static char rcs_id[] = "$Id: bumpit.c,v 1.7 1993/02/14 07:27:06 glewis Exp glewis $";
#include <stdio.h>
#include <ctype.h>
#include <math.h>
#include "t3dlib.h"
#include "noise.h"
#ifdef __STDC__
#include <stdlib.h>
#include <strings.h>
#include "bumpit_protos.h"
#endif
/* Do this with includes: double atof(), sqrt(); */
#define NUMARGS 10
double args[NUMARGS];
double defargs[NUMARGS] = {
1.0, /* max_X */
1.0, /* max_Y */
1.0, /* max_Z */
1.0, /* max_R */
10.0, /* Initial_scale */
5.0, /* #_of_scales */
0.4, /* Scale_ratio */
0.4, /* Amp_ratio */
0.4, /* time_ratio */
0.0 /* time */
};
#define MAX_X args[0]
#define MAX_Y args[1]
#define MAX_Z args[2]
#define MAX_R args[3]
#define INIT_SCALE args[4]
#define NUM_SCALES args[5]
#define SCALE_RATIO args[6]
#define AMP_RATIO args[7]
#define TIME_RATIO args[8]
#define TIME args[9]
main(argc, argv)
int argc;
char *argv[];
{
int i;
register OBJECT *o;
WORLD *world;
if (argc-1 > NUMARGS) {
USAGE:
fprintf(stderr, "Usage: %s max_X max_Y max_Z Initial_scale #_of_scales Scale_ratio Amp_ratio time_ratio time <in.iob >out.iob\n", argv[0]);
exit(-1);
}
for (i=1; i<argc; i++) {
if (argv[i][0]=='-' && argv[i][1]=='h') goto USAGE;
args[i-1] = (double)atof(argv[i]);
}
while (i-1<NUMARGS) { args[i-1] = defargs[i-1]; i++; }
world = read_World(stdin);
if (!world) {
fprintf(stderr, "Could not load object from stdin.\n");
exit(-1);
}
/* Now, iterate over all objects, bumping verticies with noise */
for (o=world->object; o; o=o->next)
process_DESC(o);
/* Write the object back out. */
write_TDDD(world, stdout);
exit(0);
}
void process_DESC(object)
OBJECT *object;
{
register OBJECT *obj;
register DESC *desc = object->desc;
register int i;
register double val;
/* float in[6], out[6]; */
double in[3], out[3];
double rad, addX, addY, addZ, addR;
/* Loop through list of verticies, and bump */
if (desc->pcount) {
for (i=0; i<desc->pcount; i++) {
addX = addY = addZ = 0.0;
in[0] = (double)desc->pnts[i].x;
in[1] = (double)desc->pnts[i].y;
in[2] = (double)desc->pnts[i].z;
rad = sqrt((double)in[0]*in[0]+in[1]*in[1]+in[2]*in[2]);
if (rad != 0.0) rad = 1.0/rad;
if (MAX_X != 0.0) {
val = wfractalval3(&in[0],
INIT_SCALE,
NUM_SCALES,
SCALE_RATIO,
AMP_RATIO,
TIME_RATIO,
TIME,
&out[0]);
addX = MAX_X*val;
}
if (MAX_Y != 0.0) {
in[0] = (double)desc->pnts[i].x + (double)107.28;
in[1] = (double)desc->pnts[i].y - (double)213.72;
in[2] = (double)desc->pnts[i].z + (double)172.12;
val = wfractalval3(&in[0],
INIT_SCALE,
NUM_SCALES,
SCALE_RATIO,
AMP_RATIO,
TIME_RATIO,
TIME,
&out[0]);
addY = MAX_Y*val;
}
if (MAX_Z != 0.0) {
in[0] = (double)desc->pnts[i].x - (double)573.17;
in[1] = (double)desc->pnts[i].y + (double)324.93;
in[2] = (double)desc->pnts[i].z - (double)747.88;
val = wfractalval3(&in[0],
INIT_SCALE,
NUM_SCALES,
SCALE_RATIO,
AMP_RATIO,
TIME_RATIO,
TIME,
&out[0]);
addZ = MAX_Z*val;
}
if (MAX_R != 0.0 && rad != 0.0) {
in[0] = (double)desc->pnts[i].x - (double)57.923;
in[1] = (double)desc->pnts[i].y - (double)1052.7;
in[2] = (double)desc->pnts[i].z + (double)481.08;
val = wfractalval3(&in[0],
INIT_SCALE,
NUM_SCALES,
SCALE_RATIO,
AMP_RATIO,
TIME_RATIO,
TIME,
&out[0]);
addR = MAX_R*val;
addX += addR*desc->pnts[i].x*rad;
addY += addR*desc->pnts[i].y*rad;
addZ += addR*desc->pnts[i].z*rad;
}
desc->pnts[i].x += addX;
desc->pnts[i].y += addY;
desc->pnts[i].z += addZ;
}
}
for (obj=object->child; obj; obj=obj->next)
if (!obj->extr) process_DESC(obj);
}