我想通过在屏幕上投影球体来绘制椭圆(如栅格化)。这是我的代码,但它不会在屏幕上显示任何内容。我应该使用更多功能来初始化投影吗?这种方式是否可以通过使用球体在屏幕上绘制椭圆?
GLfloat xRotated, yRotated, zRotated;
GLdouble radius=1;
void display(void);
void reshape(int x, int y);
int main (int argc, char **argv)
{
glutInit(&argc, argv);
glutInitWindowSize(800,800);
glutCreateWindow("OVAL");
zRotated = 30.0;
xRotated=43;
yRotated=50;
glutDisplayFunc(display);
glutReshapeFunc(reshape);
glutMainLoop();
return 0;
}
void display(void)
{
glMatrixMode(GL_PROJECTION);
glOrtho(0.1, 1.0, 0.1, 1.0, -1.0, 1.0);
glClear(GL_COLOR_BUFFER_BIT);
glLoadIdentity();
glTranslatef(0.0,0.0,-5.0);
glColor3f(0.9, 0.3, 0.2);
glRotatef(xRotated,1.0,0.0,0.0);
glRotatef(yRotated,0.0,1.0,0.0);
glRotatef(zRotated,0.0,0.0,1.0);
glScalef(1.0,1.0,1.0);glutSolidSphere(radius,20,20);
glFlush();
}
void reshape(int x, int y)
{
if (y == 0 || x == 0) return;
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective(39.0,(GLdouble)x/(GLdouble)y,0.6,21.0);
glMatrixMode(GL_MODELVIEW);
glViewport(0,0,x,y);
}
答案 0 :(得分:2)
你正在观察体积之外完全绘制一个球体,因此无法看到它就不足为奇了。
您的代码存在一些问题:
glLoadIndentity
和glLoadMatrix
之外的所有OpenGL矩阵函数总是将矩阵后乘矩阵到当前矩阵堆栈的当前顶部元素。在display
函数中,您可以调用glOrtho
,而无需先重置投影矩阵以进行标识。如果display
回调被多次调用,这将导致完全奇怪和不同的结果。
您应该在致电glLoadIdentity()
之前立即致电glOrtho
。
您设置了模型视图转换,以便球体的中心始终以眼睛空间中的(0,0,-5)结束。但是,你设置了一个投影矩阵,它定义了一个观察体积,它从眼睛空间的z=1
(近平面)到z=-1
(远平面),所以你的拼写实际上是在远处的平面后面。
有几种方法可以修复。通过修改glOrtho
的参数来更改视锥体可能是最简单的。例如,您可以尝试(-2, 2, -2, 2, 1, 10)
来查看球体。
目前还不清楚
是什么我想通过在屏幕上投影球体来绘制椭圆(如栅格化)。
确切意味着。如果您只想将球体扭曲为椭圆体,则可以应用一些非均匀缩放。这原则上可以在投影矩阵中完成(如果没有其他对象要显示),但是将它应用于球体的模型矩阵会更有意义 - 你已经在那里调用了glScale
,你可以试试像glScalef(1.0f, 0.5f, 1.0f);
。
另请注意,如果您的视口不是正方形,我之前建议的正交参数会导致一些失真。在现实世界中,人们希望将视口的宽高比合并到投影矩阵中。
如果您希望通过透视投影看到球体变形,则必须跳过glOrtho
altogheter并切换到透视投影矩阵。
您使用的代码已完全过时。 OpenGL矩阵堆栈已在OpenGL 3.0(2008)中弃用,并且在现代OpenGL的核心配置文件中不可用。这同样适用于内置顶点属性,如glColor
或立即模式绘制和客户端顶点数组。因此,GLUT的绘图功能也不能再与现代GL一起使用。
如果你现在真的打算学习OpenGL,我强烈建议你不要理会这种古老而又明星学习现代方式。