示例#1
0
CollisionResult collision_ray_scene_union(const Ray* ray, const Scene* scene) {
	const Scene* scene1 = ((ScenePair*)scene->data)->scene1;
	const Scene* scene2 = ((ScenePair*)scene->data)->scene2;

	const int max_iterations = 10;

	CollisionResult r1;
	{
		Ray ray2 = *ray;
		Vec3 p;
		for (int i = 0; i < max_iterations; ++i) {
			r1 = collision_ray_scene(&ray2, scene1);
			if (r1.type == None) { break; }
			p = ray_point(&ray2, r1.time);
			if (!scene_is_point_in_solid(scene2, &p)) { break; }
			Vec3 ro = ray_point(&ray2, r1.time+0.1);
			ray2 = ray_init(&ro, &ray2.direction);
		}
		if (r1.type != None) {
			Vec3 v = vec3_sub(&p, &ray->origin);
			r1.time = vec3_dot(&ray->direction, &v);
		}
	}

	CollisionResult r2;
	{
		Ray ray2 = *ray;
		Vec3 p;
		for (int i = 0; i < max_iterations; ++i) {
			r2 = collision_ray_scene(&ray2, scene2);
			if (r2.type == None) { break; }
			p = ray_point(&ray2, r2.time);
			if (!scene_is_point_in_solid(scene1, &p)) { break; }
			Vec3 ro = ray_point(&ray2, r2.time+0.1);
			ray2 = ray_init(&ro, &ray2.direction);
		}
		if (r2.type != None) {
			Vec3 v = vec3_sub(&p, &ray->origin);
			r2.time = vec3_dot(&ray->direction, &v);
		}
	}

	if (r1.type == None) {
		if (r2.type == None) {
			return (CollisionResult){.type=None};
		} else {
			return r2;
		}
	} else {
示例#2
0
/*
 * Calculate light color
 */
color lightColor(const intersection *inter, const ray *srcRay) {
	vec3 v = vector_normalized(vector_float_mul(-1.0f, srcRay->dir));
	color cD = BLACK, refCoef = reflectCoef(inter->mat.reflect_coef, inter->normal, srcRay->dir);
	// For each light calculate and sum color
	for (int k = 0; k < num_lights; ++k) {
		vec3 l = vector_minus(lights[k].position, inter->position);
		float normL = vector_norm(l);
		l = vector_normalized(l);
		// Look for object between light source and current intersection
		ray objectRay; // Ray from object to light
		ray_init(&objectRay, inter->position, l, EPSILON, normL, 0);
		float interFound = 0.0f;
		for (int i = 0; i < object_count; ++i) {
			interFound += interDist(&objectRay, &(scene[i]));
		}
		if (!interFound) {
			vec3 h = vector_normalized(vector_add(l, v));
			float sc_nl = clamp(vector_dot(inter->normal, l), 0.0f, 1.0f);
			float sc_hn = clamp(vector_dot(h, inter->normal), 0.0f, 1.0f);
			cD = vector_add(cD,
					vector_vec_mul(lights[k].col,
							vector_float_mul(sc_nl,
									(vector_add(vector_float_mul(1 / M_PI, inter->mat.kd),
											(vector_float_mul(pow(sc_hn, inter->mat.shininess), vector_float_mul(((inter->mat.shininess + 8) / (8 * M_PI)), refCoef))))))));
		}
	}
	return cD;
}
void
ray_pinit(		/* initialize ray-tracing processes */
	char	*otnm,
	int	nproc
)
{
	if (nobjects > 0)		/* close old calculation */
		ray_pdone(0);

	ray_init(otnm);			/* load the shared scene */

	ray_popen(nproc);		/* fork children */
}
示例#4
0
文件: ray.c 项目: qstemper/42
void		raycasting(t_env *e)
{
	int		x;

	x = 0;
	e->ray.pos.x = e->player.pos.x;
	e->ray.pos.y = e->player.pos.y;
	while (x < e->width)
	{
		ray_init(e, x);
		ray_calc_step_side(e);
		ray_calc_dist(e);
		ray_draw(e, x);
		x++;
	}
}
示例#5
0
/*
 * Calculate reflection color
 */
color refColor(const intersection *inter, const ray *srcRay) {
	color cR = BLACK;
	if (srcRay->depth == MAX_DEPTH)
		return cR;
	intersection refInter;
	vec3 refVec = vector_reflect(srcRay->dir, inter->normal);
	ray refRay; // Ray from object to other object
	ray_init(&refRay, inter->position, refVec, EPSILON, 1000, srcRay->depth + 1);
	int bounceFound = 0;
	for (int k = 0; k < object_count; ++k) {
		bounceFound += intersect(&refRay, &(scene[k]), &refInter);
	}
	color refCoef = reflectCoef(inter->mat.reflect_coef, inter->normal, srcRay->dir);
	if (bounceFound)
		cR = vector_vec_mul(refCoef, vector_add(refColor(&refInter, &refRay), lightColor(&refInter, &refRay)));
	else
		cR = vector_vec_mul(refCoef, SKY_COLOR);
	return cR;
}
示例#6
0
void raytrace() {
	vec3 xR = theCamera.xdir;
	vec3 yR = vector_float_mul(1 / theCamera.aspect, theCamera.ydir);
	vec3 zR = vector_float_mul(1 / (tanf(0.5 * ((theCamera.fov / 180) * M_PI))), theCamera.zdir);
	int halfWidth = WIDTH / 2, halfHeight = HEIGHT / 2;
	for (int i = 0; i < WIDTH; ++i) {
		for (int j = 0; j < HEIGHT; ++j) {
			color c = BLACK;
			float deltas[4][2] = { { .25f, .25f }, { .25f, .75f }, { .75f, .25f }, { .75f, .75f } };
			ray rays[4];
			for (int n = 0; n < 4; ++n) {
				// Calculate ray
				vec3 x = vector_float_mul((i + deltas[n][0] - halfWidth) / halfWidth, xR);
				vec3 y = vector_float_mul((j + deltas[n][1] - halfHeight) / halfHeight, yR);
				vec3 d = vector_add(x, y);
				d = vector_add(d, zR);
				ray_init(&rays[n], theCamera.position, d);
				// Calculate intersection
				intersection inter;
				int found = 0;
				for (int k = 0; k < object_count; ++k) {
					found += (intersect(&rays[n], &(scene[k]), &inter)); // Keep the closest intersection
				}
				// Calculate pixel color
				if (found) {
					color cD = lightColor(&inter, &rays[n]);
					color cR = refColor(&inter, &rays[n]);
					c = vector_add(c, vector_add(cD, cR));
				} else
					c = vector_add(c, SKY_COLOR);
			}
			// Mean
			output_image[j * WIDTH + i] = vector_float_mul(1.0f / 4.0f, c);
		}
		// Progress
		printf("%d%%\n", (int) (((float) i / WIDTH) * 100));
	}
	printf("Done :)\n");
}
示例#7
0
int
main(int argc, char *argv[])
{
#define	 check(ol,al)		if (argv[i][ol] || \
				badarg(argc-i-1,argv+i+1,al)) \
				goto badopt
#define	 check_bool(olen,var)		switch (argv[i][olen]) { \
				case '\0': var = !var; break; \
				case 'y': case 'Y': case 't': case 'T': \
				case '+': case '1': var = 1; break; \
				case 'n': case 'N': case 'f': case 'F': \
				case '-': case '0': var = 0; break; \
				default: goto badopt; }
	char  *octnm = NULL;
	char  *err;
	int  rval;
	int  i;
					/* global program name */
	progname = argv[0] = fixargv0(argv[0]);
					/* set our defaults */
	shadthresh = .1;
	shadcert = .25;
	directrelay = 0;
	vspretest = 128;
	srcsizerat = 0.;
	specthresh = .3;
	specjitter = 1.;
	maxdepth = 6;
	minweight = 1e-2;
	ambacc = 0.3;
	ambres = 32;
	ambdiv = 256;
	ambssamp = 64;
					/* option city */
	for (i = 1; i < argc; i++) {
						/* expand arguments */
		while ((rval = expandarg(&argc, &argv, i)) > 0)
			;
		if (rval < 0) {
			sprintf(errmsg, "cannot expand '%s'", argv[i]);
			error(SYSTEM, errmsg);
		}
		if (argv[i] == NULL || argv[i][0] != '-')
			break;			/* break from options */
		if (!strcmp(argv[i], "-version")) {
			puts(VersionID);
			quit(0);
		}
		if (!strcmp(argv[i], "-defaults") ||
				!strcmp(argv[i], "-help")) {
			printdefaults();
			quit(0);
		}
		if (!strcmp(argv[i], "-devices")) {
			printdevices();
			quit(0);
		}
		rval = getrenderopt(argc-i, argv+i);
		if (rval >= 0) {
			i += rval;
			continue;
		}
		rval = getviewopt(&ourview, argc-i, argv+i);
		if (rval >= 0) {
			i += rval;
			continue;
		}
		switch (argv[i][1]) {
		case 'n':				/* # processes */
			check(2,"i");
			nproc = atoi(argv[++i]);
			if (nproc <= 0)
				error(USER, "bad number of processes");
			break;
		case 'v':				/* view file */
			if (argv[i][2] != 'f')
				goto badopt;
			check(3,"s");
			rval = viewfile(argv[++i], &ourview, NULL);
			if (rval < 0) {
				sprintf(errmsg,
				"cannot open view file \"%s\"",
						argv[i]);
				error(SYSTEM, errmsg);
			} else if (rval == 0) {
				sprintf(errmsg,
					"bad view file \"%s\"",
						argv[i]);
				error(USER, errmsg);
			}
			break;
		case 'b':				/* grayscale */
			check_bool(2,greyscale);
			break;
		case 'p':				/* pixel */
			switch (argv[i][2]) {
			case 's':				/* sample */
				check(3,"i");
				psample = atoi(argv[++i]);
				break;
			case 't':				/* threshold */
				check(3,"f");
				maxdiff = atof(argv[++i]);
				break;
			case 'e':				/* exposure */
				check(3,"f");
				exposure = atof(argv[++i]);
				if (argv[i][0] == '+' || argv[i][0] == '-')
					exposure = pow(2.0, exposure);
				break;
			default:
				goto badopt;
			}
			break;
		case 'w':				/* warnings */
			rval = erract[WARNING].pf != NULL;
			check_bool(2,rval);
			if (rval) erract[WARNING].pf = wputs;
			else erract[WARNING].pf = NULL;
			break;
		case 'e':				/* error file */
			check(2,"s");
			errfile = argv[++i];
			break;
		case 'o':				/* output device */
			check(2,"s");
			dvcname = argv[++i];
			break;
		case 'R':				/* render input file */
			check(2,"s");
			strcpy(rifname, argv[++i]);
			break;
		default:
			goto badopt;
		}
	}
	err = setview(&ourview);	/* set viewing parameters */
	if (err != NULL)
		error(USER, err);
						/* set up signal handling */
	sigdie(SIGINT, "Interrupt");
	sigdie(SIGTERM, "Terminate");
#if !defined(_WIN32) && !defined(_WIN64)
	sigdie(SIGHUP, "Hangup");
	sigdie(SIGPIPE, "Broken pipe");
	sigdie(SIGALRM, "Alarm clock");
#endif
					/* open error file */
	if (errfile != NULL) {
		if (freopen(errfile, "a", stderr) == NULL)
			quit(2);
		fprintf(stderr, "**************\n*** PID %5d: ",
				getpid());
		printargs(argc, argv, stderr);
		putc('\n', stderr);
		fflush(stderr);
	}
#ifdef	NICE
	nice(NICE);			/* lower priority */
#endif
					/* get octree */
	if (i == argc)
		octnm = NULL;
	else if (i == argc-1)
		octnm = argv[i];
	else
		goto badopt;
	if (octnm == NULL)
		error(USER, "missing octree argument");
					/* set up output & start process(es) */
	SET_FILE_BINARY(stdout);
	
	ray_init(octnm);		/* also calls ray_init_pmap() */
	
/* temporary shortcut, until winrview is refactored into a "device" */
#ifndef WIN_RVIEW
	rview();			/* run interactive viewer */


	devclose();			/* close output device */
#endif

	/* PMAP: free photon maps */
	ray_done_pmap();
	
#ifdef WIN_RVIEW
	return 1;
#endif
	quit(0);

badopt:
	sprintf(errmsg, "command line error at '%s'", argv[i]);
	error(USER, errmsg);
	return 1; /* pro forma return */

#undef	check
#undef	check_bool
}