Math.cpp

 
 
#include "Math.h"
#include "Camera.h"

Cube ::Cube(float x, float y, float z)
{
	vertexCount = 8 ;
	polyCount = 12 ;

	position.x = x ;
	position.y = y ;
	position.z = z ;

	float scaler = 0.2 ;

	localVertices[0].x = -50  * scaler ;
	localVertices[0].y = 50 * scaler ;
	localVertices[0].z = -50 * scaler ;
	localVertices[0].w = 1 ;

	localVertices[1].x = 50 * scaler ;
	localVertices[1].y = 50 * scaler ;
	localVertices[1].z = -50 * scaler ;
	localVertices[1].w = 1 ;

	localVertices[2].x = 50 * scaler ;
	localVertices[2].y = -50 * scaler ;
	localVertices[2].z = -50 * scaler ;
	localVertices[2].w = 1 ;

	localVertices[3].x = -50 * scaler ;
	localVertices[3].y = -50 * scaler ;
	localVertices[3].z = -50 * scaler ;
	localVertices[3].w = 1 ;

	localVertices[4].x = 50 * scaler ;
	localVertices[4].y = 50 * scaler ;
	localVertices[4].z = 50 * scaler ;
	localVertices[4].w = 1 ;

	localVertices[5].x = 50 * scaler ;
	localVertices[5].y = -50 * scaler ;
	localVertices[5].z = 50 * scaler ;
	localVertices[5].w = 1 ;

	localVertices[6].x = -50 * scaler ;
	localVertices[6].y = -50 * scaler ;
	localVertices[6].z = 50 * scaler ;
	localVertices[6].w = 1 ;

	localVertices[7].x = -50 * scaler ;
	localVertices[7].y = 50 * scaler ;
	localVertices[7].z = 50 * scaler ;
	localVertices[7].w = 1 ;

	polygones[0].pVertexList = transformedVertices ;
	polygones[0].vertexIndexArray[0] = 0 ;
	polygones[0].vertexIndexArray[1] = 3 ;
	polygones[0].vertexIndexArray[2] = 2 ;

	polygones[1].pVertexList = transformedVertices ;
	polygones[1].vertexIndexArray[0] = 0 ;
	polygones[1].vertexIndexArray[1] = 2 ;
	polygones[1].vertexIndexArray[2] = 1 ;

	polygones[2].pVertexList = transformedVertices ;
	polygones[2].vertexIndexArray[0] = 1 ;
	polygones[2].vertexIndexArray[1] = 2 ;
	polygones[2].vertexIndexArray[2] = 5 ;

	polygones[3].pVertexList = transformedVertices ;
	polygones[3].vertexIndexArray[0] = 1 ;
	polygones[3].vertexIndexArray[1] = 5 ;
	polygones[3].vertexIndexArray[2] = 4 ;

	polygones[4].pVertexList = transformedVertices ;
	polygones[4].vertexIndexArray[0] = 4 ;
	polygones[4].vertexIndexArray[1] = 5 ;
	polygones[4].vertexIndexArray[2] = 6 ;

	polygones[5].pVertexList = transformedVertices ;
	polygones[5].vertexIndexArray[0] = 4 ;
	polygones[5].vertexIndexArray[1] = 6;
	polygones[5].vertexIndexArray[2] = 7 ;

	polygones[6].pVertexList = transformedVertices ;
	polygones[6].vertexIndexArray[0] = 7 ;
	polygones[6].vertexIndexArray[1] = 6 ;
	polygones[6].vertexIndexArray[2] = 3 ;

	polygones[7].pVertexList = transformedVertices ;
	polygones[7].vertexIndexArray[0] = 7 ;
	polygones[7].vertexIndexArray[1] = 3 ;
	polygones[7].vertexIndexArray[2] = 0 ;

	polygones[8].pVertexList = transformedVertices ;
	polygones[8].vertexIndexArray[0] = 7 ;
	polygones[8].vertexIndexArray[1] = 0 ;
	polygones[8].vertexIndexArray[2] = 1 ;

	polygones[9].pVertexList = transformedVertices ;
	polygones[9].vertexIndexArray[0] = 4 ;
	polygones[9].vertexIndexArray[1] = 7 ;
	polygones[9].vertexIndexArray[2] = 1 ;

	polygones[10].pVertexList = transformedVertices ;
	polygones[10].vertexIndexArray[0] = 3 ;
	polygones[10].vertexIndexArray[1] = 6 ;
	polygones[10].vertexIndexArray[2] = 5 ;

	polygones[11].pVertexList = transformedVertices ;
	polygones[11].vertexIndexArray[0] = 2 ;
	polygones[11].vertexIndexArray[1] = 3 ;
	polygones[11].vertexIndexArray[2] = 5 ;
}

