Jump to content
Unity Insider Forum

Objekt einblenden und ausblenden


Kojote

Recommended Posts

Grüße!

Hier mal ein kleines Snippet, wie man Objekte im Spiel ein und ausblenden kann. Dies funktioniert über den Standard-Shader. :)

Im Standard-Shader finden wir folgenden Code, den wir brauchen um im Material die Rendering Methode auf "Fade" zu stellen, damit eine Änderung des Alpha-Wertes möglich ist.

public static void SetupMaterialWithBlendMode(Material material, BlendMode blendMode)
{
	switch (blendMode)
	{
		case BlendMode.Opaque:
			material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
			material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.Zero);
			material.SetInt("_ZWrite", 1);
			material.DisableKeyword("_ALPHATEST_ON");
			material.DisableKeyword("_ALPHABLEND_ON");
			material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
			material.renderQueue = -1;
			break;
		case BlendMode.Cutout:
			material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
			material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.Zero);
			material.SetInt("_ZWrite", 1);
			material.EnableKeyword("_ALPHATEST_ON");
			material.DisableKeyword("_ALPHABLEND_ON");
			material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
			material.renderQueue = 2450;
			break;
		case BlendMode.Fade:
			material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.SrcAlpha);
			material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.OneMinusSrcAlpha);
			material.SetInt("_ZWrite", 0);
			material.DisableKeyword("_ALPHATEST_ON");
			material.EnableKeyword("_ALPHABLEND_ON");
			material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
			material.renderQueue = 3000;
			break;
		case BlendMode.Transparent:
			material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
			material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.OneMinusSrcAlpha);
			material.SetInt("_ZWrite", 0);
			material.DisableKeyword("_ALPHATEST_ON");
			material.DisableKeyword("_ALPHABLEND_ON");
			material.EnableKeyword("_ALPHAPREMULTIPLY_ON");
			material.renderQueue = 3000;
			break;
	}
}

Kommen wir nuzn zum Code!

Initialisierung:

SkinnedMeshRenderer smr = this.gameObject.GetComponentInChildren<SkinnedMeshRenderer>();
Material material = smr.material;
Color32 col = material.GetColor("_Color");

Methoden zum Wechseln des Rendering Mode:

    private void WechselMaterialStandard() {
        material.SetFloat("_Mode", 0);
        material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
        material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.Zero);
        material.SetInt("_ZWrite", 1);
        material.DisableKeyword("_ALPHATEST_ON");
        material.DisableKeyword("_ALPHABLEND_ON");
        material.EnableKeyword("_ALPHAPREMULTIPLY_ON");
        material.renderQueue = -1;
    }

    private void WechselMaterialFade() {
        material.SetFloat("_Mode", 2);
        material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
        material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.OneMinusSrcAlpha);
        material.SetInt("_ZWrite", 0);
        material.DisableKeyword("_ALPHATEST_ON");
        material.DisableKeyword("_ALPHABLEND_ON");
        material.EnableKeyword("_ALPHAPREMULTIPLY_ON");
        material.renderQueue = 3000;
    }

Ein- und ausblenden kann man nun zum Beispiel in eine Corouine regeln:

    private IEnumerator Coroutine() {
        WechselMaterialFade();
        while (col.a >= 10) {
            col.a -= 10;
            material.SetColor("_Color", col);
            yield return new WaitForFixedUpdate();
        }
        col.a = 0;
    }

Möchte man wieder alles sofort zurück setzen:

WechselMaterialStandard();
col.a = 255;
material.SetColor("_Color", col);

Kojote

Link zu diesem Kommentar
Auf anderen Seiten teilen

  • 2 years later...

Hallo @Kojote, ich versuche gerade, deinen Code zu übernehmen. Da ich aber mit der Programmierung von Shadern keine Ahnung habe, weis ich gar nicht, was ich hier mache. Und da es nicht läuft, habe ich noch weniger Ahnung, woran das liegen kann. Ich hatte alles ab "Initialisierung" in ein Script gesetzt (deinen ersten Abschnitt hatte ich als Erläuterung verstanden, welche nicht für die Funktion dieses Script notwendig ist) und dieses dem GameObjekt zugewiesen.

Mir wird aber für die Zeile

material = smr.material;

aus der Start Methode folgende Fehlermeldung zurückgegeben:
"NullReferenceException: Object reference not set to an instance of an object
FadeInOut.Start () (at Assets/scripts/FadeInOut.cs:19)"

Mein GameObjekt hat schon den Standard Shader mit dem Rendering Mode "Fade", ich muss also den Mode nicht auf "Fade" schalten.

Ich habe in meiner Szene verschiedene Objekte mit demselben Shader, es sollen aber die Objekte unabhängig voneinander Ein- und Ausblenden. Das schreibe ich, da ich probehalber im Inspector eines GameObjekt den Alphawert über den Schieberegler geändert habe, und alle anderen GamObjekte sich mitgeändert haben - was so nicht von mir gewünscht war.

Vielleicht kannst du (oder auch jemand anderes) mir helfen. Danke.

Link zu diesem Kommentar
Auf anderen Seiten teilen

Sorry das ich nun selber Antworte, aber nach etlichen weiteren Tutorials und dem Durchforsten der Unity - Documentation habe ich nun für mich eine Lösung gefunden (wie oben geschrieben hat mein GO schon einen Fade-Shader):
 

[SerializeField]
    float fadeTime;

    [SerializeField]
    Renderer fadeObjekt;    // hier das zu ändernde GO reinziehen
    public Color fadeAlpha;

    private void Start()
    {
        fadeAlpha = fadeObjekt.material.GetColor("_Color");
        StartCoroutine("FadeOut");
    }

    private void Update()
    {
        fadeObjekt.material.SetColor("_Color",fadeAlpha);
    }

    private IEnumerator FadeOut()
    {
        float duration = fadeTime;
        float fadeStart = 1f;
        float fadeEnd = 0f;

        for (var time = 0.0f; time<duration; time += Time.deltaTime)
        {
            var progress = time / duration;
            fadeAlpha.a = Mathf.Lerp(fadeStart, fadeEnd, progress);
            yield return null;
        }
    }

Danke aber trotzdem, da ich aufgrund der oben von Kojote aufgeführten Scriptzeilen nun doch ein kleines bischen verstehe, was ich tue.

Link zu diesem Kommentar
Auf anderen Seiten teilen

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Gast
Auf dieses Thema antworten...

×   Du hast formatierten Text eingefügt.   Formatierung jetzt entfernen

  Only 75 emoji are allowed.

×   Dein Link wurde automatisch eingebettet.   Einbetten rückgängig machen und als Link darstellen

×   Dein vorheriger Inhalt wurde wiederhergestellt.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Lädt...
×
×
  • Neu erstellen...