《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

《纹理贴图》

标签(空格分隔): OpenGL编程指南第七版


由于时间关系,这本书后面章节不再更新。

9.1 概述和示例

9.1.1 纹理贴图的步骤

《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.2 指定纹理

void glTextImage2D(GLenum target, GLint level, GLint internalFormat, GLsizei width, GLsizei height, GLint border, GLenum format, GLenum type, const GLvoid* texels);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

纹理图像的宽度和高度上的纹理单元的数量必须是2的整数次方倍。如果源图像不满足这个要求,可以用OpenGL工具库函数gluScaleImage()更改纹理图像大小。
int gluScaleImage(GLenum format, GLint widthin, GLint heightin, GLenum typein, const void* datain, GLint widthout, GLint heightout, GLenum typeout, void* dataout);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

void glCopyTexImage2D(GLenum target, GLint level, GLint internalFormat, GLint x, GLint y, GLsizei width, GLsizei height, GLint border);从帧缓冲区中读取一块矩形像素,并且把它作为新纹理的纹理单元。
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.2.1 纹理代理

OpenGL提供一种特殊的纹理目标,称为纹理代理,可用于判断当前的OpenGL实现在某种特定的纹理大小下是否支持某种特定的纹理格式。
可以用glGetIntegerv(GL_MAX_TEXTURE_SIZE, ……)查询纹理图像的最大宽度和最大高度。
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

创建纹理代理:《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
void glGetTexLevelParameter{if}v(GLenum target, GLint level, GLenum, pname, TYPE* params);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
如:
glTexImage2D(GL_PROXY_TEXTURE_2D, 0, GL_RGBA8, 64, 64, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
glGetTexLevelParameteriv(GL_PROXY_TEXTURE_2D, 0, GL_TEXTURE_WIDTH, & width);

9.2.2 替换纹理图像的全部或一部分

void glTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, const GLvoid* texels);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

void glCopyTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height);从缓冲区读取一块像素句型,并替换现有纹理数组的一部分。
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.2.3 一维纹理

void glTexImage1D(GLenum target, GLint level, GLint internalFormat, GLsizei width, GLint border, GLenum format, GLenum type, const GLvoid* texels);高默认为1
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

void glTexSubImage1D(GLenum target, GLint level, GLint xoffset, GLsizei width, GLenum format, GLenum type, const GLvoid* texels);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

void glCopyTexImage1D(GLenum target, GLint level, GLint internalFormat, GLint x, GLint y, GLsizei width, GLint border);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

void glCopyTexSubImage1D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.2.4 三维纹理

void glTexImage3D(GLenum target, GLint level, GLint internalFormat, GLsizei width, GLsizei height, GLsizei depth, GLint border, GLenum format, GLenum type, const GLvoid* texels)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

void glTexSubImage3D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLint zoffset GLsizei width, GLsizei height, GLsizei depth, GLenum format, GLenum type, const GLvoid* texels);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

void glCopyTexSubImage3D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLint zoffset, GLint x, GLint y, GLsizei width, GLsizei height);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.2.5 纹理数组

纹理数组允许把一个集合组织起来,所有的纹理都具有相同的大小,都位于更高维度的一个纹理之中(例如,二维纹理的数组是三维纹理的一部分)。
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.2.6 压缩纹理图像

在加载时压缩纹理图像
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

加载经过压缩的纹理图像
glCompressedTexImage1D(Glenum target, GLint level, GLenum internalformat, GLsizei width, GLint border, GLsizei imageSize, const GLvoid* texels);
glCompressedTexImage2D(Glenum target, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLint border, GLsizei imageSize, const GLvoid* texels);
glCompressedTexImage3D(Glenum target, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLsizei depth, GLint border, GLsizei imageSize, const GLvoid* texels);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

经过压缩的纹理替换已经加载的纹理的全部或一部分
glCompressedTexSubImage1D(Glenum target, GLint level, GLint xoffset, GLsizei width, GLsizei format, GLsizei imageSize, const GLvoid* texels);
glCompressedTexSubImage2D(Glenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsize height, GLsizei imageSize, const GLvoid* texels);
glCompressedTexSubImage3D(Glenum target, GLint level, GLint xoffset, GLint yoffset, GLint zoffset, GLsizei width, GLsize height, GLsizei depth, GLsizei imageSize, const GLvoid* texels);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.2.8 mipmap:多重细节层

《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

五个大小不同,颜色不同的纹理组成mipmap效果
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

在实际应用程序中构建Mipmap
int glGenerateMipmap(GLenum target);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

计算Mipmap层
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

Mipmap层的细节控制
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.3 过滤

屏幕上一个像素可以对应一个很广的范围,可能是一个纹理单元的一小部分(放大),也可能是多个纹理单元(缩小)。
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.4 纹理对象

《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.4.1 命名纹理对象

void glGenTextures(GLsizei n, GLuint* textureNames);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.4.2 创建和使用纹理对象

void glBindTexture(GLenum target, GLuint textureName);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.4.3 清楚纹理对象

void glDeleteTexture(GLsizei n, const GLuint* textureNames);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.4.4 常驻纹理工作集

如果想要知道多个纹理的纹理常驻状态,可以使用glAreTextureResident()函数。
GLboolean glAreTextureResident(GLsizei n, const GLuint* textureNames, GLboolean* residences);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

纹理常驻策略
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
void glPrioritizeTextures(GLsizei n, const GLuint* textureNames, const GLclampf* priorities);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.5 纹理函数

把纹理图像的颜色与物体表面的原先颜色进行组合。
void glTexEnv{if}(GLenum target, GLenum pname, TYPE param);
void glTexEnv{if}v(GLenum target, GLenum pname, TYPE* param);
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)
《OpelGL编程指南第七版》第九章:纹理贴图(笔记)

9.6 分配纹理坐标

顶点之间的纹理坐标也会进行插值均和 纹理坐标(s,t,r,q)对应顶点坐标(x,y,z,w)

9.7 纹理坐标自动生成

9.8 多重纹理