positions | 用于评估探针的世界空间位置数组。 |
lightProbes | 用于写入结果光探针的数组。 |
occlusionProbes | 用于写入结果遮挡探针的数组。 |
在给定的世界空间位置计算光探针和遮挡探针。
如果场景中没有烘焙探针,则环境探针将写入到 lightProbes
数组,Vector4
(1,1,1,1) 将写入到 occlusionProbes
数组。
如果 positions
为 null
,则会抛出 ArgumentNullException。
您可以通过将 null
传递给函数来省略 lightProbes
或 occlusionProbes
数组,但不能同时省略两者。如果两个数组都被省略,则会抛出 ArgumentException。为了获得更好的性能,应该一起计算 lightProbes
和 occlusionProbes
。
对于将数组作为参数的重载,lightProbes
和 occlusionProbes
必须至少与 positions
数组具有相同数量的元素。
对于将列表作为参数的重载,如果给定列表中没有足够的空间,则输出列表的大小将调整为适合 positions
数组的大小。
返回的探针可通过 MaterialPropertyBlock.CopySHCoefficientArraysFrom 和 MaterialPropertyBlock.CopyProbeOcclusionArrayFrom 将其复制到 MaterialPropertyBlock 对象,从而进一步用于实例化渲染。
using UnityEngine;
// This script uses OnPreCull for the rendering. It is mandatory to put the script to a Camera object. // Make sure light probes are placed and baked in the Scene. // Use Shadowmask mode and mixed lights to see occlusion probes approximating shadowness. [RequireComponent(typeof(Camera))] public class Simple : MonoBehaviour { public Material material;
private Matrix4x4[] transforms; private MaterialPropertyBlock properties; private Mesh cubeMesh;
void Start() { const int kCount = 100;
// Generate 100 random positions var positions = new Vector3[kCount]; for (int i = 0; i < kCount; ++i) positions[i] = new Vector3(Random.Range(-20.0f, 20.0f), Random.Range(-20.0f, 20.0f), Random.Range(-20.0f, 20.0f));
// Calculate probes at these positions var lightprobes = new UnityEngine.Rendering.SphericalHarmonicsL2[kCount]; var occlusionprobes = new Vector4[kCount]; LightProbes.CalculateInterpolatedLightAndOcclusionProbes(positions, lightprobes, occlusionprobes);
// Put them into the MPB properties = new MaterialPropertyBlock(); properties.CopySHCoefficientArraysFrom(lightprobes); properties.CopyProbeOcclusionArrayFrom(occlusionprobes);
// Compute the transforms list transforms = new Matrix4x4[kCount]; for (int i = 0; i < kCount; ++i) transforms[i] = Matrix4x4.Translate(positions[i]);
// Create the cube mesh cubeMesh = GameObject.CreatePrimitive(PrimitiveType.Cube).GetComponent<MeshFilter>().sharedMesh;
// Make sure the material property is assigned if (material == null || !material.enableInstancing) Debug.LogError("material must be assigned with one with instancing enabled."); }
// OnPreCull happens before every culling, which is the perfect timing to inject DrawMesh* function calls. void OnPreCull() { if (material != null && material.enableInstancing) { RenderParams rp = new RenderParams(material) { matProps = properties, lightProbeUsage = UnityEngine.Rendering.LightProbeUsage.CustomProvided, // enable instancing for probes shadowCastingMode = UnityEngine.Rendering.ShadowCastingMode.On, receiveShadows = true }; Graphics.RenderMeshInstanced(rp, cubeMesh, 0, transforms); } } }
该示例演示了如何利用烘焙的光探针来提升实例化渲染的视觉质量。