소스 검색

Fixed ortho mode and 3d picking from camera in ortho

Ivan Safrin 13 년 전
부모
커밋
0f94852b5d

+ 7 - 1
Core/Contents/Include/PolyCamera.h

@@ -64,9 +64,12 @@ namespace Polycode {
 			*/					
 			bool canSee(SceneEntity *entity);
 			
-			void setOrthoMode(bool mode);
+			void setOrthoMode(bool mode, Number orthoSizeX = 1.0, Number orthoSizeY = 1.0);
 			bool getOrthoMode();
 			
+			Number getOrthoSizeX();
+			Number getOrthoSizeY();
+						
 			/**
 			* Sets the field of view (FOV) for the camera. The larger the field of view, the more the camera can see, the smaller it is, the more zoomed in it is.
 			* @param fov The new FOV value.
@@ -125,6 +128,9 @@ namespace Polycode {
 			
 		protected:
 		
+			Number orthoSizeX;
+			Number orthoSizeY;
+					
 			Number exposureLevel;
 			bool orthoMode;
 			Number fov;

+ 4 - 1
Core/Contents/Include/PolyCoreServices.h

@@ -146,7 +146,9 @@ namespace Polycode {
 			* @see Config
 			*/																													
 			Config *getConfig();
-		
+			
+			bool drawScreensFirst;
+					
 			~CoreServices();
 		
 		protected:
@@ -155,6 +157,7 @@ namespace Polycode {
 					
 		private:
 		
+		
 			static CoreServices* overrideInstance;
 			static std::map <long, CoreServices*> instanceMap;
 			static CoreMutex *renderMutex;

+ 3 - 6
Core/Contents/Include/PolyGLRenderer.h

@@ -126,7 +126,7 @@ namespace Polycode {
 		void drawArrays(int drawType);		
 				
 		void setOrthoMode(Number xSize=0.0f, Number ySize=0.0f);
-		void _setOrthoMode();
+		void _setOrthoMode(Number orthoSizeX, Number orthoSizeY);
 		void setPerspectiveMode();
 		
 		void enableBackfaceCulling(bool val);
@@ -181,10 +181,7 @@ namespace Polycode {
 		void drawScreenQuad(Number qx, Number qy);
 				
 		void pushMatrix();
-		void popMatrix();
-		
-		bool test2DCoordinate(Number x, Number y, Polycode::Polygon *poly, const Matrix4 &matrix, bool billboardMode);
-		
+		void popMatrix();		
 		
 		Vector3 Unproject(Number x, Number y);
 		
@@ -202,7 +199,7 @@ namespace Polycode {
 		int verticesToDraw;
 		
 		GLdouble sceneProjectionMatrix[16];
-	
+		GLdouble sceneProjectionMatrixOrtho[16];	
 		
 	};
 }

+ 5 - 2
Core/Contents/Include/PolyRenderer.h

@@ -103,7 +103,7 @@ namespace Polycode {
 				
 		virtual void loadIdentity() = 0;		
 		virtual void setOrthoMode(Number xSize=0.0f, Number ySize=0.0f) = 0;
-		virtual void _setOrthoMode() = 0;
+		virtual void _setOrthoMode(Number orthoSizeX, Number orthoSizeY) = 0;
 		virtual void setPerspectiveMode() = 0;
 		
 		virtual void setTexture(Texture *texture) = 0;		
@@ -212,7 +212,7 @@ namespace Polycode {
 		
 		void addShaderModule(PolycodeShaderModule *module);
 		
-		virtual bool test2DCoordinate(Number x, Number y, Polygon *poly, const Matrix4 &matrix, bool billboardMode) = 0;
+		virtual bool test2DCoordinateInPolygon(Number x, Number y, Polygon *poly, const Matrix4 &matrix, bool testBackfacing, bool ortho, bool billboardMode);
 		
 		virtual Matrix4 getProjectionMatrix() = 0;
 		virtual Matrix4 getModelviewMatrix() = 0;
@@ -290,6 +290,9 @@ namespace Polycode {
 		bool shadersEnabled;
 		Number fov;
 		
+		Number orthoSizeX;
+		Number orthoSizeY;
+				
 		bool lightingEnabled;
 		
 		bool orthoMode;

+ 12 - 1
Core/Contents/Source/PolyCamera.cpp

@@ -85,7 +85,9 @@ bool Camera::isSphereInFrustrum(Vector3 pos, Number fRadius) {
     return true;
 }
 
-void Camera::setOrthoMode(bool mode) {
+void Camera::setOrthoMode(bool mode, Number orthoSizeX, Number orthoSizeY) {
+	this->orthoSizeX = orthoSizeX;
+	this->orthoSizeY = orthoSizeY;
 	orthoMode = mode;
 }			
 
@@ -93,6 +95,15 @@ bool Camera::getOrthoMode() {
 	return orthoMode;
 }
 
+Number Camera::getOrthoSizeX() {
+	return orthoSizeX;
+}
+
+Number Camera::getOrthoSizeY() {
+	return orthoSizeY;
+}
+
+
 void Camera::buildFrustrumPlanes() {
 
 	Matrix4 p; 

+ 17 - 6
Core/Contents/Source/PolyCoreServices.cpp

@@ -64,6 +64,7 @@ CoreServices* CoreServices::getInstance() {
 
 //#ifdef _WINDOWS
 		overrideInstance = new CoreServices;
+		overrideInstance->drawScreensFirst = false;
 		Logger::log("Creating new core services instance...\n");
 		return overrideInstance;
 //#else
@@ -211,12 +212,22 @@ void CoreServices::Update(int elapsed) {
 	timerManager->Update();
 	tweenManager->Update();
 	materialManager->Update(elapsed);
-	renderer->setPerspectiveMode();
-	sceneManager->UpdateVirtual();
-	renderer->clearScreen();
-	sceneManager->Update();
-//	renderer->setOrthoMode();
-	screenManager->Update();
+		
+	if(drawScreensFirst) {
+		renderer->clearScreen();	
+		renderer->setPerspectiveMode();
+		sceneManager->UpdateVirtual();
+		renderer->clearScreen();					
+		screenManager->Update();
+		renderer->setPerspectiveMode();
+		sceneManager->Update();	
+	} else {
+		renderer->setPerspectiveMode();
+		sceneManager->UpdateVirtual();
+		renderer->clearScreen();		
+		sceneManager->Update();
+		screenManager->Update();	
+	}	
 }
 
 SoundManager *CoreServices::getSoundManager() {

+ 7 - 41
Core/Contents/Source/PolyGLRenderer.cpp

@@ -265,45 +265,6 @@ Vector3 OpenGLRenderer::projectRayFrom2DCoordinate(Number x, Number y) {
 	return dirVec;
 }
 
-bool OpenGLRenderer::test2DCoordinate(Number x, Number y, Polycode::Polygon *poly, const Matrix4 &matrix, bool billboardMode) {
-	GLdouble nearPlane[3],farPlane[3];
-	
-	GLdouble mv[16];
-	Matrix4 camInverse = cameraMatrix.inverse();	
-	Matrix4 cmv;
-	cmv.identity();
-	cmv = cmv * camInverse;
-	
-	for(int i=0; i < 16; i++) {
-		mv[i] = cmv.ml[i];
-	}
-	
-	GLint vp[4];
-	glGetIntegerv( GL_VIEWPORT, vp );
-	
-	gluUnProject(x, yRes - y, 0.0, mv, sceneProjectionMatrix, vp,  &nearPlane[0], &nearPlane[1], &nearPlane[2]);
-	gluUnProject(x, yRes - y, 1.0, mv, sceneProjectionMatrix, vp,  &farPlane[0], &farPlane[1], &farPlane[2]);
-	
-	Vector3 nearVec(nearPlane[0], nearPlane[1], nearPlane[2]);
-	Vector3 farVec(farPlane[0], farPlane[1], farPlane[2]);
-		
-	Vector3 dirVec = farVec - nearVec;	
-	dirVec.Normalize();
-	
-	Vector3 hitPoint;
-	
-	Matrix4 fullMatrix = matrix;
-	
-	if(poly->getVertexCount() == 3) {
-		return rayTriangleIntersect(Vector3(0,0,0), dirVec, fullMatrix * (*poly->getVertex(0)), fullMatrix  * (*poly->getVertex(1)), fullMatrix *  (*poly->getVertex(2)), &hitPoint);
-	} else if(poly->getVertexCount() == 4) {
-		return (rayTriangleIntersect(Vector3(0,0,0), dirVec, fullMatrix * (*poly->getVertex(2)), fullMatrix  * (*poly->getVertex(1)), fullMatrix *  (*poly->getVertex(0)), &hitPoint) ||
-				rayTriangleIntersect(Vector3(0,0,0), dirVec, fullMatrix * (*poly->getVertex(0)), fullMatrix  * (*poly->getVertex(3)), fullMatrix *  (*poly->getVertex(2)), &hitPoint));
-	} else {
-		return false;
-	}
-}
-
 void OpenGLRenderer::enableDepthWrite(bool val) {
 	if(val)
 		glDepthMask(GL_TRUE);
@@ -490,14 +451,19 @@ void OpenGLRenderer::setFogProperties(int fogMode, Color color, Number density,
 }
 
 
-void OpenGLRenderer::_setOrthoMode() {
+void OpenGLRenderer::_setOrthoMode(Number orthoSizeX, Number orthoSizeY) {
+	this->orthoSizeX = orthoSizeX;
+	this->orthoSizeY = orthoSizeY;
+	
 	if(!orthoMode) {
 		glMatrixMode(GL_PROJECTION);
 		glPushMatrix();
 		glLoadIdentity();
-		glOrtho(-1,1,-1,1,nearPlane,farPlane);
+		glOrtho(-orthoSizeX*0.5,orthoSizeX*0.5,-orthoSizeY*0.5,orthoSizeY*0.5,-farPlane,farPlane);
 		orthoMode = true;
 	}
+	glGetDoublev( GL_PROJECTION_MATRIX, sceneProjectionMatrixOrtho);
+		
 	glMatrixMode(GL_MODELVIEW);	
 	glLoadIdentity();	
 }

+ 69 - 0
Core/Contents/Source/PolyRenderer.cpp

@@ -77,8 +77,77 @@ void Renderer::setExposureLevel(Number level) {
 	exposureLevel = level;
 }
 
+
+bool Renderer::test2DCoordinateInPolygon(Number x, Number y, Polycode::Polygon *poly, const Matrix4 &matrix, bool ortho, bool testBackfacing, bool billboardMode) {
+
+	Vector3 dirVec;
+	Vector3 origin;
+	
+	if(ortho) {
+		origin = Vector3(((x/(Number)xRes)*orthoSizeX) - (orthoSizeX*0.5), (((yRes-y)/(Number)yRes)*orthoSizeY) - (orthoSizeY*0.5), 0.0);
+		origin = cameraMatrix * origin;
+
+		dirVec = Vector3(0.0, 0.0, -1.0);
+		dirVec = cameraMatrix.rotateVector(dirVec);	
+	} else {
+		dirVec = projectRayFrom2DCoordinate(x, y);
+		origin = cameraMatrix.getPosition();	
+	}
+	
+	Vector3 hitPoint;
+	
+	Matrix4 fullMatrix = matrix;
+	
+	if(billboardMode) {
+		Matrix4 camInverse = cameraMatrix.inverse();
+		fullMatrix = fullMatrix * camInverse;
+		
+		fullMatrix.m[0][0] = 1;
+		fullMatrix.m[0][1] = 0;
+		fullMatrix.m[0][2] = 0;
+
+		fullMatrix.m[1][0] = 0;
+		fullMatrix.m[1][1] = 1;
+		fullMatrix.m[1][2] = 0;
+
+		fullMatrix.m[2][0] = 0;
+		fullMatrix.m[2][1] = 0;
+		fullMatrix.m[2][2] = 1;		
+		
+		origin = camInverse * origin;
+		dirVec = camInverse.rotateVector(dirVec);
+	}
+	
+	bool retStatus = false;	
+	
+	
+	if(poly->getVertexCount() == 3) {
+		retStatus = rayTriangleIntersect(origin, dirVec, fullMatrix * (*poly->getVertex(0)), fullMatrix  * (*poly->getVertex(1)), fullMatrix *  (*poly->getVertex(2)), &hitPoint);
+		if(testBackfacing && !retStatus) {
+			retStatus = rayTriangleIntersect(origin, dirVec, fullMatrix * (*poly->getVertex(2)), fullMatrix  * (*poly->getVertex(1)), fullMatrix *  (*poly->getVertex(0)), &hitPoint);
+		
+		}
+	} else if(poly->getVertexCount() == 4) {
+		retStatus = (rayTriangleIntersect(origin, dirVec, fullMatrix * (*poly->getVertex(2)), fullMatrix  * (*poly->getVertex(1)), fullMatrix *  (*poly->getVertex(0)), &hitPoint) ||
+				rayTriangleIntersect(origin, dirVec, fullMatrix * (*poly->getVertex(0)), fullMatrix  * (*poly->getVertex(3)), fullMatrix *  (*poly->getVertex(2)), &hitPoint));
+		if(testBackfacing && !retStatus) {
+			retStatus = (rayTriangleIntersect(origin, dirVec, fullMatrix * (*poly->getVertex(0)), fullMatrix  * (*poly->getVertex(1)), fullMatrix *  (*poly->getVertex(2)), &hitPoint) ||
+				rayTriangleIntersect(origin, dirVec, fullMatrix * (*poly->getVertex(2)), fullMatrix  * (*poly->getVertex(3)), fullMatrix *  (*poly->getVertex(0)), &hitPoint));
+		
+		}				
+	} else {
+		retStatus = false;
+	}
+	
+	return retStatus;
+}
+
 bool Renderer::rayTriangleIntersect(Vector3 ray_origin, Vector3 ray_direction, Vector3 vert0, Vector3 vert1, Vector3 vert2, Vector3 *hitPoint)
 {
+
+//	printf("TESTING RAY\nORIGIN: %f,%f,%f\nDIR: %f,%f,%f\nVERT0: %f,%f,%f\nnVERT1: %f,%f,%f\nnVERT2: %f,%f,%f\n", ray_origin.x, ray_origin.y, ray_origin.z, ray_direction.x, ray_direction.y, ray_direction.z, vert0.x, vert0.y, vert0.z, vert1.x, vert1.y, vert1.z, vert2.x, vert2.y, vert2.z);	
+
+
 	Number t,u,v;
 	t = 0; u = 0; v = 0;
 	

+ 5 - 5
Core/Contents/Source/PolyScene.cpp

@@ -225,13 +225,13 @@ void Scene::Render(Camera *targetCamera) {
 		}
 		CoreServices::getInstance()->getRenderer()->addLight(light->getLightImportance(), position, direction, light->getLightType(), light->lightColor, light->specularLightColor, light->getConstantAttenuation(), light->getLinearAttenuation(), light->getQuadraticAttenuation(), light->getIntensity(), light->getSpotlightCutoff(), light->getSpotlightExponent(), light->areShadowsEnabled(), matrixPtr, shadowMapTexture);
 	}	
-	
-	targetCamera->doCameraTransform();
-	targetCamera->buildFrustrumPlanes();
-	
+
 	if(targetCamera->getOrthoMode()) {
-		CoreServices::getInstance()->getRenderer()->_setOrthoMode();
+		CoreServices::getInstance()->getRenderer()->_setOrthoMode(targetCamera->getOrthoSizeX(), targetCamera->getOrthoSizeY());
 	}
+		
+	targetCamera->doCameraTransform();
+	targetCamera->buildFrustrumPlanes();
 	
 	CoreServices::getInstance()->getRenderer()->enableFog(fogEnabled);	
 	if(fogEnabled) {