void Cube ::RotateAroundX(float unit)
{
	float sinTheta = sin(DEGREE_TO_RADIAN((unit))) ;
	float cosTheta = cos(DEGREE_TO_RADIAN((unit))) ;

	Matrix4X4 rotateAroundY = {
		1, 0, 0, 0,
		0, cosTheta, sinTheta, 0,
		0, -sinTheta, cosTheta, 0,
		0, 0, 0, 1
	} ;

	Vector4 temp ;

	for (int i = 0; i < vertexCount; ++i)
	{
		VectorMultMatrix(&localVertices[i], &rotateAroundY, &temp) ;
		localVertices[i].x = temp.x ;
		localVertices[i].y = temp.y ;
		localVertices[i].z = temp.z ;
		localVertices[i].w = temp.w ;
	}
}

void Cube ::RotateAroundY(float unit)
{
	float sinTheta = sin(DEGREE_TO_RADIAN((unit))) ;
	float cosTheta = cos(DEGREE_TO_RADIAN((unit))) ;

	Matrix4X4 rotateAroundY = {
		cosTheta, 0, -sinTheta, 0,
		0, 1, 0, 0,
		sinTheta, 0, cosTheta, 0,
		0, 0, 0, 1
	} ;

	Vector4 temp ;

	for (int i = 0; i < vertexCount; ++i)
	{
		VectorMultMatrix(&localVertices[i], &rotateAroundY, &temp) ;
		localVertices[i].x = temp.x ;
		localVertices[i].y = temp.y ;
		localVertices[i].z = temp.z ;
		localVertices[i].w = temp.w ;
	}
}

void Cube ::RotateAroundZ(float unit)
{
	float sinTheta = sin(DEGREE_TO_RADIAN((unit))) ;
	float cosTheta = cos(DEGREE_TO_RADIAN((unit))) ;

	Matrix4X4 rotateAroundZ = {
		cosTheta, sinTheta, 0, 0,
		-sinTheta, cosTheta, 0, 0,
		0, 0, 1, 0,
		0, 0, 0, 1
	} ;

	Vector4 temp ;

	for (int i = 0; i < vertexCount; ++i)
	{
		VectorMultMatrix(&localVertices[i], &rotateAroundZ, &temp) ;
		localVertices[i].x = temp.x ;
		localVertices[i].y = temp.y ;
		localVertices[i].z = temp.z ;
		localVertices[i].w = temp.w ;
	}
}

void VectorPlusVector(Vector3* lhs, Vector3* rhs, Vector3* pResult)
{
	pResult ->x = lhs ->x + rhs ->x ;
	pResult ->y = lhs ->y + rhs ->y ;
	pResult ->z = lhs ->z + rhs ->z ;
}

void VectorMinusVector(Vector3* endPoint, Vector3* startPoint, Vector3* pResult)
{
	pResult ->x = endPoint ->x - startPoint ->x ;
	pResult ->y = endPoint ->y - startPoint ->y ;
	pResult ->z = endPoint ->z - startPoint ->z ;
}

void VectorCrossVector(Vector3* lhs, Vector3* rhs, Vector3* pResult)
{
	pResult ->x = lhs ->y * rhs ->z - lhs ->z * rhs ->y ;
	pResult ->y = lhs ->z * rhs ->x - lhs ->x * rhs ->z ;
	pResult ->z = lhs ->x * rhs ->y - lhs ->y * rhs ->x ;
}

float VectorDotVector(Vector3* lhs, Vector3* rhs)
{
	return lhs ->x * rhs ->x + lhs ->y * rhs ->y + lhs ->z * rhs ->z ;
}

void Vector4ToVector3(Vector4* resourcePoint, Vector3* newPoint)
{
	newPoint ->x = resourcePoint ->x / resourcePoint ->w ;
	newPoint ->y = resourcePoint ->y / resourcePoint ->w ;
	newPoint ->z = resourcePoint ->z / resourcePoint ->w ;
}

void InitializeMatrix(Matrix3X3* pMatrix,
	float m11, float m12, float m13,
	float m21, float m22, float m23,
	float m31, float m32, float m33)
{
	pMatrix ->m11 = m11 ; 	pMatrix ->m12 = m12 ; 	pMatrix ->m13 = m13 ;
	pMatrix ->m21 = m21 ; 	pMatrix ->m22 = m22 ; 	pMatrix ->m23 = m23 ;
	pMatrix ->m31 = m31 ; 	pMatrix ->m32 = m32 ; 	pMatrix ->m33 = m33 ;
}

void InitializeMatrix(Matrix4X4* pMatrix,
	float m11, float m12, float m13, float m14,
	float m21, float m22, float m23, float m24,
	float m31, float m32, float m33, float m34,
	float m41, float m42, float m43, float m44)
{
	pMatrix ->m11 = m11 ; 	pMatrix ->m12 = m12 ; 	pMatrix ->m13 = m13 ; pMatrix ->m14 = m14 ;
	pMatrix ->m21 = m21 ; 	pMatrix ->m22 = m22 ; 	pMatrix ->m23 = m23 ; pMatrix ->m24 = m24 ;
	pMatrix ->m31 = m31 ; 	pMatrix ->m32 = m32 ; 	pMatrix ->m33 = m33 ; pMatrix ->m34 = m34 ;
	pMatrix ->m41 = m41 ; 	pMatrix ->m42 = m42 ; 	pMatrix ->m43 = m43 ; pMatrix ->m44 = m44 ;
}

void VectorMultMatrix(Vector4* point, Matrix4X4* matrix, Vector4* pResult)
{
	for (int col = 0; col < 4; ++col)
	{
		float sum = 0 ;

		for (int row = 0; row < 4; ++row)
			sum += point ->M[row] * matrix ->M[row][col] ;

		pResult ->M[col] = sum ;
	}
}

void MatrixMultMatrix(Matrix4X4* lhs, Matrix4X4* rhs, Matrix4X4* pResult)
{
	for (int row = 0; row < 4; ++row)
	{
		for (int col = 0; col < 4; ++col)
		{
			float temp = 0 ;

			for (int i = 0; i < 4; ++i)
				temp += lhs ->M[row][i] * rhs ->M[i][col] ;

			pResult ->M[row][col] = temp ;
		}
	}
}

float GetDeterminant(const Matrix4X4* pMatrix)
{
	return pMatrix ->m11 * pMatrix ->m22 * pMatrix ->m33 * pMatrix ->m44 - pMatrix ->m11 * pMatrix ->m24 * pMatrix ->m33 * pMatrix ->m42
		+ pMatrix ->m12 * pMatrix ->m23 * pMatrix ->m34 * pMatrix ->m41 - pMatrix ->m12 * pMatrix ->m21 * pMatrix ->m34 * pMatrix ->m43
		+ pMatrix ->m13 * pMatrix ->m24 * pMatrix ->m31 * pMatrix ->m42 - pMatrix ->m13 * pMatrix ->m22 * pMatrix ->m31 * pMatrix ->m44
		+ pMatrix ->m14 * pMatrix ->m21 * pMatrix ->m32 * pMatrix ->m43 - pMatrix ->m14 * pMatrix ->m23 * pMatrix ->m32 * pMatrix ->m41 ;
}

void ScaleAccordingTo(Cube* pCube, Vector3* pAxis, float k)
{
	Matrix4X4 matrix = {
		1 + (k - 1) * pAxis ->x * pAxis ->x, (k - 1) * pAxis ->x * pAxis ->y, (k - 1) * pAxis ->x * pAxis ->z, 0, 
		(k - 1) * pAxis ->x * pAxis ->y, 1 + (k - 1) * pAxis ->y * pAxis ->y, (k - 1) * pAxis ->y * pAxis ->z, 0, 
		(k - 1) * pAxis ->x * pAxis ->z, (k - 1) * pAxis ->z * pAxis ->y, 1 + (k - 1) * pAxis ->z * pAxis ->z, 0,
		0, 0, 0, 1
	} ;

	for (int i = 0; i < pCube ->vertexCount; ++i)
		VectorMultMatrix(&pCube ->localVertices[i], &matrix, &pCube ->localVertices[i]) ;
}

void ModelToWorld(Cube* pCube)
{
	for (int i = 0; i < pCube ->vertexCount; ++i)
	{
		pCube ->transformedVertices[i].x = pCube ->localVertices[i].x + pCube ->position.x ;
		pCube ->transformedVertices[i].y = pCube ->localVertices[i].y + pCube ->position.y ;
		pCube ->transformedVertices[i].z = pCube ->localVertices[i].z + pCube ->position.z ;
		pCube ->transformedVertices[i].w = pCube ->localVertices[i].w ;
	}
}

