public static Matrix4By4 YRotation(double rotationAngleThroughYAxis) { Matrix4By4 rm = new Matrix4By4(new Matrix(new Vector(Math.Cos(Algebra.convertToRad(rotationAngleThroughYAxis)), 0, (-1) * Math.Sin(Algebra.convertToRad(rotationAngleThroughYAxis))), new Vector(0, 1, 0), new Vector(Math.Sin(Algebra.convertToRad(rotationAngleThroughYAxis)), 0, Math.Cos(Algebra.convertToRad(rotationAngleThroughYAxis)))), new Vector()); return(rm); }
// method for finding the new ray origin and new ray direction according to the DOF Ray FindDOFRay(Vector pointInThePixel) { //getting random value for aperture size that is the radius if the circle which will be in blur double randomRadius = Algebra.getRandomNumber(0, apertureSize); //similarly getting the random angle of the circle for getting the random point in the aperture size or the circle in focus double randomAngle = Algebra.getRandomNumber(0, 2 * Math.PI); //new x and y positions of camera are determined by random radius and random angle of circle having radius equal to aperture size double xPositionOfCamera = randomRadius * Math.Cos(Algebra.convertToRad(randomAngle)); double yPositionOfCamera = randomRadius * Math.Sin(Algebra.convertToRad(randomAngle)); //here assigning new x and y values for camera Vector rayOrigin = new Vector(xPositionOfCamera, yPositionOfCamera, 0); //similarly finding new ray direction and converting to world coordinates and getting it's unit vector Vector direction = pointInThePixel - rayOrigin; Vector newRayDirection = convertCameraToWorldCoordinates(direction).Normalize(); return(new Ray(rayOrigin + position, newRayDirection)); }
// making does intersect method which returns t values public override double DoesIntersect(Vector origin, Vector direction) { double txmin = (position.x - origin.x) / direction.x; // this is minimum x value of t double txmax = (maxPosition.x - origin.x) / direction.x; // this is maximum x value of t // if txmin is greater than txmax than interchanging the txmin and txmax if (txmin > txmax) { Algebra.swap(txmin, txmax); } // also doing the same process for y values of minimum and maximum positions of a box double tymin = (position.y - origin.y) / direction.y; double tymax = (maxPosition.y - origin.y) / direction.y; // if tymin is greater than tymax than interchanging both values if (tymin > tymax) { Algebra.swap(tymin, tymax); } // ray doesnot intersect if either txmin is greater than tymax or tymin is greater than txmax if ((txmin > tymax) || (tymin > txmax)) { return(-1); } // whereas txmax is greater than tymax than txmax will be tymax if (tymax < txmax) { txmax = tymax; } // similarly doing same process for z of position vectors of box i.e. minimum and maximum vectors double tzmin = (position.z - origin.z) / direction.z; double tzmax = (maxPosition.z - origin.z) / direction.z; // similarly swaping tzmin and tzmax if tzmin is greater than tzmax if (tzmin > tzmax) { Algebra.swap(tzmin, tzmax); } // ray doesnot intersect either txmin is greater than tzmax or tzmin is greater than txmax if ((txmin > tzmax) || (tzmin > txmax)) { return(-1); } // if tzmin is greater than txmin than assigning the value of txmin as tzmin if (tzmin > txmin) { txmin = tzmin; } // if tzmax is greater than txmax than assigning the value of tzmax as txmax if (tzmax < txmax) { txmax = tzmax; } // so returning tmin at last return(txmin > txmax ? txmax : txmin); }
public void Render(Scene scene, Bitmap bmp) { //creating a array for storing different types of combinations for jittered sampling double[] possibleCombinations = new double[numberOfJittered]; //if jittered is given then only it will push variables to the array if (numberOfJittered > 1) { for (int l = 0; l < numberOfJittered; l++) { possibleCombinations[l] = (double)(2 * l + 1) / (numberOfJittered * 2); } } // getting the color of the for (int i = 0; i < height; i++) { for (int j = 0; j < width; j++) { // for getting random values from 0 to 1 for super sampling or random sampling Random randomNumber = new Random(); // creating one empty color space for averaging the color for that pixel in multi sampling SColor samplingColor = new SColor(); //giving background color as black at first bmp.SetPixel(j, i, Color.FromArgb(255, 0, 0, 0)); //this is the loop for anti-aliasing(AA) that is number of samples if (numberOfJittered > 1) { numberOfSamples = (int)Math.Pow(numberOfJittered, 2); } double dz = (height / 2) / (Math.Tan(Algebra.convertToRad(fov * 0.5))); // calculating dz if (DOFUsed) { pixelSize = focalLength / dz; } else { pixelSize = 1 / dz; } Vector pointInThePixel = (new Vector((-width / 2), (height / 2), 0) + new Vector(0.5, -0.5, 0) + new Vector(j, -i, position.z)) * pixelSize; // changing the basis i.e. in terms of i and j of the image Double wOffset = 1; if (DOFUsed) { wOffset = focalLength; } for (int k = 0; k < numberOfSamples; k++) { Ray ray = new Ray(position, new Vector()); //checking number of jittered is given or not through it's default value //that is if number of jittered is not given than calculating as usual number of sampling way //otherwise that is if number of jittered is given than calculating number of jitterd out of it and checking through midpoints of those number of samples of each pixel if (numberOfJittered == 1) { double m = randomNumber.NextDouble(); // gives random number between 0 and 1 //// //Vector coordinate = new Vector((-width / 2), (height / 2), 0) + new Vector(0.5, -0.5, 0) + new Vector(j, -i, position.z); // changing the basis i.e. in terms of i and j of the image //// //if number of samplings is 1 then here the value of m will be 0.5 otherwise it will be m which is the random number from 0 to 1 double dx = (j - (width / 2) + (numberOfSamples == 1 ? 0.5 : m)) * pixelSize; // calculating dx double dy = (((height / 2) - i) + (numberOfSamples == 1 ? 0.5 : m)) * pixelSize; // calculating dy //double dz = 1;// (height / 2) / (Math.Tan(Algebra.convertToRad(fov * 0.5))); // calculating dz pointInThePixel = new Vector(dx, dy, wOffset); ray.direction = convertCameraToWorldCoordinates(pointInThePixel).Normalize(); // so vector (dx, dy, dz) will be the direction of the ray which is normalized } else { int kX = (k % numberOfJittered); // this is for finding the index of the array for giving possible value of mid points of jittered grid int kY = (k / numberOfJittered); // this is for finding the next index of the array for giving possible value pf mid points of jittered grid //Debug.Assert(kX == 0.25); double dx = j - (width / 2) + (numberOfSamples == 1 ? 0.5 : possibleCombinations[kX]); // calculating dx where possible combination is given by indexing the array double dy = ((height / 2) - i) + (numberOfSamples == 1 ? 0.5 : possibleCombinations[kY]); // calculating dy //double dz = 1;// (height / 2) / (Math.Tan(Algebra.convertToRad(fov * 0.5))); // calculating dz ray.direction = convertCameraToWorldCoordinates(new Vector(dx, dy, 1)).Normalize(); // so vector (dx, dy, dz) will be the direction of the ray which is normalized } if (DOFUsed) { ray = FindDOFRay(pointInThePixel); } // adding all the color of the samples that is given for multi sampling samplingColor += TraceRay(ray, scene, 0); } //taking the average of the color of those all samples SColor colorSampling = samplingColor / numberOfSamples; //now giving that average color of all those samples bmp.SetPixel(j, i, Color.FromArgb(colorSampling.GetAlphaColor(), colorSampling.GetRedColor(), colorSampling.GetGreenColor(), colorSampling.GetBlueColor())); } } }