Advertisement
Guest User

MethoDrawer

a guest
Jul 16th, 2015
215
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C# 4.76 KB | None | 0 0
  1. //#define DBG
  2.  
  3. using System;
  4. using System.Reflection;
  5. using System.Collections;
  6. using UnityEngine;
  7. using Vexe.Editor.GUIs;
  8. using Vexe.Editor.Types;
  9. using Vexe.Runtime.Extensions;
  10. using Vexe.Runtime.Helpers;
  11. using Vexe.Runtime.Types;
  12. using UnityObject = UnityEngine.Object;
  13.  
  14. namespace Vexe.Editor.Drawers
  15. {
  16.     public class MethodDrawer
  17.     {
  18.         private EditorMember[] argMembers;
  19.         private MethodCaller<object, object> invoke;
  20.         private object[] argValues;
  21.         private int[] argKeys;
  22.         private string niceName;
  23.         private bool initialized;
  24.  
  25.         private string comment;
  26.  
  27.         private object rawTarget;
  28.         private UnityObject unityTarget;
  29.         private int id;
  30.         private BaseGUI gui;
  31.         private bool isCoroutine;
  32.  
  33.         private BetterPrefs prefs { get { return BetterPrefs.GetEditorInstance(); } }
  34.  
  35.         private bool foldout
  36.         {
  37.             get { return prefs.Bools.ValueOrDefault(id); }
  38.             set { prefs.Bools[id] = value; }
  39.         }
  40.  
  41.         public void Initialize(MethodInfo method, object rawTarget, UnityObject unityTarget, int id, BaseGUI gui)
  42.         {
  43.             this.gui = gui;
  44.             this.rawTarget = rawTarget;
  45.             this.unityTarget = unityTarget;
  46.             this.id = id;
  47.  
  48.             if (initialized) return;
  49.             initialized = true;
  50.  
  51.             isCoroutine = method.ReturnType == typeof(IEnumerator);
  52.  
  53.             var commentAttr = method.GetCustomAttribute<CommentAttribute>();
  54.             if (commentAttr != null)
  55.                 comment = commentAttr.comment;
  56.  
  57.             niceName = method.GetNiceName();
  58.  
  59.             if (niceName.IsPrefix("dbg") || niceName.IsPrefix("Dbg"))
  60.                 niceName = niceName.Remove(0, 3);
  61.  
  62.             invoke       = method.DelegateForCall();
  63.             var argInfos = method.GetParameters();
  64.             int len      = argInfos.Length;
  65.             argValues    = new object[len];
  66.             argKeys      = new int[len];
  67.             argMembers   = new EditorMember[len];
  68.  
  69.             for (int iLoop = 0; iLoop < len; iLoop++)
  70.             {
  71.                 int i = iLoop;
  72.                 var argInfo = argInfos[i];
  73.  
  74.                 argKeys[i] = RuntimeHelper.CombineHashCodes(id, argInfo.ParameterType.Name + argInfo.Name);
  75.  
  76.                 argValues[i] = TryLoad(argInfos[i].ParameterType, argKeys[i]);
  77.  
  78.                 argMembers[i] = EditorMember.WrapGetSet(
  79.                         @get         : () =>  argValues[i],
  80.                         @set         : x => argValues[i] = x,
  81.                         @rawTarget   : rawTarget,
  82.                         @unityTarget : unityTarget,
  83.                         @attributes  : argInfo.GetCustomAttributes(true) as Attribute[],
  84.                         @name        : argInfo.Name,
  85.                         @id          : argKeys[i],
  86.                         @dataType    : argInfo.ParameterType
  87.                     );
  88.             }
  89.  
  90. #if DBG
  91.             Log("Method drawer init");
  92. #endif
  93.         }
  94.  
  95.         public bool OnGUI()
  96.         {
  97.             if (comment != null)
  98.                 gui.HelpBox(comment);
  99.  
  100.             bool changed = false;
  101.             if (Header() && argMembers.Length > 0)
  102.             {
  103.                 using (gui.Indent())
  104.                 {
  105.                     for (int i = 0; i < argMembers.Length; i++)
  106.                     {
  107.                         bool argChange = gui.Member(argMembers[i], false);
  108.                         changed |= argChange;
  109.                         if (argChange)
  110.                             TrySave(argValues[i], argKeys[i]);
  111.                     }
  112.                 }
  113.             }
  114.             return changed;
  115.         }
  116.  
  117.         private bool Header()
  118.         {
  119.             using (gui.Horizontal())
  120.             {
  121.                 if (gui.Button(niceName, GUIStyles.Mini))
  122.                 {
  123.                     var mb = unityTarget as MonoBehaviour;
  124.                     if (isCoroutine && mb != null)
  125.                         mb.StartCoroutine(invoke(rawTarget, argValues) as IEnumerator);
  126.                     else
  127.                         invoke(rawTarget, argValues);
  128.                 }
  129.  
  130.                 gui.Space(12f);
  131.                 if (argMembers.Length > 0)
  132.                 {
  133.                     foldout = gui.Foldout(foldout);
  134.                     gui.Space(-11.5f);
  135.                 }
  136.             }
  137.             return foldout;
  138.         }
  139.  
  140.         void TrySave(object obj, int key)
  141.         {
  142.             if (obj == null) return;
  143.  
  144.             var type = obj.GetType();
  145.             if (type.IsEnum || type == typeof(int))
  146.                  prefs.Ints[key] = (int)obj;
  147.             else if (type == typeof(string))
  148.                  prefs.Strings[key] = (string)obj;
  149.             else if (type == typeof(float))
  150.                  prefs.Floats[key] = (float)obj;
  151.             else if (type == typeof(bool))
  152.                  prefs.Bools[key] = (bool)obj;
  153.         }
  154.  
  155.         object TryLoad(Type type, int key)
  156.         {
  157.             if (type.IsEnum)
  158.             {
  159.                 int value = prefs.Ints.ValueOrDefault(key);
  160.                 object result = Enum.ToObject(type, value);
  161.                 return result;
  162.             }
  163.             if (type == typeof(int))
  164.                 return prefs.Ints.ValueOrDefault(key);
  165.             if (type == typeof(string))
  166.                 return prefs.Strings.ValueOrDefault(key);
  167.             if (type == typeof(float))
  168.                 return prefs.Floats.ValueOrDefault(key);
  169.             if (type == typeof(bool))
  170.                 return prefs.Bools.ValueOrDefault(key);
  171.             return type.GetDefaultValue();
  172.         }
  173.     }
  174. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement