Introduction to Vertex Textures(顶点纹理介绍)---转

Introduction to Vertex Textures
 
Ever since the appearance of programmable GPUs, there has been a significant difference between the capabilities of vertex and pixel shaders. Shader Model 3.0 took the first steps in providing common functionality between the two, and DirectX 10 took the final step and unified the Instruction Set between all types of shaders (Pixel, Vertex and the new Geometry Shaders). Since this is a XNA blog, and I didn't have the chance to experiment with DirectX10, I will focus on one feature of Shader Model 3.0 that builds towards this unification, which is Vertex Texture Fetch ( VTF ). This article will only be introductory, with little to no actual code. But a full tutorial will follow, covering several effects that can be achieved using VTF.

As you probably know by now, traditionally, Vertex Shaders deal with transforming the vertices, and manipulating or setting properties like position, color, normal, texture coordinates. After this, vertices define triangles, which are then transformed into pixels. At this step, Pixel Shaders come into play, and can be used for texturing, bump mapping, normal mapping, and lots of other effects we all love.

Vertex Texture Fetch allows us to read data from textures inside a Vertex Shader, just like Pixel Shaders do. Actually, not EXACTLY like Pixel Shaders do, there are some limitations, but I'll come back to that in a moment.

To use VTF, you will need either an Xbox 360 (which has an unified shader architecture), or a NVIDIA graphics card from the GeForce 6 series, or greater. For those owning ATI GPUs there is another technique called Render To Vertex Buffer (R2VB), which can be used to achieve similar results.

The assembler function used to read textures in a Vertex Shader is texldl. However, since I like HLSL more, and never wrote a shader in asm, I'll talk about the HLSL version. So, in HLSL, the most important instruction used for VTF is tex2Dlod.

The usage is tex2Dlod( s,t ), where s is a 2D texture sampler, and t is a 4 component vector. The instruction reads a texture, using an user-defined mipmap level. This mipmap level is specified through the 4th component of the texture coordinate vector ( t.w ).

Depending on the application you might get to use the mipmap level, or not. In most cases, I've used the default level 0, so a usual call took the form:
     tex2Dlod( textureSampler, float4( uv, 0, 0) );

Different mipmap levels can be used when you intend to simulate water or terrain using VTF, but the levels have to be computed manually.

Vertex Textures behave like Pixel Textures except for the following restrictions:
¤ Bilinear and Trilinear filtering are not supported directly in hardware. However, these can be implemented manually in the Vertex Shader
¤ Anisotropic Filtering is not supported in hardware
¤ Level of detail (mipmap level) is not available, and has to be computed manually

Implementing bilinear filtering in vertex textures is not too complicated, and most times, the performance hit will not be too high, since neighboring pixels are usually present in the cache. Other types of filtering (trilinear,bicubic) can also be implemented, but they need more texture fetches, and use several mipmaps levels, so the performance hit is much higher. I will cover bilinear filtering in one part of the tutorial that will come soon.

Keep in mind that a vertex texture fetch is not as fast as a pixel texture fetch, so using vertex textures carelessly can yield some serious performance hits. Some tips on improving performance when using VTF are:
¤ Use dynamic branching in shaders to avoid vertex texture fetching when it may not be necessary.
¤ When using VTF for displacement mapping, use grids of different granularities for things close to the viewer or far from the viewer (see geometry clipmaps)
¤ do no use a Vertex Texture as a way to pass constants to the vertex shader, since VTF is much slower than reading 

constants That concludes the introduction to vertex textures. The tutorial will continue, and show some examples of what can be done using vertex textures.

You can find a small sample that morphs terrain between two heightmaps, using vertex textures, here. It is for Windows, so you'll need a NVIDIA GeForce 6 series video card, or higher. Here is the Xbox 360 version, but I didn't get to test this before uploading it, since my Xbox is not available, at the moment.

Note: the downloads are .ccgame packages, so you'll need to have XNA GSE 1.0 Refresh installed.

I hope this was interesting enough. If you have any suggestions, or if there are any mistakes in my facts, please point them to me.



