opengl es 坐标变换怎样将屏幕坐标转为世界坐标

11:52 提问
opengl屏幕坐标转世界坐标的问题
我正在试图用opengl实现一个类似google earth那样的功能:
1),相机永远面向地球的球心
2),鼠标定点拖动旋转,也就是鼠标按住地球上一个点移动的时候,这个点就跟随鼠标的位置运动,鼠标动了多长,相机就旋转多长,一开始按住的那个点一直处于鼠标的位置,而不要跑开了
现在我已经实现了基本的旋转部分,拖动鼠标相机就转动,但没有定点转动,现在就剩下定点拖动旋转这个功能了,我的思路是将鼠标点击屏幕的屏幕坐标转换成opengl的世界坐标,通过这个点构造一个射线,求出射线和地球的交点坐标,如果射线和地球没有相交,则不会产生任何效果。如果有相交,则计算鼠标移动到下一个位置的时候的屏幕射线与地球的交点坐标,通过两个坐标的值近似计算成鼠标在地球表面划过的弧长,然后将这个长度作为偏移量算出相机旋转的量。
现在的问题是屏幕坐标转世界坐标异常,不管点击屏幕上的任何一点,计算出的世界坐标都几乎一样,只有小数点后好几位的值有细微差别,旋转相机或者远离或靠近地球时坐标值会改变,但依然屏幕任何一点的坐标都差不多一样,计算坐标转换的代码如下:
void screen2world(int x, int y)
GLint viewport[4];
GLdouble modelview[16];
GLdouble projection[16];
GLfloat winX, winY, winZ;
GLdouble posX, posY, posZ;
glGetDoublev(GL_MODELVIEW_MATRIX, modelview);
glGetDoublev(GL_PROJECTION_MATRIX, projection);
glGetIntegerv(GL_VIEWPORT, viewport);
winX = (float)x;
winY = (float)viewport[3] - (float)y;
glReadPixels(x, int(winY), 1, 1, GL_DEPTH_COMPONENT, GL_FLOAT, &winZ);
gluUnProject(winX, winY, winZ, modelview, projection, viewport, &posX, &posY, &posZ);
请问一下出现问题的原因可能是什么?另外我的鼠标定点拖动旋转的思路有问题吗?还有就是有没有实现类似google earth那样的拖动旋转功能的demo源码可供查考,谢谢
准确详细的回答,更有利于被提问者采纳,从而获得C币。复制、灌水、广告等回答会被删除,是时候展现真正的技术了!
其他相关推荐www.apkbus.com - Database Error
Discuz! Database Error
已经将此出错信息详细记录, 由此给您带来的访问不便我们深感歉意.关于屏幕坐标转换为opengl坐标
[问题点数:20分,结帖人huangqiyin]
关于屏幕坐标转换为opengl坐标
[问题点数:20分,结帖人huangqiyin]
不显示删除回复
显示所有回复
显示星级回复
显示得分回复
只显示楼主
匿名用户不能发表回复!|三维坐标系及坐标变换初步
OpenGL ES 图形庫最终的结果是在二维平面上显示 3D 物体(常称作模型 Model)這是因為目前的打部分显示器还只能显示二维图形。但我们在构造 3D 模型时必須要有空间想象能力,所有对模型的描述还是使用三维坐标。也就是使用 3D 建模,而有 OpenGL ES 库来完成从 3D 模型到二维屏幕上的显示。
这个过程可以分成三个部分:
坐标变换,坐标变换通过使用变换矩阵来描述,因此学习 3D 绘图需要了解一些空间几何,矩阵运算的知识。三维坐标通常使用齐次坐标来定义。变换矩阵操作可以分为视角(Viewing),模型(Modeling)和投影(Projection)操作,這些操作可以有选择,平移,缩放,正侧投影,透视投影等。
由于最終的 3D 模型需要在一个矩形窗口中显示,因此在这个窗口之外的部分需要裁剪掉以提高绘图效率,对应3D 图形,裁剪是将处在剪切面之外的部分扔掉。
在最终绘制到显示器(2D 屏幕),需要建立起变换后的坐标和屏幕像素之间的对应关系,这通常称为「视窗」坐标变换(Viewport) transformation.
如果我们使用照相机拍照的过程做类比,可以更好的理解 3D 坐标变换的过程。
拍照时第一步是架起三角架並把相机的镜头指向需要拍摄的场景,对应到 3D 变换为 viewing transformation (平移或是选择 Camera )
然后摄影师可能需要调整被拍場景中某個物体的角度,位置,比如摄影师給架好三角架后給你拍照时,可以要让你调整站立姿势或是位置。對應到 3D 繪製就是 Modeling transformation (調整所繪模型的位置,角度或是縮放比例)。
之后摄影师可以需要調整镜头取景(拉近或是拍攝遠景),相机取景框所能拍攝的場景會隨鏡頭的伸縮而變換,對應到 3D 繪图則為 Projection transformation(裁剪投影場景)。
按下快門後,对于數碼相机可以直接在屏幕上显示當前拍攝的照片,一般可以充满整個屏幕(相当于将坐标做規範化處理 NDC),此時你可以使用縮放放大功能显示照片的部分。对应到 3D 绘图相当于 viewport transformation (可以對最終的图像縮放显示等)
下图为 Android OpenGL ES 坐标变换的过程:
Object Coordinate System: 也称作Local coordinate System,用來定义一個模型本身的坐標系。
World Coordinate System: 3d 虚拟世界中的绝对坐标系,定义好這個坐标系的原点就可以用来描述模型的实现的位置,Camera 的位置,光源的位置。
View Coordinate System: 一般使用用来计算光照效果。
Clip Coordinate System:
对 3D 场景使用投影机换裁剪視角。
Normalized device coordinate System (NDC): 规范后坐标系。
Windows Coordinate System: 最后屏幕显示的 2D 坐标系統,一般原点定义在屏幕左上角。
对于 Viewing transformation (平移,选择相机)和 Modeling transformation(平移,选择模型)可以合并起來看,只是应为向左移动相机,和相机不同将模型右移的效果是等效的。
所以在 OpenGL ES 中,
使用 GL10.GL_MODELVIEW 来同時指定 viewing matrix 和 modeling matrix.
使用 GL10.GL_PROJECTION 指定投影变换,OpenGL 支持透視投影和正侧投影(一般用于工程制图)。
使用 glViewport 指定 Viewport 变换。
此时再看看下面的代码,就不是很难理解了,后面就逐步介绍各种坐标变换。
public void onSurfaceChanged(GL10 gl, int width, int height) {
// Sets the current view port to the new size.
gl.glViewport(0, 0, width, height);
// Select the projection matrix
gl.glMatrixMode(GL10.GL_PROJECTION);
// Reset the projection matrix
gl.glLoadIdentity();
// Calculate the aspect ratio of the window
GLU.gluPerspective(gl, 45.0f, (float) width / (float) height, 0.1f, 100.0f);
// Select the modelview matrix
gl.glMatrixMode(GL10.GL_MODELVIEW);
// Reset the modelview matrix
gl.glLoadIdentity();android OpenGL Es2.0 从世界坐标转屏幕,我有代码,但是好像不太正确,请高手来看下.
[问题点数:100分,结帖人Ptrtoptr]
android OpenGL Es2.0 从世界坐标转屏幕,我有代码,但是好像不太正确,请高手来看下.
[问题点数:100分,结帖人Ptrtoptr]
不显示删除回复
显示所有回复
显示星级回复
显示得分回复
只显示楼主
2015年9月 移动开发大版内专家分月排行榜第二2015年6月 移动开发大版内专家分月排行榜第二2014年12月 移动开发大版内专家分月排行榜第二2014年7月 移动开发大版内专家分月排行榜第二2013年12月 移动开发大版内专家分月排行榜第二2013年11月 移动开发大版内专家分月排行榜第二2013年10月 移动开发大版内专家分月排行榜第二
2014年11月 移动开发大版内专家分月排行榜第三2014年2月 移动开发大版内专家分月排行榜第三
匿名用户不能发表回复!|

我要回帖

更多关于 opengl es2.0屏幕坐标 的文章

 

随机推荐