gluPerspective、glViewport、gluLookAt 以及 GL_PROJECTION 和 GL_MODELVIEW 矩阵 [英] gluPerspective, glViewport, gluLookAt and the GL_PROJECTION and GL_MODELVIEW Matricies

查看:21
本文介绍了gluPerspective、glViewport、gluLookAt 以及 GL_PROJECTION 和 GL_MODELVIEW 矩阵的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想使用gluPerspective"、glViewport"和gluLookAt"来操作我的相机和屏幕.

I want to use 'gluPerspective', 'glViewport' and 'gluLookAt' to manipulate my camera and screen.

哪些函数适用于哪种矩阵模式?我应该/必须以什么顺序使用它们?

Which functions to I apply to which matrix mode? And in what order should I / must I use them?

例如,我试图像这样设置我的屏幕和相机:(但它不起作用!)

For example, I am trying to set up my screen and camera like this: (But it is not working!)

glMatrixMode(GL_PROJECTION) // Apply following to projection matrix - is this correct?
glLoadIdentity(); // Reset first
glPerspective(45.0, (double)w/(double)h, 1.0, 200.0); // Set perspective
glViewport(0, 0, w, h); // Set viewport

glMatrixMode(GL_MODELVIEW); // Apply following to modelview - should glViewport come under here?
glLoadIdentity(); // Reset first
gluLookAt(px, py, pz, cx, cy, cz, ux, uy, uz); // Set position, centre and then up vectors
// This surely comes after calling GL_MODELVIEW?

我已经四处寻找在线文档,我了解这些功能,只是不知道它们应该去哪里以及按什么顺序!

I have looked around for online documentation, and I understand the functions, just not where they should go and in what order!

现在已经过去了几个月,我正在添加一个快速编辑来显示我用来使用 OpenGL 渲染事物的系统.这是为了帮助以后看到这个问题的其他人.

It is several months later now and I am adding a quick edit to show the system I use to render things with OpenGL. This is to help others who see this question in the future.

我主要使用两种方法.

方法一:

此方法将所有内容组合在一起.

This method groups everything together.

// Firstly, the window may have been resized so re-create the viewing area
glViewport(0, 0, width_of_window_rendering_area, height_of_window_rendering area);

这将重新创建视口以在窗口内部的整个区域上进行渲染.使用 sfml,您可以执行诸如 window.width() 或 window.height() 之类的操作,或者类似的操作,具体取决于您使用的窗口工具包(glut、glfw、sdl 等)...

This recreates the viewport for rendering over the entire area of the inside of the window. With sfml, you would do something like window.width() or window.height(), or something similar depending on which windowing toolkit you use (glut, glfw, sdl etc)...

// The second step is to add a projection matrix. There are three main ones I like to use
// Uncomment the one you want
glMatrixMode(GL_PROJECTION); // Tell OpenGL to manipulate the correct matrix stack
glLoadIdentity(); // Reset the projection matrix, or bad things happen after multiple calls to below functions!
// glOrtho( ... ) // Uncomment to use 2D rendering
// gluPerspective( ... ) // Uncomment to use (easy) 3D rendering
glFrustrum( ... ) // Uncomment to use (harder/less intuitive?) 3D rendering
glMatrixMode(GL_MODELVIEW); // I always prefer to leave OpenGL in the modelview manipulation mode.
    // I consider it the "default" and safest mode to leave OpenGL in, as any rogue
    // calls to functions changing its contents is likely to mess up your geometry
    // which should be visible as a problem on the screen, which tells you you need
    // to fix something! Manipulating the other matrix stacks may not show obvious
    // problems.

您需要从glOrtho"、gluPerspective"和glFrustrum"这三个中选择一个.还有'gluOrtho2D',但要小心使用!(我更喜欢用glOrtho"自己指定近平面和远平面.)您还需要将..."替换为函数的参数.

You will need to select one of the three out of 'glOrtho', 'gluPerspective' and 'glFrustrum'. There is also 'gluOrtho2D', but use that with care! (I prefer to specify near and far planes myself with 'glOrtho'.) You need to replace the '...' with your arguments to the function also.

// The third step is to clear the screen and set your camera / geometry position
glClear(GL_COLOR_BUFFER_BIT); // use bitwise OR ('||') with 'GL_DEPTH_BUFFER_BIT' and 'GL_STENCIL_BUFFER_BIT' if required
gluLookAt( ... );
// I like to use gluLookAt, or at least I _italic_used to! Now I implement my own camera...
 // That is another fun thing you should try if you are comfortable with 3D geometry and hard math!

// The fourth step is to draw your scene. You may want to put lighting stuff first or in with the drawing
glutWireTeapot( ... );

方法二:

第二种方法和上面一样,只是把第一步移到一个单独的函数中.然后您必须检测窗口调整大小事件并调用此函数.使用 glut,您可以指定回调.使用 SFML,您可以在调整窗口大小时检测事件.我忘记了 SDL 的工作原理,但它是相似的.我还没有了解 glfw 是如何工作的.

The second method is the same as above, but to move the first step into a separate function. Then you must detect window resize events and call this function. With glut, you can specify a callback. With SFML you can detect an event when the window is resized. I forget how SDL works, but it is similar. I have not yet learned how glfw works.

希望能帮到你.

一些 OpenGL 新手(可能曾经包括我自己)尝试在 PROJECTION 矩阵上指定相机平移.不要这样做 - 我觉得它搞砸了照明和其他可能的事情.

Some OpenGL novices (probably myself included at one time) try to specify camera translations on the PROJECTION matrix. Do not do this - I head it messes up lighting and possibly other things.

推荐答案

我将我的 reshape 回调函数定义为:

I define my reshape callback function as:

在开始时调用一次 glViewport(...).

然后用单位矩阵重新加载投影矩阵:

Then reload the projection matrix with an identity matrix:

glMatrixMode(GL_PROJECTION);
glLoadIdentity();

那么:

glPerspective(...)
glMatrixMode(GL_MODELVIEW);

gluLookAt(...) 如果您需要更改相机位置,可以稍后随时调用.

gluLookAt(...) can be called anytime later if you need to change your camera position.

适用于我的简单目的.

这篇关于gluPerspective、glViewport、gluLookAt 以及 GL_PROJECTION 和 GL_MODELVIEW 矩阵的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