Rayplane function acts weird (c++)

Started by
3 comments, last by Jossos 11 years ago

Here is a screenshot of my program and the problem I'm having:

myappnotworking.jpg

(I drew the mouse in yellow to show the problem since print screen doesn't copy the cursor)

At the 1,1 tile coordinate, the mouse ray-plane function works just fine. But as I venture out accross the map, the offset gets more and more extreme, and I have no idea why this is happening.

Here is my rayplane function (returns true if there's an intersection):


bool rayplane(vector3d n, vector3d s, vector3d d, vector3d p1, vector3d p2, vector3d p3, vector3d p4, float* dist, vector3d* point)
{
	// Dot product of the normal vector and the direction vector
	float a = d.x*n.x + d.y*n.y + d.z*n.z;	

	if (a == 0)			// If the ray is parallel to the plane
		return false;
	
	float t = (((p1.x*n.x + p1.y*n.y + p1.z*n.z) - (n.x*s.x + n.y*s.y + n.z*s.z)) / a);
	if (t < 0)
		return false;

	// The intersection of the plane
	float x = s.x + t*d.x;
	float y = s.y + t*d.y;
	float z = s.z + t*d.z;
	vector3d cp(x,y,z);	// Collision point - The problem is this result - Everything after this point works correctly.

	/*** The < 0.00001 corrects for precision innacuracies ***/
	if (abs(trianglearea(p1,p3,p4)-trianglearea(p1,p4,cp)-trianglearea(p1,p3,cp)-trianglearea(p3,p4,cp))<0.00001 ||
		abs(trianglearea(p1,p2,p3)-trianglearea(p1,p2,cp)-trianglearea(p2,p3,cp)-trianglearea(p1,p3,cp))<0.00001)
		return true;
	return false;
}

It checks each of the two triangles that make up each tile(quad) for an intersection. n = normal vector (I set this to (0, 1, 0) for a normal facing up. s = start point, d = direction point and p1 - p4 is each vertex of the quad.

The trianglearea Function:


float trianglearea(vector3d p1, vector3d p2, vector3d p3)
{
	// sqrt(s^2 + b^2 + c^2)

	// a, b and c are the lengths of the triangle sides
	float a = sqrt((p2.x-p1.x)*(p2.x-p1.x)+(p2.y-p1.y)*(p2.y-p1.y)+(p2.z-p1.z)*(p2.z-p1.z));
	float b = sqrt((p3.x-p2.x)*(p3.x-p2.x)+(p3.y-p2.y)*(p3.y-p2.y)+(p3.z-p2.z)*(p3.z-p2.z));
	float c = sqrt((p3.x-p1.x)*(p3.x-p1.x)+(p3.y-p1.y)*(p3.y-p1.y)+(p3.z-p1.z)*(p3.z-p1.z));
	float s = (a+b+c)/2;

	return (sqrt(s*(s-a)*(s-b)*(s-c)));
}

And here is how the Rayplane function is used in the program (the mouse coord is converted to world coords prior, as is the far coord):


if (rayplane(vector3d(0.0, 1.0, 0.0), mousePosNear, mousePosFar, vector3d(0.0 + i, 0.0, 0.0 + j), 
                                                                 vector3d(1.0 + i, 0.0, 0.0 + j), 
                                                                 vector3d(1.0 + i, 0.0, 1.0 + j), 
                                                                 vector3d(0.0 + i, 0.0, 1.0 + j)))
{
    ...Do stuff
}

Help is always appreciated.

Advertisement

This problem is typical of aspect ratio problems. Be sure that the function that creates the ray from the mouse point is really a match for your projection and view matrices. This is not trivial, because most of the time people use a focal system to ray-cast (placing the screen plane at focal distance) and this can omit some importants anisotropy that actually happens using a 4D projection matrix.

To very quickly verify that it is this problem, or something else, set your window totally square and tests again.

This problem is typical of aspect ratio problems. Be sure that the function that creates the ray from the mouse point is really a match for your projection and view matrices. This is not trivial, because most of the time people use a focal system to ray-cast (placing the screen plane at focal distance) and this can omit some importants anisotropy that actually happens using a 4D projection matrix.

To very quickly verify that it is this problem, or something else, set your window totally square and tests again.

The ray from the mouse is perfectly fine. I tested this by drawing an object in the 3d location of the mousenear and then the mousefar coordinates. They match up exactly with the mouse (a big green dot behind the mouse position). I wish it was a problem with just that, but is evidently not the case.

Try a 2D hash map:

http://www.gamedev.net/page/resources/_/technical/game-programming/spatial-hashing-r2697

vector3d cp(x,y,z); // Collision point

This is the line that seems to have the error, and the collisiion point shifts as I travel further on the x and z planes. I have trouble chasing the error back coz im not so great at the math, but everything after this line works perfectly fine. Man this has been haunting me for weeks, anyone who can help is a godsend.

This topic is closed to new replies.

Advertisement