Post by Richard Moss on Jul 10, 2019 19:21:48 GMT
Hello,
I'm currently working my way though the book and have implemented the Chapter 6 test "Computing the normal on a transformed sphere". Except I just cannot get it to pass and I can't work out why. All previous tests are passing and I've backtracked looking to see if any of my previous implementations are faulty and I can't spot anything obviously wrong. Calculating a normal needs too many moving parts for me to post the full source code, so I'll include just the method and then the test output - maybe the pattern of the "actual" value will give a clue as to what is going wrong.
Test output:
(Ignore the [sgx] nonsense, the test framework I'm using requires all those descriptions to be unique)
I've also included the actual C# test steps below that I've implemented.
While I'm learning a fair amount from this book, Mathematics in generally is definitely not my strong point; any advice that can help me figure out where I've gone wrong would be appreciated.
Thanks;
Richard Moss
I'm currently working my way though the book and have implemented the Chapter 6 test "Computing the normal on a transformed sphere". Except I just cannot get it to pass and I can't work out why. All previous tests are passing and I've backtracked looking to see if any of my previous implementations are faulty and I can't spot anything obviously wrong. Calculating a normal needs too many moving parts for me to post the full source code, so I'll include just the method and then the test output - maybe the pattern of the "actual" value will give a clue as to what is going wrong.
public static Tuple NormalAt(Sphere sphere, Tuple worldPoint)
{
Tuple objectPoint;
Tuple objectNormal;
Tuple worldNormal;
objectPoint = Matrix.Invert(sphere._transform) * worldPoint;
objectNormal = objectPoint - sphere._origin;
worldNormal = Matrix.Transpose(Matrix.Invert(sphere._transform)) * objectNormal;
worldNormal.W = 0;
return Tuple.Normalize(worldNormal);
}
Test output:
Given s ← sphere() [sqa]
-> done: SpheresSteps.Scenario17Step1() (0.0s)
And m ← scaling(1, 0.5, 1) * rotation_z(π/5) [sqb]
-> done: SpheresSteps.Scenario17Step2(1, 0.5, 1, 5) (0.0s)
And set_transform(s, m) [sqc]
-> done: SpheresSteps.Scenario17Step3() (0.0s)
When n ← normal_at(s, point(0, √2/2, -√2/2)) [sqd]
-> done: SpheresSteps.Scenario17Step4(0, 2, 2, 2, 2) (0.0s)
Then n = vector(0, 0.97014, -0.24254) [sqe]
-> error: Assert.AreEqual failed. Expected:<{X=0, Y=0.97014, Z=-0.24254, W=0}>. Actual:<{X=-2.044423E-08, Y=0.9701425, Z=0.2425356, W=0}>.
(Ignore the [sgx] nonsense, the test framework I'm using requires all those descriptions to be unique)
I've also included the actual C# test steps below that I've implemented.
[Given(@"s ← sphere\(\) \[sqa]")]
public void Scenario17Step1()
{
_sphere = new Sphere(Tuple.Point(0, 0, 0), 1);
}
[Given(@"m ← scaling\((.*), (.*), (.*)\) \* rotation_z\(π/(.*)\) \[sqb]")]
public void Scenario17Step2(float x, float y, float z, float r)
{
_transform = Matrix.Scale(x, y, z) * Matrix.RotateZ(MathF.PI / r);
}
[Given(@"set_transform\(s, m\) \[sqc]")]
public void Scenario17Step3()
{
_sphere.Transform = _transform;
}
[When(@"n ← normal_at\(s, point\((.*), √(.*)/(.*), -√(.*)/(.*)\)\) \[sqd]")]
public void Scenario17Step4(float x, float yr, float yd, float zr, float zd)
{
_normal = Sphere.NormalAt(_sphere, Tuple.Point(x, MathF.Sqrt(yr) / yd, MathF.Sqrt(zr) / zd));
}
[Then(@"n = vector\((.*), (.*), (.*)\) \[sqe]")]
public void Scenario17Step5(float x, float y, float z)
{
Tuple expected;
Tuple actual;
expected = Tuple.Vector(x, y, z);
actual = _normal;
Assert.AreEqual(expected, actual);
}
While I'm learning a fair amount from this book, Mathematics in generally is definitely not my strong point; any advice that can help me figure out where I've gone wrong would be appreciated.
Thanks;
Richard Moss