1. 程式人生 > >Unity 設定材質屬性事件

Unity 設定材質屬性事件

材質著色器屬性

在過場動畫時,可能需要動態修改材質屬性的事件,Unity 的材質Material通過SetColorSetVector等介面來更改設定其屬性值。在編輯器程式碼中,有個MaterialProperty公開類,作為材質屬性設定和獲取的介面。

它將材質屬性型別分為5種:

public enum PropType
{
    Color,
    Vector,
    Float,
    Range,
    Texture
}

將紋理型別分為3種:

public enum TexDim
{
    Unknown = -1,
    None,
    Tex2D = 2
, Tex3D, Cube, Any = 6 }

可獲取和設定值包括colorValuefloatValuevectorValuetextureValue,那麼設計更改材質屬性事件也可按此來設計。

材質屬性更改事件

對事件的物體,做材質屬性的修改。

using System;
using UnityEngine;

namespace CinemaDirector
{
    [CutsceneItemAttribute("Material", "Set Material Propery", CutsceneItemGenre.ActorItem)]
    public
class SetMaterialProperyEvent : CinemaActorEvent { public enum PropType { Color, Vector, Float, Range, Texture } [Flags] public enum TextureModifyType { Texture = 1, TextureOffset = 2
, TextureScale = 4 } public string shaderName = String.Empty; public PropType propType = PropType.Texture; public string propName = "_MainTex"; public Color colorValue; public Vector4 vectorValue; public float floatValue; public Texture textureValue; public int textureModifyType = (int)TextureModifyType.Texture; public Vector2 textureOffsetValue; public Vector2 textureScaleValue = Vector2.one; public override void Trigger(GameObject Actor) { if (!Application.isPlaying || string.IsNullOrEmpty(propName) || !Actor) { return; } Renderer[] mrs = Actor.GetComponentsInChildren<Renderer>(); foreach (var mr in mrs) { ModifyMaterialProp(mr); } } private void ModifyMaterialProp(Renderer mr) { if (!mr) { return; } Material mat = mr.material; if (!mat || !mat.shader) { return; } if (mat.shader.name != shaderName) { return; } switch (propType) { case PropType.Color: mat.SetColor(propName, colorValue); break; case PropType.Vector: mat.SetVector(propName, vectorValue); break; case PropType.Float: case PropType.Range: mat.SetFloat(propName, floatValue); break; case PropType.Texture: if (((TextureModifyType)textureModifyType & TextureModifyType.Texture) != 0) { mat.SetTexture(propName, textureValue); } if (((TextureModifyType)textureModifyType & TextureModifyType.TextureOffset) != 0) { mat.SetTextureOffset(propName, textureOffsetValue); } if (((TextureModifyType)textureModifyType & TextureModifyType.TextureScale) != 0) { mat.SetTextureScale(propName, textureScaleValue); } break; } } } }

SetMaterialProperyEvent 的檢視器設計

雖然SetMaterialProperyEvent指令碼可以達到執行時修改材質屬性,但是在編輯時,需要手動去檢視此時材質所擁有的屬性,是比較麻煩的。可以做個編輯器類,自動獲取當前所有可更改的材質屬性,讓使用者去選擇。

新建SetMaterialProperyEventInspector指令碼,在OnEnable的時候,通過MaterialEditor.GetMaterialProperties來獲得材質的所有屬性。接著,將所有的屬性描述列出來,讓使用者選擇即可。