public HitResult(bool isHit, IFigure figure, double distance, double u, double v, Tuple4 objectPoint, Tuple4 pointOnSurface, Tuple4 pointOverSurface, Tuple4 pointUnderSurface, Tuple4 surfaceNormal, Tuple4 eyeVector, Tuple4 reflectionVector, bool isInside) { IsHit = isHit; Figure = figure; Distance = distance; U = u; V = v; ObjectPoint = objectPoint; PointOnSurface = pointOnSurface; PointOverSurface = pointOverSurface; PointUnderSurface = pointUnderSurface; SurfaceNormal = surfaceNormal; EyeVector = eyeVector; ReflectionVector = reflectionVector; IsInside = isInside; }
public GradientPattern(IMatrix transformation, Tuple4 colorA, Tuple4 colorB) : base(transformation) { ColorA = colorA; ColorB = colorB; colorDelta = Tuple4.Subtract(ColorB, colorA); }
public CheckerPattern(IMatrix transformation, Tuple4 colorA, Tuple4 colorB, bool is3D) : base(transformation) { ColorA = colorA; ColorB = colorB; Is3D = is3D; }
protected override Intersection[] GetBaseIntersections(Ray ray) { var dir_cross_e2 = Tuple4.CrossProduct(ray.dir, E2); var det = Tuple4.DotProduct(E1, dir_cross_e2); if (Constants.EpsilonZero(Math.Abs(det))) { return(null); } var f = 1.0 / det; var p1_to_origin = Tuple4.Subtract(ray.origin, P1); var u = f * Tuple4.DotProduct(p1_to_origin, dir_cross_e2); if ((u < 0.0) || (u > 1.0)) { return(null); } var origin_cross_e1 = Tuple4.CrossProduct(p1_to_origin, E1); var v = f * Tuple4.DotProduct(ray.dir, origin_cross_e1); if ((v < 0.0) || ((u + v) > 1.0)) { return(null); } var t = f * Tuple4.DotProduct(E2, origin_cross_e1); return(new Intersection[] { new Intersection(t, this) }); }
public void SimpleCameraTest() { // Ray cast for screen coordinate 0,0 { var camera = new SimpleCamera(new Tuple4(0.0, 0.0, -4.0, TupleFlavour.Point), 6.0, 600, 800); var ray = camera.GetRay(0, 0); var expectedRay = new Ray( new Tuple4(0.0, 0.0, -4.0, TupleFlavour.Point), Tuple4.Normalize(new Tuple4(-3.0, 3.0, 1.0, TupleFlavour.Vector))); Assert.Equal(expectedRay.origin, ray.origin); Assert.Equal(expectedRay.dir, ray.dir); var t = Tuple4.Add(ray.origin, Tuple4.Scale(ray.dir, 4.35890)); Assert.Equal(new Tuple4(-3.0, 3.0, -3.0, TupleFlavour.Point), t); } // Ray cast for screen coordinate width,height { var camera = new SimpleCamera(new Tuple4(0.0, 0.0, -4.0, TupleFlavour.Point), 6.0, 600, 800); var ray = camera.GetRay(600, 800); var expectedRay = new Ray( new Tuple4(0.0, 0.0, -4.0, TupleFlavour.Point), Tuple4.Normalize(new Tuple4(3.0, -3.0, 1.0, TupleFlavour.Vector))); Assert.Equal(expectedRay.origin, ray.origin); Assert.Equal(expectedRay.dir, ray.dir); } { var camera = new SimpleCamera(new Tuple4(0, 0, -1.0, TupleFlavour.Point), 2.0, 600, 600); var ray = camera.GetRay(0, 0); var t = Tuple4.Add(ray.origin, Tuple4.Scale(ray.dir, 1.73205)); Assert.Equal(new Tuple4(-1.0, 1.0, 0.0, TupleFlavour.Point), t); } }
public void Then_vector(string id, double t1, double t2, double t3) { var v = new Tuple4(t1, t2, t3, TupleFlavour.Vector); Assert.Equal(v, tuple[id]); }
public void CanAddTwoTuple4Values() { var a1 = new Tuple4(3, -2, 5, 1); var a2 = new Tuple4(-2, 3, 1, 0); Assert.Equal(new Tuple4(1, 1, 6, 1), a1 + a2); }
public FPSCamera(Tuple4 origin, double pitch, double yaw, double fieldOfView, double screenWidth, double screenHeight) { this.Origin = origin; this.FieldOfView = fieldOfView; this.ScreenWidth = screenWidth; this.ScreenHeight = screenHeight; this.yaw = yaw; this.pitch = pitch; this.Transformation = MatrixOperations.Geometry3D.EulerAnglesTransform(origin, pitch, yaw); aspect = screenWidth / screenHeight; var halfView = Math.Tan(fieldOfView / 2.0); if (Constants.EpsilonCompare(aspect, 1.0) || aspect > 1.0) { tangy = halfView / aspect; tangx = halfView; } else { tangy = halfView; tangx = halfView * aspect; } PixleSize = tangx * 2 / screenWidth; }
public void Then_position(string id, double t, double x, double y, double z) { var expected = new Tuple4(x, y, z, TupleFlavour.Point); var actual = ray[id].PositionAt(t); Assert.Equal(expected, actual); }
private static Lighting GetIntensity(IMaterial material, Tuple4 lightDirection, double intensity, Tuple4 eyeVector, Tuple4 pointOnSurface, Tuple4 surfaceNormal) { var diffuse = 0.0; var specular = 0.0; var cosine = Tuple4.DotProduct(lightDirection, surfaceNormal); if (cosine >= 0) { diffuse = cosine * material.Diffuse; if (material.IsShining()) { // var reflected = Tuple4.Subtract(Tuple4.Scale(surfaceNormal, 2 * Tuple4.DotProduct(surfaceNormal, lightDirection)), lightDirection); var reflected = Tuple4.Reflect(Tuple4.Negate(lightDirection), surfaceNormal); var reflectedDotDir = Tuple4.DotProduct(reflected, eyeVector); if (reflectedDotDir > 0) { specular = material.Specular * Math.Pow(reflectedDotDir / (reflected.Length() * eyeVector.Length()), material.Shininess); } } } return(diffuse, specular, intensity); }
public static double Schlick(HitResult hit, double refractiveIndexEntering, double refractiveIndexExiting) { // find the cosine of the angle between the eye and normal vectors double cosI = Tuple4.DotProduct(hit.EyeVector, hit.SurfaceNormal); // total internal reflection can only occur if n1 > n2 if (refractiveIndexEntering > refractiveIndexExiting) { double ration = refractiveIndexEntering / refractiveIndexExiting; double sinTheta2 = ration * ration * (1.0 - cosI * cosI); if (sinTheta2 > 1.0) { return(1.0); } // compute cosine of theta_t using trig identity var cosTheta = Math.Sqrt(1.0 - sinTheta2); // when n1 > n2, use cos(theta_t) instead cosI = cosTheta; } var r0 = Math.Pow((refractiveIndexEntering - refractiveIndexExiting) / (refractiveIndexEntering + refractiveIndexExiting), 2); return(r0 + (1 - r0) * Math.Pow((1 - cosI), 5)); }
protected internal override double DistanceFrom(Tuple4 point) { if (point.IsVector()) { throw new ArgumentException("Argument is not a point"); } // If d.x < 0, then -1 < p.x < 1, and same logic applies to p.y, p.z // So if all components of d are negative, then p is inside the unit cube // vec3 d = abs(p) - vec3(1.0, 1.0, 1.0); double dX = Math.Abs(point.X) - 1.0; double dY = Math.Abs(point.Y) - 1.0; double dZ = Math.Abs(point.Z) - 1.0; // Assuming p is inside the cube, how far is it from the surface? // Result will be negative or zero. double insideDistance = Math.Min(Math.Max(dX, Math.Max(dY, dZ)), 0.0); // Assuming p is outside the cube, how far is it from the surface? // Result will be positive or zero. if (dX < 0.0) { dX = 0.0; } if (dY < 0.0) { dY = 0.0; } if (dZ < 0.0) { dZ = 0.0; } double outsideDistance = Math.Sqrt(dX * dX + dY * dY + dZ * dZ); return(insideDistance + outsideDistance); }
public void TupleDotProductTest() { var t1 = new Tuple4(-1, 7, 3, TupleFlavour.Vector); var t2 = new Tuple4(4, 5, 6, TupleFlavour.Vector); Assert.Equal(49.0, Tuple4.DotProduct(t1, t2)); }
public Tuple4 GetLocalNormal(IFigure figure, Tuple4 point) { var objectPoint = TransformWorldPointToObjectPoint(point); var normal = GetBaseNormal(figure, objectPoint, 0.0, 0.0); return(normal); }
public void Then_scale_scalar3(string a, double s, double t1, double t2, double t3) { var c = Tuple4.Scale(cache[a], s); Assert.True(Constants.EpsilonCompare(t1, c.X)); Assert.True(Constants.EpsilonCompare(t2, c.Y)); Assert.True(Constants.EpsilonCompare(t3, c.Z)); }
protected override Tuple4 GetColorAtPattern(Tuple4 pointInPatternSpace) { if (Math.Floor(pointInPatternSpace.X * pointInPatternSpace.X + pointInPatternSpace.Z * pointInPatternSpace.Z) % 2 == 0) { return(ColorA); } return(ColorB); }
public void Then_plus3(string a, string b, double t1, double t2, double t3) { var c = Tuple4.Add(cache[a], cache[b]); Assert.True(Constants.EpsilonCompare(t1, c.X)); Assert.True(Constants.EpsilonCompare(t2, c.Y)); Assert.True(Constants.EpsilonCompare(t3, c.Z)); }
public void Then_normalize(string a, double t1, double t2, double t3) { var c = Tuple4.Normalize(cache[a]); Assert.True(Constants.EpsilonCompare(t1, c.X)); Assert.True(Constants.EpsilonCompare(t2, c.Y)); Assert.True(Constants.EpsilonCompare(t3, c.Z)); }
public void Then_cross(string a, string b, double t1, double t2, double t3) { var c = Tuple4.CrossProduct(cache[a], cache[b]); Assert.True(Constants.EpsilonCompare(t1, c.X)); Assert.True(Constants.EpsilonCompare(t2, c.Y)); Assert.True(Constants.EpsilonCompare(t3, c.Z)); }
protected override Tuple4 GetColorAtPattern(Tuple4 pointInPatternSpace) { if ((Math.Floor(pointInPatternSpace.X) + Math.Floor((Is3D ? 1.0 : 0.0) * pointInPatternSpace.Y) + Math.Floor(pointInPatternSpace.Z)) % 2 == 0) { return(ColorA); } return(ColorB); }
public Tuple4 GetNormal(IFigure figure, Tuple4 point, double u, double v) { if (figure != null && !(figure == this || figure.Parent == this)) { throw new ArgumentException($"{nameof(figure)} is not part of this figure"); } return(GetTransformedNormal(figure, point, u, v).normal); }
public void TupleNegateTest() { var t1 = new Tuple4(1, 7, 3, TupleFlavour.Vector); var expected = new Tuple4(-1, -7, -3, TupleFlavour.Vector); Assert.Equal(expected, Tuple4.Negate(t1)); }
public void TupleScaleByTest() { var t1 = new Tuple4(1, 7, 3, TupleFlavour.Vector); var expected = new Tuple4(0.5, 3.5, 1.5, TupleFlavour.Vector); Assert.Equal(expected, Tuple4.Scale(t1, 0.5)); }
public Tuple4 GetColor(Tuple4 point) { if (transformation != null && transformation != Matrix4x4.Identity) { point = MatrixOperations.Geometry3D.Transform(inverseTransformation, point); } return(GetColorAtPattern(point)); }
public void TupleCrossProductTest() { var t1 = new Tuple4(1, 7, 3, TupleFlavour.Vector); var t2 = new Tuple4(4, 5, 6, TupleFlavour.Vector); var expected = new Tuple4(27, 6, -23, TupleFlavour.Vector); Assert.Equal(expected, Tuple4.CrossProduct(t1, t2)); }
public void TupleReflectTest() { var t1 = new Tuple4(1, 7, 3, TupleFlavour.Vector); var t2 = new Tuple4(4, 5, 6, TupleFlavour.Vector); var expected = new Tuple4(-455, -563, -681, TupleFlavour.Vector); Assert.Equal(expected, Tuple4.Reflect(t1, t2)); }
protected internal override double DistanceFrom(Tuple4 point) { if (point.IsVector()) { throw new ArgumentException("Argument is not a point"); } return(Math.Sqrt(point.X * point.X + point.Y * point.Y + point.Z * point.Z) - 1.0); }
public void TupleAddTest() { var t1 = new Tuple4(1, 2, 3, TupleFlavour.Vector); var t2 = new Tuple4(4, 5, 6, TupleFlavour.Vector); var expected = new Tuple4(5, 7, 9, TupleFlavour.Vector); Assert.Equal(expected, Tuple4.Add(t1, t2)); }
public void TupleSubtractTest() { var t1 = new Tuple4(1, 7, 3, TupleFlavour.Vector); var t2 = new Tuple4(4, 5, 6, TupleFlavour.Vector); var expected = new Tuple4(-3, 2, -3, TupleFlavour.Vector); Assert.Equal(expected, Tuple4.Subtract(t1, t2)); }
public void TupleScaleTest() { var t1 = new Tuple4(1, 7, 3, TupleFlavour.Vector); var t2 = new Tuple4(4, 5, 6, TupleFlavour.Vector); var expected = new Tuple4(4, 35, 18, TupleFlavour.Vector); Assert.Equal(expected, Tuple4.Scale(t1, t2)); }