2012-04-08 6 views
0

Ich implementiere einen Kegelstumpf-bezogenen Code, und der Culling-Test gibt nichts zurück, selbst wenn viele sichtbare Objekte vorhanden sind. Meine mathematische Support-Bibliothek bietet keine Unterstützung für die Ebene oder ähnliches. Daher wird ein Großteil dieses Codes von Grund auf mit wenig verfügbaren Tests geschrieben. Wenn Sie Vorschläge bezüglich der Fehlerstelle haben, informieren Sie bitte. Zum Glück gibt es davon nicht viel, so Little'Wall'o'Code folgt:Frustum Intersektionscode gibt schlechten Wert zurück

class Plane { 
    public: 
     Plane() { 
      r0 = Math::Vector(0,0,0); 
      normal = Math::Vector(0,1,0); 
     } 
     Plane(Math::Vector p1, Math::Vector p2, Math::Vector p3) { 
      r0 = p1; 
      normal = Math::Cross(p2 - p1, p3 - p1); 
     } 
     Math::Vector r0; 
     Math::Vector normal; 
    }; 
    class Frustum { 
    public: 
     Frustum(
      const std::array<Math::Vector, 8>& points 
      ) 
     { 
      planes[0] = Plane(points[0], points[1], points[2]); 
      planes[1] = Plane(points[4], points[5], points[6]); 
      planes[2] = Plane(points[0], points[1], points[4]); 
      planes[3] = Plane(points[2], points[3], points[6]); 
      planes[4] = Plane(points[0], points[2], points[4]); 
      planes[5] = Plane(points[1], points[3], points[5]); 
     } 
     Plane planes[6]; 
    }; 

     // http://www.cescg.org/CESCG-2002/DSykoraJJelinek/index.html 
     bool Intersects(Math::AABB lhs, const Frustum& rhs) const { 
      for(int i = 0; i < 6; i++) { 
       Math::Vector pvertex = lhs.TopRightFurthest; 
       Math::Vector nvertex = lhs.BottomLeftClosest; 
       if (rhs.planes[i].normal.x <= -0.0f) { 
        std::swap(pvertex.x, nvertex.x); 
       } 
       if (rhs.planes[i].normal.y <= -0.0f) { 
        std::swap(pvertex.y, nvertex.y); 
       } 
       if (rhs.planes[i].normal.z <= -0.0f) { 
        std::swap(pvertex.z, nvertex.z); 
       } 
       if (Math::Dot(nvertex - rhs.planes[i].r0, rhs.planes[i].normal) > 0.0f) { 
        return false; 
       } 
      } 
      return true; 
     } 

Bemerkenswert ist auch, dass ich ein linkshändiges Koordinatensystem bin mit, so invertiert ich das Ergebnis der Kreuzprodukt (innerhalb der Cross-Funktion).

Edit: Wie genau gesagt, verpasste ich die Vertex-Indizes. Sie sind so indiziert, dass jedes Bit die Ecke auf einer Achse angibt, dh 0 gibt in dieser Reihenfolge die Rechte, die Oberseite und die Rückseite an.

Auch ich entschuldige mich für die allgemein niedrige Qualität der Frage, aber ich habe keine Ahnung, was noch hinzuzufügen. Ich habe keine Compiler-Warnungen oder -Fehler und nicht genug Verständnis, um etwas zu verstehen, was ich im Debugger lesen könnte - das ist außerhalb meines normalen Feldes. Und der Code kompiliert mit einer relativ offensichtlichen Implementierung von Vector und AABB.

+3

Ernsthaft? Du schreibst ein "Hier ist mein Code. Wo ist der Fehler?" Frage? –

+0

Es hilft, wenn Sie beschreiben, wie Sie Ihre Frustum-Vertices indiziert haben. –

+1

@Oli: Was muss ich noch anbieten? Ich habe zum Beispiel keine Compiler-Warnungen oder -Fehler, und ich verstehe das sicher nicht gut genug, um irgend etwas, was ich im Debugger sehen könnte, sinnvoll zu machen. – Puppy

Antwort

3

Ich vermute, dass dies auf Ihre Beschriftung der Scheitelpunkte und die Reihenfolge, in der Sie die Punkte angeben, kommt. Sie sollten konsistent sein in der Richtung, in der Sie die Scheitelpunkte angeben, im Uhrzeigersinn oder gegen den Uhrzeigersinn, abhängig von Ihrem Koordinatensystem. Dies sollte in Bezug auf das äußere Gesicht (oder das innere Gesicht je nachdem, wie Sie es betrachten) sein.

In meinen Augen sieht es so aus, als ob die Normalen in dieselbe Richtung weisen, was falsch ist.

enter image description here

so dass diejenigen Flächen gegen den Uhrzeigersinn um die Normale Angabe gibt mir

0 1 2 
    5 4 7 
    1 5 6 
    4 0 3 
    3 2 6 
    1 0 4 

Ihr Beispiel von 0 1 2 und 4 5 6 ergibt 2 Normalen die in die gleiche Richtung zeigen, wenn sie sollten in entgegengesetzte Richtungen zeigen

+0

Das Nachbestellen meiner Flugzeuge war eine große Verbesserung, aber ich bin noch nicht weit genug vom Wald entfernt. Das Culling funktioniert in einigen Regionen korrekt, in anderen nicht. Ich werde es leicht ändern, da meine Vertex-Indizes sich etwas von Ihren unterscheiden. Nebenbei - ich habe ein LH-Koordinatensystem, erfordert das eine Bestellung im Uhrzeigersinn oder gegen den Uhrzeigersinn? – Puppy

+0

Raten Sie, dass es im Uhrzeigersinn erfordert. Ich habe meine Scheitelpunkte neu geordnet, damit sie mit Ihrer Indizierung übereinstimmen, und dann habe ich den ersten und letzten Teil jeder Komponente getauscht, und jetzt funktioniert es! Du bist der Winrar – Puppy

Verwandte Themen