2012-04-13 4 views
1

Ich habe diese Klasse für AABB, die ich im Internet found und es funktioniert, wenn Mesh bewegt, aber wenn ich Mesh drehen natürlich funktioniert nicht mehr, auch ich Ich habe bemerkt, dass es eine Transformationsfunktion hat, also denke ich, dass das ist, was ich verwenden muss, damit es funktioniert, nachdem ich das Ineinander greifen, aber ich bin ein wenig neu mit Matrix und ich weiß nicht, wie man es benutzt:Verwandle diese AABB, nachdem ich ein Netz gedreht habe, damit es wieder passt

#ifndef AABB_H 
    #define AABB_H 

    class aabb { 
    public: 
    aabb() { min.x = min.y = min.z = 1e24f; max.x = max.y = max.z = -1e24f; } 
    aabb &operator =(const aabb &a) { min = a.min; max = a.max; return *this; } 

    vec3d min, max; 

    vec3d center() { return ((min + max) * 0.5f); } 

    void empty() { min.x = min.y = min.z = 1e24f; max.x = max.y = max.z = -1e24f; } 
    void add(const vec3d &pnt) { 
     if (pnt.x < min.x) min.x = pnt.x; 
     if (pnt.x > max.x) max.x = pnt.x; 
     if (pnt.y < min.y) min.y = pnt.y; 
     if (pnt.y > max.y) max.y = pnt.y; 
     if (pnt.z < min.z) min.z = pnt.z; 
     if (pnt.z > max.z) max.z = pnt.z; 
    } 
    void transform(const mat3x3 &m, const vec3d &trans) { 
     vec3d oldmin = min, oldmax = max; 
     min = max = trans; 
     if (m.m11 > 0.0f) { min.x += m.m11 * oldmin.x; max.x += m.m11 * oldmax.x; } 
      else { min.x += m.m11 * oldmax.x; max.x += m.m11 * oldmin.x; } 
     if (m.m12 > 0.0f) { min.y += m.m21 * oldmin.x; max.y += m.m21 * oldmax.x; } 
      else { min.y += m.m21 * oldmax.x; max.y += m.m21 * oldmin.x; } 
     if (m.m13 > 0.0f) { min.z += m.m31 * oldmin.x; max.z += m.m31 * oldmax.x; } 
      else { min.z += m.m31 * oldmax.x; max.z += m.m31 * oldmin.x; } 
     if (m.m21 > 0.0f) { min.x += m.m12 * oldmin.y; max.x += m.m12 * oldmax.y; } 
      else { min.x += m.m12 * oldmax.y; max.x += m.m12 * oldmin.y; } 
     if (m.m22 > 0.0f) { min.y += m.m22 * oldmin.y; max.y += m.m22 * oldmax.y; } 
      else { min.y += m.m22 * oldmax.y; max.y += m.m22 * oldmin.y; } 
     if (m.m23 > 0.0f) { min.z += m.m32 * oldmin.y; max.z += m.m32 * oldmax.y; } 
      else { min.z += m.m32 * oldmax.y; max.z += m.m32 * oldmin.y; } 
     if (m.m31 > 0.0f) { min.x += m.m13 * oldmin.z; max.x += m.m13 * oldmax.z; } 
      else { min.x += m.m13 * oldmax.z; max.x += m.m13 * oldmin.z; } 
     if (m.m32 > 0.0f) { min.y += m.m23 * oldmin.z; max.y += m.m23 * oldmax.z; } 
      else { min.y += m.m23 * oldmax.z; max.y += m.m23 * oldmin.z; } 
     if (m.m33 > 0.0f) { min.z += m.m33 * oldmin.z; max.z += m.m33 * oldmax.z; } 
      else { min.z += m.m33 * oldmax.z; max.z += m.m33 * oldmin.z; } 
    } 

    bool contains(const vec3d &a) { return (a.x >= min.x) && (a.x <= max.x) && (a.y >= min.y) && (a.y <= max.y) && (a.z >= min.z) && (a.z <= max.z); } 
    vec3d closest(const vec3d &a) { 
     vec3d r; 
     if (a.x < min.x) r.x = min.x; 
      else if (a.x > max.x) r.x = max.x; 
       else r.x = a.x; 

     if (a.y < min.y) r.y = min.y; 
      else if (a.y > max.y) r.y = max.y; 
       else r.y = a.y; 

     if (a.z < min.z) r.z = min.z; 
      else if (a.z > max.z) r.z = max.z; 
       else r.z = a.z; 
     return r; 
    } 
    }; 
    #endif 

