1_Unity學習筆記,就讓我們先來說說MonoBehaviour吧!

是的,我這邊並不會告訴各位怎麼安裝Unity請自己上網爬文,這裡從C#開始出發告訴各位如何使用Unity。 請把在下我當作業餘的來看看吧,這裡只會記下我的經驗。 Awake() Start() Update() FixedUpdate() LateUpdate() 通常會看到以上這種東東,來來來來,這是甚麼呢? 關於流程圖的部分就請各位自由爬文,在下可以算是個懶人哈哈! 總之在這邊稍微介紹一下,一般來說看起來會像是:  Awake()     ↓    Start()     ↓ FixedUpdate()←←     ↓      ↑  Update()   ↑     ↓      ↑  LateUpdate()→→↑ 的流程,每個場景開始,會先執行每個物件身上的Awake(),接著執行每個物件身上的Start() 都執行完後將會迴圈所有物件依照如上圖的順序。 FixedUpdate最重要的是他每次間隔都是絕對的,在Edit > Project Settings > Time 可以找到 Update則是針對每一禎都會執行,因為禎數會隨著遊戲效能而有所不同,因此Update的間隔都不一定,可以利用Time.deltaTime取得每一禎的時候再秒數的比例。 LateUpdate就跟Update一樣,不過會觸發在Update後面。 另外介紹一些我個人比較常用到的: OnApplicationFocus 當遊戲被縮小或失去焦點的時候會觸發 OnApplicationPause 當遊戲被暫停的時候,電話來了之類的 OnApplicationQuit 當玩家離開遊戲前會先觸發此才關閉程式 OnCollisionEnter 當碰撞到的時候 OnCollisionEnter2D 同上,2D時使用,忽略Z軸 OnCollisionExit 當碰撞體離開時 OnCollisionExit2D 同上,2D時使用,忽略Z軸 OnCollisionStay 當碰...

EditorGUILayout學習筆記


看來是時候是要來記錄EditorGUILayout要怎麼寫了。

『 EditorWindow 』

一般來說會看起來像是這樣:


public class CreateSkill : EditorWindow
{
    [MenuItem("創造/新技能")]
    public static void CreateSkills()
    {
        EditorWindow window = EditorWindow.CreateInstance<CreateSkill>();
        window.Show();
    }
    private bool isOK = false;
    private GUIStyle gs = new GUIStyle();
    public string Index;
 
    void OnGUI()
    {
        EditorGUIUtility.labelWidth = 100;
        gs.alignment = TextAnchor.UpperCenter;
        if (!isOK)
        {
   //do something
            isOK = true;
        }

        EditorGUILayout.LabelField("<----技能資料---->", gs);
        Index = EditorGUILayout.TextField("技能ID", Index);
 
        if(GUILayout.Button("確定"))
        {
            this.Close();
        }
    }
}

以下容我來介紹一下:

【作為EditorWindow的入口】

[MenuItem("上面工具列/子選單")]
裡面是實體化EditorWindow:
EditorWindow.CreateInstance<CreateSkill>();
及顯示視窗
window.Show(); //window是EditorWindow的物件

接著就會使用OnGUI內的東西,簡單來說每一禎都會渲染視窗,所以使用區域變數是無法跨禎使用,請多加注意。
另外,是由上至下渲染的,所以無法回頭改變已經渲染完的東西。

【然後第一行】
EditorGUIUtility.labelWidth = 100; //指定EditorGUILayout的Label的寬度都預設100
這是我最常用到的哈哈,其他很少碰到,以後碰到再介紹~

GUIStyle客製化樣式:
GUIStyle gs = new GUIStyle(); //必須先New出一個GUIStyle
gs.alignment = TextAnchor.UpperCenter; //設定要改變的參數
EditorGUILayout.LabelField("<----技能資料---->", gs); //指定給要使用此GUIStyle的物件

isOK是因為我不想每一禎都渲染作為初始化用的部分,在此省略。哈哈哈哈。

【內容】
在製作工具或等等的東西時,有時候會需要自定義輸入的畫面,所以有了EditorWindow,裡面可以客製化各式各樣的輸入及顯示部分。
GUILayout及EditorGUILayout是可以混用的,非常方便。

以下介紹一些我常用的一些輸入框:
variable = EditorGUILayout.TextField(variable); //variable為string
一般的字串輸入框

variable = EditorGUILayout.TextArea(variable); //variable為string
一般的字串輸入區域

variable = EditorGUILayout.PasswordField(variable); //variable為string
一般的密碼的輸入區域,你懂得

