zoukankan      html  css  js  c++  java
  • 3D Computer Grapihcs Using OpenGL

    本节将采用两种方法绘制两个三角形。

    先看第一种方法的代码

    MyGlWindow.cpp

     1 #include <glglew.h>
     2 #include "MyGlWindow.h"
     3 
     4 void MyGlWindow::initializeGL()
     5 {
     6     glewInit();
     7 
     8     GLfloat verts[] =
     9     {
    10         +0.0f, +0.0f,
    11         +1.0f, +1.0f,
    12         -1.0f, +1.0f,
    13 
    14         +0.0f, +0.0f,
    15         -1.0f, -1.0f,
    16         +1.0f, -1.0f,
    17     };
    18     GLuint myBufferID;
    19     glGenBuffers(1, &myBufferID);
    20     glBindBuffer(GL_ARRAY_BUFFER, myBufferID);
    21     glBufferData(GL_ARRAY_BUFFER, sizeof(verts), verts, GL_STATIC_DRAW);
    22     glEnableVertexAttribArray(0);
    23     glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 0, 0);
    24 }
    25 
    26 void MyGlWindow::paintGL()
    27 {
    28     glViewport(0, 0, width(), height());
    29     glDrawArrays(GL_TRIANGLES, 0, 6);
    30 }

    和上一节的代码很相似,区别是verts数组增加了6个元素(能额外表示3个顶点),另外glDrawArrays()函数的最后一个参数变成了6,表示绘制六个顶点。这样当然就可以绘制2个三角形了。

    但是这种方法造成了一个浪费,代码中可以看到两次出现了(0.0,0.0)点。

    EBO

    OpenGL允许我们提供一个索引数组用来指定三角形的顶点组成顺序。这个数组通常被称为EBO。

    看第二种绘制三角形的方法:

     1 #include <glglew.h>
     2 #include "MyGlWindow.h"
     3 
     4 void MyGlWindow::initializeGL()
     5 {
     6     glewInit();
     7 
     8     GLfloat verts[] =
     9     {
    10         +0.0f, +0.0f, //0
    11         +1.0f, +1.0f, //1
    12         -1.0f, +1.0f, //2
    13         -1.0f, -1.0f, //3
    14         +1.0f, -1.0f, //4
    15     };
    16     GLuint vertexBufferID;
    17     glGenBuffers(1, &vertexBufferID);
    18     glBindBuffer(GL_ARRAY_BUFFER, vertexBufferID);
    19     glBufferData(GL_ARRAY_BUFFER, sizeof(verts), verts, GL_STATIC_DRAW);
    20     glEnableVertexAttribArray(0);
    21     glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 0, 0);
    22 
    23     GLushort indices[] =
    24     {
    25         0,1,2,
    26         0,3,4,
    27     };
    28     GLuint indexBufferID;
    29     glGenBuffers(1, &indexBufferID);
    30     glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBufferID);
    31     glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices), indices, GL_STATIC_DRAW);
    32 }
    33 
    34 void MyGlWindow::paintGL()
    35 {
    36     glViewport(0, 0, width(), height());
    37     glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_SHORT, 0);
    38 }

    *注:为了区分两个Buffer,我们这里把之前的myBufferID改名为vertexBufferID

    23-31行和顶点位置设置代码(8-19行)非常相似。

    28-29行创建了另外一个BufferObject- indexBuffer

    30行把indexBuffer绑定到GL_ELEMENT_ARRAY_BUFFER绑定点上

    31行对其填充数据,其数据内容是一个GLushort类型的数组,每三个元素表示一个三角形的顶点索引,索引值是相对于verts数组来说的(参考verts中的注释)。这里使用GLushort而不使用GLint的原因是GLushort给了我们更大的数据存储量,索引始终都是正整数,所以使用unsigned类型更合理。

    在paintGL函数中,这次不使用glDrawArrays函数了,改用glDrawElements()函数绘制

    第二个参数表示6个顶点

    第三个参数表示indices数组的类型

    第四个参数表示偏移值

    使用EBO在本例中仅节约了一个顶点位置数据,但是在复杂的模型中,会节约非常多的数据。

  • 相关阅读:
    PyTorch学习笔记之Variable_and_function_cat
    PyTorch学习笔记之DataLoaders
    PyTorch学习笔记之nn的简单实例
    PyTorch学习笔记之Tensors 2
    PyTorch学习笔记之Tensors
    webdriver定位元素
    Python面向对象、继承和多态
    python中json文件处理涉及的四个函数json.dumps()和json.loads()、json.dump()和json.load()的区分
    Python定义类时为什么要继承object类
    Python数据类型
  • 原文地址:https://www.cnblogs.com/AnKen/p/8331198.html
Copyright © 2011-2022 走看看