13 Ağustos 2016 Cumartesi

Script Execution Order

Unity3D bazen yazdığınız Scriptin diğerlerinden daha önce çalışmasını isteyebilirsiniz. Bunu yapmanın iki yolu vardır. Bu iki yolu sırasıyla adım adım yapalım.

A. Unity Editor üzerinden elle ayarlama:

Diyelim ki 5 tane ayrı scriptiniz var bunlar ScriptA, ScriptB, ScriptC, ScriptD, ScriptE.

Bunların şu sırayla çalışmasını istiyorum ScriptA, ScriptC, ScriptD, ScriptB, ScriptE.


  1. İlk önce Unity içinden şu sırayla Script Execution Order özelliklerine ulaşalım.
    Edit > Project Settings > Script Execution Order
    Karşımıza Inspector içinde aşağıdaki resimde olduğu gibi bir alan açılacak.
  2. Burada "+" işaretine tıkladığımızda projemizde yazılmış olan Scriptler listelenir. Açılan Listeden ScriptA yı seçelim. Ardından tekrar "+" ya tıklayıp listeden ScriptC yi seçelim ve istediğimiz sırayı oluşturana kadar bu işlemi tekrarlayalım ve "Apply" butonuna tıklayalım. Eğer sıralamayı değiştirmek isterseniz "=" butonuna tıklayıp ilgili sıraya sürekleyip bırakarak sıralamayı değiştirebilirsiniz. Eğer bu sıralamanın dışında olmasını isdeğiniz bir Script varsa
    "-" ye basarak listeden çıkarabilirsiniz. Yapmış olduğunuz değişiklikleri kaybetmemek için "Apply" butonuna basmayı unutmayın. Yazmış olduğunuz bütün scritleri buraya eklemenize gerek yok. Burada ki sıralamanın amacı özel olarak çalışmasını istediğimiz scritleri ve sırasını belirtmek. Listede Gördüğünüz gibi yanlarında rakamlar bulunmakta bunları isterseniz değiştirebilirsiniz. Listede ilk sırada bulunan Script ilk çalışır son bulunan Script en son çalışır.


B. Kod ile Dinamik Script Execution Order oluşturma:

Yine aynı sıralamayı kod ile yapalım.


  1. Bunun için Hazırlamış olduğumuz ScriptA, B... E Scriptlerine bir göz atalım.

  2. using UnityEngine;
    
    public class ScriptA : MonoBehaviour {
    
    }
    
    using UnityEngine;
    
    public class ScriptB : MonoBehaviour {
    
    }
    
    using UnityEngine;
    
    public class ScriptC : MonoBehaviour {
    
    }
    
    using UnityEngine;
    using System.Collections;
    
    public class ScriptD : MonoBehaviour {
    
    }
    
    using UnityEngine;
    
    public class ScriptE : MonoBehaviour {
    
    }

  3. Yazmış olduğıumuz bu Scriptlere sıralama özelliğini verecek Scriptimizi yazalım.

  4. using System;
    using UnityEngine;
    
    public class ScriptOrder : Attribute
    {
        [HideInInspector]
        public int order;
            
        public ScriptOrder(int order)
        {
            this.order = order;
            Debug.Log("+ ScriptOrder : " + this.order);
        }
    }
    

  5. Yazmış olduğumuz bu Scriptlerin Orderlarını (çalışma sıralarını) belirtelim.

  6. using UnityEngine;
    
    [ScriptOrder(-1000)]
    public class ScriptA : MonoBehaviour {
    
    }
    
    using UnityEngine;
    
    [ScriptOrder(-970)]
    public class ScriptB : MonoBehaviour {
    
    }
    
    using UnityEngine;
    
    [ScriptOrder(-990)]
    public class ScriptC : MonoBehaviour {
    
    }
    
    using UnityEngine;
    using System.Collections;
    
    [ScriptOrder(-980)]
    public class ScriptD : MonoBehaviour {
    
    }
    
    using UnityEngine;
    
    [ScriptOrder(-960)]
    public class ScriptE : MonoBehaviour {
    
    }

  7. Şimdi ise bu sıralamaları Unity Editore aktaracak Editor Scriptimizi yazalım. Bunun için Asset klasörü altında yeni bir klasör oluşturup ismini Editor olarak değiştirelim. Ve yeni bir Script oluşturalım. İsmine de ScriptOrderManager diyelim. ScriptOrderManager Scriptinin içeriği aşağıdaki gibi olacak.

  8. using System;
    using UnityEditor;
    
    [InitializeOnLoad]
    public class ScriptOrderManager
    {
    
        static ScriptOrderManager()
        {
            foreach (MonoScript monoScript in MonoImporter.GetAllRuntimeMonoScripts())
            {
                if (monoScript.GetClass() != null)
                {
                    foreach (var a in Attribute.GetCustomAttributes(monoScript.GetClass(), typeof(ScriptOrder)))
                    {
                        var currentOrder = MonoImporter.GetExecutionOrder(monoScript);
                        var newOrder = ((ScriptOrder)a).order;
                        if (currentOrder != newOrder)
                            MonoImporter.SetExecutionOrder(monoScript, newOrder);
                    }
                }
            }
        }
    }
    
  9. Unity de yine Edit > Project Settings > Script Execution Order şeklinde Inspectordan Execution Order penceresini açıtığınızda otomatik olarak sıralamanın kodda belirttiğimiz gibi değiştiğini göreceksiniz. Bu sıralamayı artık bu pencere üzerinden değiştiremezsiniz. Değiştirmek istediğinizde sırasını kod üzerinden değiştirmeniz gerekecektir. Çünkü Unity her değişiklik yaptığınızda ScriptOrderManager scriptini çalıştırıp sıralamayı kodda belirttiğiniz şekilde yapacaktır. Bu sayede kazara değerleri silmenize ve/veya değiştirmenize karşı korumaya almış olursunuz.

Hiç yorum yok:

Yorum Gönder