variable = EditorGUILayout.IntField(variable); //variable為int
一般的數字輸入框,如要限制最大值及最小值,幾乎只能額外寫限制數值下方有小提如何限制

variable = EditorGUILayout.IntSlider(variable); //variable為int
數字輸入框,旁邊送你一個可以拖曳調整數值的組件;
也可以額外設定最小值及最大值EditorGUILayout.IntSlider(variable,Min,Max); //variable為int

variable = EditorGUILayout.IntPopup(variable,new string[] { "一", "二", "三" },new int[] { 1, 2, 3 }); //variable為int
數字輸入框,為下拉式的數字選擇框,new string[] { }放的是顯示的選項,new int[] { }是對應string[]{ }的數值


variable = EditorGUILayout.Popup(variable, new string[] { "零", "一", "二" }); //variable為int
跟上面很像,不過這個是純選項,回傳的是選擇到的索引值



variable = (variableEnum)EditorGUILayout.EnumPopup(variable); //variable為variableEnum
列舉選擇框,我認為非常好用,就是直接給列舉選項就是了,記得要轉回列舉型態

variable = EditorGUILayout.LongField(variable); //variable為long
一般的Long輸入框

variable = EditorGUILayout.FloatField(variable); //variable為float
一般的float的輸入框

variable = EditorGUILayout.DoubleField(variable); //variable為Double
一般的double的輸入框

variable = EditorGUILayout.Vector2Field(variable); //variable為Vector2
一般的Vector2輸入框,有x,y向量
         
variable = EditorGUILayout.Vector3Field(variable); //variable為Vector3
一般的Vector3輸入框,有x,y,z向量
         
variable = EditorGUILayout.RectField(variable); //variable為Rect
一般的Rect輸入框,有x,y,w,h向量
         
variable = EditorGUILayout.ColorField(variable); //variable為Color
回傳Color的輸入框,會出現一個顏色選擇框,有r,g,b,a值,順帶一提,其數值皆為0~1
         
variable = EditorGUILayout.Toggle(variable); //variable為bool
就是平常用的CheckBox那樣的東西,嘛
         
variable = EditorGUILayout.ToggleLeft(variable); //variable為bool
就是上面的那個東西,不過如果有Label的話就會把勾選的選項放在左邊
         
EditorGUILayout.LabelField("這裡寫想顯示的東西");
就是有必需顯示的訊息就用此組件

EditorGUILayout.PrefixLabel("這裡寫想顯示的東西");
如果有需要顯示在輸入框之前的文字就寫在此
         
EditorGUILayout.Space();
單純就是排版用的空白,
有時候我也會用EditorGUILayout.LabelField(""); 來空格




【特別介紹(物件輸入框)】
         
variable = EditorGUILayout.ObjectField(variable,typeof(System.Type),false) as System.Type; //variable為某種物件,該物件是個Type都可以
但是...這很難用...
先介紹一下,variable就是物件,typeof(System.Type)就是指定是甚麼Type,false是指是否能選取場景中的物件
         
原則上各位朋友們會遇到的,應該最常使用莫過於材質或精靈圖吧!
variable = EditorGUILayout.ObjectField(variable, typeof(Sprite), false) as Sprite; //variable為Sprite
variable = (Material)EditorGUILayout.ObjectField(variable, typeof(Material), false); //variable為Material
也可以寫成這樣轉換,但轉換失敗會出錯就是了。不過一般來說指定type就已經會過濾非該type的物件不能選入,但是還是有特殊狀況。
Sprite有正方形(可預覽),以及跟物件一樣的輸入面板,可以透過指定GUILayout的高度Height低於高於60來切換。
         
如果你想用自定義的物件,可以這樣用:
         
variable = (MyClass)EditorGUILayout.ObjectField(variable, typeof(MyClass), false); //variable為MyClass
         
原則上這樣就可以實現,但是還要記得在該MyClass裡面指定:
public class SceneA : ScriptableObject //繼承父物件,設定為客製的Asset
         
如果想要直接選擇某些Script,就要再多做一些處理:
MonoScript variable; //先宣告一個MonoScript
variable = EditorGUILayout.ObjectField("額外動畫", variable, typeof(MonoScript), false) as MonoScript; //variable為MonoScript
         
然後再選擇完後,如果是要加到遊戲物件的話就用:
(MyClass)MyGameObject.AddComponent(variable.GetClass()); //加入Script物件給遊戲物件


