Beispiel #1
0
Vect Vect::vectAdd(Vect v) {
	return Vect (x + v.getVectX(), y + v.getVectY(), z + v.getVectZ());
}
Beispiel #2
0
Vect Vect::crossProduct(Vect v) {
	return Vect (y * v.getVectZ() - z * v.getVectY(), z * v.getVectX() - x * v.getVectZ(), x * v.getVectY() - y * v.getVectX());
}
Beispiel #3
0
Color getColorAt(Vect intersection_position, Vect intersecting_ray_direction, vector<Object*> scene_objects, int index_of_winning_object, vector<Source*> light_sources,  double accuracy, double ambientlight, int bounces){
	
	Color winning_object_color = scene_objects.at(index_of_winning_object)->getColor();
	Vect winning_object_normal = scene_objects.at(index_of_winning_object)->getNormalAt(intersection_position);

	if (winning_object_color.getColorSpecial() == 2){
		//tile floor

		int square = (int)floor(intersection_position.getVectX()) + (int)floor(intersection_position.getVectZ());

		if ((square % 2) == 0) {
			//black
			winning_object_color.setColorRed(0);
			winning_object_color.setColorGreen(0);
			winning_object_color.setColorBlue(0);
		}else{
			//white
			winning_object_color.setColorRed(1);
			winning_object_color.setColorGreen(1);
			winning_object_color.setColorBlue(1);
		}
	}

	Color final_color = winning_object_color.colorScalar(ambientlight);

	if (winning_object_color.getColorSpecial() > 0 && winning_object_color.getColorSpecial() <= 1){
		//reflection from objects that have spec value
		double dot1 = winning_object_normal.dotProduct(intersecting_ray_direction.negative());
		Vect scalar1 = winning_object_normal.vectMult(dot1);
		Vect add1 = scalar1.vectAdd(intersecting_ray_direction);
		Vect scalar2 = add1.vectMult(2);
		Vect add2 = intersecting_ray_direction.negative().vectAdd(scalar2);
		Vect reflection_direction = add2.normalize();

		Ray reflection_ray (intersection_position, reflection_direction);

		//determine what the ray intersects first
		vector<double> reflection_intersections;

		for(int reflection_index = 0; reflection_index < scene_objects.size(); reflection_index++){
			reflection_intersections.push_back(scene_objects.at(reflection_index)->findIntersection(reflection_ray));
		}

		int index_of_winning_object_with_reflection = winningObjectIndex(reflection_intersections);

		if (index_of_winning_object_with_reflection != -1){
			//reflection ray missed everything else
			//recursive number to keep track of light bounces
			int numberOfBounces = bounces;
			if (numberOfBounces < 2){
				numberOfBounces++;
				//determine the position and direction at the point of intersection with the ray
				// the ray only affects the color if it reflects off something
				Vect reflection_intersection_position = intersection_position.vectAdd(reflection_direction.vectMult(reflection_intersections.at(index_of_winning_object_with_reflection)));
				Vect reflection_intersection_ray_direction = reflection_direction;

				Color reflection_intersection_color = getColorAt(reflection_intersection_position, reflection_intersection_ray_direction,scene_objects,index_of_winning_object_with_reflection,light_sources, accuracy, ambientlight,numberOfBounces);

				final_color = final_color.colorAdd(reflection_intersection_color.colorScalar(winning_object_color.getColorSpecial()));
			}
		}

	}

	for (int light_index = 0; light_index < light_sources.size(); light_index++){
		Vect light_direction = light_sources.at(light_index)->getLightPosition().vectAdd(intersection_position.negative()).normalize();

		float cosine_angle = winning_object_normal.dotProduct(light_direction);

		if (cosine_angle > 0){
			// test for shadows
			bool shadowed = false;

			Vect distance_to_light = light_sources.at(light_index)->getLightPosition().vectAdd(intersection_position.negative());
			float distance_to_light_magnitude = distance_to_light.magnitude();

			Ray shadow_ray(intersection_position, light_sources.at(light_index)->getLightPosition().vectAdd(intersection_position.negative()).normalize());

			vector<double> secondary_intersections;


			for (int object_index = 0; object_index < scene_objects.size() && shadowed == false; object_index++){
				secondary_intersections.push_back(scene_objects.at(object_index)->findIntersection(shadow_ray));
			}

			for (int c = 0; c < secondary_intersections.size(); c++){
				if(secondary_intersections.at(c) > accuracy){
					if (secondary_intersections.at(c) <= distance_to_light_magnitude){
						shadowed = true;
					}
					break;
				}
			}
			if (shadowed == false){
				final_color = final_color.colorAdd(winning_object_color.colorMultiply(light_sources.at(light_index)->getColor()).colorScalar(cosine_angle));

				if (winning_object_color.getColorSpecial() > 0 && winning_object_color.getColorSpecial() <= 1){
					//special 0 to 1
					double dot1 = winning_object_normal.dotProduct(intersecting_ray_direction.negative());
					Vect scalar1 = winning_object_normal.vectMult(dot1);
					Vect add1 = scalar1.vectAdd(intersecting_ray_direction);
					Vect scalar2 = add1.vectMult(2);
					Vect add2 = intersecting_ray_direction.negative().vectAdd(scalar2);
					Vect reflection_direction = add2.normalize();

					double specular = reflection_direction.dotProduct(light_direction);
					if (specular > 0){
						specular = pow(specular, 10);
						final_color = final_color.colorAdd(light_sources.at(light_index)->getColor().colorScalar(specular*winning_object_color.getColorSpecial()));
					}
				}
			}
			

		}
	}

	return final_color.clip();
}
Beispiel #4
0
double Vect::dotProduct(Vect v) {
	return x * v.getVectX() + y * v.getVectY() + z * v.getVectZ();
}
Beispiel #5
0
int renderFunction(void *data){
		while(runThread){
			int secNum = (int)data;
			if(threadsFinishedRendering[secNum-1] == false){
				clock_t start;
				double duration;
				start = clock();

				Vect campos (camtrackerx-1.2, camtrackery, camtrackerz);

				//Vect cam_sphere_pos (camtrackerx,camtrackery,camtrackerz);
				//Sphere cam_sphere (cam_sphere_pos, 1, pretty_blue);
				Vect diff_btw (campos.getVectX() - look_at.getVectX(), campos.getVectY() - look_at.getVectY(), campos.getVectZ() - look_at.getVectZ()); //difference between camera's coor - look at

				Vect camdir = diff_btw.negative().normalize();
				Vect camright = Y.crossProduct(camdir).normalize();
				Vect camdown = camright.crossProduct(camdir);

				Camera scene_cam (campos, camdir, camright, camdown);

				Light scene_light (light_pos,white_light);
				vector<Source*> light_sources;
				light_sources.push_back(dynamic_cast<Source*>(&scene_light));

				vector<Object*> scene_objects;
				scene_objects.push_back(dynamic_cast<Object*>(&scene_sphere));
				scene_objects.push_back(dynamic_cast<Object*>(&scene_sphere2));
				//scene_objects.push_back(dynamic_cast<Object*>(&cam_sphere));
				scene_objects.push_back(dynamic_cast<Object*>(&scene_plane));

				double xamnt, yamnt;
				int aa_index;

				for (int x = 0; x < width; x++){
					for (int y  = (int)((height/numOfThreads)*(secNum-1)); y < (int)((height/numOfThreads)*(secNum)); y++){

					
						//blank pixel
						double tempRed[aadepth*aadepth];
						double tempGreen[aadepth*aadepth];
						double tempBlue[aadepth*aadepth];

						for (int aax = 0; aax < aadepth; aax++){
							for(int aay = 0; aay < aadepth; aay++){

								aa_index = aay*aadepth + aax;

								srand(time(0));

								//create the ray from the camera to this pixel
								if(aadepth == 1){
									//start with no anti aliasing
									if (width > height) {
										//the image is wider than tall
										xamnt = ((x+0.5)/width)*aspectratio - (((width-height)/(double)height)/2);
										yamnt = ((height -y) + 0.5)/height;
									}else if (height > width){
										//the image is taller than wide
										xamnt = (x+0.5)/ width;
										yamnt = (((height - y) + 0.5)/height)/aspectratio - (((height - width)/(double)width)/2);
									}else{
										//the image is square
										xamnt = (x+0.5)/width;
										yamnt = ((height - y) + 0.5)/height;
									}
								}else{
									//anti alias
									if (width > height) {
										//the image is wider than tall
										xamnt = ((x+(double)aax/((double)aadepth - 1))/width)*aspectratio - (((width-height)/(double)height)/2);
										yamnt = ((height -y) + (double)aax/((double)aadepth - 1))/height;
									}else if (height > width){
										//the image is taller than wide
										xamnt = (x+(double)aax/((double)aadepth - 1))/ width;
										yamnt = (((height - y) + (double)aax/((double)aadepth - 1))/height)/aspectratio - (((height - width)/(double)width)/2);
									}else{
										//the image is square
										xamnt = (x+(double)aax/((double)aadepth - 1))/width;
										yamnt = ((height - y) + (double)aax/((double)aadepth - 1))/height;
									}
								}



								Vect cam_ray_origin = scene_cam.getCameraPosition();
								Vect cam_ray_direction = camdir.vectAdd(camright.vectMult(xamnt - 0.5).vectAdd(camdown.vectMult(yamnt - 0.5))).normalize();

								Ray cam_ray (cam_ray_origin, cam_ray_direction);

								vector<double> intersections;
								//0.02 seconds up to this point^


								for (int index = 0; index < scene_objects.size(); index++){
									//loops through each object in scene and finds intersection
									intersections.push_back(scene_objects.at(index)->findIntersection(cam_ray));
								}
								//0.08 seconds to this point^

								int index_of_winning_object = winningObjectIndex(intersections);
								//0.104 seconds to this point^

								//painting the scene
								if (index_of_winning_object == -1){
									tempRed[aa_index] = 0;
									tempGreen[aa_index] = 0;
									tempBlue[aa_index] = 0;
									//pixels[y * width + x] = 0;
								}else{
									//index is a hit on an object in the scene
									if (intersections.at(index_of_winning_object) > accuracy){
										//determine the position and direction vectors at the point of intersection

										Vect intersection_position = cam_ray_origin.vectAdd(cam_ray_direction.vectMult(intersections.at(index_of_winning_object)));
										Vect intersecting_ray_direction = cam_ray_direction;
				
										Color intersection_color = getColorAt(intersection_position, intersecting_ray_direction, scene_objects, index_of_winning_object, light_sources, accuracy, ambientlight,0);
										tempRed[aa_index] = intersection_color.getColorRed()*255;
										tempGreen[aa_index] = intersection_color.getColorGreen()*255;
										tempBlue[aa_index] = intersection_color.getColorBlue()*255;

										//pixels[y * width + x] = createRGBA(255,(int)(intersection_color.getColorRed()*255), (int)(intersection_color.getColorGreen()*255), (int)(intersection_color.getColorBlue()*255));

									}
								}
								if(y == (int)((height/numOfThreads)*(secNum-1))){pixels[y * width + x] = 0x00ff0000;}
								//0.308 seconds to this point^, about 0.080 is for rendering pixels
							}
						}

						double totalRed = 0;
						double totalGreen = 0;
						double totalBlue = 0;

						for(int iRed = 0; iRed < aadepth*aadepth; iRed++){
							totalRed = totalRed + tempRed[iRed];
						}
						for(int iGreen = 0; iGreen < aadepth*aadepth; iGreen++){
							totalGreen = totalGreen + tempGreen[iGreen];
						}
						for(int iBlue = 0; iBlue < aadepth*aadepth; iBlue++){
							totalBlue = totalBlue + tempBlue[iBlue];
						}

						double avgRed = totalRed/(aadepth*aadepth);
						double avgGreen = totalGreen/(aadepth*aadepth);
						double avgBlue = totalBlue/(aadepth*aadepth);

						pixels[y * width + x] = createRGBA(255,avgRed,avgGreen,avgBlue);
					}
				}
				//delete tempBlue, tempGreen, tempRed;
				threadsFinishedRendering[secNum-1] = true;
				duration = ( clock() - start ) / (double) CLOCKS_PER_SEC;
				threadsSpeed[secNum-1] = duration;
				//cout << "Thread Number: " << secNum << " with time: " << duration << " seconds" << endl; 
			}
		}
		return 0;
}