从高度图生成法线贴图? [英] Generating a normal map from a height map?
问题描述
我正在使用随机分形为视频游戏程序性地产生污垢斑块。我已经使用中点位移算法生成了高度图,并将其保存到纹理。我有一些想法,如何把它变成法线的纹理,但一些反馈将非常感激。
I'm working on procedurally generating patches of dirt using randomized fractals for a video game. I've already generated a height map using the midpoint displacement algorithm and saved it to a texture. I have some ideas for how to turn that into a texture of normals, but some feedback would be much appreciated.
我的高度纹理目前是一个257 x 257灰度图片(高度值会根据公开程度进行调整):
My height texture is currently a 257 x 257 gray-scale image (height values are scaled for visibility purposes):
我的想法是,图像的每个像素代表一个256 x 256网格的格子坐标(因此,为什么有257 x 257高)。这意味着坐标(i,j)处的法线由在(i,j),(i,j + 1),(i + 1,j)和(i + 1,j + 1) )(分别称为A,B,C和D)。
My thinking is that each pixel of the image represents a lattice coordinate in a 256 x 256 grid (hence, why there are 257 x 257 heights). That would mean that the normal at coordinate (i, j) is determined by the heights at (i, j), (i, j + 1), (i + 1, j), and (i + 1, j + 1) (call those A, B, C, and D, respectively).
因此,给定A,B,C和D的3D坐标,到:
So given the 3D coordinates of A, B, C, and D, would it make sense to:
- 将四个分成两个三角形:ABC和BCD
- 计算那些两个面通过交叉乘积
- 分成两个三角形:ACD和ABD
- 计算这两个面的法线
- 平均四个法线
- split the four into two triangles: ABC and BCD
- calculate the normals of those two faces via cross product
- split into two triangles: ACD and ABD
- calculate the normals of those two faces
- average the four normals
...或者有更简单的方法吗?
...or is there a much easier method that I'm missing?
推荐答案
示例来自我的水面渲染着色器的GLSL代码:
Example GLSL code from my water surface rendering shader:
#version 130
uniform sampler2D unit_wave
noperspective in vec2 tex_coord;
const vec2 size = vec2(2.0,0.0);
const ivec3 off = ivec3(-1,0,1);
vec4 wave = texture(unit_wave, tex_coord);
float s11 = wave.x;
float s01 = textureOffset(unit_wave, tex_coord, off.xy).x;
float s21 = textureOffset(unit_wave, tex_coord, off.zy).x;
float s10 = textureOffset(unit_wave, tex_coord, off.yx).x;
float s12 = textureOffset(unit_wave, tex_coord, off.yz).x;
vec3 va = normalize(vec3(size.xy,s21-s01));
vec3 vb = normalize(vec3(size.yx,s12-s10));
vec4 bump = vec4( cross(va,vb), s11 );
结果是一个凹凸向量:xyz = normal,a = height
The result is a bump vector: xyz=normal, a=height
这篇关于从高度图生成法线贴图?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!