【转】OpenGL随笔(1)—— mipmap 详解

注:本文使用的所有 OpenGL 函数来自 OpenGL 4.5,优先使用 DSA。

  使用 mipmap 时,OpenGL 根据被映射对象的大小(单位是像素),自动决定使用纹理图的哪个分辨率级别。mipmap 表示着纹理的层次细节(LOD),随着对象图像变小,使用纹理图的大小将减少。mipmap 需要一些额外的计算和纹理存储空间(大概三分之一),但这些消耗是值得的,如果不使用 mipmap ,那么映射到更小图像上的纹理将随着物体移动而闪烁。 
  OpenGL 的 mipmap 省去了纹素大小和多边形大小的缩放因子 λ 的详细讨论,不更改则使用默认值。下文将使用默认的 mipmap 参数,最后会讨论控制 λ 的细节。 
  参数 GL_TEXTURE_MIN_FILTER 控制在 mipmap 级数大于 0 时如何重建纹素。这个参数共有 6 个设置。前两个与用于放大的相同,GL_NEAREST 和 GL_LINEAR。选择这两个参数会禁用 mipmap,OpenGL 将使用纹理的基数级(级数0)。其他四个模式启用 mipmap,并控制着 mipmap 的使用。这四个值分别是 GL_NEAREST_MIPMAP_NEAREST、GL_LINEAR_MIPMAP_NEAREST、GL_NEAREST_MIPMAP_LINEAR、GL_LINEAR_MIPMAP_LINEAR。名字结构的第一部分控制纹素的构造,表示当前采用纹理的构造方式;第二部分控制 mipmap 级之间采样模式,NEAREST 表示只使用最近的 mipmap 级,LINEAR 则表示最近的两个 mipmap 线性插值。 
  为了使用 mipmap,必须提供纹理在最大尺寸和 1x1 图之间的所有大小是 2 的幂的纹理级别。如果不想使用 mipmap 到 1x1 纹理的所有变化,可以将 GL_TEXTURE_MAX_LEVEL 的值设置为提供的最大级数,并且 OpenGL 不会考虑更进一步的级别。如果纹理最高级别的分辨率不是正方形,那么一个维度将比另外一个首先到达大小为 1 的纹素。在这种情况下,将继续对这个维度创建新的层级,直到两个维度到达 1x1 的形式为止。例如,如果最高分辨率是 64x16,则必须提供大小 32x8,16x4,8x2,4x1,2x1 和 1x1。mipmap 小图纹素的获取对应于大图 4 个纹素的加权平均。 
  需要特别注意的一点是 glTextureStorage* 生成的纹理空间是不可变的,也就是说不可以使用 glGenerateTextureMipmap 来自动生成函数,而只能用 glTextrueSubImage2D 来手动载入各级纹理;试图让 OpenGL 自动生成 mipmap,请使用 glTextureImage*。 
  OpenGL 提供一个函数,其在应用程序的控制下为纹理自动生成所有的 mipmap—— glGenerateTextureMipmap。在 OpenGL 实现中,它提供了通过采样高分辨率图像来生成更低分辨率图像的一个机制。这通常使用着色器和纹理滤波硬件来实现。这个技术通常被设计用于性能多于质量,并且在不同的实现之间有变化。如果想要高质量的结果,最好自己生成和提供 mipmap 图像。如果需要快速生成 mipmap 链并且对获得的任何结果都满意,可以使用 glGenerateTextureMipmap 函数。 
  计算特定像素的纹理级别时,其结果取决于纹理图像和纹理映射的多边形大小比例因子。我们称这个比例因子为 ρ,再定义第二个值 λ,且 λ=log2ρ+lodbias(因为纹理图像可以是多维的,所以声明 ρ 是所有维的最大比例因子是很重要)。 
  lodbias 是采样器的细节层次偏移,在 glSamplerParameteri 中设置参数为 GL_TEXTURE_LOD_BIAS 来修改它,从而修改 λ。默认 lodbias=0.0,如果 λ≤0.0,意味着纹素小于像素,所以使用放滤波器。如果 λ>0.0,则使用缩小滤波器。如果缩小滤波器使用 mipmap,那么 λ 是 mipmap 级别。 
  例如,如果纹理图像是 64x64 像素,多边形大小是 32x32 像素,那么 ρ=2.0(单个维度的比值),则 λ=1.0。如果纹理图像是 64x32 纹素,并且多边形尺寸是 8x16 像素,那么 ρ=8.0(x 比例是 8.0,y 比例是 2.0,则使用最大值),因此 λ=3.0。计算 λ 和 ρ 的方程如下:

