Android/windows 顶点对应方法(shader)

下面的方式windows和安卓下都可以使用

纹理的渲染

有了纹理对象且存储了图像数据后, 就可以拿来进行纹理渲染了. 
使用时, 直接再次绑定GL_TEXTURE_2D即可, 表示接下来读取GL_TEXTURE_2D时要使用的是_textureID纹理对象中的数据:

// 第一行和第三行不是严格必须的,默认使用GL_TEXTURE0作为当前激活的纹理单元
glActiveTexture(GL_TEXTURE5); // 指定纹理单元GL_TEXTURE5
glBindTexture(GL_TEXTURE_2D, _textureID); // 绑定,即可从_textureID中取出图像数据。
glUniform1i(_textureSlot, 5); // 与纹理单元的序号对应
 
 
  • 1
  • 2
  • 3
  • 4
  • 1
  • 2
  • 3
  • 4

纹理数据可以跟纹理坐标一一对应, 在OpenGL坐标中呈现出来.

GLfloat texCoords[] = {
    0, 0,//左下
    1, 0,//右下
    0, 1,//左上
    1, 1,//右上
};
glVertexAttribPointer(_textureCoordsSlot, 2, GL_FLOAT, GL_FALSE, 0, texCoords);
glEnableVertexAttribArray(_textureCoordsSlot);
 
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

纹理坐标也同样存储于一个数组中, 使用glVertexAttribPointer方法将其传递给对应的插槽_textureCoordsSlot, 继而传递给Shader中的TextureCoords变量. 
注意, 纹理坐标的坐标系与OpenGL不同, 左下角是原点.

有了纹理数据和纹理坐标, 接下来只需要我们已经很熟悉的顶点绘制方式将OpenGL画布绘制出来即可. 
这里, 顶点坐标与纹理坐标的位置要一一对应, 即将图像的某个点绘制到OpenGL画布的对应点. 
如果我们只是普通的渲染图片, 则将左下, 右下, 左上, 右上这四个点一一对应起来就好了.

GLfloat vertices[] = {
    -1, -1, 0,   //左下
    1,  -1, 0,   //右下
    -1, 1,  0,   //左上
    1,  1,  0 }; //右上
glVertexAttribPointer(_positionSlot, 3, GL_FLOAT, GL_FALSE, 0, vertices);
glEnableVertexAttribArray(_positionSlot);

// 一旦纹理数据准备好,两个坐标系的顶点位置一一对应好。
// 就直接绘制顶点即可, 具体的绘制方式就与纹理坐标和纹理数据没有关系了。
glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);

glBindTexture(GL_TEXTURE_2D, 0); // 使用完之后解绑GL_TEXTURE_2D
[_eaglContext presentRenderbuffer:GL_RENDERBUFFER];
 
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14

这样, 使用OpenGLES来渲染一张图片的过程就结束了.

实际上, 准备好了纹理数据, 并且将纹理坐标传递给了Shader之后, 就不再需要对其进行操作了. 
因此, 至于要不要使用VBO来优化顶点绘制的效率, 就是另外一回事了.



使用索引和VBO来绘制

那么, 既然如此, 再来回顾一下索引数组和VBO的使用吧.

const GLfloat vertices[] = {
    -1, -1, 0,   //左下
    1,  -1, 0,   //右下
    -1, 1,  0,   //左上
    1,  1,  0 }; //右上

GLuint vertexBuffer;
glGenBuffers(1, &vertexBuffer);
glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);

glVertexAttribPointer(_positionSlot, 3, GL_FLOAT, GL_FALSE, 0, 0);
glEnableVertexAttribArray(_positionSlot);


const GLubyte indices[] = {
    0,1,2,
    1,2,3
};
GLuint indexBuffer;
glGenBuffers(1, &indexBuffer);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices), indices, GL_STATIC_DRAW);

glDrawElements(GL_TRIANGLE_STRIP, sizeof(indices)/sizeof(indices[0]), GL_UNSIGNED_BYTE, 0);

说明:安卓下,生成buffer方法如下:

 
 
package com.android.gallery3d.glrenderer;
 
import android.opengl.GLES20;
 
import javax.microedition.khronos.opengles.GL11;
import javax.microedition.khronos.opengles.GL11ExtensionPack;
 
public class GLES20IdImpl implements GLId {
 
     private final int [] mTempIntArray = new int [ 1 ];
 
     @Override
     public int generateTexture() {
 
         GLES20.glGenTextures( 1 , mTempIntArray, 0 );
         GLES20Canvas.checkError();
         return mTempIntArray[ 0 ];
     
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值