Auch als zusätzliche Daten möchte ich nur Mesh in Y-axix drehen, weil es ein Marine-Spiel ist.

Danke für die Antworten.

Antwort

1

Ich erkenne diesen Code aus dem Buch 3d Mathe Primer für Grafik und Spieleentwicklung, aber es ist nicht genau das Gleiche. Ich kann sehen, dass der Übersetzungsteil funktionieren würde, aber keine Drehung. Das Trans ist der Übersetzungsteil Ihrer Matrix. Im Buch wird auch eine Bounding Box an die Methode übergeben. Im Code, den Sie gefunden haben, wird dieser entfernt und durch das Speichern der alten Min- und Max-Werte ersetzt, mit denen in der Methode begonnen wird. Der Code wird die Min- und Max-Werte auf unendlich erweitern (nur hinzufügen und weiter und weiter). Der Code ist optimiert, so dass nicht alle 8 Eckpunkte transformiert werden, sondern stattdessen, wie ein Punkt durch eine Matrix transformiert wird und herauszufinden, welcher von diesen nach der Transformation den kleinsten Wert hat. Der Trick, um die gesamte Summe zu minimieren, besteht darin, jedes der Produkte für jedes der 9 Elemente in der Matrix einzeln zu minimieren.

So etwas funktioniert für mich ...

public void add(float[] p) { 
    if (p[0] < mOriginalMin[0]) { 
     mOriginalMin[0] = p[0]; 
    } 
    if (p[0] > mOriginalMax[0]) { 
     mOriginalMax[0] = p[0]; 
    } 
    if (p[1] < mOriginalMin[1]) { 
     mOriginalMin[1] = p[1]; 
    } 
    if (p[1] > mOriginalMax[1]) { 
     mOriginalMax[1] = p[1]; 
    } 
    if (p[2] < mOriginalMin[2]) { 
     mOriginalMin[2] = p[2]; 
    } 
    if (p[2] > mOriginalMax[2]) { 
     mOriginalMax[2] = p[2]; 
    } 
} 

public void transform(Matrix44 mat) { 
    /** Get the translation part */ 
    mCurrMin[0] = mCurrMax[0] = mat.m[12]; 
    mCurrMin[1] = mCurrMax[1] = mat.m[13]; 
    mCurrMin[2] = mCurrMax[2] = mat.m[14]; 

    if (mat.m[0] > 0) { 
     mCurrMin[0] += mat.m[0] * mOriginalMin[0]; 
     mCurrMax[0] += mat.m[0] * mOriginalMax[0]; 
    } else { 
     mCurrMin[0] += mat.m[0] * mOriginalMax[0]; 
     mCurrMax[0] += mat.m[0] * mOriginalMin[0]; 
    } 
      .....etc etc. 
0

Ich denke, dass 'trans' bedeutet übersetzen nicht transformieren (Hinweis: Hier werden keine Matrixoperationen durchgeführt). Apropos Transformationen und Matrizen - da ist deine Antwort. Wenn das Objekt gedreht, übersetzt oder skaliert wird, sollten Sie seine globale (Welt-) Matrix erhalten und die Min- und Max-Werte damit multiplizieren. Dann berechnen Sie Ihr Zentrum neu.

Verwandte Themen