直角坐标系转球坐标系 Equirectangular 理解 代码 Unity
起
IBL相关,得到dir后需要从HDR图采样,但HDR图是Equirectangular Map,所以需要将dir转球坐标系(得到经纬)再转UV。
从定义到实现都有很多约定俗成的东西,记录一下。
承
由于代码实现需要固定phi的范围。发现需要按符号分类处理,分类其实挺麻烦的。于是到网上找“标准”做法。
这里不能用数学上的标准arctan函数,得改造一下用atan2,它长这样:
幸好,hlsl实现了atan2。
所以代码是:
-
//x: phi [0,2PI)
-
//y: theta [0,PI]
-
//z: r
-
//https://www.gamedev.net/forums/topic/602211-fast-way-to-get-spherical-coordinates/
-
float3 CartesianToSpherical(in float3 xyz)
-
{
-
float r = length(xyz);
-
xyz *= 1.f / r;
-
float theta = acos(xyz.z);
-
-
float phi = atan2(xyz.y, xyz.x); //atan2 [-PI,PI]
-
phi = (phi < 0) ? 2 * PI : 0;
-
-
return float3(phi, theta, r);
-
}
转
由于Unity的坐标系和数学常用的坐标系不同,又因为我们要以垂直方向为极轴,获得Equirectangular Map的UV。所以转球系之前,得先把坐标从Unity系转一下到标准系:
-
float3 XYZ_StandardFromUnity(float3 p)
-
{
-
p.z = -p.z;
-
p.xyz = p.xzy;
-
return p;
-
}
-
-
float2 EquirectangularToUV(float3 dir)
-
{
-
float2 uv = 0;
-
dir = normalize(dir);
-
dir = XYZ_StandardFromUnity(dir);
-
//!!!
-
//由于转球系是需要有x,y,z规定的,
-
//所以要先转成标准方向
-
// get theta phi from x, y comp (phi [0,2PI) theta [0,PI] )
-
float3 sphereCoord = CartesianToSpherical(dir);
-
...
-
}
合
最后归一化经纬,就得到UV了。
-
float2 EquirectangularToUV(float3 dir)
-
{
-
...
-
uv.x = sphereCoord.x;
-
uv.x /= 2 * PI;
-
-
uv.y = sphereCoord.y;
-
uv.y /= PI;
-
-
uv = saturate(uv);
-
uv.y = 1 - uv.y;
-
return uv;
-
}
最后看下结果,nice。
这篇好文章是转载于:学新通技术网
- 版权申明: 本站部分内容来自互联网,仅供学习及演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,请提供相关证据及您的身份证明,我们将在收到邮件后48小时内删除。
- 本站站名: 学新通技术网
- 本文地址: /boutique/detail/tanhfieija
系列文章
更多
同类精品
更多
-
photoshop保存的图片太大微信发不了怎么办
PHP中文网 06-15 -
Android 11 保存文件到外部存储,并分享文件
Luke 10-12 -
《学习通》视频自动暂停处理方法
HelloWorld317 07-05 -
word里面弄一个表格后上面的标题会跑到下面怎么办
PHP中文网 06-20 -
photoshop扩展功能面板显示灰色怎么办
PHP中文网 06-14 -
微信公众号没有声音提示怎么办
PHP中文网 03-31 -
excel下划线不显示怎么办
PHP中文网 06-23 -
excel打印预览压线压字怎么办
PHP中文网 06-22 -
怎样阻止微信小程序自动打开
PHP中文网 06-13 -
TikTok加速器哪个好免费的TK加速器推荐
TK小达人 10-01