我个人的翻译,有错误的地方请指出:
顶点纹理介绍

    在以前的可编程GPU渲染管线内顶点着色器和像素着色器在拥有的能力方面还是有比较大的差别的。从Shader Model 3.0开始对两者提供更多的通用功能,并且Directx10最终现实了在不同着色器的之间的指令集统一化(包括像素、顶点和新添加的几何着色器)。因为这是这个关于XNA的博客,所以我不能够用Directx10来描述,我将用Shader Model 3.0来描述顶点纹理的查询(Vertex Texture Fetch, VTF)。这篇文章只是作为一个介绍,同时会提供一些伪代码,但作为一篇全面的介绍性文章,我将文章里谈论一些关于用VTF实现的效果。
    或许你已经了解了顶点着色器通常是用来处理顶点的转化处理工作的,包括计算和设置比如顶点的空间坐标、颜色、法向量和纹理坐标。经过顶点着色器处理后,GPU用顶点来建立三角形信息,然后进行片段处理。在这个阶段,像素着色器进行的计算诸如纹理填充,凹凸贴图,法向量贴图和很多你想要的其它效果。
    我们能够像像素着色器一样,使用顶点纹理查询功能在顶点着色器中读取纹理中的数据。但事实上他们之间还是有点差别,我将在稍后讲述。
    使用VTF,硬件上你需要Xbox 360(统一着色器框架)或者NVIDIA显卡GeForce6系列以上的显卡。对于ATI显卡来说,其使用另一种称为渲染到顶点缓冲的技术(R2VB)来达到和顶点纹理查询相似的效果。
    在顶点照色器里读取顶点纹理的汇编指令是 texldl.然而我更喜欢用HLSL而不是用汇编来写照色代码,所以我讲的都是关于HLSL版本的。在HLSL中,VTF的查询的最重要的指令 tex2Dlod
   对于tex2Dlod(s,t)来说,其中参数s是一个2维纹理样本,参数t是一个4维向量。这个指令读取一个用户指定的mipmap层的纹理。读取的mipmap的层数是由4维向量纹理坐标中的t.w来决定的。
   根据程序的实际情况,你可能会使用mipmap或者不使用它。在大都数情况下,我会使用mipmap的第0层纹理,用函数来表示如下:
tex2Dlod( textureSampler, float4( uv, 0, 0 ) );
当你模拟水面或者地形时,你可以根据需要来读取mipmap不同纹理层次,但是这个具体是哪一个层需要自己来计算。
   顶点纹理和片段纹理在行为上相似,但有下面几个限制:
        ¤ 顶点着色器在硬件上不支持双线性和三线性过滤器,但这个可以自己手动计算
¤ 顶点着色器在硬件上不支持各向异性过滤器
¤ 顶点着色器不能够自动得到mipmap层,需要自己手动计算
   在顶点着色器里实现双线性过滤器的实现并不复杂,但是在大都是情况下,纹理查询的命中率并不是很高,因为相邻的纹理经常保留在高速缓冲器内。其它类型的过滤器(三线性,双三次)同样也能够实现,但是需要更多的纹理查询次数,并且需要用mipmap的不同层,所以纹理的命中率会相对来说高很多。关于双线性纹理滤波器作为这个指南文章的一部分马上将在后面介绍。
   你需要记住的是顶点纹理查询没有在片段照色器中纹理查询来的快,所以顶点纹理使用不当会得到相当差的命中率。下面一些是提高VTF性能的技巧:
¤ 当顶点纹理查询不是必须的时候,在着色器中使用动态分支来避免使用顶点纹理查询
¤ 当使用VTF进行映射位移的时候,根据物体里视点的远近来使用不同粒度的栅格(看 geometry clipmaps的介绍)
¤ 不要在顶点着色器里使用顶点纹理来传递常量值,因为VTF读取的速度比常量读取慢很多
  先对顶点纹理介绍到这儿,相关的介绍在还会继续,并且会展示一些使用顶点纹理查询的例子。
  你能够找到一些小的例子比如使用顶点纹理查询两张高度图来建立地形。这是一个 windows版本的,所以你需要一块至少GeForce6以上的显卡。这是 XBox360版本的,因为我暂时还没有Xbox,所以这个版本的程序我还没测试过。

Note:下载的文件是.ccgame文件,所以你需要安装XNA GSE Refresh 1.0。
我希望你们会对这个感兴趣。如果有任何建议,或者我有任何错误,望请指出。


我的疑惑:
the performance hit will not be too high, since neighboring pixels are usually present in the cache.
按照我的翻译和理解,为什么保留在高速缓冲器里的纹理单位范围命中率低呢?
  

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值