OpenGL實現3D空間中移動影象
阿新 • • 發佈:2020-08-19
Qt_OpenGL:3D空間中移動影象,供大家參考,具體內容如下
//.h
#ifndef GLWIDGET_H #define GLWIDGET_H #include <QGLWidget> #include <QtOpenGL> class QGLWidget; class QTimer; typedef struct Stars{ public: int r,g,b; GLfloat dist,angle; }Stars; class GLWidget : public QGLWidget { Q_OBJECT public: GLWidget(QWidget *parent = 0); ~GLWidget(); protected: void initializeGL(); void paintGL(); void resizeGL(int w,int h); void keyPressEvent(QKeyEvent*); void timerEvent(QTimerEvent*); private: bool fullscreen; GLfloat rotate_angle; GLfloat zoom; GLfloat title; GLfloat spin; GLuint loop; bool twinkle; GLfloat blend; private: void loadTextures(); GLuint texture[1]; }; #endif // GLWIDGET_H
//.cpp
#include "glwidget.h" #include <glut.h> #include <QtGui> #include <QtCore> //好吧我承認全部變數不好 GLfloat light_ambient[4] = {0.5,0.5,1.0}; GLfloat light_diffiuse[4] = {1.0,1.0,1.0}; GLfloat light_position[4] = {0.0,0.0,2.0,0.0}; static const int num = 50; static Stars stars[num]; GLWidget::GLWidget(QWidget *parent) : QGLWidget(parent) { fullscreen = false; rotate_angle = 0.0; zoom = -15.0; title = 90.0; spin = 0.1; loop = 0; twinkle = false; blend = false; startTimer(5); } void GLWidget::initializeGL(){ setGeometry(300,150,500,500); loadTextures(); glEnable(GL_TEXTURE_2D); glShadeModel(GL_SMOOTH); glClearColor(0.0,0.5); glClearDepth(1.0); glEnable(GL_DEPTH_TEST); glDepthFunc(GL_LEQUAL); glHint(GL_PERSPECTIVE_CORRECTION_HINT,GL_NICEST); glBlendFunc(GL_SRC_ALPHA,GL_ONE); glEnable(GL_BLEND); //為num個星星物件賦初值 for(loop = 0; loop < num; ++loop){ stars[loop].angle = 0.0; stars[loop].dist = (float(loop)/num) * 5.0; stars[loop].r = rand() % 256; stars[loop].g = rand() % 256; stars[loop].b = rand() % 256; } } void GLWidget::paintGL(){ glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glBindTexture(GL_TEXTURE_2D,texture[0]); for(loop = 0; loop < num; ++loop){ glLoadIdentity(); glTranslatef(0.0,zoom); //移向螢幕裡面 glRotatef(title,0.0); //沿x軸旋轉title glRotatef(stars[loop].angle,0.0); //每個星星沿y軸旋轉自己的角度 glTranslatef(stars[loop].dist,0.0); //平移 glRotatef(-stars[loop].angle,0.0); //沿y軸反轉 glRotatef(-title,0.0); //沿x軸反轉 if(twinkle){ //如果星星閃爍 glColor4ub(stars[num-loop-1].r,stars[num-loop-1].g,stars[num-loop-1].b,255); glBegin(GL_QUADS); glTexCoord2f(0.0f,0.0f); glVertex3f(-1.0f,-1.0f,0.0f); glTexCoord2f(1.0f,0.0f); glVertex3f( 1.0f,1.0f); glVertex3f( 1.0f,1.0f,0.0f); glTexCoord2f(0.0f,1.0f); glVertex3f(-1.0f,0.0f); glEnd(); } //如果星星不閃爍 glRotatef(spin,0.0f,1.0f); //沿z軸自轉spin glColor4ub(stars[loop].r,stars[loop].g,stars[loop].b,255); glBegin(GL_QUADS); glTexCoord2f(0.0f,0.0f); glTexCoord2f(1.0f,0.0f); glTexCoord2f(0.0f,0.0f); glEnd(); spin += 0.01f; stars[loop].angle += float(loop)/num; stars[loop].dist -= 0.01f; //距離逐漸減小,即越來越靠近螢幕 if(stars[loop].dist < 0){ stars[loop].dist += 5.0f; stars[loop].r = rand() % 256; stars[loop].g = rand() % 256; stars[loop].b = rand() % 256; } } } void GLWidget::resizeGL(int w,int h){ if( 0 == h){ h = 1; } glViewport(0,(GLsizei)w,(GLsizei)h); glMatrixMode(GL_PROJECTION); glLoadIdentity(); gluPerspective(45.0,(GLdouble)w/(GLdouble)h,0.1,100.0); glColor4f(1.0f,0.5f); glBlendFunc(GL_SRC_ALPHA,GL_ONE); glMatrixMode(GL_MODELVIEW); glLoadIdentity(); } void GLWidget::keyPressEvent(QKeyEvent *event){ switch(event->key()){ case Qt::Key_T:{ twinkle = !twinkle; updateGL(); break; } case Qt::Key_B:{ blend = !blend; if(blend){ glEnable(GL_BLEND); glDisable(GL_DEPTH_TEST); }else{ glDisable(GL_BLEND); glEnable(GL_DEPTH_TEST); //色彩混合和深度快取不能同時開啟 } updateGL(); break; } case Qt::Key_PageUp:{ //移向螢幕 zoom -= 0.2; updateGL(); break; } case Qt::Key_PageDown:{ //移向螢幕外 zoom += 0.2; updateGL(); break; } case Qt::Key_Up:{ //加快旋轉速度 title += 0.5; updateGL(); break; } case Qt::Key_Down:{ title -= 0.5; updateGL(); break; } case Qt::Key_F1:{ fullscreen = !fullscreen; if(fullscreen){ showFullScreen(); }else{ setGeometry(300,500); showNormal(); } updateGL(); break; } case Qt::Key_Escape:{ close(); } } } void GLWidget::loadTextures(){ QImage tex,buf; if(!buf.load(":Star.bmp")){ qWarning("Cannot open the image..."); QImage dummy(128,128,QImage::Format_RGB32); dummy.fill(Qt::green); buf = dummy; } tex = convertToGLFormat(buf); glGenTextures(1,&texture[0]); glBindTexture(GL_TEXTURE_2D,texture[0]); glTexImage2D(GL_TEXTURE_2D,3,tex.width(),tex.height(),GL_RGBA,GL_UNSIGNED_BYTE,tex.bits()); glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR); glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_NEAREST); } void GLWidget::timerEvent(QTimerEvent *){ updateGL(); } GLWidget::~GLWidget() { }
//main.cpp
#include "glwidget.h" #include <QApplication> int main(int argc,char *argv[]) { QApplication a(argc,argv); GLWidget w; w.show(); return a.exec(); }
//執行結果截圖:
以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支援我們。