我知道您只想平铺纹理的一个子集,对吗?然后事情变得复杂了。
假设我们想要在 u1 和 u2 值之间平铺 u 坐标,u1 < u2。
然后我们需要一个函数 f(u),所以
f(0.0) = u1
f(0.5) = (u1+u2)/2
f(0.9999) = u2
f(1.0) = u1
f(1.5) = (u1+u2)/2
f(1.9999) = u2
f(2.0) = u1
and so on...
一个合适的函数是f(u) = frac(u) * (u2-u1) + u1
v坐标也是一样,f(v) = frac(v) * (v2-v1) + v1
请注意,它是平铺而不镜像。如果需要镜像,那么函数应该是三角波函数,即t(x) = arcsin(sin(pi*(x-0.5)))/pi+0.5
和f(u) = t(u) * (u2-u1) + u1
。不过,使用三角函数可能会很昂贵。
我不知道固定管道是否可行,但您可以在像素着色器(HLSL 代码)中轻松完成:
// float2 tex_coord -> (u,v) from vertex shader, in [0,n] range,
// n - number of repetitions
// float2 tex1, tex2 -> constants, subrange of [0,1] coords that will be tiled
// no mirroring
float4 color = tex2D(sampler, frac(tex_coord) * (tex2-tex1) + tex1);
或者
// mirroring, t(x) = arcsin(sin(pi*(x-0.5)))/pi+0.5
float4 color = tex2D(sampler, t(tex_coord) * (tex2-tex1) + tex1);
编辑:计算三角波函数的更好方法:t1(x) = abs(2(0.5x-floor(0.5x+0.5)))
或t2(x) = abs(2(frac(0.5x+0.5))-1)
(与 t1 不完全相同,但适用于非负数)。