【較沒機會碰到】
variable = EditorGUILayout.BoundsField(variable); //variable為Bounds
將會回傳Bounds,是指三維的方框邊界,一個類似Box的物件的邊界值
variable = EditorGUILayout.CurveField(variable); //variable為AnimationCurve
將會回傳一個AnimationCurve,動畫曲線,目前我還沒實際使用的機會,需要用到的各位朋友們,就請自己去研究啦!

另外,以上的所有EditorGUILayout都可以加上其"Label"說明文字,及GUILayoutOption[],如下:
variable = EditorGUILayout.IntField("說明文字", variable,GUILayout.Width(100));

【排版】
//最後須要介紹的就是排版的部分了,請容我緩緩道來:

將元素都橫向排列
EditorGUILayout.BeginHorizontal();
    需要排列的元素們
EditorGUILayout.EndHorizontal();
         
將元素都縱向排列
EditorGUILayout.BeginVertical();
    需要排列的元素們
EditorGUILayout.EndVertical();
         
將區域設定成可滑動區域
scrollPos = EditorGUILayout.BeginScrollView(scrollPos); //scrollPos是捲動的位置
    需要排列的元素們
EditorGUILayout.EndHorizontal();
         
將區域設定成可展開/回收區域
foldbool = EditorGUILayout.Foldout(foldbool); //foldbool是展開/回收狀態
if(foldbool)
{
    需要排列的元素們
}
         
聽說有個甚麼EditorGUILayout.BeginFadeGroup();但我不會用所以跳過
另外還有一個EditorGUILayout.BeginToggleGroup;CheckBox群組也可以設為區域

而以上,沒錯,都有另一個使用方式,如下:
using (var v = new EditorGUILayout.VerticalScope()) //將元素都縱向排列
{
    需要排列的元素們
}
         
using (var h = new EditorGUILayout.HorizontalScope()) //將元素都橫向排列
{
    需要排列的元素們
}
         
using (var scrollView = new EditorGUILayout.ScrollViewScope()) //將區域設定成可滑動區域
{
    scrollPos = scrollView.scrollPosition;
    需要排列的元素們
}

備註: 在區域中也可以使用GUILayout,例:
using (var v = new EditorGUILayout.VerticalScope(GUILayout.Height(60))) //將元素都縱向排列
{
    需要排列的元素們
}

【按鈕】
if(GUILayout.Button("確定"))
{
    //要做的事情
}
EditorGUILayout沒有按鈕,所以只能使用GUILayout的按鈕,因為通用性蠻高的所以EditorWindow就沒額外的按鈕了吧。
if裡面指的是按下按鈕後要做的事情,如果要加上額外的樣式也是可以加在後面,如if(GUILayout.Button("確定"),GUILayout.Width(60))

【關閉】
this.Close();
關閉目前的EditorWindow


『 同場加映 』

【如何限制數值】
目前我比較常用以下兩個簡單的方法
1.
int temp = EditorGUILayout.IntField(variable); //variable為int
if (temp > Max) temp = Max;
if (temp > Min) temp = Min;
variable = temp;

2.
variable = Mathf.Clamp(EditorGUILayout.IntField(variable),Min,Max);

【如何存出檔案】
如我要存成Prefab(遊戲物件)可以使用PrefabUtility:
PrefabUtility.CreatePrefab("Assets/prefab/" + prefabName + ".prefab", newGameObject); //儲存預置物到外部

如果要存成一般的Asset物件,可以用AssetDatabase:
AssetDatabase.CreateAsset(MyAsset, string.Format("Assets/{0}.asset", MyAssetName));

【讀取檔案】
不論prefab還是Asset我幾乎都使用:
(GameObject)AssetDatabase.LoadAssetAtPath(string.Format("Assets/{0}.prefab", newGameObject), typeof(GameObject));
或把GameObject換成要讀取的東西。

【Unity.Object】
基本上Sprite,GameObject,Material都屬於Unity.Object,而我特別拿來介紹是有個特別的Asset要備註。
SceneAsset,
沒錯,這是場景物件,副檔名是".unity",而這個物件只能使用在UnityEditor,
各位朋友們肯定想問,那如果在遊戲中要使用場景資源怎麼辦?
只能 -- 使用string記住Scene的名稱,這是我這邊目前的辦法。



以上是這篇筆記的全部內容,如果有任何一段有幫助到你就太好了。

留言

這個網誌中的熱門文章

Unity儲存以及讀取

1_Unity學習筆記,就讓我們先來說說MonoBehaviour吧!