继续用“ShaderLab学习小结(十八)cubemap”中所做的shader
想要让它能对周围的环境进行反射
思路就是要让它的cubemap里的内容是周围环境的映射
shader不变,就要想办法进行映射,这就要用到c#代码了
核心的方法是
public bool Camera.RenderToCubemap(RenderTexture cubemap)
顾名思义,这个是Camera的一个方法,渲染至cubemap
返回ture则渲染成功
看unity document中的说明
即从这个camera渲染出一张静态的cubemap
虽说camera能看到的也只是他的视方向上的物体,但这个方法显然是这个camera所在位置的上下左右前后
既然我们最后是要让这个渲染出来的cubemap赋在我们指定的这个球体上,那么这个camera的位置要和球体一样
即camera的位置在球心
而且,camera还不能看到这个球体,不然直接就被球挡住了吧
不过经过实验发现,camera并没有被球挡住,我想可能是背面剔除的原因,从球的内部向外看是看不见球的
我们先搭建一个简单的场景
如图,一个plane作地面,周围有一个拉长了的cube,一个capsule和一个cylinder
中间进行2倍缩放的球体就是我们要操作的对象了,它上面已经赋上了这个cubemap的shader,只是没给贴图
在他的位置(中心)建了一个camera
给camera上绑了一个c#脚本
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class SKRenderToCube : MonoBehaviour {
public GameObject sph; //1.
private Camera cam;
void Start () {
cam = GetComponent();
if (sph != null)
{
Material mat = sph.GetComponent().material;
if (mat != null)
{
RenderTexture cubemap = new RenderTexture(128, 128, 16); //2.
cubemap.dimension = UnityEngine.Rendering.TextureDimension.Cube; //3.
cam.RenderToCubemap(cubemap); //4
mat.SetTexture("_Cube", cubemap); //5.
}
}
}
}
按注释位置
这个是用于在unity中把球体拖过来,以便下面的代码能赋上值
RenderTexture cubemap = new RenderTexture(128, 128, 16); //2.
创建一个RenderTexture,这也是我们最后要赋到球体上的
128,128是宽高,16是depth颜色缓冲区深度吧,16位
cubemap.dimension = UnityEngine.Rendering.TextureDimension.Cube; //3.
这行应该就是确定此RenderTexture的类型是cubemap
cam.RenderToCubemap(cubemap); //4
渲染
mat.SetTexture("_Cube", cubemap); //5.
把渲染后的RenderTexture赋给球体
最终效果:
可见,球体表面反射了周围的环境,包括近处的物体和远处的天空
这里的代码是建立在场景不发生任何变化的情况之下的
如果有物体移动,或者缩放,或者出现、消失
或者光线变化,cubemap只是一开始生成了一次,是不会随着发生改变的
这样映射的结果就会出现错误
能想到的最直接的办法就是写在Update里,就不赘述了
另外有需要云服务器可以了解下创新互联cdcxhl.cn,海内外云服务器15元起步,三天无理由+7*72小时售后在线,公司持有idc许可证,提供“云服务器、裸金属服务器、高防服务器、香港服务器、美国服务器、虚拟主机、免备案服务器”等云主机租用服务以及企业上云的综合解决方案,具有“安全稳定、简单易用、服务可用性高、性价比高”等特点与优势,专为企业上云打造定制,能够满足用户丰富、多元化的应用场景需求。