λbase(x,y)=log2[ρ(x,y)]
λ′(x,y)=λbase+clamp(biastexobj+biasshader

  Mipmap 级别的计算可以进一步通过一些采样器参数来控制。GL_TEXTURE_LOD_BIAS 可以用来偏移 λ。计算 λ 后,可以截取边界到用户设置的范围。这通过参数 GL_TEXTURE_MIN_LOD 和 GL_TEXTURE_MAX_LOD 给出,可以通过函数 glSamplerParameterf 或 glTextureParameterf 来设置。GL_TEXTURE_MIN_LOD 和 GL_TEXTURE_MAX_LOD 默认值分别为 -1000.0 和 1000.0。GL_TEXTURE_MIN_LOD 和 GL_TEXTURE_MAX_LOD 在下式中分别用 lodmin 和 lodmax 来表示:

λ=⎧⎩⎨⎪⎪⎪⎪lodmax,λ′,lodmin,undefined,λ′>lodmaxlodmin≤λ′≤lodmaxλ′<lodminlodmin>lodmax

  除了计算 λ 时控制 lodmin、lodmax 和 λbase 的参数,通过 GL_TEXTURE_BASE_LEVEL 和 GL_TEXTURE_MAX_LEVEL 参数来提供 mipmap 选择 level 的进一步控制,这些参数使用 glSamplerParameteri 来设置。GL_TEXTURE_BASE_LEVEL 设置被采样的最低 mipmap 级别(最高分辨率), GL_TEXTURE_MAX_LEVEL 设置被采样的最高 mipmap 级别(最低分辨率),用来限制采样级别范围。 
  GL_TEXTURE_BASE_LEVEL 的一个潜在的用处是纹理流。使用纹理流时,完整纹理对象的存储使用函数(例如 glTextureStorage2D)分配但没有加载初始数据。随着应用程序的运行,新对象进入视野,加载从最低到最高分辨率的纹理数据。即使还没有加载完整的纹理,但为了保证有意义的东西显示给用户,可以设置 GL_TEXTURE_BASE_LEVEL 的值为已经加载的最高分辨率 mipmap 级别。使用这个方法,随着加载越来越多的纹理数据,屏幕上的图像将获得越来越高的逼真度。

参考:The OpenGL® Programming Guide 9th Edition

版权声明:转载请附带本文地址,谢谢~
原文地址:http://blog.csdn.net/qq_33274326/article/details/54866088

posted on 2018-02-15 23:03 时空观察者9号 阅读(...) 评论(...) 编辑 收藏

【转】OpenGL随笔(1)—— mipmap 详解相关推荐

  1. openGL API glGetShaderInfoLog函数详解

    glGetShaderInfoLog详解 官方文档 翻译 例子 代码分析 glGetShaderInfoLog输出错误 工程下载 官方文档 官网文档 Name glGetShaderInfoLog - ...

  2. openGL GLSL texture()函数详解

    前言 一般,在三维项目添加纹理的时候,经常会看到有和纹理操作的函数,先看一段片元着色器程序:在片元着色器中 #version 450 coreout vec4 FragColor;in vec2 Te ...

  3. Mipmap详解(有无Mipmap区别、原理、优点、缺点、优化)

    一.先了解纹理过滤         想要了解为什么要使用Mipmap,首先要知道纹理过滤是什么.         当你在玩吃鸡的时候可能会发现一个现象,一个人在距离你5米的地方,可以观察到敌人的一举一 ...

  4. OpenGL中phong光照模型详解

    版权 cesuolidec4 https://blog.csdn.net/xiewenzhao123/article/details/54600191 引言 现实世界的光照是极其复杂的,而且会受到诸多 ...

  5. OpenGL点精灵PointSprite详解: 纹理映射,旋转,缩放,移动

    第一,什么是点精灵 openGL的图形由顶点构成,以后利用顶点进行纹理的映射.点精灵就是,一个顶点被当作一个精灵来处理.特别之处就是,一个顶点也可进行纹理贴出.例如,原来是个顶点构成的一个矩形,现在一 ...

  6. OpenGL点精灵PointSprite详解

    第一,什么是点精灵 openGL的图形由顶点构成,以后利用顶点进行纹理的映射.点精灵就是,一个顶点被当作一个精灵来处理.特别之处就是,一个顶点也可进行纹理贴出.例如,原来是个顶点构成的一个矩形,现在一 ...

  7. OpenGL之gluLookAt 函数详解

    本文代码是基于上一篇文章"基于Viusal C++ 2015 MFC单文档程序中搭建OpenGL框架"的基础上运行 void gluLookAt(GLdouble eyex,GLd ...

  8. openGL API glProgramUniform详解

    openGL API glProgramUniform详解 前言 一.官方文档 二.翻译 例子 运行结果 代码下载 前言 openGL API 之glProgramUniform详解 一.官方文档 g ...

  9. osgEarth的Rex引擎原理分析(三十五)osgEarth地球椭球体ellipsoid 大地基准面datum 地图投影Projection详解

    目标:(二十九)中的问题83 地球椭球体的中心为地心,形状为椭球体 大地基准面是适应某一区域的椭球体,球体中心不一定在地心 地图投影是球面和平面映射关系的方法 Horizontal Datum A d ...

最新文章

  1. ABAP TBL隐藏列
  2. 提高网速软件_【干货】C盘空间不够用,这款软件或许会帮到你!一键清除C盘多余文件...
  3. Jquery获取服务器端控件ID的方法
  4. Error format not a string literal and no format arguments解决方案
  5. 云化要求下,数据库架构如何演进?
  6. 程序员能自己独立进行程序开发,为何要去公司上班呢?真相出来了!
  7. emui内核支持kvm吗_KVM虚拟化详解
  8. java学习中,instanceof 关键字 和 final 关键字、值的传递(java 学习中的小记录)...
  9. 网络从业人员职业规划路线图
  10. PHP设计模式——模板模式
  11. 二、VS插件之VassistX
  12. 38译码器和416译码器
  13. 有Pytz时区列表吗?
  14. 联想启天m430安装黑苹果 10500 big sur 11.6
  15. Typecho独立下载插件安装与使用
  16. 手把手教如何用Linux下IIO设备(附代码)
  17. 爬虫 | Python爬取20000+猫眼影评实战
  18. 关于字符集的测试报告(转)
  19. 一步一步做高性能服务器(C++) -- Day 0
  20. 判断一年放了多少天假

热门文章

  1. Python中使用httpx模块详解
  2. 项目成本管理:制订项目成本管理计划
  3. Jenkins修改插件下载地址为国内下载地址与安装中文插件
  4. Android中怎样在工具类中获取Context对象
  5. Node响应中文时解决乱码问题
  6. Junit单元测试时提示:Method should have no parameters
  7. 数据库相关(JDBC,存储过程,以及大文本数据处理,mvc设计模式)
  8. 一文解读:如何从 0 到 1 打造小程序爆款裂变
  9. 2018 中国准独角兽 TOP 50 夏榜发布!146 家投资机构、227 家企业参与
  10. 编译x86架构的openwrt系统,让笔记本从u盘启动openwrt