在使用 C++ 在 OpenGL 中移动形状时按时间自动旋转形状
Posted
技术标签:
【中文标题】在使用 C++ 在 OpenGL 中移动形状时按时间自动旋转形状【英文标题】:Auto-Rotating shapes by time while moving them in OpenGL with C++ 【发布时间】:2020-06-11 12:40:10 【问题描述】:我想让我的形状随时间旋转,同时我可以使用键盘移动它们(左-右、下-上、前-后)我添加了一个名为 timer()
的函数,它应该改变立方体的角度和时间金字塔。
问题是代码在glutPostOverlayRedisplay();
函数处不断中断,它说:
在 Opengl.exe 中的 0x10004813 (glut32.dll) 处引发异常:0xC0000005: 访问冲突读取位置 0x00000020。
我该如何解决这个问题,为什么会这样? 这是代码:
#include <GL/glut.h>
int object = 0;
float xLeftRight[] 0, 0 ;
float yDownUp[] 0, 0 ;
float zFrontBack[] 0, 0 ;
float PyramidAngle = 0.0;
float CupeAngle = 0.0;
int t_refresh = 20;//ms
float degree = 0;
float xscale = 1, yscale = 1, zscale = 1;
void Keyboard(int buttons, int x, int y)
switch (buttons)
case GLUT_KEY_F1: object = 0; break;
case GLUT_KEY_F2: object = 1; break;
case GLUT_KEY_LEFT: xLeftRight[object] -= 0.1; break;
case GLUT_KEY_RIGHT: xLeftRight[object] += 0.1; break;
case GLUT_KEY_DOWN: yDownUp[object] -= 0.1; break;
case GLUT_KEY_UP: yDownUp[object] += 0.1; break;
case GLUT_KEY_PAGE_UP: zFrontBack[object] -= 0.1; break;
case GLUT_KEY_PAGE_DOWN: zFrontBack[object] += 0.1; break;
glutPostRedisplay();
void Settings()
glClearColor(1, 1, 1, 0);
glClearDepth(1.0f);
glEnable(GL_DEPTH_TEST);
glDepthFunc(GL_LEQUAL);
glShadeModel(GL_SMOOTH);
glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
void DrawingFunction()//painting
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glPushMatrix();
glMatrixMode(GL_MODELVIEW);
glLoadIdentity(); //reset
glTranslatef(1.5f, 0.0f, -6.0f); // rotate left and back by time
glRotatef(PyramidAngle, 1.0f, 1.0f, 0.0f);
glColor3f(1.0, 0.0, 0.0);
glScalef(xscale, yscale, zscale);
glTranslatef(xLeftRight[0], yDownUp[0], zFrontBack[0]); //move the pyramid (if object = 0)
glBegin(GL_TRIANGLES);
// front
glColor3f(1.0f, 0.0f, 0.0f); //red
glVertex3f(0.0f, 1.0f, 0.0f);
glColor3f(0.0f, 1.0f, 0.0f); //green
glVertex3f(-1.0f, -1.0f, 1.0f);
glColor3f(0.0f, 0.0f, 1.0f); //blue
glVertex3f(1.0f, -1.0f, 1.0f);
// right
glColor3f(1.0f, 0.0f, 0.0f); //red
glVertex3f(0.0f, 1.0f, 0.0f);
glColor3f(0.0f, 0.0f, 1.0f); //blue
glVertex3f(1.0f, -1.0f, 1.0f);
glColor3f(0.0f, 1.0f, 0.0f); //green
glVertex3f(1.0f, -1.0f, -1.0f);
// back
glColor3f(1.0f, 0.0f, 0.0f); //red
glVertex3f(0.0f, 1.0f, 0.0f);
glColor3f(0.0f, 1.0f, 0.0f); //green
glVertex3f(1.0f, -1.0f, -1.0f);
glColor3f(0.0f, 0.0f, 1.0f); //blue
glVertex3f(-1.0f, -1.0f, -1.0f);
// left
glColor3f(1.0f, 0.0f, 0.0f); //red
glVertex3f(0.0f, 1.0f, 0.0f);
glColor3f(0.0f, 0.0f, 1.0f); //blue
glVertex3f(-1.0f, -1.0f, -1.0f);
glColor3f(0.0f, 1.0f, 0.0f); //green
glVertex3f(-1.0f, -1.0f, 1.0f);
glEnd();
glPopMatrix();
glPushMatrix();
glLoadIdentity();//(Reset model-view matrix)
glTranslatef(-2.0f, 0.0f, -7.0f); // rotate the cube right and back by time
glRotatef(CupeAngle, 1.0f, 0.0f, 0.0f);
glTranslatef(xLeftRight[1], yDownUp[1], zFrontBack[1]); //move the cube (if object = 1)
glBegin(GL_QUADS); //cube
glColor3f(1.0f, 0.0f, 1.0f);
glVertex3f(1.0f, 1.0f, -1.0f);
glVertex3f(-1.0f, 1.0f, -1.0f);
glVertex3f(-1.0f, 1.0f, 1.0f);
glVertex3f(1.0f, 1.0f, 1.0f);
glColor3f(1.0f, 0.5f, 0.0f);
glVertex3f(1.0f, -1.0f, 1.0f);
glVertex3f(-1.0f, -1.0f, 1.0f);
glVertex3f(-1.0f, -1.0f, -1.0f);
glVertex3f(1.0f, -1.0f, -1.0f);
glColor3f(0.0f, 0.0f, 1.0f);
glVertex3f(1.0f, 1.0f, 1.0f);
glVertex3f(-1.0f, 1.0f, 1.0f);
glVertex3f(-1.0f, -1.0f, 1.0f);
glVertex3f(1.0f, -1.0f, 1.0f);
glColor3f(1.0f, 1.0f, 0.0f);
glVertex3f(1.0f, -1.0f, -1.0f);
glVertex3f(-1.0f, -1.0f, -1.0f);
glVertex3f(-1.0f, 1.0f, -1.0f);
glVertex3f(1.0f, 1.0f, -1.0f);
glColor3f(1.0f, 0.0f, 0.0f);
glVertex3f(-1.0f, 1.0f, 1.0f);
glVertex3f(-1.0f, 1.0f, -1.0f);
glVertex3f(-1.0f, -1.0f, -1.0f);
glVertex3f(-1.0f, -1.0f, 1.0f);
glColor3f(0.0f, 1.0f, 0.0f);
glVertex3f(1.0f, 1.0f, -1.0f);
glVertex3f(1.0f, 1.0f, 1.0f);
glVertex3f(1.0f, -1.0f, 1.0f);
glVertex3f(1.0f, -1.0f, -1.0f);
glEnd();
glutSwapBuffers();
PyramidAngle += 1.0f; //changing the angle
CupeAngle -= 0.2f; //changing the angle
glPopMatrix();
void timer(int value)
glutPostOverlayRedisplay();
glutTimerFunc(t_refresh, timer, 0);
void ViewSetting(int x, int y)
int aspect = x / y;
glViewport(0, 0, x, y);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective(45, aspect, 0.1, 20);
int main(int argc, char** argv)
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_DOUBLE);
glutInitWindowPosition(50, 50);
glutInitWindowSize(800, 600);
glutCreateWindow("3d shapes");
glutDisplayFunc(DrawingFunction);
glutReshapeFunc(ViewSetting);
glutSpecialFunc(Keyboard);
Settings();
glutTimerFunc(0, timer, 0);
glutMainLoop();
return 0;
【问题讨论】:
【参考方案1】:glutPostOverlayRedisplay
将当前窗口的覆盖标记为需要重新显示(参见Overlay Management)。
你必须使用glutPostRedisplay
:
void timer(int value)
glutPostRedisplay();
glutTimerFunc(t_refresh, timer, 0);
【讨论】:
以上是关于在使用 C++ 在 OpenGL 中移动形状时按时间自动旋转形状的主要内容,如果未能解决你的问题,请参考以下文章
在 OpenGL 中使用箭头键移动一些形状 - 它缩小而不是移动
如何在 C++ 中使用 sdl、opengl 移动相机时修复奇怪的相机旋转