void RemoveBackface(PolySelfContained* polyList, int count, Vector3* pViewPortPosition)
{
	for (int i = 0; i < count; ++i)
	{
		Vector3 point0 ;
		point0.x = polyList[i].vertexList[0].x ;
		point0.y = polyList[i].vertexList[0].y ;
		point0.z = polyList[i].vertexList[0].z ;

		Vector3 point1 ;
		point1.x = polyList[i].vertexList[1].x ;
		point1.y = polyList[i].vertexList[1].y ;
		point1.z = polyList[i].vertexList[1].z ;

		Vector3 point2 ;
		point2.x = polyList[i].vertexList[2].x ;
		point2.y = polyList[i].vertexList[2].y ;
		point2.z = polyList[i].vertexList[2].z ;

		//	  1
		//	  /
		//	 /
		//	/
		// 0\
		//	 \
		//    \
		//     \
		//      2

		Vector3 u ;
		VectorMinusVector(&point1, &point0, &u) ;

		Vector3 v ;
		VectorMinusVector(&point2, &point0, &v) ;

		Vector3 n ;
		VectorCrossVector(&v, &u, &n) ;

		Vector3 view ;
		VectorMinusVector(pViewPortPosition, &point0, &view) ;

		float dotValue = VectorDotVector(&n, &view) ;

		if (dotValue <= 0)
			polyList[i].removed = true ;
		else
			polyList[i].removed = false ;
	}
}

void WorldToCamera(PolySelfContained* polyList, int count, Matrix4X4* pMatrix)
{
	Vector4 temp ;

	for (int i = 0; i < count; ++i)
	{
		if (polyList[i].removed)
			continue ;

		VectorMultMatrix(&polyList[i].vertexList[0], pMatrix, &temp) ;
		polyList[i].vertexList[0] = temp;

		VectorMultMatrix(&polyList[i].vertexList[1], pMatrix, &temp) ;
		polyList[i].vertexList[1]= temp ;

		VectorMultMatrix(&polyList[i].vertexList[2], pMatrix, &temp) ;
		polyList[i].vertexList[2] = temp ;
	}
}

void CameraToClip(PolySelfContained* polyList, int count, Matrix4X4* pMatrix)
{
	Vector4 temp ;

	for (int i = 0; i < count; ++i)
	{
		if (polyList[i].removed)
			continue ;

		VectorMultMatrix(&polyList[i].vertexList[0], pMatrix, &temp) ;
		polyList[i].vertexList[0] = temp ;

		VectorMultMatrix(&polyList[i].vertexList[1], pMatrix, &temp) ;
		polyList[i].vertexList[1]= temp ;

		VectorMultMatrix(&polyList[i].vertexList[2], pMatrix, &temp) ;
		polyList[i].vertexList[2] = temp ;
	}
}

void ClipToPerspective(PolySelfContained* polyList, int count, float nearDistance)
{
	for (int i = 0; i < count; ++i)
	{
		if (polyList[i].removed)
			continue ;

		float w = polyList[i].vertexList[0].w ;
		polyList[i].vertexList[0].x /= w ;
		polyList[i].vertexList[0].y /= w ;
		polyList[i].vertexList[0].z = nearDistance ;

		w = polyList[i].vertexList[1].w ;
		polyList[i].vertexList[1].x /= w ;
		polyList[i].vertexList[1].y /= w ;
		polyList[i].vertexList[1].z = nearDistance ;

		w = polyList[i].vertexList[2].w ;
		polyList[i].vertexList[2].x /= w ;
		polyList[i].vertexList[2].y /= w ;
		polyList[i].vertexList[2].z = nearDistance ;
	}
}

