Archived

This topic is now archived and is closed to further replies.

SkinnyM

Using the dot product

Recommended Posts

SkinnyM    122
Hello again. My whole goal is to be able to test to see if i can see a rectangle or not in 3d space. So far what i did, is i get the vector from the objects position to my position, and then i get the vector for my view. Then i normalize them and do the dot product. I then used acos() to turn it into radians so i could get degree''s from it. Ok seems ok, but it DIDNT work.. i have messed with it and such and i came up with another idea, my second idea was the find the rectangles normal and then use that as the vector to pass in with my view to the dotproduct. Still, it doesnt work. What i hope to do, is get the degree''s between each object, and test it against my perspective, which is 60 degree''s and see if i can see it. THat is my goal. Can anyone tell me what i am doing wrong. here is teh code for my first idea. //Check Visibility CVector PlayerView, ObjectToPlayer; CVector View; View = Player.GetView(); PlayerView.x = cosf(View.x*DEGTORAD); PlayerView.y = -sinf(View.y*DEGTORAD); PlayerView.z = sinf(View.x*DEGTORAD); ObjectToPlayer = Player.GetPosition() - TextureObject.GetPosition(); PlayerView = PlayerView.Normalize(); ObjectToPlayer = ObjectToPlayer.Noramlize(); float Dot = PlayerView.DotProduct(ObjectToPlayer); float Degree = acos(Dot); Degree *= RADTODEG; //60.0 is my perspective if(Degree <= 60.0f) TestFont.RenderText(0, 28, "Can See Degree: %f", Degree); else TestFont.RenderText(0, 28, "Cant See Degree: %f", Degree); ////////////////////////

Share this post


Link to post
Share on other sites
RipTorn    722
cos 60 degrees is 0.5

so if DOT(v1,v2) equals 0.5 then the angle is 60 (assuming they are normalized). Which saves a acosf call. if DOT(v1,v2) is zero, the vectors are at right angles no matter their length...

I never convert to degrees, and I do a _lot_ of dot product operations... It''s slow, not needed and not guarenteed to work correctly as the range of the result is always 180 degrees which can cause problems sometimes.

What you should do, is get the view direction from the modelview matrix. This is almost certainly the problem in the code.

get the view direction from the model view matrix:

this is slow and bad code. And should be done ONLY after the camera is set up. never again.

float mat[16];

glGetFloatfv(GL_MODELVIEW_MATRIX,mat);

Vector3 view;

view.x=-mat[8];
view.y=-mat[9];
view.z=-mat[10];

view.normalize();


You should consider using Matrix objects for all this sorta stuff. It''s good your using a Vector class.

clickety

| - My (new) little website - | - email me - |

Share this post


Link to post
Share on other sites
SkinnyM    122
This is what i have for the code:

CVector PlayerView, ObjectToPlayer;
/*
View = Player.GetView();

PlayerView.x = cosf(View.x*DEGTORAD);
PlayerView.y = -sinf(View.y*DEGTORAD);
PlayerView.z = sinf(View.x*DEGTORAD);
*/

static float mat[16];

glGetFloatv(GL_MODELVIEW_MATRIX,mat);

CVector View;

View.x=-mat[8];
View.y=-mat[9];
View.z=-mat[10];

View = View.Normalize();

ObjectToPlayer = Player.GetPosition() - TextureObject.GetPosition();
ObjectToPlayer = ObjectToPlayer.Normalize();

float Dot = View.DotProduct(ObjectToPlayer);

//90.0 is my perspective
if(Dot >= 0.5f)
TestFont.RenderText(0, 28, "Can See Degree: %f", Dot);
else
TestFont.RenderText(0, 28, "Cant See Degree: %f", Dot);
////////////////////////

Here is what i have in my scene, i have a textured rectangle in the middle of the scene, and when i walk around it, i want to be able to know if i am able to see it. Then code above for some reason isnt working, sometimes it works, other times it is totally off.

Any other ideas?

Share this post


Link to post
Share on other sites
RipTorn    722
further more,

as for acutlaly working out if a cube is on screen with dot products, and the like, it''s a lot harder than, say, a sphere.

what your doing is testing if the centre point of the rectangle is on screen. Where as a rectangle has size.

testing all the corners will usually be ok, but there are problems with this... for example if your really close to the rectangle looking at it''s centre, no corner will be on screen but the centre will be... There are many other cases where this will happen but generally it doesn''t cause too many problems.

To avoid this is difficult, you can do it many ways (test the edges with the frustum, then test the closest point on the rectangle to the view point... etc... it''s not easy.

Treating it as a sphere is probably the best bet, since it''s still quite accurate and it''s also nice and quick. And, what you are doing right now is treating the view frustum as a cone, not 4 planes, so that is inaccuracy anyway.

| - My (new) little website - | - email me - |

Share this post


Link to post
Share on other sites
SkinnyM    122
Do you guys have any other ideas? I am still having the problem, i came up with a possible problem with how i get the angle. When i get the view at which i am looking, the degree''s could be a negative or a postive value depending on which way i moved the mouse. So Say i move the cursor to the right, the value goes up, but then lets say i move it alot to the left. The value would be a negative and it would no longer coorspond to 360+1 being my orignal view. Could that possibly be a problem with the calculations?

Any ideas?

"What we do in life, echos in eternity" -- Gladiator

Share this post


Link to post
Share on other sites
orbano    130
the 4x4 matrix''s 8,9 and 10th element does not decribe the position. to do the simple backface culling:
assuming that you have a triangle with vertices a,b,c, then the normal:
n=(a-b)x(c-b) (actually it is not a normal, but it will do)
the view vector:
v=a-camerapos
and finally:
bool IsTriangleVisible = (n*v<0) (or >0 i dont know, im too tired now).
and getting the camrapos:
cm*[0,0,0,1]=[cm[13],cm[14],cm[15]] where cm is the 4x4 camramatrix

Share this post


Link to post
Share on other sites