Hello World!
I’m trying to check if my camera collides with a cube. My camera is represented as a sphere.
The cube is represented as six infinite planes. The function SphereInStaticObj(…) checks whether
the sphere is in front of all six planes or not. I think this sounds ok, but however, it does not really
work. I’ve never had matrices or vectors in maths at school, and all I know about it, I’ve collected
in several tutorials in the net. That’s why I do not find the mistake in my equations, and so I’m asking
you more advanced people for help (once more).
The problem:
The cube is correctly detected, when the camera moves inside it. But in some positions of the camera, the
function returns “true” although it’s outside the cube.
THE HEADER:
//------------------------------------------------------------------------------------------------------------------------------------ typedef float BOX[6][4]; // 6 planes, containing 3 values for a point on the plane, and the 4th value for the distance. // The BOX-values are extracted automatically by the function "NewStaticObj(...)". typedef float BOXpoints[18]; // Here you can store the 6 points of the box. typedef float BOXnormals[18]; // Here you can store the 6 normals of the box. The order must be the same as in BOXpoints (first // BOXpoints must fit to the first BOXnormal). class Collision { private: Vectorz *vect; // This is a vector-class, from which only the dot-product is used. BOX *staticObj; // staticObj is a dynamic array of BOX to store some BOXes. public: Collision(int num) { staticObj = new BOX[num]; vect = new Vectorz(); } //the constructor requires the number of the BOXes //that we want to create, for setting the size of the statcObj-array. ~Collision() { delete[] staticObj; delete vect; } void NewStaticObj(int, BOXpoints, BOXnormals); // This function extracts the points and normals of the box and calculates //the distances from the six points to the origin and the six points. These values are stored in the //staticObj-array. The int-parameter is just an indey for the number of the box. bool SphereInStaticObj(float, float, float, float, int); // The first three params are the point of the sphere. The 4th //param is the distance of the sphere. The 5th param is the number of the BOX we want to check. }; //------------------------------------------------------------------------------------------------------------------------------------
CPP - FILE:
//------------------------------------------------------------------------------------------------------------------------------------ void Collision::NewStaticObj(int num, BOXpoints p, BOXnormals n) { BOX box; VECTOR N, P; //VECTOR is defined as an array of three values. N stands for normal, P for point. float dist; for (int i=0; i < 6; i++) { N[0] = n[i*3 + 0]; // ...put the BOXpoints ans BOXnormals in VECTOR-arrays to make them valid N[1] = n[i*3 + 1]; // params for the dot-function. N[2] = n[i*3 + 2]; P[0] = p[i*3 + 0]; P[1] = p[i*3 + 1]; P[2] = p[i*3 + 2]; dist = vect->Dot(P, N); // This should produce the negated distance of the plane from the origin. box[i][0] = P[0]; box[i][1] = P[1]; box[i][2] = P[2]; box[i][3] = dist; } memcpy(staticObj[num], box, sizeof(box)); // Now we've extracted the values to store in a BOX of the staticObj-array. } bool Collision::SphereInStaticObj(float x, float y, float z, float r, int num) { for (int p = 0; p < 6; p++) // check if the distance is smaller than the negated radius of the sphere. if (staticObj[num][p][0] * x + staticObj[num][p][1] * y + staticObj[num][p][2] * z + staticObj[num][p][3] <= -r) return false; return true; } //------------------------------------------------------------------------------------------------------------------------------------
I’ve commented the code as good as possible, you see that everything is based on the plane-equation
Ax+Bx+Cx+d=0.
Thaks in advance for your help !!!
mathias_123