Просмотр исходного кода

Add the hit function to get the closest non negative hit, and add some mecanisme to test that properly and report when no valid hit occur.

Godzil 4 лет назад
Родитель
Сommit
c4418683c6
4 измененных файлов с 99 добавлено и 1 удалено
  1. 1 0
      source/include/intersect.h
  2. 3 0
      source/include/intersection.h
  3. 25 1
      source/intersect.cpp
  4. 70 0
      tests/intersect_test.cpp

+ 1 - 0
source/include/intersect.h

@@ -23,6 +23,7 @@ public:
     void add(Intersection i);
     int count() { return this->num; };
     Intersection operator[](const int p) { return this->list[p]; }
+    Intersection hit();
 };
 
 #endif //DORAYME_INTERSECT_H

+ 3 - 0
source/include/intersection.h

@@ -21,6 +21,9 @@ public:
 
 public:
     Intersection(double t, Object *object) : t(t), object(object) { };
+    bool nothing() { return (this->object == nullptr); };
+
+    bool operator==(const Intersection &b) const { return ((this->t == b.t) && (this->object == b.object)); };
 };
 
 #endif //DORAYME_INTERSECTION_H

+ 25 - 1
source/intersect.cpp

@@ -7,9 +7,11 @@
  *
  */
 #include <stdlib.h>
-
+#include <math_helper.h>
 #include <intersect.h>
 
+#include <float.h>
+
 #define MIN_ALLOC (2)
 
 Intersect::Intersect()
@@ -27,4 +29,26 @@ void Intersect::add(Intersection i)
         this->list = (Intersection *)realloc(this->list, sizeof(Object *) * this->allocated);
     }
     this->list[this->num++] = i;
+}
+
+Intersection Intersect::hit()
+{
+    int i;
+    double minHit = DBL_MAX;
+    uint32_t curHit = -1;
+    for(i = 0; i < this->num; i++)
+    {
+        if ((this->list[i].t >= 0) && (this->list[i].t < minHit))
+        {
+            curHit = i;
+            minHit = this->list[i].t;
+        }
+    }
+
+    if (curHit == -1)
+    {
+        return Intersection(0, nullptr);
+    }
+
+    return this->list[curHit];
 }

+ 70 - 0
tests/intersect_test.cpp

@@ -59,4 +59,74 @@ TEST(IntersectTest, Intersect_sets_the_object_on_the_intersection)
     ASSERT_EQ(xs.count(), 2);
     ASSERT_EQ(xs[0].object, (Object *)&s);
     ASSERT_EQ(xs[1].object, (Object *)&s);
+}
+
+TEST(IntersectTest, The_hit_when_all_intersection_have_positive_t)
+{
+    Sphere s = Sphere();
+    Intersect xs = Intersect();
+
+    Intersection i1 = Intersection(1, &s);
+    Intersection i2 = Intersection(2, &s);
+
+    xs.add(i1);
+    xs.add(i2);
+
+    Intersection i = xs.hit();
+
+    ASSERT_EQ(i, i1);
+}
+
+TEST(IntersectTest, The_hit_when_some_intersection_have_negative_t)
+{
+    Sphere s = Sphere();
+    Intersect xs = Intersect();
+
+    Intersection i1 = Intersection(-1, &s);
+    Intersection i2 = Intersection(2, &s);
+    Intersection i3 = Intersection(12, &s);
+
+    xs.add(i1);
+    xs.add(i2);
+    xs.add(i3);
+
+    Intersection i = xs.hit();
+
+    ASSERT_EQ(i, i2);
+}
+
+TEST(IntersectTest, The_hit_when_all_intersection_have_negative_t)
+{
+    Sphere s = Sphere();
+    Intersect xs = Intersect();
+
+    Intersection i1 = Intersection(-2, &s);
+    Intersection i2 = Intersection(-1, &s);
+
+    xs.add(i1);
+    xs.add(i2);
+
+    Intersection i = xs.hit();
+
+    ASSERT_TRUE(i.nothing());
+}
+
+TEST(IntersectTest, The_hit_is_always_the_lowest_nonnegative_intersection)
+{
+    Sphere s = Sphere();
+    Intersect xs = Intersect();
+
+    Intersection i1 = Intersection(5, &s);
+    Intersection i2 = Intersection(7, &s);
+    Intersection i3 = Intersection(-3, &s);
+    Intersection i4 = Intersection(2, &s);
+
+    xs.add(i1);
+    xs.add(i2);
+    xs.add(i3);
+    xs.add(i4);
+
+    Intersection i = xs.hit();
+
+    ASSERT_EQ(i, i4);
 }