void CameraToperspective(PolySelfContained* polyList, int count, float viewPortWidth, float viewPortHeight, float fov)
{
	float viewDistance = (viewPortWidth - 1) / 2 / tan(fov / 2) ;

	Matrix4X4 projectionMatrix = {
		1, 0, 0, 0,
		0, 1, 0, 0,
		0, 0, 1, 1 / viewDistance,
		0, 0, 0, 0
	} ;

	Vector4 temp ;

	for (int i = 0; i < count; ++i)
	{
		if (polyList[i].removed)
			continue ;

		VectorMultMatrix(&polyList[i].vertexList[0], &projectionMatrix, &temp) ;
		polyList[i].vertexList[0] = temp ;
		polyList[i].vertexList[0].x /= polyList[i].vertexList[0].w ;
		polyList[i].vertexList[0].y /= polyList[i].vertexList[0].w ;
		polyList[i].vertexList[0].z /= polyList[i].vertexList[0].w ;

		VectorMultMatrix(&polyList[i].vertexList[1], &projectionMatrix, &temp) ;
		polyList[i].vertexList[1] = temp ;
		polyList[i].vertexList[1].x /= polyList[i].vertexList[1].w ;
		polyList[i].vertexList[1].y /= polyList[i].vertexList[1].w ;
		polyList[i].vertexList[1].z /= polyList[i].vertexList[1].w ;

		VectorMultMatrix(&polyList[i].vertexList[2], &projectionMatrix, &temp) ;
		polyList[i].vertexList[2] = temp ;
		polyList[i].vertexList[2].x /= polyList[i].vertexList[2].w ;
		polyList[i].vertexList[2].y /= polyList[i].vertexList[2].w ;
		polyList[i].vertexList[2].z /= polyList[i].vertexList[2].w ;
	}
}

void PerspectiveToScreen(PolySelfContained* polyList, int count, float viewPortWidth, float viewPortHeight)
{
	Vector4 temp ;

	for (int i = 0; i < count; ++i)
	{
		if (polyList[i].removed)
			continue ;

		//polyList[i].vertexList[0].x = viewPortWidth * (polyList[i].vertexList[0].x + 1) / 2 ;
		//polyList[i].vertexList[0].y = viewPortHeight * (polyList[i].vertexList[0].y + 1) / 2 ;

		//polyList[i].vertexList[1].x = viewPortWidth * (polyList[i].vertexList[1].x + 1) / 2 ;
		//polyList[i].vertexList[1].y = viewPortHeight * (polyList[i].vertexList[1].y + 1) / 2 ;

		//polyList[i].vertexList[2].x = viewPortWidth * (polyList[i].vertexList[2].x + 1) / 2 ;
		//polyList[i].vertexList[2].y = viewPortHeight * (polyList[i].vertexList[2].y + 1) / 2 ;

		polyList[i].vertexList[0].x = (polyList[i].vertexList[0].x + 1) * (viewPortWidth / 2 - 0.5) ;
		polyList[i].vertexList[0].y = (viewPortHeight - 1) - (polyList[i].vertexList[0].y + 1) * (viewPortHeight / 2 - 0.5) ;

		polyList[i].vertexList[1].x = (polyList[i].vertexList[1].x + 1) * (viewPortWidth / 2 - 0.5) ;
		polyList[i].vertexList[1].y = (viewPortHeight - 1) - (polyList[i].vertexList[1].y + 1) * (viewPortHeight / 2 - 0.5) ;

		polyList[i].vertexList[2].x = (polyList[i].vertexList[2].x + 1) * (viewPortWidth / 2 - 0.5) ;
		polyList[i].vertexList[2].y = (viewPortHeight - 1) - (polyList[i].vertexList[2].y + 1) * (viewPortHeight / 2 - 0.5) ;

		//temp.x = viewPortWidth / 2 - 0.5 + polyList[i].vertexList[0].x ;
		//temp.y = viewPortHeight / 2 - 0.5 - polyList[i].vertexList[0].y ;
		//temp.z = polyList[i].vertexList[0].z ;
		//temp.w = polyList[i].vertexList[0].w ;

		//polyList[i].vertexList[0] = temp ;

		//temp.x = viewPortWidth / 2 - 0.5 + polyList[i].vertexList[1].x ;
		//temp.y = viewPortHeight / 2 - 0.5 - polyList[i].vertexList[1].y ;
		//temp.z = polyList[i].vertexList[1].z ;
		//temp.w = polyList[i].vertexList[1].w ;

		//polyList[i].vertexList[1] = temp ;

		//temp.x = viewPortWidth / 2 - 0.5 + polyList[i].vertexList[2].x ;
		//temp.y = viewPortHeight / 2 - 0.5 - polyList[i].vertexList[2].y ;
		//temp.z = polyList[i].vertexList[2].z ;
		//temp.w = polyList[i].vertexList[2].w ;

		//polyList[i].vertexList[2] = temp ;
	}
}


你可能感兴趣的:(Math.cpp)