Sign in to follow this  
Spa8nky

[C++ to C#] This following method doesn't make sense to me, can anyone help?

Recommended Posts

The method called is used to clip the current triangles vertices to 4 planes:
long count = ClipPolygon(3, newVertex, newNormal, newVertex, newNormal);
Now what I can't understand is why newVertex and newNormal are used twice for the following method:
long Decal::ClipPolygon(long vertexCount, const vector3 *vertex, const vector3 *normal, vector3 *newVertex, vector3 *newNormal) const
{
	vector3		tempVertex[9];
	vector3		tempNormal[9];
	
	// Clip against all six planes
	long count = ClipPolygonAgainstPlane(leftPlane, vertexCount, vertex, normal, tempVertex, tempNormal);
	if (count != 0)
	{
		count = ClipPolygonAgainstPlane(rightPlane, count, tempVertex, tempNormal, newVertex, newNormal);
		if (count != 0)
		{
			count = ClipPolygonAgainstPlane(bottomPlane, count, newVertex, newNormal, tempVertex, tempNormal);
			if (count != 0)
			{
				count = ClipPolygonAgainstPlane(topPlane, count, tempVertex, tempNormal, newVertex, newNormal);
				if (count != 0)
				{
					count = ClipPolygonAgainstPlane(backPlane, count, newVertex, newNormal, tempVertex, tempNormal);
					if (count != 0)
					{
						count = ClipPolygonAgainstPlane(frontPlane, count, tempVertex, tempNormal, newVertex, newNormal);
					}
				}
			}
		}
	}
	
	return (count);
}

It seems that vertex and normal are only ever used once in a test against the first plane but then the newVertex and newNormal are used in the remaining tests. This makes absolutely no sense to me. Why have the same paramters twice? Is one set of parameters supposed to remain unchanged and the other is to be filled with new data based on the unchanged set. If so, why only use the unchanged set in the first plane test? The ClipPolygonAgainstPlane method is as follows:
long Decal::ClipPolygonAgainstPlane(const vector4& plane, long vertexCount, const vector3 *vertex, const vector3 *normal, vector3 *newVertex, vector3 *newNormal)
{
	bool	negative[10];
	
	// Classify vertices
	long negativeCount = 0;
	for (long a = 0; a < vertexCount; a++)
	{
		bool neg = (DotProduct(plane, vertex[a]) < 0.0F);
		negative[a] = neg;
		negativeCount += neg;
	}
	
	// Discard this polygon if it's completely culled
	if (negativeCount == vertexCount) return (0);
	
	long count = 0;
	for (long b = 0; b < vertexCount; b++)
	{
		// c is the index of the previous vertex
		long c = (b != 0) ? b - 1 : vertexCount - 1;
		
		if (negative[b])
		{
			if (!negative[c])
			{
				// Current vertex is on negative side of plane,
				// but previous vertex is on positive side.
				const vector3& v1 = vertex[c];
				const vector3& v2 = vertex[b];
				float t = DotProduct(plane, v1) / (plane.x * (v1.x - v2.x) + plane.y * (v1.y - v2.y) + plane.z * (v1.z - v2.z));
				newVertex[count] = v1 * (1.0F - t) + v2 * t;
				
				const vector3& n1 = normal[c];
				const vector3& n2 = normal[b];
				newNormal[count] = n1 * (1.0F - t) + n2 * t;
				count++;
			}
		}
		else
		{
			if (negative[c])
			{
				// Current vertex is on positive side of plane,
				// but previous vertex is on negative side.
				const vector3& v1 = vertex[b];
				const vector3& v2 = vertex[c];
				float t = DotProduct(plane, v1) / (plane.x * (v1.x - v2.x) + plane.y * (v1.y - v2.y) + plane.z * (v1.z - v2.z));
				newVertex[count] = v1 * (1.0F - t) + v2 * t;
				
				const vector3& n1 = normal[b];
				const vector3& n2 = normal[c];
				newNormal[count] = n1 * (1.0F - t) + n2 * t;
				count++;
			}
			
			// Include current vertex
			newVertex[count] = vertex[b];
			newNormal[count] = normal[b];
			count++;
		}
	}
	
	// Return number of vertices in clipped polygon
	return (count);
}

If anyone can clear this up for me then I would be very grateful. I am currently porting it to C# and the design of the code bamboozles me.

Share this post


Link to post
Share on other sites
The easiest tool to use to see what a bit of code does is the debugger. Just step through it line by line and watch what happens to the variables. Here's what I think it does from just reading the code, you should check through yourself with a debugger to make sure I got it right.

The way the ClipPolygonAgainstPlane() function works is that it takes an input array of vertices with normals, and writes into an output array of vertices with normals, which have been clipped. It returns the length of the output array. Zero meaning that everything has been clipped away.

The ClipPolygon() function calls ClipPolygonAgainstPlane() up to six times (once for each clip plane), passing the results from the previous call as the parameter to the next one. It alternates between storing results in the local 'temp' arrays and the passed in output arrays to do this.

It looks like it does it that way, and assumes the number of vertices won't be more than 9 at any point, to avoid having to allocate storage on the heap and minimize stack usage.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this