├── .gitattributes ├── .gitignore ├── .vsconfig ├── Assets ├── Demo.meta ├── Demo │ ├── Demo_01.meta │ └── Demo_01 │ │ ├── DemoScene.unity │ │ ├── DemoScene.unity.meta │ │ ├── Enemy.cs │ │ ├── Enemy.cs.meta │ │ ├── EnemyFSM.cs │ │ ├── EnemyFSM.cs.meta │ │ ├── EnemyFactory.cs │ │ ├── EnemyFactory.cs.meta │ │ ├── EnemyManager.cs │ │ ├── EnemyManager.cs.meta │ │ ├── EventDefine.cs │ │ ├── EventDefine.cs.meta │ │ ├── Flyer.prefab │ │ ├── Flyer.prefab.meta │ │ ├── Main.cs │ │ ├── Main.cs.meta │ │ ├── Walker.prefab │ │ └── Walker.prefab.meta ├── Test.meta ├── Test │ ├── Test Serialization.meta │ ├── Test Serialization │ │ ├── SerializeUtil.cs │ │ ├── SerializeUtil.cs.meta │ │ ├── classA.cs │ │ ├── classA.cs.meta │ │ ├── classB.cs │ │ └── classB.cs.meta │ ├── TestAssembly.asmdef │ └── TestAssembly.asmdef.meta ├── ZTools.meta └── ZTools │ ├── Core.meta │ ├── Core │ ├── Event │ │ ├── EventDispatcher.cs │ │ └── EventDispatcher.cs.meta │ ├── FSM.meta │ ├── FSM │ │ ├── BaseState.cs │ │ ├── BaseState.cs.meta │ │ ├── FSMManager.cs │ │ ├── FSMManager.cs.meta │ │ ├── IFSM.cs │ │ ├── IFSM.cs.meta │ │ ├── readme.md │ │ └── readme.md.meta │ ├── Math.meta │ ├── Math │ │ ├── MathUtil.cs │ │ └── MathUtil.cs.meta │ ├── Singleton.meta │ └── Singleton │ │ ├── Singleton.cs │ │ ├── Singleton.cs.meta │ │ ├── USingleton.cs │ │ └── USingleton.cs.meta │ ├── Debug.meta │ ├── Debug │ ├── FPS.meta │ ├── FPS │ │ ├── FPS.cs │ │ └── FPS.cs.meta │ ├── Gizmos.meta │ ├── Gizmos │ │ ├── ZGizmos.cs │ │ └── ZGizmos.cs.meta │ ├── Log.meta │ ├── Log │ │ ├── LogUtil.cs │ │ ├── LogUtil.cs.meta │ │ ├── LogWindow.cs │ │ └── LogWindow.cs.meta │ ├── Overdraw.meta │ └── Overdraw │ │ ├── Editor.meta │ │ ├── Editor │ │ ├── OverdrawToolWindow.cs │ │ ├── OverdrawToolWindow.cs.meta │ │ ├── Resources.meta │ │ └── Resources │ │ │ ├── DebugOverdrawInt.shader │ │ │ ├── DebugOverdrawInt.shader.meta │ │ │ ├── OverdrawParallelReduction.compute │ │ │ └── OverdrawParallelReduction.compute.meta │ │ ├── Overdraw.cs │ │ ├── Overdraw.cs.meta │ │ ├── OverdrawMonitor.cs │ │ └── OverdrawMonitor.cs.meta │ ├── Editor.meta │ ├── Editor │ ├── CustomAttibute.meta │ ├── CustomAttibute │ │ ├── Layer.meta │ │ ├── Layer │ │ │ ├── LayerPropertyDrawer.cs │ │ │ ├── LayerPropertyDrawer.cs.meta │ │ │ ├── ShowLayerAttribute.cs │ │ │ ├── ShowLayerAttribute.cs.meta │ │ │ ├── ShowSortingLayerAttribute.cs │ │ │ ├── ShowSortingLayerAttribute.cs.meta │ │ │ ├── SortingLayerPropertyDrawer.cs │ │ │ └── SortingLayerPropertyDrawer.cs.meta │ │ ├── ReadOnly.meta │ │ ├── ReadOnly │ │ │ ├── ReadOnlyAttribute.cs │ │ │ ├── ReadOnlyAttribute.cs.meta │ │ │ ├── ReadOnlyPropertyDrawer.cs │ │ │ └── ReadOnlyPropertyDrawer.cs.meta │ │ ├── readme.md │ │ └── readme.md.meta │ ├── CustomInspector.meta │ └── CustomInspector │ │ ├── MyTestClass.cs │ │ ├── MyTestClass.cs.meta │ │ ├── MyTestClassEditor.cs │ │ └── MyTestClassEditor.cs.meta │ ├── Game.meta │ ├── Game │ ├── ActionSequence.meta │ ├── ActionSequence │ │ ├── ActionSequence.cs │ │ ├── ActionSequence.cs.meta │ │ ├── ActionSequenceManager.cs │ │ └── ActionSequenceManager.cs.meta │ ├── Collision.meta │ ├── Collision │ │ ├── CollisionAbility.cs │ │ ├── CollisionAbility.cs.meta │ │ ├── CollisionConfig.cs │ │ ├── CollisionConfig.cs.meta │ │ ├── CollisionManager.cs │ │ ├── CollisionManager.cs.meta │ │ ├── CollisionMath.cs │ │ ├── CollisionMath.cs.meta │ │ ├── Editor.meta │ │ └── Editor │ │ │ ├── CollisonConfigEditor.cs │ │ │ └── CollisonConfigEditor.cs.meta │ ├── Hierachy.meta │ ├── Hierachy │ │ ├── BaseAbility.cs │ │ ├── BaseAbility.cs.meta │ │ ├── BaseActor.cs │ │ ├── BaseActor.cs.meta │ │ ├── BaseObject.cs │ │ ├── BaseObject.cs.meta │ │ ├── BaseObjectFactory.cs │ │ ├── BaseObjectFactory.cs.meta │ │ ├── BaseObjectManager.cs │ │ ├── BaseObjectManager.cs.meta │ │ ├── GamePlay.cs │ │ ├── GamePlay.cs.meta │ │ ├── Readme.md │ │ └── Readme.md.meta │ ├── Input.meta │ ├── Input │ │ ├── InputManager.cs │ │ └── InputManager.cs.meta │ ├── PersistData.meta │ ├── PersistData │ │ ├── PersistDataHelper.cs │ │ ├── PersistDataHelper.cs.meta │ │ ├── PersistDataManager.cs │ │ └── PersistDataManager.cs.meta │ ├── Pool.meta │ ├── Pool │ │ ├── GameObjectPool.cs │ │ └── GameObjectPool.cs.meta │ ├── ReactSystem.meta │ ├── UI.meta │ └── UI │ │ ├── ButtonGroupClick.cs │ │ └── ButtonGroupClick.cs.meta │ ├── Plugin.meta │ ├── Plugin │ ├── Animation.meta │ ├── Animation │ │ ├── DOTween Pro 0.9.690.unitypackage │ │ └── DOTween Pro 0.9.690.unitypackage.meta │ ├── Optimize Sprite Mesh.meta │ └── Optimize Sprite Mesh │ │ ├── SpriteSharp Mesh Optimizer.unitypackage │ │ └── SpriteSharp Mesh Optimizer.unitypackage.meta │ ├── ZToolsAssembly.asmdef │ └── ZToolsAssembly.asmdef.meta ├── Packages ├── manifest.json └── packages-lock.json ├── ProjectSettings ├── AudioManager.asset ├── ClusterInputManager.asset ├── DynamicsManager.asset ├── EditorBuildSettings.asset ├── EditorSettings.asset ├── GraphicsSettings.asset ├── InputManager.asset ├── NavMeshAreas.asset ├── NetworkManager.asset ├── PackageManagerSettings.asset ├── Physics2DSettings.asset ├── PresetManager.asset ├── ProjectSettings.asset ├── ProjectVersion.txt ├── QualitySettings.asset ├── TagManager.asset ├── TimeManager.asset ├── UnityConnectSettings.asset ├── VFXManager.asset └── VersionControlSettings.asset ├── README.md └── UserSettings └── EditorUserSettings.asset /.gitattributes: -------------------------------------------------------------------------------- 1 | # Auto detect text files and perform LF normalization 2 | * text=auto 3 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | Library/ 2 | Temp/ 3 | *.csproj 4 | *.sln 5 | .vs/ 6 | obj/ 7 | Logs/ 8 | .vscode/settings.json 9 | UpgradeLog.htm -------------------------------------------------------------------------------- /.vsconfig: -------------------------------------------------------------------------------- 1 | { 2 | "version": "1.0", 3 | "components": [ 4 | "Microsoft.VisualStudio.Workload.ManagedGame" 5 | ] 6 | } 7 | -------------------------------------------------------------------------------- /Assets/Demo.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 4cc93ecf89783bf4dbf8e24cf974a427 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/Demo/Demo_01.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 6119f5b3df7e3e4419d29d8174fd34ff 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/DemoScene.unity.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: e0935558b019b204a896b31d9d9e1835 3 | DefaultImporter: 4 | externalObjects: {} 5 | userData: 6 | assetBundleName: 7 | assetBundleVariant: 8 | -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/Enemy.cs: -------------------------------------------------------------------------------- 1 | using System.Collections; 2 | using System.Collections.Generic; 3 | using UnityEngine; 4 | using ZTools.Core; 5 | using ZTools.Game; 6 | using ZTools.Editor.CustomAttribute; 7 | namespace ZTools.Demo 8 | { 9 | public enum EnemyType 10 | { 11 | none, 12 | walker, 13 | flyer, 14 | } 15 | 16 | 17 | public class Enemy : BaseActor 18 | { 19 | [SerializeField] private EnemyType _type = EnemyType.none; 20 | public override int TypeID => (int)_type; 21 | 22 | public float Health { get; private set; } 23 | public FSM FSM { get; private set; } 24 | 25 | public override void Init() 26 | { 27 | base.Init(); 28 | Health = 100f; 29 | Singleton>.Instance.AddListener(EventID.OnDamage, OnDamageHandler); 30 | FSM = FSMManager.Instance.createFSM(this, new IdleState(), new GlobalState()); 31 | FSM.Start(); 32 | } 33 | 34 | private void OnDamageHandler(EventData data) 35 | { 36 | if (data is DamageData msg) 37 | { 38 | 39 | } 40 | } 41 | 42 | public override void UnInit() 43 | { 44 | base.UnInit(); 45 | FSM.Stop(); 46 | } 47 | 48 | 49 | #region Sense Layer, receive game event 50 | 51 | 52 | //this event may from collision module 53 | private void OnHurt() 54 | { 55 | Health -= 10f; 56 | FSM.OnMessage(new LocalMsg(LocalMsg.ID.onHurt)); 57 | } 58 | 59 | //this event may from animation module 60 | private void OnAttackEnd() 61 | { 62 | FSM.OnMessage(new LocalMsg(LocalMsg.ID.onAttackEnd)); 63 | } 64 | 65 | #endregion 66 | 67 | #region Action Layer, called by fsm 68 | 69 | public void DoIdle() 70 | { 71 | //logic do sth 72 | //animator do sth 73 | } 74 | 75 | public void DoAttack() 76 | { 77 | //logic do sth 78 | //animator do sth 79 | } 80 | 81 | public void DoDie() 82 | { 83 | //Destroy(gameObject); 84 | } 85 | 86 | #endregion 87 | 88 | } 89 | } -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/Enemy.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 34d7835d2c4555e428a694438ed9ebb2 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/EnemyFSM.cs: -------------------------------------------------------------------------------- 1 | using ZTools.Core; 2 | 3 | namespace ZTools.Demo 4 | { 5 | //this shortcut is only valid in this file 6 | using BaseState = BaseState; 7 | 8 | //event definition. use struct to avoid GC 9 | public struct LocalMsg 10 | { 11 | public enum ID 12 | { 13 | onHurt, 14 | onAttackEnd, 15 | onTurn, 16 | } 17 | 18 | public ID eventID; 19 | public object eventData; 20 | 21 | public LocalMsg(ID id, object data = null) 22 | { 23 | eventID = id; 24 | eventData = data; 25 | } 26 | } 27 | 28 | /// 29 | /// 30 | /// State definition. Class is used to utilize inheritance. Cache state obj if you care. 31 | /// 32 | /// In state defination, we write structral behavior of owner, not specific hebavior. 33 | /// In other words, we should be as abstract as possible to write fsm code, 34 | /// focusing on state-change logic, leaving how-to-do logic to owner itself. 35 | /// e.g. we don't care how owner performs its attack behavior, just call owner.doAttack(); 36 | /// 37 | /// Usually we have a class called GlobalState which is always alive when FSM running, 38 | /// it's very useful to handle msg that every state needs. 39 | /// 40 | /// 41 | 42 | public class GlobalState : BaseState 43 | { 44 | public override object OnMessage(Enemy owner, LocalMsg msg) 45 | { 46 | if (msg.eventID == LocalMsg.ID.onHurt) 47 | { 48 | if(owner.Health <= 0) 49 | { 50 | owner.FSM.ChangeState(new DeadState()); 51 | } 52 | } 53 | return null; 54 | } 55 | } 56 | 57 | 58 | public class IdleState : BaseState 59 | { 60 | public override void Enter(Enemy owner, object param) 61 | { 62 | base.Enter(owner, param); 63 | owner.DoIdle(); 64 | } 65 | 66 | public override object OnMessage(Enemy owner, LocalMsg msg) 67 | { 68 | if(msg.eventID == LocalMsg.ID.onTurn) 69 | { 70 | owner.FSM.ChangeState(new AttackState("someparameter")); 71 | } 72 | 73 | return null; 74 | } 75 | } 76 | 77 | 78 | public class AttackState : BaseState 79 | { 80 | private string _attackParam; 81 | 82 | //use this way to pass parameter when enter another state 83 | public AttackState(string attackParam = null) 84 | { 85 | _attackParam = attackParam; 86 | } 87 | 88 | public override void Enter(Enemy owner, object param) 89 | { 90 | base.Enter(owner, param); 91 | owner.DoAttack(); 92 | } 93 | 94 | //receive selfEvent 95 | public override object OnMessage(Enemy owner, LocalMsg msg) 96 | { 97 | if(msg.eventID == LocalMsg.ID.onAttackEnd) 98 | { 99 | owner.FSM.ChangeState(new IdleState()); 100 | } 101 | 102 | return null; 103 | } 104 | } 105 | 106 | 107 | public class DeadState : BaseState 108 | { 109 | public override void Enter(Enemy owner, object param) 110 | { 111 | base.Enter(owner, param); 112 | owner.DoDie(); 113 | } 114 | } 115 | 116 | 117 | } -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/EnemyFSM.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 37355aebfe192db41877c8f3f586c26c 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/EnemyFactory.cs: -------------------------------------------------------------------------------- 1 | using System.Collections; 2 | using System.Collections.Generic; 3 | using UnityEngine; 4 | using ZTools.Game; 5 | 6 | namespace ZTools.Demo 7 | { 8 | public class EnemyFactory : BaseObjectFactory 9 | { 10 | protected override void ListToDic() 11 | { 12 | if (_prefabList != null) 13 | { 14 | for (int i = 0; i < _prefabList.Length; i++) 15 | { 16 | _prefabDic.Add(_prefabList[i].TypeID, _prefabList[i]); 17 | } 18 | } 19 | } 20 | } 21 | } -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/EnemyFactory.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 57e8c3ed7a2a90c4f8c47bdb12a5db14 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/EnemyManager.cs: -------------------------------------------------------------------------------- 1 | using System.Collections; 2 | using System.Collections.Generic; 3 | using UnityEngine; 4 | using ZTools.Game; 5 | 6 | namespace ZTools.Demo 7 | { 8 | public class EnemyManager : BaseObjectManager 9 | { 10 | 11 | } 12 | } -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/EnemyManager.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 1f73f423580c15c45a31ec21b260def1 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/EventDefine.cs: -------------------------------------------------------------------------------- 1 | namespace ZTools.Demo 2 | { 3 | public enum EventID 4 | { 5 | OnTurn, 6 | OnDamage, 7 | } 8 | 9 | public abstract class EventData 10 | { 11 | 12 | } 13 | 14 | public class DamageData : EventData 15 | { 16 | public int damage; 17 | 18 | } 19 | } -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/EventDefine.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: b38e033817e4497491567a9c3a935e61 3 | timeCreated: 1631973780 -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/Flyer.prefab: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!1 &3836556517607589283 4 | GameObject: 5 | m_ObjectHideFlags: 0 6 | m_CorrespondingSourceObject: {fileID: 0} 7 | m_PrefabInstance: {fileID: 0} 8 | m_PrefabAsset: {fileID: 0} 9 | serializedVersion: 6 10 | m_Component: 11 | - component: {fileID: 6724201172343197660} 12 | - component: {fileID: 5173783581928109382} 13 | m_Layer: 0 14 | m_Name: Flyer 15 | m_TagString: Untagged 16 | m_Icon: {fileID: 0} 17 | m_NavMeshLayer: 0 18 | m_StaticEditorFlags: 0 19 | m_IsActive: 1 20 | --- !u!4 &6724201172343197660 21 | Transform: 22 | m_ObjectHideFlags: 0 23 | m_CorrespondingSourceObject: {fileID: 0} 24 | m_PrefabInstance: {fileID: 0} 25 | m_PrefabAsset: {fileID: 0} 26 | m_GameObject: {fileID: 3836556517607589283} 27 | m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} 28 | m_LocalPosition: {x: 328.05133, y: 102.34433, z: -3.7780824} 29 | m_LocalScale: {x: 1, y: 1, z: 1} 30 | m_Children: [] 31 | m_Father: {fileID: 0} 32 | m_RootOrder: 0 33 | m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} 34 | --- !u!114 &5173783581928109382 35 | MonoBehaviour: 36 | m_ObjectHideFlags: 0 37 | m_CorrespondingSourceObject: {fileID: 0} 38 | m_PrefabInstance: {fileID: 0} 39 | m_PrefabAsset: {fileID: 0} 40 | m_GameObject: {fileID: 3836556517607589283} 41 | m_Enabled: 1 42 | m_EditorHideFlags: 0 43 | m_Script: {fileID: 11500000, guid: 34d7835d2c4555e428a694438ed9ebb2, type: 3} 44 | m_Name: 45 | m_EditorClassIdentifier: 46 | _type: 1 47 | -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/Flyer.prefab.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: a8ba6a78f5a50884282b5f67c90bf0e0 3 | PrefabImporter: 4 | externalObjects: {} 5 | userData: 6 | assetBundleName: 7 | assetBundleVariant: 8 | -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/Main.cs: -------------------------------------------------------------------------------- 1 | using System.Collections; 2 | using System.Collections.Generic; 3 | using UnityEngine; 4 | using ZTools.Game; 5 | namespace ZTools.Demo 6 | { 7 | 8 | public class Main : MonoBehaviour 9 | { 10 | private EnemyManager enemyManager; 11 | public EnemyFactory factory; 12 | 13 | IEnumerator Start() 14 | { 15 | enemyManager = new EnemyManager(); 16 | enemyManager.Init(factory); 17 | 18 | yield return null; 19 | 20 | enemyManager.Generate(EnemyType.flyer); 21 | 22 | enemyManager.UnInit();//after unInit, nothing will be generate. 23 | 24 | yield return new WaitForSeconds(2f); 25 | 26 | enemyManager.Generate(EnemyType.walker); 27 | } 28 | 29 | } 30 | } -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/Main.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: c8da6ba056a44db4796ff9bc0a4f2fdc 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/Walker.prefab: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!1 &4039355001904696134 4 | GameObject: 5 | m_ObjectHideFlags: 0 6 | m_CorrespondingSourceObject: {fileID: 0} 7 | m_PrefabInstance: {fileID: 0} 8 | m_PrefabAsset: {fileID: 0} 9 | serializedVersion: 6 10 | m_Component: 11 | - component: {fileID: 7973782025597901075} 12 | - component: {fileID: 3293371080505174343} 13 | m_Layer: 0 14 | m_Name: Walker 15 | m_TagString: Untagged 16 | m_Icon: {fileID: 0} 17 | m_NavMeshLayer: 0 18 | m_StaticEditorFlags: 0 19 | m_IsActive: 1 20 | --- !u!4 &7973782025597901075 21 | Transform: 22 | m_ObjectHideFlags: 0 23 | m_CorrespondingSourceObject: {fileID: 0} 24 | m_PrefabInstance: {fileID: 0} 25 | m_PrefabAsset: {fileID: 0} 26 | m_GameObject: {fileID: 4039355001904696134} 27 | m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} 28 | m_LocalPosition: {x: 328.05133, y: 102.34433, z: -3.7780824} 29 | m_LocalScale: {x: 1, y: 1, z: 1} 30 | m_Children: [] 31 | m_Father: {fileID: 0} 32 | m_RootOrder: 0 33 | m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} 34 | --- !u!114 &3293371080505174343 35 | MonoBehaviour: 36 | m_ObjectHideFlags: 0 37 | m_CorrespondingSourceObject: {fileID: 0} 38 | m_PrefabInstance: {fileID: 0} 39 | m_PrefabAsset: {fileID: 0} 40 | m_GameObject: {fileID: 4039355001904696134} 41 | m_Enabled: 1 42 | m_EditorHideFlags: 0 43 | m_Script: {fileID: 11500000, guid: 34d7835d2c4555e428a694438ed9ebb2, type: 3} 44 | m_Name: 45 | m_EditorClassIdentifier: 46 | _type: 0 47 | -------------------------------------------------------------------------------- /Assets/Demo/Demo_01/Walker.prefab.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 00e9a3f654dd5534faf96902c372743b 3 | PrefabImporter: 4 | externalObjects: {} 5 | userData: 6 | assetBundleName: 7 | assetBundleVariant: 8 | -------------------------------------------------------------------------------- /Assets/Test.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: b267d483a0fdd6e44bab18aa6d91189b 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/Test/Test Serialization.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: c97e79fbae9a9ad4bbe669b7904d7606 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/Test/Test Serialization/SerializeUtil.cs: -------------------------------------------------------------------------------- 1 | using System.Collections; 2 | using System.Collections.Generic; 3 | using System.IO; 4 | using System.Runtime.Serialization.Formatters.Binary; 5 | using UnityEngine; 6 | 7 | namespace ZTools.Test 8 | { 9 | public class SerializeUtil : MonoBehaviour 10 | { 11 | public classA obj; 12 | 13 | public string relativePath = "/classAData.bytes"; 14 | 15 | public bool useJson = false; 16 | 17 | public void save() 18 | { 19 | FileStream stream = new FileStream(Application.persistentDataPath + relativePath, FileMode.Create); 20 | 21 | BinaryFormatter formatter = new BinaryFormatter(); 22 | formatter.Serialize(stream, new classA.SerializedClassA(obj)); 23 | 24 | stream.Close(); 25 | 26 | } 27 | 28 | public void load() 29 | { 30 | string path = Application.persistentDataPath + relativePath; 31 | if(File.Exists(path)) 32 | { 33 | BinaryFormatter formatter = new BinaryFormatter(); 34 | FileStream stream = new FileStream(path, FileMode.Open); 35 | 36 | classA.SerializedClassA data = formatter.Deserialize(stream) as classA.SerializedClassA; 37 | 38 | stream.Close(); 39 | 40 | data.deserialize(obj); 41 | } 42 | else 43 | { 44 | Debug.LogError("file not exist on:" + path); 45 | } 46 | } 47 | } 48 | } -------------------------------------------------------------------------------- /Assets/Test/Test Serialization/SerializeUtil.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 9a537addc14dbab47ad21599dd68116e 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/Test/Test Serialization/classA.cs: -------------------------------------------------------------------------------- 1 | using System.Collections; 2 | using System.Collections.Generic; 3 | using UnityEngine; 4 | 5 | namespace ZTools.Test 6 | { 7 | 8 | public class classA : MonoBehaviour 9 | { 10 | public static classA instance; 11 | 12 | public List myList = new List() { 1, 2, 3 }; 13 | //public AType aType = AType.small; 14 | //public Dictionary dic = new Dictionary(); 15 | 16 | public string newData = "ddd"; 17 | 18 | public enum AType 19 | { 20 | small, 21 | big, 22 | } 23 | 24 | [System.Serializable] 25 | public class SerializedClassA 26 | { 27 | public float[] position; 28 | public List list; 29 | //public Dictionary dic; 30 | 31 | //public AType type; 32 | public string newd; 33 | 34 | public SerializedClassA(classA a) 35 | { 36 | position = new float[3]; 37 | position[0] = a.transform.position.x; 38 | position[1] = a.transform.position.y; 39 | position[2] = a.transform.position.z; 40 | 41 | 42 | list = new List(a.myList); 43 | 44 | //dic = a.dic; 45 | 46 | //type = a.aType; 47 | 48 | newd = a.newData; 49 | } 50 | 51 | public void deserialize(classA a) 52 | { 53 | a.transform.position = new Vector3(position[0], position[1],position[2]); 54 | a.myList = list; 55 | //a.aType = type; 56 | //a.dic = dic; 57 | a.newData = newd; 58 | } 59 | } 60 | 61 | private void Awake() 62 | { 63 | instance = this; 64 | } 65 | 66 | public void printDic() 67 | { 68 | //foreach (var kvp in dic) 69 | //{ 70 | // Debug.Log("k=" + kvp.Key.ToString() + ",v=" + kvp.Value.ToString()); 71 | //} 72 | } 73 | } 74 | } -------------------------------------------------------------------------------- /Assets/Test/Test Serialization/classA.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 3db20aec1a1b3eb4db6d1f3c7dc49511 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 100 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/Test/Test Serialization/classB.cs: -------------------------------------------------------------------------------- 1 | using System.Collections; 2 | using System.Collections.Generic; 3 | using UnityEngine; 4 | 5 | namespace ZTools.Test 6 | { 7 | public class classB : MonoBehaviour 8 | { 9 | private void Awake() 10 | { 11 | } 12 | } 13 | } -------------------------------------------------------------------------------- /Assets/Test/Test Serialization/classB.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 93cae529d9b6e81498fc8b6c0c9529f3 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 200 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/Test/TestAssembly.asmdef: -------------------------------------------------------------------------------- 1 | { 2 | "name": "TestAssembly" 3 | } 4 | -------------------------------------------------------------------------------- /Assets/Test/TestAssembly.asmdef.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: a8bdf2a89b03c1846839e2c33b842cae 3 | AssemblyDefinitionImporter: 4 | externalObjects: {} 5 | userData: 6 | assetBundleName: 7 | assetBundleVariant: 8 | -------------------------------------------------------------------------------- /Assets/ZTools.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 0c746deddab447944ba4e1418ad67766 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Core.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 4a702122b85249dd9ba74efd4acb9cce 3 | timeCreated: 1631629757 -------------------------------------------------------------------------------- /Assets/ZTools/Core/Event/EventDispatcher.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | 3 | namespace ZTools.Core 4 | { 5 | public delegate void EventHandler(TData data); 6 | 7 | public interface IEventDispatcher 8 | { 9 | void AddListener(TEventID id, EventHandler handler); 10 | void RemoveListener(TEventID id, EventHandler handler); 11 | void Dispatch(TEventID id, TData data); 12 | } 13 | 14 | /// 15 | /// Dispatch event immediately. Can use it as T in to make it singleton. 16 | /// 17 | /// (1) Event data type is , but it may cause boxing when you pass a value type such as an int. 18 | /// Use to define your unified data type if you need. 19 | /// 20 | /// 21 | /// (2) Internally it use default IEqualityComparer for TEventID. 22 | /// If you use enum as TEventID in Unity5.6 or older, it will cause boxing. 23 | /// If you use custom struct as TEventID, it will cause boxing, too. 24 | /// Use to define your own IEqualityComparer to eliminate boxing. 25 | /// 26 | /// 27 | public class EventDispatcher : IEventDispatcher 28 | { 29 | private EventDispatcher _internalDispatcher; 30 | 31 | public EventDispatcher() 32 | { 33 | _internalDispatcher = new EventDispatcher(); 34 | } 35 | 36 | public void AddListener(TEventID id, EventHandler handler) 37 | { 38 | _internalDispatcher.AddListener(id, handler); 39 | } 40 | 41 | public void RemoveListener(TEventID id, EventHandler handler) 42 | { 43 | _internalDispatcher.RemoveListener(id, handler); 44 | } 45 | 46 | public void Dispatch(TEventID id, object data) 47 | { 48 | _internalDispatcher.Dispatch(id,data); 49 | } 50 | } 51 | 52 | /// 53 | /// EventDispatcher with custom data type. 54 | /// Can use it as T in to make it singleton. 55 | /// 56 | public class EventDispatcher : IEventDispatcher 57 | { 58 | private EventDispatcher _internalDispatcher; 59 | 60 | public EventDispatcher() 61 | { 62 | _internalDispatcher = new EventDispatcher(null); 63 | } 64 | 65 | public void AddListener(TEventID id, EventHandler handler) 66 | { 67 | _internalDispatcher.AddListener(id, handler); 68 | } 69 | 70 | public void RemoveListener(TEventID id, EventHandler handler) 71 | { 72 | _internalDispatcher.RemoveListener(id, handler); 73 | } 74 | 75 | public void Dispatch(TEventID id, TData data) 76 | { 77 | _internalDispatcher.Dispatch(id, data); 78 | } 79 | 80 | private class FakeComparer : IEqualityComparer 81 | { 82 | public bool Equals(TEventID x, TEventID y) 83 | { 84 | return false; 85 | } 86 | 87 | public int GetHashCode(TEventID obj) 88 | { 89 | return 0; 90 | } 91 | } 92 | } 93 | 94 | 95 | /// 96 | /// EventDispatcher with custom data type, and custom IEqualityComparer for TEventID. 97 | /// Can use it as T in to make it singleton. 98 | /// 99 | public class EventDispatcher : IEventDispatcher 100 | where TComparer: IEqualityComparer, new() 101 | { 102 | private Dictionary>> _handlers = null; 103 | 104 | public EventDispatcher(): this(new TComparer()){} 105 | 106 | public EventDispatcher(TComparer cp) 107 | { 108 | _handlers = new Dictionary>>(cp); 109 | } 110 | 111 | public void AddListener(TEventID eventID, EventHandler handlerToAdd) 112 | { 113 | if (_handlers.ContainsKey(eventID)) 114 | { 115 | _handlers[eventID].Add(handlerToAdd); 116 | } 117 | else 118 | { 119 | _handlers[eventID] = new List> { handlerToAdd }; 120 | } 121 | } 122 | 123 | public void RemoveListener(TEventID eventID, EventHandler handlerToRemove) 124 | { 125 | if (_handlers.ContainsKey(eventID)) 126 | { 127 | var handlers = _handlers[eventID]; 128 | for (int i = 0; i < handlers.Count; i++) 129 | { 130 | if (handlerToRemove == handlers[i]) 131 | { 132 | _handlers[eventID].RemoveAt(i); 133 | } 134 | } 135 | } 136 | } 137 | 138 | public void Dispatch(TEventID eventID, TData data = default) 139 | { 140 | if (_handlers.ContainsKey(eventID)) 141 | { 142 | for (int j = 0; j < _handlers[eventID].Count; j++) 143 | { 144 | var handler = _handlers[eventID][j]; 145 | handler(data); 146 | } 147 | } 148 | } 149 | } 150 | 151 | } -------------------------------------------------------------------------------- /Assets/ZTools/Core/Event/EventDispatcher.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 59dfe37b3fdfee944803599af0293ae0 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Core/FSM.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 35d843870f029aa419620ce75ad4243a 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Core/FSM/BaseState.cs: -------------------------------------------------------------------------------- 1 | namespace ZTools.Core 2 | { 3 | /// 4 | /// base class for state, used in FSM (Finite state machine) 5 | /// 6 | public abstract class BaseState where T : class 7 | { 8 | public virtual object OnMessage(T owner, M msg) { return null; } 9 | 10 | public virtual void Enter(T owner, object param) { } 11 | 12 | public virtual void Update(T owner) { } 13 | 14 | public virtual void Exit(T owner) { } 15 | 16 | public override string ToString() 17 | { 18 | return this.GetType().Name; 19 | } 20 | } 21 | 22 | } -------------------------------------------------------------------------------- /Assets/ZTools/Core/FSM/BaseState.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 387348dca659c7a48917b349388ff0de 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Core/FSM/FSMManager.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using ZTools.Debug; 3 | 4 | namespace ZTools.Core 5 | { 6 | /// 7 | /// create and drive FSM 8 | /// 9 | public class FSMManager : USingleton 10 | { 11 | private List allFSMs = null; 12 | 13 | public FSM createFSM(T owner, BaseState state, BaseState globalState) where T : class where M:struct 14 | { 15 | var newFSM = new FSM(owner, state, globalState); 16 | 17 | if (this.allFSMs == null) 18 | { 19 | this.allFSMs = new List(); 20 | } 21 | 22 | this.allFSMs.Add(newFSM); 23 | 24 | newFSM.OnSelfDispose += onFSMStop; 25 | 26 | return newFSM; 27 | } 28 | 29 | private void onFSMStop(IFSM fsm) 30 | { 31 | int idx = -1; 32 | 33 | if (this.allFSMs != null && fsm != null) 34 | { 35 | idx = this.allFSMs.IndexOf(fsm); 36 | if (idx >= 0) 37 | { 38 | fsm.OnSelfDispose -= onFSMStop; 39 | 40 | if (!fsm.IsRunning) 41 | { 42 | this.allFSMs.RemoveAt(idx); 43 | } 44 | else 45 | { 46 | ZLog.error(fsm.ToString(), "should stop before delete from list"); 47 | } 48 | } 49 | } 50 | } 51 | 52 | private void LateUpdate() 53 | { 54 | if (this.allFSMs == null) 55 | { 56 | return; 57 | } 58 | 59 | foreach (var fsm in this.allFSMs) 60 | { 61 | if(fsm.IsRunning) 62 | { 63 | fsm.Update(); 64 | } 65 | } 66 | } 67 | } 68 | } -------------------------------------------------------------------------------- /Assets/ZTools/Core/FSM/FSMManager.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: ee31501331733c642acadedb4a320c02 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Core/FSM/IFSM.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using ZTools.Debug; 4 | 5 | namespace ZTools.Core 6 | { 7 | /// 8 | /// Provide a unified interface managed by . 9 | /// 10 | public interface IFSM 11 | { 12 | public bool IsRunning { get; set; } 13 | public void Start(); 14 | public void Pause(); 15 | public void Resume(); 16 | public void Stop(); 17 | public void Update(); 18 | 19 | public delegate void OnDispose(IFSM fsm); 20 | public event OnDispose OnSelfDispose; 21 | } 22 | 23 | 24 | /// 25 | /// FSM (Finite state machine) 26 | /// 27 | /// T is FSM's owner's type. 28 | /// M is custom msg type. 29 | /// 30 | /// Change state immediately rather than next frame to keep simplicity and robustness. 31 | /// 32 | /// Notice that one state may not call update() if time interval between enter() and exit() is less than one frame interval. 33 | /// 34 | /// All onMessage function return an object. 35 | /// This is useful when you want to get some data/response immediately. 36 | /// 37 | /// globalState is a state that receive msg at anytime. 38 | /// This is very useful when all your states need to respond the same msg. 39 | /// E.g. when HP less than 0, die whatever state. 40 | /// 41 | /// -----Example code---- 42 | /// fsm = FSMFactory.createFSM(owner, new IdleState(), new GlobalState()); 43 | /// fsm.start(); 44 | /// fsm.onMessage(new YourMsgType()); 45 | /// fsm.stop(); 46 | /// 47 | /// 48 | public class FSM : IFSM where T : class 49 | { 50 | public bool IsRunning { get; set; } 51 | 52 | private T owner; 53 | private BaseState curState; 54 | private BaseState lastState; 55 | private BaseState globalState; 56 | 57 | public event IFSM.OnDispose OnSelfDispose; 58 | 59 | public FSM(T owner, BaseState state, BaseState globalState) 60 | { 61 | this.IsRunning = false; 62 | this.owner = owner; 63 | this.lastState = state; 64 | this.curState = state; 65 | this.globalState = globalState; 66 | } 67 | 68 | public void Start() 69 | { 70 | if (!this.IsRunning) 71 | { 72 | this.IsRunning = true; 73 | this.curState.Enter(this.owner, null); 74 | } 75 | } 76 | 77 | public void Pause() 78 | { 79 | this.IsRunning = false; 80 | } 81 | 82 | public void Resume() 83 | { 84 | this.IsRunning = true; 85 | } 86 | 87 | public void Stop() 88 | { 89 | if (this.IsRunning) 90 | { 91 | this.curState.Exit(this.owner); 92 | this.IsRunning = false; 93 | this.OnSelfDispose?.Invoke(this); 94 | } 95 | } 96 | 97 | public void Update() 98 | { 99 | if (this.IsRunning) 100 | { 101 | if (this.curState != null) { this.curState.Update(this.owner); } 102 | if (this.globalState != null) { this.globalState.Update(this.owner); } 103 | } 104 | } 105 | 106 | /// 107 | /// dispatch a message to fsm and get a return msg. 108 | /// 109 | public object OnMessage(M msg, bool retFromGlobal = false) 110 | { 111 | object msgRet = null; 112 | object msgRetGlobal = null; 113 | if (this.IsRunning) 114 | { 115 | if (this.curState != null) { msgRet = this.curState.OnMessage(this.owner, msg); } 116 | if (this.globalState != null) { msgRetGlobal = this.globalState.OnMessage(this.owner, msg); } 117 | } 118 | return retFromGlobal ? msgRetGlobal : msgRet; 119 | } 120 | 121 | /// 122 | /// change state immediately with some data 123 | /// 124 | public void ChangeState(BaseState newState, object param = null) 125 | { 126 | if (!this.IsRunning) 127 | { 128 | ZLog.error("Cannot change state, FSM is not runnning"); 129 | return; 130 | } 131 | 132 | if (newState == null) 133 | { 134 | ZLog.error(owner, "cannot change state to null"); 135 | return; 136 | } 137 | if (this.lastState == null || this.curState == null) 138 | { 139 | ZLog.error(owner, "Fatal error: _lastSate || _curState = null, newState=", newState); 140 | return; 141 | } 142 | 143 | if (newState.GetType().Equals(this.curState.GetType())) 144 | { 145 | ZLog.warn(this.owner, "cannot change to the same state:", this.curState); 146 | return; 147 | } 148 | 149 | if (this.owner == null) 150 | { 151 | ZLog.error("_owner = null"); 152 | return; 153 | } 154 | 155 | this.lastState = this.curState; 156 | this.curState = newState; 157 | 158 | ZLog.log(this.owner, this.lastState, this.curState); 159 | 160 | this.lastState.Exit(this.owner); 161 | this.curState.Enter(this.owner, param); 162 | } 163 | 164 | public bool IsInState(Type type) 165 | { 166 | return this.curState.GetType().Equals(type); 167 | } 168 | 169 | public string GetStateName() 170 | { 171 | return this.curState.GetType().Name; 172 | } 173 | } 174 | } -------------------------------------------------------------------------------- /Assets/ZTools/Core/FSM/IFSM.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: d38511b29f31eee47b5edf6d6e8b97f3 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Core/FSM/readme.md: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pps43/ZToolsForUnity/a49170d2a8246b4fec630b65e4b95d6f38d75406/Assets/ZTools/Core/FSM/readme.md -------------------------------------------------------------------------------- /Assets/ZTools/Core/FSM/readme.md.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: a7208da965b39bd42a9c2f5658be9cb0 3 | TextScriptImporter: 4 | externalObjects: {} 5 | userData: 6 | assetBundleName: 7 | assetBundleVariant: 8 | -------------------------------------------------------------------------------- /Assets/ZTools/Core/Math.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 65c437625085bd144b6294eb7e863208 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Core/Math/MathUtil.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | namespace ZTools.Core 3 | { 4 | public class MathUtil 5 | { 6 | 7 | #region Mapping 8 | 9 | /// 10 | /// Generate a unique number from 2 numbers. 11 | /// This method is better than famous Cantor's method. 12 | /// http://szudzik.com/ElegantPairing.pdf 13 | /// 14 | public static uint PairTwoNumber(uint a, uint b) 15 | { 16 | uint x = 0; 17 | try 18 | { 19 | checked 20 | { 21 | if (a > b) 22 | { 23 | x = a * a + a + b; 24 | } 25 | else 26 | { 27 | x = b * b + a; 28 | } 29 | } 30 | } 31 | catch (System.OverflowException e) 32 | { 33 | UnityEngine.Debug.LogError(e.ToString()); 34 | } 35 | return x; 36 | } 37 | 38 | #endregion 39 | 40 | #region Random 41 | public static bool RandomBool() 42 | { 43 | return UnityEngine.Random.value > 0.5f; 44 | } 45 | #endregion 46 | 47 | #region Space Geometry 48 | 49 | #region Projection/Cast a Point to Line segment (2D) 50 | 51 | /// 52 | /// Project point p along with castDir to line segment (v,w). when isRay defines the projection is on a ray or line. 53 | /// Return 0 means the projection point is inside the line segment. 54 | /// Return -1 means the projection point is on the left side of line segment. 55 | /// Return 1 means right side. 56 | /// 57 | /// To understand this method, refer to twoLineSegmentInterSection、point2LineSegmentDistance 58 | /// 59 | public static int castPointToLineSegment(Vector2 p, Vector2 q1, Vector2 q2, Vector2 castDir, bool isRay, out Vector2 interSectPoint) 60 | { 61 | // Ray: P = p + castDir * t (t>=0) 62 | // LineSeg: Q = v + (w-v) * s (0<=s<=1) 63 | interSectPoint = Vector2.positiveInfinity; 64 | 65 | Vector2 p1 = p; 66 | Vector2 p2 = p + castDir; 67 | int isInside = int.MaxValue; 68 | 69 | //put q1 as left point 70 | if (q1.x > q2.x) 71 | { 72 | Vector2 qTemp = q1; 73 | q1 = q2; q2 = qTemp; 74 | } 75 | 76 | float d = (p2.x - p1.x) * (q2.y - q1.y) - (p2.y - p1.y) * (q2.x - q1.x); 77 | 78 | if (d != 0f) // not parallel, nor colinear 79 | { 80 | float t = ((q1.x - p1.x) * (q2.y - q1.y) - (q1.y - p1.y) * (q2.x - q1.x)) / d; 81 | float s = ((q1.x - p1.x) * (p2.y - p1.y) - (q1.y - p1.y) * (p2.x - p1.x)) / d; 82 | if (t >= 0f && isRay == true || isRay == false) 83 | { 84 | isInside = s < 0f ? -1 : (s > 1f ? 1 : 0); 85 | s = Mathf.Clamp(s, 0, 1);//if outside line, project back 86 | interSectPoint = q1 + s * (q2 - q1); 87 | } 88 | } 89 | 90 | return isInside; 91 | 92 | } 93 | 94 | #endregion 95 | 96 | #region Distance between Point and Line segment (2D) 97 | 98 | /// 99 | /// Shortest distance between point p and line segment (v,w). 100 | /// Also returns t which can calculate the project point of p = v + t * (w - v) 101 | /// Also returns distance vector as distVector. 102 | /// 103 | public static float point2LineSegmentDistance(Vector2 p, Vector2 v, Vector2 w, out float t, out Vector2 distVector) 104 | { 105 | float sqrLen = (v - w).sqrMagnitude; 106 | if (sqrLen == 0f) 107 | { 108 | t = 0; 109 | distVector = v - p; 110 | } 111 | else 112 | { 113 | t = Mathf.Clamp(Vector2.Dot(p - v, w - v) / sqrLen, 0, 1); 114 | Vector2 pProjection = v + t * (w - v); 115 | distVector = pProjection - p; 116 | } 117 | 118 | return distVector.magnitude; 119 | } 120 | 121 | /// 122 | /// Shortest distance between point p and line segment (v,w). 123 | /// 124 | public static float point2LineSegmentDistance(Vector2 p, Vector2 v, Vector2 w) 125 | { 126 | return point2LineSegmentDistance(p, v, w, out _, out _); 127 | } 128 | #endregion 129 | 130 | #region Distance between two 2D Line segment (2D) 131 | 132 | /// 133 | /// Shortest distance between two line segment(p1,p2) and(q1,q2)。If intersects, return 0 134 | /// 135 | /// 136 | public static float twoLineSegmentDistance(Vector2 p1, Vector2 p2, Vector2 q1, Vector2 q2) 137 | { 138 | if (twoLineSegmentInterSection(p1, p2, q1, q2)) 139 | { 140 | return 0f; 141 | } 142 | else 143 | { 144 | float d1 = point2LineSegmentDistance(p1, q1, q2); 145 | float d2 = point2LineSegmentDistance(p2, q1, q2); 146 | float d3 = point2LineSegmentDistance(q1, p1, p2); 147 | float d4 = point2LineSegmentDistance(q2, p1, p2); 148 | return Mathf.Min(d1, d2, d3, d4); 149 | } 150 | } 151 | #endregion 152 | 153 | #region Intersection between two line segments (2D) 154 | 155 | /// 156 | /// Judge if two line segments intersects with each other, and return intersect point. 157 | /// Two line segments are defined as (p1,p2) and (q1,q2), respectively. 158 | /// 159 | /// is intersected or not. 160 | public static bool twoLineSegmentInterSection(Vector2 p1, Vector2 p2, Vector2 q1, Vector2 q2, out Vector2 interSectPoint) 161 | { 162 | interSectPoint = Vector2.negativeInfinity; 163 | 164 | float d = (p2.x - p1.x) * (q2.y - q1.y) - (p2.y - p1.y) * (q2.x - q1.x); 165 | 166 | if (d == 0f) 167 | { 168 | return false; //parallel, or colinear 169 | } 170 | 171 | float u = ((q1.x - p1.x) * (q2.y - q1.y) - (q1.y - p1.y) * (q2.x - q1.x)) / d; 172 | float v = ((q1.x - p1.x) * (p2.y - p1.y) - (q1.y - p1.y) * (p2.x - p1.x)) / d; 173 | 174 | if (u < 0f || u > 1f || v < 0f || v > 1f) 175 | { 176 | return false; // outside 177 | } 178 | 179 | interSectPoint = p1 + u * (p2 - p1); 180 | 181 | return true; 182 | } 183 | 184 | /// 185 | /// Judge if two line segments intersects with each other. 186 | /// Two line segments are defined as (p1,p2) and (q1,q2), respectively. 187 | /// 188 | /// is intersected or not. 189 | public static bool twoLineSegmentInterSection(Vector2 p1, Vector2 p2, Vector2 q1, Vector2 q2) 190 | { 191 | return twoLineSegmentInterSection(p1, p2, q1, q2, out _); 192 | } 193 | 194 | #endregion 195 | 196 | #endregion 197 | } 198 | } -------------------------------------------------------------------------------- /Assets/ZTools/Core/Math/MathUtil.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 4b1a9de1d62586a418d953eed1f4cef4 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Core/Singleton.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: d6d8b48cf27c72c4988792c16ebf64cc 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Core/Singleton/Singleton.cs: -------------------------------------------------------------------------------- 1 | namespace ZTools.Core 2 | { 3 | using System; 4 | /// 5 | /// Multithread-safe singleton of type T. 6 | /// 7 | /// Your type. 8 | public class Singleton where T: new() 9 | { 10 | private Singleton() {} 11 | 12 | #if UNITY_2019_1_OR_NEWER 13 | private static Lazy _instance = new Lazy(() => new T()); 14 | 15 | public static T Instance => _instance.Value; 16 | #else 17 | private static T _instance; 18 | private static object _syncRoot = new object(); 19 | 20 | public static T Instance 21 | { 22 | get 23 | { 24 | if (_instance == null) 25 | { 26 | lock (_syncRoot) 27 | { 28 | if (_instance == null) 29 | _instance = new T(); 30 | } 31 | } 32 | return _instance; 33 | } 34 | } 35 | #endif 36 | } 37 | } -------------------------------------------------------------------------------- /Assets/ZTools/Core/Singleton/Singleton.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: d7eae6a9e3c744a1be908f274aee4f9a 3 | timeCreated: 1631548117 -------------------------------------------------------------------------------- /Assets/ZTools/Core/Singleton/USingleton.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | 3 | namespace ZTools.Core 4 | { 5 | public abstract class USingleton : MonoBehaviour where T : MonoBehaviour 6 | { 7 | private static T instance; 8 | 9 | public static T Instance 10 | { 11 | get 12 | { 13 | if (instance == null) 14 | { 15 | T[] objs = GameObject.FindObjectsOfType(true); 16 | if (objs.Length > 0) 17 | { 18 | instance = objs[0]; 19 | for (int i = 1; i < objs.Length; i++) 20 | { 21 | GameObject.Destroy(objs[i].gameObject); 22 | } 23 | } 24 | else 25 | { 26 | GameObject newObj = new GameObject(typeof(T).Name); 27 | DontDestroyOnLoad(newObj); 28 | instance = newObj.AddComponent(); 29 | } 30 | } 31 | 32 | return instance; 33 | } 34 | } 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /Assets/ZTools/Core/Singleton/USingleton.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 51eea8964eb6d2a4f93c20df3a1cef8d 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: cc1a029d63cd7be438b2fb4be58cf583 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/FPS.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 94fdeba07e297a6499a36f6b1dab03f1 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/FPS/FPS.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | using UnityEngine.UI; 3 | 4 | namespace ZTools.Debug 5 | { 6 | /// 7 | /// To display framerate, attach Text or TextMesh compnent to this script 8 | /// 9 | public class FPS : MonoBehaviour 10 | { 11 | public int targetFrameRate = 60; 12 | public TextMesh textArea; 13 | public Text text; 14 | [SerializeField] private float _updateInterval = 0.5f; // seconds 15 | 16 | private float _frameCount = 0f; 17 | private float _dt = 0.0f; 18 | private float _fps = 0.0f; 19 | 20 | private void Awake() 21 | { 22 | Application.targetFrameRate = targetFrameRate; 23 | } 24 | 25 | void Update() 26 | { 27 | _frameCount++; 28 | _dt += Time.deltaTime; 29 | if (_dt > _updateInterval) 30 | { 31 | _fps = _frameCount / _dt; 32 | _frameCount = 0f; 33 | 34 | _dt -= _updateInterval; 35 | //dt = 0; // this is not accurate 36 | show(); 37 | } 38 | } 39 | 40 | void show() 41 | { 42 | if (textArea != null) 43 | textArea.text = _fps.ToString("0.0"); 44 | 45 | if (text != null) 46 | text.text = _fps.ToString("0.0"); 47 | } 48 | } 49 | } -------------------------------------------------------------------------------- /Assets/ZTools/Debug/FPS/FPS.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 6208c3658ffb16d48bc602f7f3355b44 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Gizmos.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: c627fad665c216f46a55a8d7dcd9be7d 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Gizmos/ZGizmos.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | namespace ZTools.Debug 3 | { 4 | /// 5 | /// draw gizmos with color 6 | /// 7 | public class ZGizmos 8 | { 9 | public static void DrawLine(Vector3 from, Vector3 to, Color newColor) 10 | { 11 | Color ori = Gizmos.color; 12 | Gizmos.color = newColor; 13 | Gizmos.DrawLine(from, to); 14 | Gizmos.color = ori; 15 | } 16 | 17 | public static void DrawSphere(Vector3 center, float radius, Color newColor) 18 | { 19 | Color ori = Gizmos.color; 20 | Gizmos.color = newColor; 21 | Gizmos.DrawSphere(center, radius); 22 | Gizmos.color = ori; 23 | } 24 | 25 | public static void DrawArrow(Vector3 begin, Vector3 end, Color newColor) 26 | { 27 | Color ori = Gizmos.color; 28 | Gizmos.color = newColor; 29 | 30 | Gizmos.DrawLine(begin, end); 31 | 32 | float arrowHeadAngle = 20; 33 | float arrowHeadLength = 5; 34 | 35 | Vector3 direction = end - begin; 36 | Vector3 right = Quaternion.LookRotation(direction) * Quaternion.Euler(arrowHeadAngle, 0, 0) * Vector3.back; 37 | Vector3 left = Quaternion.LookRotation(direction) * Quaternion.Euler(-arrowHeadAngle, 0, 0) * Vector3.back; 38 | Vector3 up = Quaternion.LookRotation(direction) * Quaternion.Euler(0, arrowHeadAngle, 0) * Vector3.back; 39 | Vector3 down = Quaternion.LookRotation(direction) * Quaternion.Euler(0, -arrowHeadAngle, 0) * Vector3.back; 40 | 41 | Gizmos.DrawRay(end, right * arrowHeadLength); 42 | Gizmos.DrawRay(end, left * arrowHeadLength); 43 | 44 | Gizmos.color = ori; 45 | } 46 | 47 | public static void DrawCircle2D(Vector3 center, float radius, Color newColor) 48 | { 49 | #if UNITY_EDITOR 50 | Color ori = UnityEditor.Handles.color; 51 | UnityEditor.Handles.color = newColor; 52 | 53 | UnityEditor.Handles.DrawWireDisc(center, Vector3.back, radius); 54 | UnityEditor.Handles.color = ori; 55 | #endif 56 | 57 | } 58 | } 59 | } -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Gizmos/ZGizmos.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: af078c80046760548921e018c5616358 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Log.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 2d08ad198a5cf224a9d2ed706dd53874 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Log/LogUtil.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | using System.Text; 3 | using System.IO; 4 | #if UNITY_EDITOR 5 | using UnityEditor; 6 | using System.Reflection; 7 | using System; 8 | using System.Collections.Generic; 9 | #endif 10 | namespace ZTools.Debug 11 | { 12 | /// 13 | /// Use LogFilter to do filename-based filtering. 14 | /// Use Zlog.logLevel to do importance-based filtering. 15 | /// Modity _line, _filePath according to your project before use. 16 | /// 17 | public class ZLog 18 | { 19 | public static bool isLogOn = true; // swith on/off 20 | public static LogLevel logLevel = LogLevel.info; 21 | private static int _line = 148;// Must be the line number of "UnityEngine.Debug.Log" in this file. 22 | private static string _filePath = "Assets/ZTools/Debug/Log/LogUtil.cs";//Modify to your actual path 23 | public enum LogLevel 24 | { 25 | verbose, 26 | info, 27 | warning, 28 | error, 29 | } 30 | 31 | private const string INFO_COLOR = "green"; 32 | private const string WARNING_COLOR = "magenta"; 33 | private const string ERROR_COLOR = "red"; 34 | private static StringBuilder _sb = new StringBuilder(); 35 | 36 | 37 | public static void log(T msg) 38 | { 39 | if (!isLogOn) { return; } 40 | logFormat(LogLevel.info, msg.ToString()); 41 | } 42 | 43 | public static void log(T1 m1, T2 m2) 44 | { 45 | if (!isLogOn) { return; } 46 | _sb.Length = 0; 47 | _sb.Append(m1).Append(m2); 48 | logFormat(LogLevel.info, _sb.ToString()); 49 | } 50 | 51 | public static void log(T1 m1, T2 m2, T3 m3) 52 | { 53 | if (!isLogOn) { return; } 54 | _sb.Length = 0; 55 | _sb.Append(m1).Append(m2).Append(m3); 56 | logFormat(LogLevel.info, _sb.ToString()); 57 | } 58 | 59 | public static void warn(T msg) 60 | { 61 | if (!isLogOn) { return; } 62 | logFormat(LogLevel.warning, msg.ToString()); 63 | } 64 | 65 | public static void warn(T1 m1, T2 m2) 66 | { 67 | if (!isLogOn) { return; } 68 | _sb.Length = 0; 69 | _sb.Append(m1).Append(m2); 70 | logFormat(LogLevel.warning, _sb.ToString()); 71 | } 72 | 73 | public static void warn(T1 m1, T2 m2, T3 m3) 74 | { 75 | if (!isLogOn) { return; } 76 | _sb.Length = 0; 77 | _sb.Append(m1).Append(m2).Append(m3); 78 | logFormat(LogLevel.warning, _sb.ToString()); 79 | } 80 | 81 | public static void error(T msg) 82 | { 83 | if (!isLogOn) { return; } 84 | logFormat(LogLevel.error, msg.ToString()); 85 | } 86 | 87 | public static void error(T1 m1, T2 m2) 88 | { 89 | if (!isLogOn) { return; } 90 | _sb.Length = 0; 91 | _sb.Append(m1).Append(m2); 92 | logFormat(LogLevel.error, _sb.ToString()); 93 | } 94 | 95 | public static void error(T1 m1, T2 m2, T3 m3) 96 | { 97 | if (!isLogOn) { return; } 98 | _sb.Length = 0; 99 | _sb.Append(m1).Append(m2).Append(m3); 100 | logFormat(LogLevel.error, _sb.ToString()); 101 | } 102 | 103 | 104 | public static void assert(bool condition, string msg = "") 105 | { 106 | if (string.IsNullOrEmpty(msg)) 107 | { 108 | UnityEngine.Debug.Assert(condition); 109 | } 110 | else 111 | { 112 | UnityEngine.Debug.Assert(condition, msg); 113 | } 114 | } 115 | 116 | private static void logFormat(LogLevel level, string msg) 117 | { 118 | if ((int)level < (int)logLevel) 119 | { 120 | return; 121 | } 122 | 123 | #if UNITY_EDITOR 124 | System.Diagnostics.StackTrace stackTrace = new System.Diagnostics.StackTrace(true); 125 | var stackFrame = stackTrace.GetFrame(2); 126 | string fullFileName = stackFrame.GetFileName(); 127 | string fileName = Path.GetFileName(fullFileName); 128 | 129 | if (LogFilter.blackList.Contains(fileName)) 130 | { 131 | return; 132 | } 133 | _logStackFrames.Add(stackFrame); 134 | #endif 135 | _sb.Length = 0; 136 | string colorStr = INFO_COLOR; 137 | if (level == LogLevel.warning) 138 | { 139 | colorStr = WARNING_COLOR; 140 | } 141 | else if (level == LogLevel.error) 142 | { 143 | colorStr = ERROR_COLOR; 144 | } 145 | string timeStr = Time.realtimeSinceStartup.ToString("0.000"); 146 | 147 | _sb.AppendFormat("Z|{1}| {2}", colorStr, timeStr, msg/*, stackMsgStr*/); 148 | UnityEngine.Debug.Log(_sb.ToString()); 149 | } 150 | 151 | #if UNITY_EDITOR 152 | private static int _instanceID; 153 | private static List _logStackFrames = new List(); 154 | //ConsoleWindow 155 | private static object _consoleWindowInstance; 156 | private static object _logListView; 157 | private static FieldInfo _logListViewTotalRowsFieldInfo; 158 | private static FieldInfo _logListViewCurrentRowFieldInfo; 159 | //LogEntry 160 | private static MethodInfo _logEntriesGetEntryMethod; 161 | private static object _logEntryInstance; 162 | 163 | private static FieldInfo _logEntryConditionFieldInfo; 164 | private static FieldInfo _consoleWindowFieldInfo; 165 | private static FieldInfo _listViewFieldInfo; 166 | static ZLog() 167 | { 168 | _instanceID = AssetDatabase.LoadAssetAtPath(_filePath).GetInstanceID(); 169 | _logStackFrames.Clear(); 170 | 171 | getConsoleWindowListView(); 172 | } 173 | 174 | private static void getConsoleWindowListView() 175 | { 176 | if (_logListView == null) 177 | { 178 | Assembly unityEditorAssembly = Assembly.GetAssembly(typeof(EditorWindow)); 179 | Type consoleWindowType = unityEditorAssembly.GetType("UnityEditor.ConsoleWindow"); 180 | 181 | _consoleWindowFieldInfo = consoleWindowType.GetField("ms_ConsoleWindow", BindingFlags.Static | BindingFlags.NonPublic); 182 | _consoleWindowInstance = _consoleWindowFieldInfo.GetValue(null); 183 | if (_consoleWindowInstance == null) 184 | { 185 | return; 186 | } 187 | _listViewFieldInfo = consoleWindowType.GetField("m_ListView", BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Default); 188 | _logListView = _listViewFieldInfo.GetValue(_consoleWindowInstance); 189 | _logListViewTotalRowsFieldInfo = _listViewFieldInfo.FieldType.GetField("totalRows", BindingFlags.Instance | BindingFlags.Public); 190 | _logListViewCurrentRowFieldInfo = _listViewFieldInfo.FieldType.GetField("row", BindingFlags.Instance | BindingFlags.Public); 191 | 192 | Type logEntriesType = unityEditorAssembly.GetType("UnityEditor.LogEntries"); 193 | _logEntriesGetEntryMethod = logEntriesType.GetMethod("GetEntryInternal", BindingFlags.Static | BindingFlags.Public); 194 | Type logEntryType = unityEditorAssembly.GetType("UnityEditor.LogEntry"); 195 | _logEntryInstance = Activator.CreateInstance(logEntryType); 196 | _logEntryConditionFieldInfo = logEntryType.GetField("condition", BindingFlags.Instance | BindingFlags.Public); 197 | } 198 | } 199 | private static System.Diagnostics.StackFrame getListViewRowCount() 200 | { 201 | getConsoleWindowListView(); 202 | if (_logListView == null) 203 | return null; 204 | else 205 | { 206 | int totalRows = (int)_logListViewTotalRowsFieldInfo.GetValue(_logListView); 207 | int row = (int)_logListViewCurrentRowFieldInfo.GetValue(_logListView); 208 | int logByThisClassCount = 0; 209 | for (int i = totalRows - 1; i >= row; i--) 210 | { 211 | _logEntriesGetEntryMethod.Invoke(null, new object[] { i, _logEntryInstance }); 212 | string condition = _logEntryConditionFieldInfo.GetValue(_logEntryInstance) as string; 213 | if (condition.Contains("Z|"))// special mark to identify if it's called by this script 214 | logByThisClassCount++; 215 | } 216 | 217 | while (_logStackFrames.Count > totalRows) 218 | _logStackFrames.RemoveAt(0); 219 | if (_logStackFrames.Count >= logByThisClassCount) 220 | return _logStackFrames[_logStackFrames.Count - logByThisClassCount]; 221 | return null; 222 | } 223 | } 224 | 225 | [UnityEditor.Callbacks.OnOpenAssetAttribute(0)] 226 | public static bool OnOpenAsset(int instanceID, int line) 227 | { 228 | if (instanceID == _instanceID && _line == line) 229 | { 230 | var stackFrame = getListViewRowCount(); 231 | if (stackFrame != null) 232 | { 233 | string fileName = stackFrame.GetFileName(); 234 | string fileAssetPath = fileName.Substring(fileName.IndexOf("Assets")); 235 | AssetDatabase.OpenAsset(AssetDatabase.LoadAssetAtPath(fileAssetPath), stackFrame.GetFileLineNumber()); 236 | return true; 237 | } 238 | } 239 | 240 | return false; 241 | } 242 | #endif 243 | } 244 | 245 | public class LogFilter 246 | { 247 | // log called by filenames listed here will be blocked. 248 | public static HashSet blackList = new HashSet() 249 | { 250 | //"xxx.cs", 251 | //"yyy.cs", 252 | 253 | }; 254 | } 255 | } -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Log/LogUtil.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: b8de9bf88a4802140b48f93b900f2bc0 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Log/LogWindow.cs: -------------------------------------------------------------------------------- 1 | using System.Text; 2 | using UnityEngine; 3 | using UnityEngine.UI; 4 | namespace ZTools.Debug 5 | { 6 | /// 7 | /// print unity log onto screen. 8 | /// use it on target device to see log immediately 9 | /// 10 | public class LogWindow : MonoBehaviour 11 | { 12 | public int maxLogLine = 20;//clear after exceed 13 | 14 | private TextMesh _textArea; 15 | private StringBuilder _sb = new StringBuilder(); 16 | private Text _textUI; 17 | private int _curLogLine = 0; 18 | 19 | private void Awake() 20 | { 21 | _textArea = GetComponent(); 22 | _textUI = GetComponent(); 23 | //DontDestroyOnLoad(gameObject); 24 | _curLogLine = 0; 25 | } 26 | 27 | void OnEnable() 28 | { 29 | Application.logMessageReceived += LogMessage; 30 | } 31 | 32 | void OnDisable() 33 | { 34 | Application.logMessageReceived -= LogMessage; 35 | } 36 | 37 | private void LogMessage(string message, string stackTrace, LogType type) 38 | { 39 | _curLogLine++; 40 | if(_curLogLine > maxLogLine) 41 | { 42 | _curLogLine = 0; 43 | _sb.Length = 0; 44 | } 45 | 46 | if (type == LogType.Error || type == LogType.Exception) 47 | { 48 | _sb.Append("").Append(message).Append("").Append("\n"); 49 | 50 | } 51 | else if(type == LogType.Warning) 52 | { 53 | _sb.Append("").Append(message).Append("").Append("\n"); 54 | } 55 | else 56 | { 57 | _sb.Append(message).Append("\n"); 58 | } 59 | if (_textArea) 60 | { 61 | _textArea.text = _sb.ToString(); 62 | } 63 | if(_textUI) 64 | { 65 | _textUI.text = _sb.ToString(); 66 | } 67 | 68 | } 69 | } 70 | } -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Log/LogWindow.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 384d57781f67b6a44badec67b693f155 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 2a616dd6e87310241945283d64bece16 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw/Editor.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 426c777497f163d4781bcb8bb5bab7fe 3 | folderAsset: yes 4 | timeCreated: 1498554440 5 | licenseType: Pro 6 | DefaultImporter: 7 | userData: 8 | assetBundleName: 9 | assetBundleVariant: 10 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw/Editor/OverdrawToolWindow.cs: -------------------------------------------------------------------------------- 1 | using UnityEditor; 2 | using UnityEngine; 3 | 4 | /// A simple tool to track the exact amount of overdraw in the game window. This tool 5 | /// only shows the result, to check out how this is implemented. 6 | public class OverdrawToolWindow : EditorWindow 7 | { 8 | [MenuItem("Tools/Overdraw Tool")] 9 | public static void ShowWindow() 10 | { 11 | var window = GetWindow(); 12 | window.Focus(); 13 | } 14 | 15 | string camName; 16 | public void OnGUI() 17 | { 18 | using (new GUILayout.HorizontalScope()) 19 | { 20 | camName = GUILayout.TextField(camName); 21 | 22 | if (GUILayout.Button("Assign Camera")) 23 | { 24 | OverdrawMonitor.Instance.setCameraToAnalysis(camName); 25 | } 26 | } 27 | 28 | using (new GUILayout.HorizontalScope()) 29 | { 30 | if (GUILayout.Button("Start")) 31 | { 32 | OverdrawMonitor.Instance.StartMeasurement(); 33 | OverdrawMonitor.Instance.ResetSampling(); 34 | OverdrawMonitor.Instance.ResetExtreemes(); 35 | } 36 | 37 | if (GUILayout.Button("End")) 38 | { 39 | OverdrawMonitor.Instance.Stop(); 40 | } 41 | } 42 | 43 | using (new GUILayout.HorizontalScope()) 44 | { 45 | GUILayout.Label("Max\n" + OverdrawMonitor.Instance.MaxOverdraw.ToString("0.000")); 46 | GUILayout.FlexibleSpace(); 47 | GUILayout.Label("Average\n" + OverdrawMonitor.Instance.AccumulatedAverageOverdraw.ToString("0.000")); 48 | } 49 | 50 | Repaint(); 51 | } 52 | } -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw/Editor/OverdrawToolWindow.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: e48bb4c477ace5046a9bdf6ca27a50af 3 | timeCreated: 1498554219 4 | licenseType: Pro 5 | MonoImporter: 6 | serializedVersion: 2 7 | defaultReferences: [] 8 | executionOrder: 0 9 | icon: {instanceID: 0} 10 | userData: 11 | assetBundleName: 12 | assetBundleVariant: 13 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw/Editor/Resources.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 633512af7657fe7469c43935e7fee4fc 3 | folderAsset: yes 4 | timeCreated: 1498554083 5 | licenseType: Pro 6 | DefaultImporter: 7 | userData: 8 | assetBundleName: 9 | assetBundleVariant: 10 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw/Editor/Resources/DebugOverdrawInt.shader: -------------------------------------------------------------------------------- 1 | // Upgrade NOTE: replaced 'mul(UNITY_MATRIX_MVP,*)' with 'UnityObjectToClipPos(*)' 2 | 3 | Shader "Debug/OverdrawInt" 4 | { 5 | Properties 6 | { 7 | [Header(Hardware settings)] 8 | [Enum(UnityEngine.Rendering.CullMode)] HARDWARE_CullMode ("Cull faces", Float) = 2 9 | [Enum(On, 1, Off, 0)] HARDWARE_ZWrite ("Depth write", Float) = 1 10 | } 11 | SubShader 12 | { 13 | Tags { "RenderType"="Opaque" "LightMode" = "ForwardBase" "Queue" = "Geometry+50"} 14 | LOD 100 15 | 16 | Pass 17 | { 18 | Cull [HARDWARE_CullMode] 19 | ZWrite [HARDWARE_ZWrite] 20 | Blend One One 21 | 22 | CGPROGRAM 23 | #pragma vertex vert 24 | #pragma fragment frag 25 | #pragma exclude_renderers d3d11_9x 26 | 27 | struct appdata 28 | { 29 | float4 vertex : POSITION; 30 | }; 31 | 32 | struct v2f 33 | { 34 | float4 vertex : SV_POSITION; 35 | }; 36 | 37 | v2f vert (appdata v) 38 | { 39 | v2f o; 40 | o.vertex = UnityObjectToClipPos(v.vertex); 41 | return o; 42 | } 43 | 44 | float4 frag (v2f i) : SV_Target 45 | { 46 | // 1 / 512 = 0.001953125; 1 / 1024 = 0.0009765625 47 | return 0.0009765625; 48 | } 49 | ENDCG 50 | } 51 | } 52 | } 53 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw/Editor/Resources/DebugOverdrawInt.shader.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: c1abde7e6c981d6409529b791c8e6142 3 | timeCreated: 1498554405 4 | licenseType: Pro 5 | ShaderImporter: 6 | defaultTextures: [] 7 | userData: 8 | assetBundleName: 9 | assetBundleVariant: 10 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw/Editor/Resources/OverdrawParallelReduction.compute: -------------------------------------------------------------------------------- 1 | #pragma kernel CSMain 2 | 3 | // Defines 4 | #define SIZEX 32 5 | #define SIZEY 32 6 | #define GROUPSIZE SIZEX*SIZEY 7 | 8 | groupshared int accumulator[GROUPSIZE]; 9 | 10 | Texture2D Overdraw; 11 | RWStructuredBuffer Output; 12 | 13 | [numthreads(SIZEX,SIZEY,1)] 14 | void CSMain (uint3 gid : SV_GroupID, uint3 inp : SV_DispatchThreadID, uint gtidx : SV_GroupIndex) 15 | { 16 | accumulator[gtidx] = (int)(Overdraw[inp.xy].x * 1024); 17 | 18 | // Wait for all 19 | GroupMemoryBarrierWithGroupSync(); 20 | 21 | [unroll] 22 | for (uint ix = GROUPSIZE >> 1; ix > 0; ix = ix >> 1) 23 | { 24 | if (gtidx < ix) 25 | { 26 | accumulator[gtidx] = (accumulator[gtidx] + accumulator[gtidx + ix]); 27 | } 28 | GroupMemoryBarrierWithGroupSync(); 29 | } 30 | 31 | if (gtidx != 0) return; 32 | 33 | Output[gid.y * 128 + gid.x] = accumulator[0]; 34 | } 35 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw/Editor/Resources/OverdrawParallelReduction.compute.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 17691d60c3e3edc428e83ce7be3bbc6a 3 | timeCreated: 1498554239 4 | licenseType: Pro 5 | ComputeShaderImporter: 6 | currentAPIMask: 4 7 | userData: 8 | assetBundleName: 9 | assetBundleVariant: 10 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw/Overdraw.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | using UnityEngine.UI; 3 | 4 | namespace ZTools.Debug 5 | { 6 | /// 7 | /// Analysis overdraw when play. 8 | /// Attach to an empty gameobject, and drag Camera and resultText to this script. 9 | /// This will give accumulatedAverageOverdraw and maxOverdraw. 10 | /// TODO : due to performance issue, this only runs in Editor Mode. 11 | /// 12 | public class Overdraw : MonoBehaviour 13 | { 14 | [Header("Camera Gameobject Name")] 15 | public string cameraToAnalysisName; 16 | public float sampleInterval = 1; 17 | public bool isOpen = true; 18 | public Text resultText; 19 | 20 | //Max overdraw ratio 21 | public float maxOverdraw { get; private set; } 22 | //Moving average overdraw ratio 23 | public float accumulatedAverageOverdraw { get { return _accumulatedIntervalOverdraw / _intervalFrames; } } 24 | 25 | private Camera _cameraToAnalysis; 26 | private Camera _overdrawCamera; 27 | private RenderTexture _overdrawTexture; 28 | private ComputeShader _computeShader; 29 | 30 | private const int DATA_SIZE = 128 * 128; 31 | private int[] _inputData = new int[DATA_SIZE]; 32 | private int[] _resultData = new int[DATA_SIZE]; 33 | private ComputeBuffer _resultBuffer; 34 | private Shader _replacementShader; 35 | 36 | // Last measurement 37 | /// The number of shaded fragments in the last frame. 38 | public long totalShadedFragments { get; private set; } 39 | /// The overdraw ration in the last frame. 40 | public float overdrawRatio { get; private set; } 41 | 42 | // Sampled measurement 43 | /// Number of shaded fragments in the measured time span. 44 | public long intervalShadedFragments { get; private set; } 45 | /// The average number of shaded fragments in the measured time span. 46 | public float intervalAverageShadedFragments { get; private set; } 47 | /// The average overdraw in the measured time span. 48 | public float intervalAverageOverdraw { get; private set; } 49 | 50 | 51 | private long _accumulatedIntervalFragments; 52 | private float _accumulatedIntervalOverdraw; 53 | private long _intervalFrames; 54 | private float _intervalTime = 0; 55 | 56 | /// 57 | /// switch on/off overdraw analysis 58 | /// 59 | /// 60 | public void setOpenClose(bool isOn) 61 | { 62 | isOpen = isOn; 63 | resultText.gameObject.SetActive(isOn); 64 | } 65 | 66 | private void Awake() 67 | { 68 | #if !UNITY_EDITOR 69 | return; //TODO too slow on mobile 70 | #else 71 | UnityEditor.EditorApplication.ExecuteMenuItem("Edit/Graphics Emulation/No Emulation"); 72 | #endif 73 | var camobj = GameObject.Find(cameraToAnalysisName); 74 | if (camobj != null) 75 | { 76 | _cameraToAnalysis = camobj.GetComponent(); 77 | } 78 | if (_cameraToAnalysis == null) 79 | { 80 | UnityEngine.Debug.LogWarning("Overdraw Analysis. no camera selected, use camera.main"); 81 | _cameraToAnalysis = Camera.main; 82 | } 83 | 84 | _replacementShader = Shader.Find("Debug/OverdrawInt"); 85 | 86 | _overdrawCamera = gameObject.AddComponent();// 87 | _overdrawCamera.CopyFrom(_cameraToAnalysis); 88 | _overdrawCamera.SetReplacementShader(_replacementShader, null); 89 | 90 | RecreateTexture(_cameraToAnalysis, _overdrawCamera); 91 | RecreateComputeBuffer(); 92 | 93 | _computeShader = Resources.Load("OverdrawParallelReduction"); 94 | 95 | for (int i = 0; i < _inputData.Length; i++) { _inputData[i] = 0; } 96 | } 97 | 98 | private void LateUpdate() 99 | { 100 | if (!isOpen) { return; } 101 | 102 | _overdrawCamera.CopyFrom(_cameraToAnalysis); 103 | _overdrawCamera.clearFlags = CameraClearFlags.SolidColor; 104 | _overdrawCamera.backgroundColor = Color.black; 105 | _overdrawCamera.targetTexture = _overdrawTexture; 106 | _overdrawCamera.SetReplacementShader(_replacementShader, null); 107 | 108 | transform.position = _cameraToAnalysis.transform.position; 109 | transform.rotation = _cameraToAnalysis.transform.rotation; 110 | 111 | RecreateTexture(_cameraToAnalysis, _overdrawCamera); 112 | 113 | 114 | _intervalTime += Time.deltaTime; 115 | if (_intervalTime > sampleInterval) 116 | { 117 | intervalShadedFragments = _accumulatedIntervalFragments; 118 | intervalAverageShadedFragments = (float)_accumulatedIntervalFragments / _intervalFrames; 119 | intervalAverageOverdraw = (float)_accumulatedIntervalOverdraw / _intervalFrames; 120 | 121 | displayResult(); 122 | 123 | _intervalTime -= sampleInterval; 124 | 125 | _accumulatedIntervalFragments = 0; 126 | _accumulatedIntervalOverdraw = 0; 127 | _intervalFrames = 0; 128 | 129 | } 130 | } 131 | 132 | private void OnPostRender() 133 | { 134 | if (!isOpen) { return; } 135 | 136 | int kernel = _computeShader.FindKernel("CSMain"); 137 | 138 | RecreateComputeBuffer(); 139 | 140 | // Setting up the data 141 | _resultBuffer.SetData(_inputData); 142 | _computeShader.SetTexture(kernel, "Overdraw", _overdrawTexture); 143 | _computeShader.SetBuffer(kernel, "Output", _resultBuffer); 144 | 145 | int xGroups = (_overdrawTexture.width / 32); 146 | int yGroups = (_overdrawTexture.height / 32); 147 | 148 | // Summing up the fragments 149 | _computeShader.Dispatch(kernel, xGroups, yGroups, 1); 150 | _resultBuffer.GetData(_resultData); 151 | 152 | // Getting the results 153 | totalShadedFragments = 0; 154 | for (int i = 0; i < _resultData.Length; i++) 155 | { 156 | totalShadedFragments += _resultData[i]; 157 | } 158 | 159 | overdrawRatio = (float)totalShadedFragments / (xGroups * 32 * yGroups * 32); 160 | 161 | _accumulatedIntervalFragments += totalShadedFragments; 162 | _accumulatedIntervalOverdraw += overdrawRatio; 163 | _intervalFrames++; 164 | 165 | //Debug.Log("_accumulatedIntervalOverdraw: " + _accumulatedIntervalOverdraw + "/"+ _intervalFrames); 166 | 167 | if (overdrawRatio > maxOverdraw) maxOverdraw = overdrawRatio; 168 | } 169 | 170 | public void OnDestroy() 171 | { 172 | if (_overdrawCamera != null) 173 | { 174 | _overdrawCamera.targetTexture = null; 175 | } 176 | if (_resultBuffer != null) _resultBuffer.Release(); 177 | } 178 | 179 | /// Checks if the overdraw texture should be updated. This needs to happen if the main camera 180 | /// configuration changes. 181 | private void RecreateTexture(Camera cameraToAnalysis, Camera myOverdrawCamera) 182 | { 183 | if (_overdrawTexture == null) 184 | { 185 | _overdrawTexture = new RenderTexture(myOverdrawCamera.pixelWidth, myOverdrawCamera.pixelHeight, 24, RenderTextureFormat.RFloat); 186 | _overdrawTexture.enableRandomWrite = true; 187 | myOverdrawCamera.targetTexture = _overdrawTexture; 188 | } 189 | 190 | if (cameraToAnalysis.pixelWidth != _overdrawTexture.width || cameraToAnalysis.pixelHeight != _overdrawTexture.height) 191 | { 192 | _overdrawTexture.Release(); 193 | _overdrawTexture.width = cameraToAnalysis.pixelWidth; 194 | _overdrawTexture.height = cameraToAnalysis.pixelHeight; 195 | } 196 | } 197 | 198 | private void RecreateComputeBuffer() 199 | { 200 | if (_resultBuffer != null) return; 201 | _resultBuffer = new ComputeBuffer(_resultData.Length, 4); 202 | } 203 | private void displayResult() 204 | { 205 | resultText.text = "Overdraw(Cur/Max):" + accumulatedAverageOverdraw.ToString("0.00") + " / " + maxOverdraw.ToString("0.00"); 206 | } 207 | } 208 | } -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw/Overdraw.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: c4a26d8b6af49de4aafeee3d891edb35 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Debug/Overdraw/OverdrawMonitor.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 35d88df0531cbd44f98a9d605e8a55b3 3 | timeCreated: 1498554150 4 | licenseType: Pro 5 | MonoImporter: 6 | serializedVersion: 2 7 | defaultReferences: [] 8 | executionOrder: 0 9 | icon: {instanceID: 0} 10 | userData: 11 | assetBundleName: 12 | assetBundleVariant: 13 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 1b088df116f3bf04f8b0fc42cc23e469 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: e79c64b1c51f0754783d20066c439d0c 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/Layer.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: b67cba26364c2b149b6820563048a0c0 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/Layer/LayerPropertyDrawer.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using UnityEditor; 3 | using UnityEngine; 4 | namespace ZTools.Editor 5 | { 6 | 7 | [CustomPropertyDrawer(typeof(ShowLayerAttribute))] 8 | public class LayerPropertyDrawer : PropertyDrawer 9 | { 10 | 11 | public override void OnGUI(Rect position, SerializedProperty property, GUIContent label) 12 | { 13 | int selected = -1; 14 | //show dropdown menu 15 | List layerNames = new List(); 16 | for (int i = 8; i <= 31; i++) // custom layer always starts from 8 17 | { 18 | string layerName = LayerMask.LayerToName(i); 19 | if (layerName.Length > 0) 20 | { 21 | layerNames.Add(layerName); 22 | } 23 | } 24 | 25 | selected = property.intValue - 8; 26 | 27 | EditorGUI.BeginProperty(position, label, property); 28 | position = EditorGUI.PrefixLabel(position, GUIUtility.GetControlID(FocusType.Passive), label); 29 | selected = EditorGUI.Popup(position, selected, layerNames.ToArray()); 30 | EditorGUI.EndProperty(); 31 | 32 | if (selected >= 0) 33 | { 34 | property.intValue = selected + 8; 35 | } 36 | } 37 | } 38 | } -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/Layer/LayerPropertyDrawer.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 14d1eea96ffd7924d92954a1fea07f14 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/Layer/ShowLayerAttribute.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | namespace ZTools.Editor 3 | { 4 | /// 5 | /// Select layer in your script 6 | /// e.g. 7 | /// [ShowLayer] public int layer; 8 | /// gameobject.layer = layer; 9 | /// 10 | public class ShowLayerAttribute : PropertyAttribute 11 | { 12 | } 13 | } -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/Layer/ShowLayerAttribute.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 42a63ef7a9d96f544b83779c77555f5e 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/Layer/ShowSortingLayerAttribute.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | 3 | /// 4 | /// Select sortinglayer in your script 5 | /// e.g. 6 | /// [ShowSortingLayer] [SerializeField] private string renderLayer = ""; 7 | /// gameobject.layer = layer; 8 | /// 9 | public class ShowSortingLayerAttribute : PropertyAttribute 10 | { 11 | } 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/Layer/ShowSortingLayerAttribute.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 5d5fbad6166c8e44da9c6a537457b193 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/Layer/SortingLayerPropertyDrawer.cs: -------------------------------------------------------------------------------- 1 | using UnityEditor; 2 | using UnityEngine; 3 | 4 | //适用于 [ShowSortingLayer] public string sortingLayer 5 | [CustomPropertyDrawer(typeof(ShowSortingLayerAttribute))] 6 | public class SortingLayerPropertyDrawer : PropertyDrawer 7 | { 8 | public override void OnGUI(Rect position, SerializedProperty property, GUIContent label) 9 | { 10 | int selected = -1; 11 | 12 | var names = new string[SortingLayer.layers.Length]; 13 | for (int i = 0; i < SortingLayer.layers.Length; i++) 14 | { 15 | names[i] = SortingLayer.layers[i].name; 16 | if (property.stringValue == names[i]) 17 | selected = i; 18 | } 19 | 20 | EditorGUI.BeginProperty(position, label, property); 21 | position = EditorGUI.PrefixLabel(position, GUIUtility.GetControlID(FocusType.Passive), label); 22 | selected = EditorGUI.Popup(position, selected, names); 23 | EditorGUI.EndProperty(); 24 | 25 | if (selected >= 0) 26 | property.stringValue = names[selected]; 27 | } 28 | 29 | //适用于 int sortingLayer 30 | //public override void OnGUI(Rect position, SerializedProperty property, GUIContent label) 31 | //{ 32 | // if (property.propertyType != SerializedPropertyType.Integer) 33 | // { 34 | // Debug.LogError("SortedLayer property should be an integer ( the layer id )"); 35 | // } 36 | // else 37 | // { 38 | // SortingLayerField(new GUIContent("Sorting Layer"), property, EditorStyles.popup, EditorStyles.label); 39 | // } 40 | //} 41 | 42 | //public static void SortingLayerField(GUIContent label, SerializedProperty layerID, GUIStyle style, GUIStyle labelStyle) 43 | //{ 44 | // MethodInfo methodInfo = typeof(EditorGUILayout).GetMethod("SortingLayerField", BindingFlags.Static | BindingFlags.NonPublic, null, new[] { typeof(GUIContent), typeof(SerializedProperty), typeof(GUIStyle), typeof(GUIStyle) }, null); 45 | 46 | // if (methodInfo != null) 47 | // { 48 | // object[] parameters = new object[] { label, layerID, style, labelStyle }; 49 | // methodInfo.Invoke(null, parameters); 50 | // } 51 | //} 52 | 53 | 54 | //适用于 int sortingLayer 55 | ///** 56 | // * Is called to draw a property. 57 | // * 58 | // * @param position Rectangle on the screen to use for the property GUI. 59 | // * @param property The SerializedProperty to make the custom GUI for. 60 | // * @param label The label of the property. 61 | // */ 62 | //public override void OnGUI(Rect position, SerializedProperty property, GUIContent label) 63 | //{ 64 | // if (property.propertyType != SerializedPropertyType.Integer) 65 | // { 66 | // // Integer is expected. Everything else is ignored. 67 | // return; 68 | // } 69 | // EditorGUI.LabelField(position, label); 70 | 71 | // position.x += EditorGUIUtility.labelWidth; 72 | // position.width -= EditorGUIUtility.labelWidth; 73 | 74 | // string[] sortingLayerNames = GetSortingLayerNames(); 75 | // int[] sortingLayerIDs = GetSortingLayerIDs(); 76 | 77 | // int sortingLayerIndex = Mathf.Max(0, System.Array.IndexOf(sortingLayerIDs, property.intValue)); 78 | // sortingLayerIndex = EditorGUI.Popup(position, sortingLayerIndex, sortingLayerNames); 79 | // property.intValue = sortingLayerIDs[sortingLayerIndex]; 80 | //} 81 | 82 | ///** 83 | // * Retrives list of sorting layer names. 84 | // * 85 | // * @return List of sorting layer names. 86 | // */ 87 | //private string[] GetSortingLayerNames() 88 | //{ 89 | // System.Type internalEditorUtilityType = typeof(InternalEditorUtility); 90 | // PropertyInfo sortingLayersProperty = internalEditorUtilityType.GetProperty( 91 | // "sortingLayerNames", BindingFlags.Static | BindingFlags.NonPublic); 92 | // return (string[])sortingLayersProperty.GetValue(null, new object[0]); 93 | //} 94 | 95 | ///** 96 | // * Retrives list of sorting layer identifiers. 97 | // * 98 | // * @return List of sorting layer identifiers. 99 | // */ 100 | //private int[] GetSortingLayerIDs() 101 | //{ 102 | // System.Type internalEditorUtilityType = typeof(InternalEditorUtility); 103 | // PropertyInfo sortingLayersProperty = internalEditorUtilityType.GetProperty( 104 | // "sortingLayerUniqueIDs", BindingFlags.Static | BindingFlags.NonPublic); 105 | // return (int[])sortingLayersProperty.GetValue(null, new object[0]); 106 | //} 107 | } 108 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/Layer/SortingLayerPropertyDrawer.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 1f89e757c03c4be4dad6ef30bfab1459 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/ReadOnly.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 3f6fd8f2bb6957e4ea0298b4fe1ae2eb 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/ReadOnly/ReadOnlyAttribute.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | namespace ZTools.Editor.CustomAttribute 3 | { 4 | /// 5 | /// use this to make field readonly in editor; 6 | /// e.g. [ReadOnly] [SerializedField] private bool myVar = true; 7 | /// 8 | public class ReadOnlyAttribute : PropertyAttribute 9 | { 10 | public string Info 11 | { 12 | get; 13 | protected set; 14 | } 15 | 16 | public ReadOnlyAttribute() 17 | { 18 | Info = null; 19 | } 20 | 21 | public ReadOnlyAttribute(string info) 22 | { 23 | Info = info; 24 | } 25 | } 26 | } -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/ReadOnly/ReadOnlyAttribute.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 40b376044680a3041807eebf9bb67530 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/ReadOnly/ReadOnlyPropertyDrawer.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | using UnityEditor; 3 | namespace ZTools.Editor.CustomAttribute 4 | { 5 | [CustomPropertyDrawer(typeof(ReadOnlyAttribute))] 6 | public class ReadOnlyPropertyDrawer : PropertyDrawer 7 | { 8 | const float _InfoHeightScaler = 1.5f; 9 | 10 | private float _PropertyHeight = 0; 11 | 12 | public override float GetPropertyHeight(SerializedProperty property, GUIContent label) 13 | { 14 | var roattrib = attribute as ReadOnlyAttribute; 15 | 16 | _PropertyHeight = EditorGUI.GetPropertyHeight(property, label, true); 17 | 18 | if (!string.IsNullOrEmpty(roattrib.Info)) 19 | { 20 | return _PropertyHeight * (1.0f + _InfoHeightScaler); 21 | } 22 | 23 | return _PropertyHeight; 24 | } 25 | 26 | public override void OnGUI(Rect position, SerializedProperty property, GUIContent label) 27 | { 28 | var roattrib = attribute as ReadOnlyAttribute; 29 | 30 | if (!string.IsNullOrEmpty(roattrib.Info)) 31 | { 32 | position.height = _PropertyHeight * _InfoHeightScaler; 33 | 34 | EditorGUI.HelpBox(position, roattrib.Info, MessageType.Info); 35 | 36 | position.y += _PropertyHeight * _InfoHeightScaler; 37 | } 38 | 39 | GUI.enabled = false; 40 | 41 | EditorGUI.PropertyField(position, property, label, true); 42 | 43 | GUI.enabled = true; 44 | } 45 | } 46 | } -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/ReadOnly/ReadOnlyPropertyDrawer.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: e46547ddbc459c14c965056b90c021fc 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/readme.md: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pps43/ZToolsForUnity/a49170d2a8246b4fec630b65e4b95d6f38d75406/Assets/ZTools/Editor/CustomAttibute/readme.md -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomAttibute/readme.md.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 7229b998a77aafb4785d8dc91e23d032 3 | TextScriptImporter: 4 | externalObjects: {} 5 | userData: 6 | assetBundleName: 7 | assetBundleVariant: 8 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomInspector.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 6f452953b396b7141a49aa684d77d429 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomInspector/MyTestClass.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using UnityEngine; 3 | namespace ZTools.Editor.Demo 4 | { 5 | public enum ColliderType 6 | { 7 | player, 8 | enemy, 9 | weapon, 10 | detector, 11 | } 12 | 13 | 14 | [Serializable] 15 | public class ChooseType 16 | { 17 | public string name; 18 | public ColliderType type; 19 | public bool isChoose; 20 | 21 | public ChooseType(ColliderType t, bool choose = true) 22 | { 23 | type = t; 24 | name = t.ToString(); 25 | isChoose = choose; 26 | } 27 | 28 | public override string ToString() 29 | { 30 | return name + "," + isChoose.ToString(); 31 | } 32 | } 33 | 34 | 35 | public class MyTestClass : MonoBehaviour 36 | { 37 | //private field must be SerializeField to be viable from editor script 38 | [SerializeField] private ChooseType[] _correspondType; 39 | [SerializeField] private ColliderType _selfType = ColliderType.player;//default value 40 | 41 | 42 | public bool canEdit = true; 43 | 44 | public string infoStr = "Click it on to enable editing!"; 45 | 46 | 47 | public void resetCorrespondType() 48 | { 49 | UnityEngine.Debug.Log(gameObject.name + ", resetCollisionFrom. selfType:" + _selfType.ToString()); 50 | resetCorrespondType(_selfType); 51 | } 52 | 53 | //will call in compnent menu -> Reset 54 | private void Reset() 55 | { 56 | resetCorrespondType(); 57 | } 58 | 59 | //reset _correspondType to default settings 60 | private void resetCorrespondType(ColliderType selfType) 61 | { 62 | switch (selfType) 63 | { 64 | case ColliderType.player: 65 | _correspondType = new ChooseType[] { new ChooseType(ColliderType.weapon), new ChooseType(ColliderType.enemy) }; 66 | break; 67 | 68 | case ColliderType.enemy: 69 | _correspondType = new ChooseType[] { new ChooseType(ColliderType.weapon), new ChooseType(ColliderType.player) }; 70 | break; 71 | 72 | case ColliderType.weapon: 73 | _correspondType = new ChooseType[] { new ChooseType(ColliderType.player)}; 74 | break; 75 | case ColliderType.detector: 76 | _correspondType = new ChooseType[] { new ChooseType(ColliderType.player), new ChooseType(ColliderType.enemy) }; 77 | break; 78 | default: 79 | break; 80 | } 81 | } 82 | 83 | 84 | } 85 | } -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomInspector/MyTestClass.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 329f24e5111eb89459795c945d9b7e93 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomInspector/MyTestClassEditor.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | using UnityEditor; 3 | using ZTools.Editor.Demo; 4 | 5 | namespace ZTools.Editor.CustomInspector 6 | { 7 | //show MyTestClass._selfType, and show diffrent _correspondType according to _selfType's value 8 | [CustomEditor(typeof(MyTestClass))] 9 | public class CollisionJudgeAbilityEditor: UnityEditor.Editor 10 | { 11 | SerializedProperty selfType; 12 | SerializedProperty correspondTypes; 13 | SerializedProperty canEdit; 14 | SerializedProperty infoStr; 15 | 16 | void OnEnable() 17 | { 18 | selfType = serializedObject.FindProperty("_selfType"); 19 | correspondTypes = serializedObject.FindProperty("_correspondType"); 20 | canEdit = serializedObject.FindProperty("canEdit"); 21 | infoStr = serializedObject.FindProperty("infoStr"); 22 | } 23 | 24 | public override void OnInspectorGUI() 25 | { 26 | serializedObject.Update(); //sync from object 27 | 28 | EditorGUILayout.PropertyField(canEdit);//show selfType using default style 29 | 30 | GUI.enabled = canEdit.boolValue; //disable editing following items, use GUI.enable = true to re-enable. 31 | 32 | if (!canEdit.boolValue) 33 | { 34 | EditorGUILayout.LabelField(infoStr.stringValue);//only show if canEdit == false 35 | } 36 | 37 | EditorGUI.BeginChangeCheck(); // detect whether selftype has changed 38 | 39 | EditorGUILayout.PropertyField(selfType, new GUIContent("SelfType =>"));//show selfType using default style, but using another label. 40 | 41 | serializedObject.ApplyModifiedProperties(); //write to object now because object resetCollisionFrom() need to use new value to do sth. 42 | serializedObject.Update(); //sync from object 43 | 44 | if (EditorGUI.EndChangeCheck()) 45 | { 46 | (target as MyTestClass)?.resetCorrespondType();//refresh 47 | } 48 | 49 | show(correspondTypes); 50 | 51 | serializedObject.ApplyModifiedProperties();// write to object 52 | } 53 | 54 | 55 | private void show(SerializedProperty ChooseTypeArray) 56 | { 57 | GUILayout.Space(10); 58 | GUILayout.Label("Can collide with:"); 59 | GUILayout.BeginVertical(); 60 | for (int i = 0; i < ChooseTypeArray.arraySize; i++) 61 | { 62 | EditorGUILayout.BeginHorizontal(); 63 | 64 | EditorGUILayout.LabelField(ChooseTypeArray.GetArrayElementAtIndex(i).FindPropertyRelative("name").stringValue, GUILayout.Width(100)); 65 | 66 | //show bool value and sync to SerializedProperty (not directly to object) 67 | ChooseTypeArray.GetArrayElementAtIndex(i).FindPropertyRelative("isChoose").boolValue = EditorGUILayout.Toggle(ChooseTypeArray.GetArrayElementAtIndex(i).FindPropertyRelative("isChoose").boolValue); 68 | 69 | EditorGUILayout.EndHorizontal(); 70 | } 71 | GUILayout.EndVertical(); 72 | } 73 | } 74 | } -------------------------------------------------------------------------------- /Assets/ZTools/Editor/CustomInspector/MyTestClassEditor.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 9ce5857f8a1cb6e498eea323c2129835 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 01381a1b63aba8148b796d092d057f93 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/ActionSequence.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 9417c81fff9c2a54aa24007f7a915af1 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/ActionSequence/ActionSequence.cs: -------------------------------------------------------------------------------- 1 | using System.Collections; 2 | using System.Collections.Generic; 3 | using UnityEngine; 4 | using System; 5 | using ZTools.Debug; 6 | 7 | namespace ZTools.Game 8 | { 9 | /// 10 | /// Chains some actions sequentially ( with less coding than coroutine). 11 | /// 12 | /// - How to use: 13 | /// 14 | /// ActionSequence seq = ActionSequenceManager.create(); 15 | /// seq.Then(()=> dosth)).Then(doCoroutine()).Then(new WaitForSeconds(1f)); 16 | /// seq.Run(); 17 | /// 18 | /// - Notice: 19 | /// 20 | /// You'd better **not cache** seq as class member or sth in order to reuse, 21 | /// because seq's life is controlled by its manager, not you. 22 | /// 23 | /// - Support action type: 24 | /// 25 | /// Normal function、IEnumerator、YieldInstruction、CustomYieldInstruction. 26 | /// 27 | /// - Support feature: 28 | /// 29 | /// Callback after one action finish. 30 | /// Nested seq. 31 | /// 32 | public class ActionSequence : MonoBehaviour 33 | { 34 | class ActionItem 35 | { 36 | public string name; 37 | public IEnumerator coroutine; 38 | public YieldInstruction yieldInstruction; 39 | public CustomYieldInstruction customYield; 40 | public Action func; 41 | public Action funcWithParam; 42 | public Action funcWithParamAndCallBack; 43 | 44 | public object param; 45 | public float timeOut; //not used now. in case of blocking 46 | 47 | System.Text.StringBuilder _sb = new System.Text.StringBuilder(); 48 | 49 | public ActionItem() 50 | { 51 | coroutine = null; 52 | func = null; 53 | funcWithParamAndCallBack = null; 54 | funcWithParam = null; 55 | 56 | param = null; 57 | timeOut = -1f; 58 | } 59 | 60 | 61 | public override string ToString() 62 | { 63 | _sb.Length = 0; 64 | 65 | if (func != null) 66 | { 67 | string s = func.Method.Name; 68 | if (s.StartsWith("<")) 69 | { 70 | _sb.Append("Anomymous Func:"); 71 | } 72 | _sb.Append(s); 73 | } 74 | else if (yieldInstruction != null) 75 | { 76 | var type = yieldInstruction.GetType(); 77 | if (type == typeof(WaitForSeconds)) 78 | { 79 | var prop = typeof(WaitForSeconds).GetField("m_Seconds", 80 | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); 81 | var va = prop.GetValue(yieldInstruction); 82 | string s = va.ToString(); 83 | 84 | _sb.Append("WaitForSeconds: "); 85 | _sb.Append(s); 86 | } 87 | 88 | } 89 | 90 | return _sb.ToString(); 91 | } 92 | } 93 | 94 | private Queue _actionSequence = new Queue(); 95 | 96 | public bool IsFinshed { get; set; }//lifecycle must be controlled by ActionSequenceManager. 97 | 98 | public event Action OnFinished; 99 | 100 | 101 | #region public func 102 | 103 | public void Run() 104 | { 105 | DoNextAction(); 106 | } 107 | 108 | 109 | public void Stop() 110 | { 111 | StopAllCoroutines(); 112 | _actionSequence.Clear(); 113 | OnFinished?.Invoke(this); 114 | } 115 | 116 | 117 | public ActionSequence Then(IEnumerator enumerator) 118 | { 119 | if (enumerator != null) 120 | { 121 | ActionItem item = new ActionItem 122 | { 123 | name = enumerator.ToString(), 124 | coroutine = enumerator 125 | }; 126 | Enqueue(item); 127 | } 128 | return this; 129 | } 130 | 131 | 132 | public ActionSequence Then(YieldInstruction yieldInstruction) 133 | { 134 | if (yieldInstruction != null) 135 | { 136 | ActionItem item = new ActionItem 137 | { 138 | name = yieldInstruction.ToString(), 139 | yieldInstruction = yieldInstruction, 140 | }; 141 | Enqueue(item); 142 | } 143 | 144 | return this; 145 | } 146 | 147 | 148 | public ActionSequence Then(CustomYieldInstruction customYield) 149 | { 150 | if (customYield != null) 151 | { 152 | ActionItem item = new ActionItem 153 | { 154 | name = customYield.ToString(), 155 | customYield = customYield, 156 | }; 157 | Enqueue(item); 158 | } 159 | return this; 160 | } 161 | 162 | 163 | public ActionSequence Then(Action func) 164 | { 165 | if (func != null) 166 | { 167 | ActionItem item = new ActionItem 168 | { 169 | name = func.ToString(), 170 | func = func, 171 | }; 172 | Enqueue(item); 173 | } 174 | return this; 175 | } 176 | 177 | 178 | public ActionSequence Then(Action func, object param1) 179 | { 180 | if (func != null) 181 | { 182 | ActionItem item = new ActionItem 183 | { 184 | name = $"{func.ToString()} with param", 185 | funcWithParam = func, 186 | param = param1, 187 | }; 188 | Enqueue(item); 189 | } 190 | return this; 191 | } 192 | 193 | 194 | public ActionSequence Then(Action func, object param, Action myCallBack) 195 | { 196 | if (func != null) 197 | { 198 | ActionItem item = new ActionItem 199 | { 200 | name = $"{func.ToString()} with param & callback", 201 | funcWithParamAndCallBack = func, 202 | func = myCallBack, 203 | param = param, 204 | }; 205 | Enqueue(item); 206 | } 207 | return this; 208 | } 209 | 210 | #endregion 211 | 212 | 213 | #region private func 214 | 215 | private void Enqueue(ActionItem item) 216 | { 217 | IsFinshed = false; 218 | 219 | ZLog.log($"[{GetInstanceID().ToString()}] dequeue:{item.ToString()}"); 220 | 221 | _actionSequence.Enqueue(item); 222 | } 223 | 224 | 225 | private void DoNextAction() 226 | { 227 | if (_actionSequence.Count > 0) 228 | { 229 | ActionItem item = _actionSequence.Peek(); 230 | _actionSequence.Dequeue(); 231 | 232 | ZLog.log($"[{GetInstanceID().ToString()}] dequeue:{item.ToString()}"); 233 | 234 | // exceptions may raise, but ActionSequence should keep operating. 235 | try 236 | { 237 | if (item.funcWithParamAndCallBack != null) 238 | { 239 | item.funcWithParamAndCallBack(item.param, item.func); 240 | FinishOne(); 241 | } 242 | else if (item.funcWithParam != null) 243 | { 244 | item.funcWithParam(item.param); 245 | FinishOne(); 246 | } 247 | else if (item.func != null) 248 | { 249 | item.func(); 250 | FinishOne(); 251 | } 252 | else if (item.coroutine != null) 253 | { 254 | StartCoroutine(DoItemCoroutine(item)); 255 | } 256 | else if (item.yieldInstruction != null) 257 | { 258 | StartCoroutine(DoItemYieldInstruction(item)); 259 | } 260 | else if (item.customYield != null) 261 | { 262 | StartCoroutine(DoItemCustomYieldInstruction(item)); 263 | } 264 | } 265 | catch(Exception e) 266 | { 267 | ZLog.warn(e.ToString()); 268 | OnFinished?.Invoke(this); 269 | } 270 | } 271 | else 272 | { 273 | OnFinished?.Invoke(this); 274 | } 275 | } 276 | 277 | 278 | private void FinishOne() 279 | { 280 | //ZLog.log("finishOne, rest action =", _actionSequence.Count.ToString()); 281 | ZLog.log($"[{GetInstanceID().ToString()}] finishOne, rest action = { _actionSequence.Count.ToString()}"); 282 | 283 | DoNextAction(); 284 | } 285 | 286 | 287 | private IEnumerator DoItemCoroutine(ActionItem item) 288 | { 289 | yield return item.coroutine; 290 | FinishOne(); 291 | } 292 | 293 | 294 | private IEnumerator DoItemYieldInstruction(ActionItem item) 295 | { 296 | yield return item.yieldInstruction; 297 | FinishOne(); 298 | } 299 | 300 | 301 | private IEnumerator DoItemCustomYieldInstruction(ActionItem item) 302 | { 303 | yield return item.customYield; 304 | FinishOne(); 305 | } 306 | #endregion 307 | 308 | 309 | } 310 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/ActionSequence/ActionSequence.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: f9222ed7894e73a4ea36c0e0e1d9e585 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/ActionSequence/ActionSequenceManager.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using UnityEngine; 3 | 4 | namespace ZTools.Game 5 | { 6 | /// 7 | /// All ActionSequence objects run on this manager, and can be reused if you turn on "reuse". 8 | /// 9 | /// TODO:when gameobject that calls the ActionSequence destroys, ActionSequenceManager should auto finish corresponding ActionSequence. 10 | /// So far, the gameobject should take this responsibility. 11 | /// 12 | public class ActionSequenceManager : MonoBehaviour 13 | { 14 | private static List _allSeq = new List(); 15 | private static ActionSequenceManager _instance; 16 | 17 | public static bool reuse = false; 18 | 19 | public static ActionSequence Create() 20 | { 21 | if (_instance == null) 22 | { 23 | GameObject obj = new GameObject 24 | { 25 | name = "ActionSequenceManager" 26 | }; 27 | //obj.hideFlags = HideFlags.HideInHierarchy; 28 | _instance = obj.AddComponent(); 29 | } 30 | 31 | ActionSequence newSeq = null; 32 | 33 | if (reuse) 34 | { 35 | for (int i = 0; i < _allSeq.Count; i++) 36 | { 37 | if (_allSeq[i].IsFinshed) 38 | { 39 | newSeq = _allSeq[i]; 40 | break; 41 | } 42 | } 43 | } 44 | 45 | if (newSeq == null) 46 | { 47 | newSeq = _instance.gameObject.AddComponent(); 48 | _allSeq.Add(newSeq); 49 | } 50 | 51 | newSeq.OnFinished += onFinish; 52 | newSeq.IsFinshed = false; 53 | 54 | return newSeq; 55 | } 56 | 57 | 58 | private static void onFinish(ActionSequence seq) 59 | { 60 | seq.IsFinshed = true; 61 | seq.OnFinished -= onFinish; 62 | 63 | if (!reuse) 64 | { 65 | _allSeq.Remove(seq); 66 | Destroy(seq); 67 | } 68 | } 69 | } 70 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/ActionSequence/ActionSequenceManager.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 8550b2ddd32e694479db853b925cd081 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: e1cac51b26532d34a8cbda51397aba53 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision/CollisionAbility.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using UnityEngine; 3 | using ZTools.Editor.CustomAttribute; 4 | using ZTools.Debug; 5 | 6 | namespace ZTools.Game.Collision 7 | { 8 | /// 9 | /// You may use this enum to identify colliders, 10 | /// or just delete this and use tags instead. 11 | /// 12 | public enum ColliderType 13 | { 14 | none, 15 | hero, 16 | sword, 17 | enemy, 18 | } 19 | 20 | /// 21 | /// Collision filtering takes 2 step: 22 | /// 1. Use Layer collision matrix defined in project settings. 23 | /// 2. TypeTest (Optional) using self-defined matrix. 24 | /// 3. ExclusiveTest (Optional). 25 | /// 26 | /// However, there is dispute in step 2's necessity and redundance, 27 | /// since listerners of OnGameCollisionEnter event always need to 28 | /// use "if" to filter different types for different game logic. 29 | /// 30 | /// 31 | public class CollisionAbility : BaseAbility 32 | { 33 | 34 | /// 35 | /// 2D and 3D objects cannot collide together. 36 | /// 37 | public bool Is2DMode = true; 38 | 39 | /// 40 | /// Use user-defined collision matrix to filter collision. 41 | /// You can turn it off if you find it's annoying. 42 | /// 43 | public bool UseTypeTest = true; 44 | 45 | /// 46 | /// The value "true" means this object can only be in one pair of collision. 47 | /// For example, 48 | /// A collide with B and C simultaneously, which means there are 2 pair of collisions. 49 | /// If we use exclusive test, A will only handle the first collision with B or C. 50 | /// 51 | public bool UseExclusiveTest = false; 52 | 53 | /// 54 | /// Turn it on to receive both collison and trigger event. 55 | /// 56 | public bool CanReceiveBothCollisionAndTrigger = true; 57 | 58 | /// 59 | /// Sometimes when handling a pair of collision, 60 | /// we want to block out all other collision without calling UnInit(). 61 | /// 62 | /// Assign this value to false in this scenario. 63 | /// 64 | /// e.g. when an enemy dies, it may no longer collide with other weapon according to your game design, 65 | /// but if you use FSM, it will turn to dead state in next frame, so weapon still collides in this frame. 66 | /// If you call UnInit() immediately, it may cause none object reference error in another BaseObject's script, 67 | /// since ontrigger function's order is ramdom in one collision pair. 68 | /// 69 | [ReadOnly] public bool CanReceiveMoreCollision = false; 70 | 71 | 72 | public event Action OnGameCollisionEnter; 73 | public event Action OnGameCollisionExit; 74 | 75 | public ColliderType Type { get { return _type; } } 76 | [SerializeField] private ColliderType _type = ColliderType.none; //modify in editor 77 | 78 | public override void Init(BaseObject ownerObject) 79 | { 80 | base.Init(ownerObject); 81 | CanReceiveMoreCollision = true; 82 | } 83 | 84 | public override void UnInit() 85 | { 86 | base.UnInit(); 87 | CanReceiveMoreCollision = false; 88 | } 89 | 90 | #region Unity Collision Enter event 91 | 92 | private void OnCollisionEnter(UnityEngine.Collision other) 93 | { 94 | if (!HasInit || other == null) { return; } 95 | if (Is2DMode) { return; } 96 | 97 | CollisionAbility ca = other.gameObject.GetComponent(); 98 | ProcessCollisionEnter(ca); 99 | } 100 | private void OnCollisionEnter2D(Collision2D other) 101 | { 102 | if (!HasInit || other == null) { return; } 103 | if (!Is2DMode) { return; } 104 | 105 | CollisionAbility ca = other.gameObject.GetComponent(); 106 | ProcessCollisionEnter(ca); 107 | } 108 | private void OnTriggerEnter(Collider other) 109 | { 110 | if (!HasInit || other == null) { return; } 111 | if (Is2DMode) { return; } 112 | 113 | if (CanReceiveBothCollisionAndTrigger) 114 | { 115 | CollisionAbility ca = other.gameObject.GetComponent(); 116 | ProcessCollisionEnter(ca); 117 | } 118 | 119 | } 120 | private void OnTriggerEnter2D(Collider2D other) 121 | { 122 | if (!HasInit || other == null) { return; } 123 | if (!Is2DMode) { return; } 124 | 125 | if (CanReceiveBothCollisionAndTrigger) 126 | { 127 | CollisionAbility ca = other.gameObject.GetComponent(); 128 | ProcessCollisionEnter(ca); 129 | } 130 | } 131 | #endregion 132 | 133 | #region Unity Collison Exit event 134 | 135 | private void OnCollisionExit(UnityEngine.Collision other) 136 | { 137 | if (!HasInit || other == null) { return; } 138 | if (Is2DMode) { return; } 139 | 140 | CollisionAbility ca = other.gameObject.GetComponent(); 141 | ProcessCollisionExit(ca); 142 | } 143 | private void OnCollisionExit2D(Collision2D other) 144 | { 145 | if (!HasInit || other == null) { return; } 146 | if (!Is2DMode) { return; } 147 | 148 | CollisionAbility ca = other.gameObject.GetComponent(); 149 | ProcessCollisionExit(ca); 150 | } 151 | private void OnTriggerExit(Collider other) 152 | { 153 | if (!HasInit || other == null) { return; } 154 | if (Is2DMode) { return; } 155 | 156 | if (CanReceiveBothCollisionAndTrigger) 157 | { 158 | CollisionAbility ca = other.gameObject.GetComponent(); 159 | ProcessCollisionExit(ca); 160 | } 161 | } 162 | private void OnTriggerExit2D(Collider2D other) 163 | { 164 | if (!HasInit || other == null) { return; } 165 | if (!Is2DMode) { return; } 166 | 167 | if (CanReceiveBothCollisionAndTrigger) 168 | { 169 | CollisionAbility ca = other.gameObject.GetComponent(); 170 | ProcessCollisionExit(ca); 171 | } 172 | } 173 | 174 | #endregion 175 | 176 | 177 | private void ProcessCollisionEnter(CollisionAbility other) 178 | { 179 | if (CanCollideWith(other)) 180 | { 181 | OnGameCollisionEnter?.Invoke(other); 182 | } 183 | } 184 | 185 | 186 | private void ProcessCollisionExit(CollisionAbility other) 187 | { 188 | if (CanCollideWith(other)) 189 | { 190 | OnGameCollisionExit?.Invoke(other); 191 | } 192 | } 193 | 194 | 195 | private bool CanCollideWith(CollisionAbility other) 196 | { 197 | if (!HasInit || other == null) { return false; } 198 | 199 | bool passTypeTest = UseTypeTest ? 200 | GamePlay.instance.collisionManager.CanPassTypeTest(this, other) : true; 201 | 202 | if (passTypeTest) 203 | { 204 | bool passExclusiveTest = UseExclusiveTest ? 205 | GamePlay.instance.collisionManager.CanPassExclusiveTest(this, other) : true; 206 | 207 | if (passExclusiveTest) 208 | { 209 | return true; 210 | } 211 | else 212 | { 213 | ZLog.log(owner.name, "fails Exclusive Test with:", other.owner.name); 214 | } 215 | } 216 | else 217 | { 218 | ZLog.log(owner.name, "fails Type Test with type:", other.Type); 219 | } 220 | return false; 221 | } 222 | } 223 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision/CollisionAbility.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 4460c65dae1355c4fbb810d0426624eb 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision/CollisionConfig.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Text; 4 | using UnityEngine; 5 | 6 | namespace ZTools.Game.Collision 7 | { 8 | /// 9 | /// customized collision matrix. 10 | /// Better not use this because its redundancy will lead to endless confusion. 11 | /// 12 | [CreateAssetMenu(fileName = "NewCollisonConfig", menuName = "ZTools/CollisionConfig")] 13 | public class CollisionConfig : ScriptableObject 14 | { 15 | //Dictionary cannot be serialized in unity, even in your custom editor, it seems to be saved. Use 1-D array instead, cause 2-D array are not supported either. 16 | //[SerializeField] public Dictionary matrix2D = new Dictionary(); 17 | [SerializeField] private bool[] matrixArray; 18 | [SerializeField] public string[] allTypeNames; 19 | 20 | //public int width { get; private set; } // property cannot be serialized in unity. 21 | //public int height { get; private set; } 22 | public int width; 23 | public int height; 24 | 25 | public void init() 26 | { 27 | allTypeNames = Enum.GetNames(typeof(ColliderType)); 28 | width = allTypeNames.Length; 29 | height = allTypeNames.Length; 30 | 31 | //TODO resortName into diffrent layer group 32 | 33 | matrixArray = new bool[width * height]; 34 | 35 | for (int i = 0; i < width; i++) 36 | { 37 | for (int j = 0; j < height; j++) 38 | { 39 | matrixArray[i * height + j] = false; 40 | } 41 | } 42 | } 43 | 44 | //refresh while keep old value as much as you can 45 | public void Refresh() 46 | { 47 | var newNames = Enum.GetNames(typeof(ColliderType)); 48 | 49 | if (nameHasChanged(allTypeNames, newNames)) 50 | { 51 | var oldMatrixDic = new Dictionary>(); 52 | for (int i = 0; i < width; i++) 53 | { 54 | for (int j = 0; j < height; j++) 55 | { 56 | if (matrixArray[i * height + j]) 57 | { 58 | if (!oldMatrixDic.ContainsKey((ColliderType)i)) 59 | { 60 | oldMatrixDic.Add((ColliderType)i, new HashSet()); 61 | } 62 | oldMatrixDic[(ColliderType)i].Add((ColliderType)j); 63 | } 64 | } 65 | } 66 | 67 | allTypeNames = newNames; 68 | width = allTypeNames.Length; 69 | height = width; 70 | 71 | matrixArray = new bool[width * height]; 72 | 73 | for (int i = 0; i < width; i++) 74 | { 75 | for (int j = 0; j < height; j++) 76 | { 77 | if (oldMatrixDic.ContainsKey((ColliderType)i) && oldMatrixDic[(ColliderType)i].Contains((ColliderType)j)) 78 | { 79 | this[i, j] = true; 80 | } 81 | else 82 | { 83 | this[i, j] = false; 84 | } 85 | } 86 | } 87 | } 88 | } 89 | 90 | private bool nameHasChanged(string[] oldName, string[] newName) 91 | { 92 | if (oldName == null || newName == null) { return false; } 93 | 94 | return oldName.Length != newName.Length; //TODO more accurate algorithm to detect difference 95 | } 96 | 97 | public override string ToString() 98 | { 99 | StringBuilder sb = new StringBuilder(); 100 | sb.Append("(width, height) = (").Append(width).Append(", ").Append(height); 101 | for (int i = 0; i < width; i++) 102 | { 103 | for (int j = 0; j < height; j++) 104 | { 105 | if (matrixArray[i * height + j]) 106 | { 107 | sb.Append((ColliderType)i). 108 | Append(" <==> "). 109 | Append((ColliderType)j).Append(", "); 110 | } 111 | } 112 | } 113 | 114 | return sb.ToString(); 115 | } 116 | 117 | public bool this[int i, int j] 118 | { 119 | get 120 | { 121 | if (i < width && j < height && matrixArray != null) 122 | { 123 | return matrixArray[i * height + j]; 124 | } 125 | else 126 | { 127 | return false; 128 | } 129 | } 130 | set 131 | { 132 | if (i < width && j < height && matrixArray != null) 133 | { 134 | matrixArray[i * height + j] = value; 135 | } 136 | } 137 | } 138 | 139 | } 140 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision/CollisionConfig.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 21e0b0e77305dd845b9095687b1a7474 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision/CollisionManager.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using UnityEngine; 3 | using ZTools.Debug; 4 | 5 | namespace ZTools.Game.Collision 6 | { 7 | 8 | /// 9 | /// When 3 object collide in one frame, everyone will receive a collision event. 10 | /// This is not always desirable. 11 | /// Sometimes we want to collision only happen in two object in one frame, 12 | /// Then we need a center to record some info. 13 | /// 14 | /// Notice, the call order of onTriggerEnter function is random ! 15 | /// 16 | /// 17 | public class CollisionManager : MonoBehaviour 18 | { 19 | internal class CollisionPairInfo 20 | { 21 | public CollisionPairInfo(CollisionAbility c1, CollisionAbility c2) 22 | { 23 | _c1 = c1; 24 | _c2 = c2; 25 | } 26 | private CollisionAbility _c1 = null; 27 | private CollisionAbility _c2 = null; 28 | 29 | public bool has(CollisionAbility c) 30 | { 31 | return _c1 == c || _c2 == c; 32 | } 33 | 34 | public bool isEqual(CollisionAbility c1, CollisionAbility c2) 35 | { 36 | if((_c1 == c1 && _c2==c2) || (_c1 == c2 && _c2 == c1)) 37 | { 38 | return true; 39 | } 40 | else 41 | { 42 | return false; 43 | } 44 | } 45 | } 46 | 47 | private static HashSet _beInCollisionCache = new HashSet(); 48 | 49 | [SerializeField] private CollisionConfig _collisionConfig = null; 50 | 51 | //clear before next frame 52 | void LateUpdate() 53 | { 54 | _beInCollisionCache.Clear(); 55 | } 56 | 57 | public bool CanPassTypeTest(CollisionAbility me, CollisionAbility other) 58 | { 59 | if (me == null || other == null) 60 | return false; 61 | 62 | if(_collisionConfig != null) 63 | { 64 | return _collisionConfig[(int)me.Type, (int)other.Type]; 65 | } 66 | else 67 | { 68 | ZLog.warn("no collison config file attached."); 69 | return true; 70 | } 71 | } 72 | 73 | /// 74 | /// c1 and c2 must be in same pair or not recorded at all to return a valid collison 75 | /// 76 | public bool CanPassExclusiveTest(CollisionAbility me, CollisionAbility other) 77 | { 78 | //illegal 79 | if (me == null || other == null /*|| c1.abilityOwner == null || c2.abilityOwner == null*/) 80 | { 81 | return false; 82 | } 83 | 84 | //same pair 85 | foreach (var pairInfo in _beInCollisionCache) 86 | { 87 | if(pairInfo.isEqual(me, other)) 88 | { 89 | return true; 90 | } 91 | } 92 | 93 | //maybe new pair. examine CanCollideMoreInCollision 94 | if(me.CanReceiveMoreCollision && other.CanReceiveMoreCollision) 95 | { 96 | //ZLog.verbose("add", c1.abilityOwner.name, ",", c2.abilityOwner.name); 97 | _beInCollisionCache.Add(new CollisionPairInfo(me, other)); 98 | return true; 99 | } 100 | 101 | return false; 102 | } 103 | } 104 | } 105 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision/CollisionManager.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 99cfd94d8f4e2c2469b5f3ee631ff081 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision/CollisionMath.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | 3 | namespace ZTools.Game.Collision 4 | { 5 | public class CollisionMath 6 | { 7 | private const int MAX_OVERLAPPED_CACHE = 50; 8 | private static Collider2D[] _overlappedCache = new Collider2D[MAX_OVERLAPPED_CACHE]; 9 | 10 | 11 | #region None physics-based method. Only need collider. 12 | 13 | #region Overlaping 14 | 15 | 16 | /// 17 | /// Judge if a point is inside my collider. 18 | /// 19 | /// 20 | public bool IsPointInside(Collider2D my, Vector2 point) 21 | { 22 | return my.OverlapPoint(point); 23 | 24 | } 25 | 26 | /// 27 | /// Get all the filtered colliders that overlap with my collider. 28 | /// 29 | /// filter example: 30 | /// 31 | /// ContactFilter2D filter = new ContactFilter2D(); 32 | /// filter.SetLayerMask(LayerMask.GetMask("Default")); 33 | /// filter.useLayerMask = true; 34 | /// 35 | /// The number of valid results in res array 36 | public int GetAllOverlappedColliders(Collider2D my, ContactFilter2D filter, Collider2D[] res) 37 | { 38 | return my.OverlapCollider(filter, res); 39 | } 40 | 41 | /// 42 | /// Judge if collider other overlaps with my collider after filtering. 43 | /// 44 | /// 45 | public bool IsTwoColliderOverlap(Collider2D my, Collider2D other, ContactFilter2D filter) 46 | { 47 | int num = GetAllOverlappedColliders(my, filter, _overlappedCache); 48 | if (num > 0) 49 | { 50 | for (int i = 0; i < num; i++) 51 | { 52 | if (_overlappedCache[i] == other) 53 | { 54 | return true; 55 | } 56 | } 57 | } 58 | 59 | return false; 60 | } 61 | 62 | #endregion 63 | 64 | 65 | #region Casting 66 | 67 | #endregion 68 | 69 | 70 | #endregion 71 | 72 | 73 | 74 | #region Physics-based method. Need rigidbody and collider. 75 | 76 | #region Ray Casting 77 | 78 | //if (Physics.Raycast(originPos, dir, out hit, range, layerMask )) 79 | //{ 80 | // hit.transform.name 碰到的物体名称 81 | // hit.point 碰撞点 82 | // hit.normal 碰撞点的表面法线(向外) 83 | //} 84 | 85 | #endregion 86 | 87 | #region Shape Casting 88 | 89 | #endregion 90 | 91 | 92 | #endregion 93 | 94 | 95 | } 96 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision/CollisionMath.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 20f3bd2764ecc8b43a5e8476ad0c05b5 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision/Editor.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: a92f9ee6c47572a4fbaf8b32846214a1 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision/Editor/CollisonConfigEditor.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | using UnityEditor; 3 | using ZTools.Game.Collision; 4 | using ZTools.Debug; 5 | 6 | namespace ZTools.Editor 7 | { 8 | [CustomEditor(typeof(CollisionConfig))] 9 | public class CollisonConfigEditor : UnityEditor.Editor 10 | { 11 | bool valueChange = false; 12 | 13 | public override void OnInspectorGUI() 14 | { 15 | CollisionConfig config = target as CollisionConfig; 16 | 17 | GUILayout.Label("Back To Empty state"); 18 | if (GUILayout.Button("init/reset")) 19 | { 20 | config.init(); 21 | ZLog.log(config.ToString()); 22 | } 23 | 24 | GUILayout.Space(20); 25 | GUILayout.Label("Sync if you change ColliderType"); 26 | if (GUILayout.Button("Refresh")) 27 | { 28 | config.Refresh(); 29 | ZLog.log(config.ToString()); 30 | valueChange = true; 31 | } 32 | 33 | GUILayout.Space(20); 34 | if (valueChange) 35 | { 36 | if (GUILayout.Button("Value changed, Click or Press Ctrl + S", GUILayout.Height(50))) 37 | { 38 | valueChange = false; 39 | AssetDatabase.SaveAssets(); 40 | } 41 | } 42 | 43 | show(config); 44 | 45 | EditorUtility.SetDirty(config); //This is very important 46 | 47 | } 48 | 49 | private void show(CollisionConfig config) 50 | { 51 | int labelSize = 50; 52 | // find the longest label 53 | for (int i = 0; i < config.allTypeNames.Length; i++) 54 | { 55 | var textDimensions = GUI.skin.label.CalcSize(new GUIContent(config.allTypeNames[i])); 56 | if (labelSize < textDimensions.x) 57 | labelSize = (int)textDimensions.x; 58 | } 59 | labelSize += 30; 60 | 61 | if(true) 62 | { 63 | int checkboxSize = 16; 64 | int indent = 0; 65 | var topLabelRect = GUILayoutUtility.GetRect(checkboxSize + labelSize, labelSize); 66 | var topLeft = new Vector2(topLabelRect.x, topLabelRect.y); 67 | var y = 0; 68 | for (int i = 0; i < config.allTypeNames.Length; i++) 69 | { 70 | var translate = new Vector3(labelSize + indent + checkboxSize * y + topLeft.x, topLeft.y , 0); 71 | //GUI.matrix = Matrix4x4.TRS(translate, Quaternion.Euler(0, 0, 90), Vector3.one); 72 | GUI.matrix = Matrix4x4.TRS(new Vector3(180+checkboxSize * y, topLeft.y,0), Quaternion.Euler(0, 0, 90), Vector3.one); 73 | GUI.Label(new Rect(0, 0, labelSize, checkboxSize), config.allTypeNames[i], "RightLabel"); 74 | y++; 75 | } 76 | 77 | GUI.matrix = Matrix4x4.identity; 78 | y = 0; 79 | for (int i = 0; i < config.allTypeNames.Length; i++) 80 | { 81 | int x = 0; 82 | var r = GUILayoutUtility.GetRect(indent + checkboxSize * config.allTypeNames.Length + labelSize, checkboxSize); 83 | GUI.Label(new Rect(/*r.x + indent*/0, r.y, labelSize, checkboxSize), config.allTypeNames[i], "RightLabel"); 84 | 85 | for (int j = 0; j < config.allTypeNames.Length; j++) 86 | { 87 | var tooltip = new GUIContent("", config.allTypeNames[i] + " with " + config.allTypeNames[j]); 88 | bool val = getValue(config,i, j); 89 | bool toggle = GUI.Toggle(new Rect(labelSize + indent + r.x + x * checkboxSize, r.y, checkboxSize, checkboxSize), val, tooltip); 90 | if (toggle != val) 91 | { 92 | setValue(config, i, j, toggle); 93 | valueChange = true; 94 | } 95 | x++; 96 | } 97 | y++; 98 | } 99 | 100 | } 101 | 102 | } 103 | 104 | private bool getValue(CollisionConfig config, int i, int j) 105 | { 106 | return config[i,j]; 107 | } 108 | private void setValue(CollisionConfig config, int i, int j, bool value) 109 | { 110 | config[i, j] = value; 111 | } 112 | 113 | } 114 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/Collision/Editor/CollisonConfigEditor.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 7b79e0c7271128645bc9fd310c1e1e10 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: e7b35b9aef55d9940b8de60a830c1a95 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/BaseAbility.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | using ZTools.Debug; 3 | 4 | namespace ZTools.Game 5 | { 6 | /// 7 | /// Base class of some functions added to individual game object. 8 | /// It's driven by BaseObject. 9 | /// 10 | public abstract class BaseAbility : MonoBehaviour 11 | { 12 | public BaseObject owner; 13 | 14 | public bool HasInit { get; private set; } 15 | 16 | public virtual void Init(BaseObject ownerObject) 17 | { 18 | if (HasInit) { ZLog.error("cannot Init twice!"); } 19 | HasInit = true; 20 | owner = ownerObject; 21 | } 22 | 23 | 24 | public virtual void UnInit() 25 | { 26 | if (!HasInit) { ZLog.error("cannot UnInit twice!"); } 27 | HasInit = false; 28 | owner = null; 29 | } 30 | 31 | } 32 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/BaseAbility.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 878907e5a8865d6418f62d25a65146e9 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/BaseActor.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using ZTools.Core; 3 | 4 | namespace ZTools.Game 5 | { 6 | /// 7 | /// Base class of an actor, 8 | /// which can be equiped with some BaseAbilities, and an FSM as AI. 9 | /// 10 | public abstract class BaseActor : BaseObject 11 | { 12 | public override void Init() 13 | { 14 | base.Init(); 15 | 16 | //init ability 17 | //create fsm via FSMFactory 18 | } 19 | 20 | public override void UnInit() 21 | { 22 | base.UnInit(); 23 | 24 | //unInit ability 25 | //stop fsm 26 | } 27 | 28 | } 29 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/BaseActor.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 06a17483f2b41c643bbe86433113f0e6 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/BaseObject.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using UnityEngine; 3 | using ZTools.Debug; 4 | 5 | namespace ZTools.Game 6 | { 7 | class InitException : ApplicationException 8 | { 9 | public InitException(string msg) : base(msg) { } 10 | } 11 | 12 | /// 13 | /// Base class of a individual game object, 14 | /// which has an Guid, and need to be managed (Init/UnInit, Create/Destroy) in your Game. 15 | /// e.g. Enemies, Items, TerrainBlocks, NPCs, etc 16 | /// 17 | /// Do not use UnityEvents like Awake(), Start(), OnDestroy() in subclass, 18 | /// unless no BaseObjectManager is controlling it (if DisposeEvent == null), 19 | /// which means BaseObject should take care of itself. 20 | /// 21 | /// TypeID is used in object pool to identify object's sub-type. 22 | /// For example, Enemy may have an enum EnemyType field called 'type', we can override TypeNum as: 23 | /// public override int TypeID => (int)type 24 | /// 25 | public abstract class BaseObject : MonoBehaviour 26 | { 27 | public ulong GUID { get; private set; } 28 | public abstract int TypeID { get; } 29 | public bool HasInit { get; private set; } 30 | 31 | public event Action DisposeEvent; 32 | 33 | #region Init/UnInit 34 | 35 | 36 | public virtual void Init() 37 | { 38 | if (HasInit) 39 | { 40 | throw new InitException(gameObject.name + " cannot Init twice!"); 41 | } 42 | 43 | HasInit = true; 44 | 45 | // register event listener, init children, etc 46 | } 47 | 48 | 49 | public virtual void UnInit() 50 | { 51 | if (!HasInit) 52 | { 53 | throw new InitException(gameObject.name + " cannot UnInit twice!"); 54 | } 55 | 56 | HasInit = false; 57 | 58 | // do: unregister event listener, uninit children 59 | } 60 | 61 | #endregion 62 | 63 | 64 | 65 | /// 66 | /// call this rather than destroy. 67 | /// 68 | protected void Dispose() 69 | { 70 | if (!HasInit) { ZLog.warn(gameObject.name, "has't Init. Dispose() makes no sense."); return; } 71 | 72 | if (DisposeEvent != null) 73 | { 74 | if (DisposeEvent.GetInvocationList().Length > 1) 75 | { 76 | ZLog.error(gameObject.name, "disposeEvent should only have one listener(Manager)"); 77 | } 78 | 79 | DisposeEvent(GUID); 80 | } 81 | else 82 | { 83 | ZLog.warn(gameObject.name, "no manager attached, destroy itself"); 84 | UnInit(); 85 | Destroy(gameObject); 86 | } 87 | } 88 | 89 | 90 | 91 | } 92 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/BaseObject.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 12916886ac4a8014e9c07dbed9737558 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/BaseObjectFactory.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections; 3 | using System.Collections.Generic; 4 | using UnityEngine; 5 | using ZTools.Debug; 6 | 7 | namespace ZTools.Game 8 | { 9 | /// 10 | /// abstract Factory 11 | /// 12 | /// Use 'int' as subType ID. 13 | /// This is compatible with GameObjectPool. 14 | /// 15 | // child class example: 16 | // public class EnemyFactory : BaseObjectFactory 17 | // { 18 | // protected override void ListToDic() 19 | // { 20 | // if (_prefabList != null) 21 | // { 22 | // for (int i = 0; i < _prefabList.Length; i++) 23 | // { 24 | // _prefabDic.Add(_prefabList[i].type, _prefabList[i]); 25 | // } 26 | // } 27 | // } 28 | // } 29 | public abstract class BaseObjectFactory : MonoBehaviour where T : BaseObject where TEnum : struct, IConvertible 30 | { 31 | private GameObjectPool _pool; 32 | 33 | [Header("Prefab's type is described in itself")] 34 | [SerializeField] protected T[] _prefabList; 35 | protected Dictionary _prefabDic; 36 | 37 | private void Awake() 38 | { 39 | _pool = new GameObjectPool(transform); 40 | _prefabDic = new Dictionary(); 41 | ListToDic(); 42 | } 43 | 44 | private void OnDestroy() 45 | { 46 | _pool.clear(); 47 | _prefabDic.Clear(); 48 | } 49 | 50 | 51 | public T GetObject(TEnum objType, Transform parent, Vector3 pos, bool isLocalPos) 52 | { 53 | int typeID = Convert.ToInt32(objType);// TODO : optimize GC here 54 | 55 | T newObj = _pool.getObject(typeID); 56 | 57 | if (newObj == null && _prefabDic.ContainsKey(typeID)) 58 | { 59 | newObj = GameObject.Instantiate(_prefabDic[typeID]); 60 | } 61 | 62 | if (newObj != null) 63 | { 64 | newObj.transform.SetParent(parent, false); 65 | if (isLocalPos) 66 | { 67 | newObj.transform.localPosition = pos; 68 | } 69 | else 70 | { 71 | newObj.transform.position = pos; 72 | } 73 | } 74 | else 75 | { 76 | ZLog.error(gameObject.name, "generate type failed:", typeID.ToString()); 77 | } 78 | 79 | return newObj; 80 | } 81 | 82 | 83 | public bool ReturnObject(T obj) 84 | { 85 | return _pool.returnObject(obj.TypeID, obj); 86 | } 87 | 88 | //这里通过子类实现来实现,避开在基类中泛型难以转化为具体类型的限制 89 | protected abstract void ListToDic(); 90 | 91 | } 92 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/BaseObjectFactory.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 737be17154dc1c8428eeda34ef5aeab5 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/BaseObjectManager.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using UnityEngine; 4 | 5 | namespace ZTools.Game 6 | { 7 | /// 8 | /// Manage a group of [T]: Create/Destroy, Init/UnInit, 9 | /// Access by GamePlay singleton. e.g. GamePlay.Instance.xxxManager 10 | /// 11 | /// [TEnum] means differenct prefabs that can be create. 12 | /// e.g. EnemyManager can Generate different types of enemies identified by EnemyType Enum. 13 | /// 14 | public abstract class BaseObjectManager where T : BaseObject where TEnum : struct, IConvertible 15 | { 16 | protected Dictionary _allObject = null; 17 | protected BaseObjectFactory _objectFactory = null; 18 | public int ActorNum { get { return _allObject?.Count ?? 0; } } 19 | 20 | 21 | /// 22 | /// if not factory assigned, this manager is unable to generate new actor. 23 | /// 24 | /// 25 | public virtual void Init(BaseObjectFactory factory = null) 26 | { 27 | _objectFactory = factory; 28 | _allObject = new Dictionary(); 29 | } 30 | 31 | public virtual void UnInit() 32 | { 33 | _objectFactory = null; 34 | RemoveALl(); 35 | } 36 | 37 | public bool Has(ulong guid) 38 | { 39 | return _allObject?.ContainsKey(guid) ?? false; 40 | } 41 | 42 | 43 | public virtual T Generate(TEnum objType, Transform parent = null, Vector3 pos = default, bool isLocalPos = true) 44 | { 45 | if (_objectFactory != null) 46 | { 47 | T newObj = _objectFactory.GetObject(objType, parent, pos, isLocalPos); 48 | if (newObj != null) 49 | { 50 | Add(newObj); 51 | return newObj; 52 | } 53 | } 54 | return null; 55 | } 56 | 57 | public void Add(T obj) 58 | { 59 | if (!Has(obj.GUID)) 60 | { 61 | _allObject.Add(obj.GUID, obj); 62 | obj.DisposeEvent += Remove; //will trigger when actor Dispose() 63 | if(!obj.HasInit) 64 | { 65 | obj.Init(); 66 | } 67 | } 68 | } 69 | 70 | public void Remove(ulong guid) 71 | { 72 | if (Has(guid)) 73 | { 74 | T obj = _allObject[guid]; 75 | obj.DisposeEvent -= Remove; 76 | _allObject.Remove(guid); 77 | 78 | if (obj.HasInit) // if actor dispose itself, need not call UnInit() 79 | { 80 | obj.UnInit(); 81 | } 82 | 83 | if (_objectFactory != null) 84 | { 85 | _objectFactory.ReturnObject(obj); 86 | } 87 | else 88 | { 89 | GameObject.Destroy(obj.gameObject); 90 | } 91 | } 92 | } 93 | 94 | private void RemoveALl() 95 | { 96 | //TODO 97 | } 98 | 99 | } 100 | } 101 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/BaseObjectManager.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: ddf7793b63dbf9d4bb3bd0fcea7cd1b1 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/GamePlay.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using UnityEngine; 3 | using ZTools.Core; 4 | using ZTools.Game.Collision; 5 | namespace ZTools.Game 6 | { 7 | /// 8 | /// Global singleton as an etry point, manage in-game modules/submanagers. 9 | /// GamePlay itself has a FSM, which include loading, playing, pause, exit state. 10 | /// 11 | public class GamePlay : MonoBehaviour 12 | { 13 | public static GamePlay instance; 14 | 15 | //public InputManager inputManager { get; private set; } 16 | //public LevelManager levelManager { get; private set; } 17 | //public EnemyManager enemyManager { get; private set; } 18 | public CollisionManager collisionManager { get; private set; } 19 | 20 | public FSM fsm { get; private set; } 21 | 22 | private void Awake() 23 | { 24 | instance = this;//temp 25 | } 26 | 27 | private void Start() 28 | { 29 | //fsm = FSMFactory.createFSM(this, new InitialState(), null); 30 | fsm.Start(); 31 | } 32 | 33 | public void InitGamePlay() 34 | { 35 | //get managers 36 | 37 | 38 | //add listener 39 | } 40 | 41 | public void UnInitGamePlay() 42 | { 43 | fsm.Stop(); fsm = null; 44 | 45 | //remove listener 46 | 47 | } 48 | 49 | } 50 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/GamePlay.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: c572049ea74b2c244b7b829e3887b057 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/Readme.md: -------------------------------------------------------------------------------- 1 | BaseObject -----> BaseObjectManager <----- BaseObjectFactory <------ GameObjectPool 2 | ​ | 3 | | 4 | ​ |------------- BaseActor <---- BaseAbility 5 | <---- BaseFSM -------------------------------------------------------------------------------- /Assets/ZTools/Game/Hierachy/Readme.md.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: b5128875431f63a4a866e948fcc7233c 3 | TextScriptImporter: 4 | externalObjects: {} 5 | userData: 6 | assetBundleName: 7 | assetBundleVariant: 8 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Input.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: e0b2d0c55283cfb4db45f89428cf75a4 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Input/InputManager.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections; 3 | using System.Collections.Generic; 4 | using UnityEngine; 5 | 6 | namespace ZTools.Game 7 | { 8 | public enum RawInputProviderType 9 | { 10 | playerTouch, 11 | playerJoystick, 12 | ai, 13 | } 14 | 15 | public enum RawInputType 16 | { 17 | PressStart, 18 | Press, 19 | PressEnd, 20 | OnButtonDown, 21 | OnButtonUp, 22 | OnButtonPressed 23 | } 24 | 25 | public interface IRawInputProvider 26 | { 27 | RawInputProviderType iType { get; } 28 | event Action OnRawInputEvent; 29 | } 30 | 31 | public interface IRawInputHandler 32 | { 33 | void OnMoveStart(Vector2 point); 34 | void OnMoveEnd(Vector2 point); 35 | void OnMove(Vector2 point, Vector2 externPoint = default); 36 | 37 | void OnButtonDown(int buttonID); 38 | void OnButtonPressed(int buttonID); 39 | void OnButtonUp(int buttonID); 40 | } 41 | 42 | /// 43 | /// unified input type. Use struct to avoid GC 44 | /// 45 | public struct RawInput 46 | { 47 | public RawInputType type; 48 | public bool isOverUI; 49 | public Vector2 vec2Data; //screen position 50 | public Vector2 vec2ExtData; 51 | } 52 | 53 | /// 54 | /// switch between different IRawInputProviders. 55 | /// switch between different IRawInputHandlers. 56 | /// 57 | public class InputManager : MonoBehaviour 58 | { 59 | 60 | } 61 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/Input/InputManager.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 589a606924415534fae8b424ecb5634f 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/PersistData.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: afac7035d4a51554c99860282cb8320b 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/PersistData/PersistDataHelper.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using UnityEngine; 4 | using UnityEngine.Events; 5 | using ZTools.Debug; 6 | 7 | namespace ZTools.Game 8 | { 9 | public enum DataLocation 10 | { 11 | memory, 12 | local,//local file 13 | remote,//network 14 | } 15 | 16 | /// 17 | /// BaseClass can be serialized and saved by BasePersistDataHelper 18 | /// 19 | [Serializable] 20 | public abstract class BaseSerializableData 21 | { 22 | public string dataTag; //usually is filename 23 | 24 | } 25 | 26 | 27 | /// 28 | /// can load/save data by BasePersistDataHelper 29 | /// 30 | public interface IDataOwner where T: BaseSerializableData 31 | { 32 | T data { get; set; } 33 | } 34 | 35 | 36 | /// 37 | /// help owner save/load its data. 38 | /// can save/load from different place. 39 | /// 40 | [Serializable] 41 | public abstract class BasePersistDataHelper where OWNER: IDataOwner where DATA : BaseSerializableData 42 | { 43 | public BasePersistDataHelper() 44 | { 45 | datafileName = System.Guid.NewGuid().ToString(); 46 | } 47 | 48 | public BasePersistDataHelper(OWNER owner) 49 | { 50 | datafileName = System.Guid.NewGuid().ToString(); 51 | _owner = owner; 52 | } 53 | 54 | public BasePersistDataHelper(OWNER owner, string fileName) 55 | { 56 | datafileName = fileName; 57 | _owner = owner; 58 | } 59 | 60 | public string datafileName; //also used as id 61 | public DataLocation saveLocation = DataLocation.local; 62 | public DataLocation loadLocation = DataLocation.local; 63 | [SerializeField]private OWNER _owner; 64 | 65 | /// 66 | /// pre-process of serialization 67 | /// 68 | /// 69 | /// 70 | protected virtual DATA encoder(OWNER obj) 71 | { 72 | return obj.data; 73 | } 74 | 75 | /// 76 | /// post-process of deserialization, 77 | /// 78 | /// 79 | /// 80 | /// 81 | protected virtual bool decoder(DATA data, ref OWNER obj) 82 | { 83 | if(data != null) 84 | { 85 | obj.data = data; 86 | return true; 87 | } 88 | else 89 | { 90 | return false; 91 | } 92 | } 93 | 94 | 95 | public bool loadData() 96 | { 97 | if (PersistDataManager.instance.load(datafileName, loadLocation) is DATA data) 98 | { 99 | return decoder(data, ref _owner); 100 | } 101 | else 102 | { 103 | ZLog.error("loadData fail. tag = ", datafileName); 104 | return false; 105 | } 106 | } 107 | 108 | public void saveData() 109 | { 110 | DATA data = encoder(_owner); 111 | if (data != null) 112 | { 113 | PersistDataManager.instance.save(datafileName, data, saveLocation); 114 | } 115 | } 116 | 117 | } 118 | 119 | 120 | 121 | 122 | } 123 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/PersistData/PersistDataHelper.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 06517fc984a9a6d4d91f8276eafaccaf 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/PersistData/PersistDataManager.cs: -------------------------------------------------------------------------------- 1 | using System.Collections; 2 | using System.Collections.Generic; 3 | using System.IO; 4 | using System.Runtime.Serialization.Formatters.Binary; 5 | using UnityEngine; 6 | using ZTools.Debug; 7 | namespace ZTools.Game 8 | { 9 | public enum SerializationMethod 10 | { 11 | json,//doto 12 | bin, 13 | //xml, 14 | //yaml, 15 | } 16 | /// 17 | /// serialization and persist data 18 | /// 19 | public class PersistDataManager 20 | { 21 | public static PersistDataManager instance 22 | { 23 | get 24 | { 25 | if (_instance == null) 26 | { 27 | _instance = new PersistDataManager(); 28 | } 29 | return _instance; 30 | } 31 | } 32 | public static PersistDataManager _instance; 33 | private PersistDataManager() { } 34 | 35 | public SerializationMethod serializationMethod = SerializationMethod.bin; 36 | 37 | //in memory 38 | private Dictionary _dataCache = new Dictionary(); 39 | 40 | #if UNITY_EDITOR 41 | private readonly string _persistPath = Application.dataPath;//rw 42 | 43 | #else 44 | private readonly string _persistPath = Application.persistentDataPath;//rw 45 | 46 | #endif 47 | private readonly string _streamPath = Application.streamingAssetsPath;//r 48 | 49 | #region public 50 | 51 | public void save(string tag, BaseSerializableData data, DataLocation location) 52 | { 53 | data.dataTag = tag; 54 | 55 | if (location == DataLocation.memory) 56 | { 57 | writeCache(tag, data); 58 | } 59 | else if (location == DataLocation.local) 60 | { 61 | writeFile(_persistPath, tag, data); 62 | } 63 | else if (location == DataLocation.remote) 64 | { 65 | ZLog.error("not yet"); 66 | } 67 | } 68 | 69 | 70 | public BaseSerializableData load(string tag, DataLocation location) 71 | { 72 | BaseSerializableData data = null; 73 | 74 | if (location == DataLocation.memory) 75 | { 76 | if (!readCache(tag, out data)) 77 | { 78 | ZLog.log("TODO: cache miss, read from file"); 79 | 80 | } 81 | } 82 | else if (location == DataLocation.local) 83 | { 84 | if (!readFile(_persistPath, tag, out data)) 85 | { 86 | ZLog.warn("TODO: file miss, read from net"); 87 | 88 | } 89 | } 90 | else if (location == DataLocation.remote) 91 | { 92 | ZLog.error("not yet"); 93 | } 94 | 95 | return data; 96 | } 97 | 98 | 99 | /// 100 | /// 一次性将cache所有条目保存到某个位置,然后清除缓存。 101 | /// 102 | public void saveCacheTo(DataLocation location) 103 | { 104 | if (location == DataLocation.local) 105 | { 106 | Directory.CreateDirectory(_persistPath);//如果已经有了就不会创建 107 | string path = _persistPath + "/" + "cache.bytes"; 108 | FileStream stream = new FileStream(path, FileMode.Create);//create new or overwritten 109 | BinaryFormatter formatter = new BinaryFormatter(); 110 | formatter.Serialize(stream, _dataCache); 111 | _dataCache.Clear(); 112 | stream.Close(); 113 | 114 | } 115 | else if (location == DataLocation.remote) 116 | { 117 | ZLog.error("not yet"); 118 | 119 | } 120 | } 121 | 122 | public void loadCacheFrom() 123 | { 124 | string path = _persistPath + "/" + "cache.bytes"; 125 | 126 | if (File.Exists(path)) 127 | { 128 | BinaryFormatter formatter = new BinaryFormatter(); 129 | FileStream stream = new FileStream(path, FileMode.Open); 130 | _dataCache = formatter.Deserialize(stream) as Dictionary; 131 | stream.Close(); 132 | } 133 | 134 | } 135 | 136 | #endregion 137 | 138 | #region private 139 | 140 | private void writeFile(string folder, string tag, BaseSerializableData data) 141 | { 142 | Directory.CreateDirectory(folder);//如果已经有了就不会创建 143 | 144 | string path = _persistPath + "/" + tag + ".bytes"; 145 | FileStream stream = new FileStream(path, FileMode.Create);//create new or overwritten 146 | 147 | if (serializationMethod == SerializationMethod.bin) 148 | { 149 | BinaryFormatter formatter = new BinaryFormatter(); 150 | formatter.Serialize(stream, data); 151 | } 152 | else if(serializationMethod == SerializationMethod.json) 153 | { 154 | //string content = JsonUtility.ToJson(data); 155 | 156 | } 157 | 158 | stream.Close(); 159 | } 160 | 161 | private void writeCache(string tag, BaseSerializableData data) 162 | { 163 | if (_dataCache.ContainsKey(tag)) 164 | { 165 | _dataCache[tag] = data; 166 | } 167 | else 168 | { 169 | _dataCache.Add(tag, data); 170 | } 171 | } 172 | 173 | private bool readCache(string tag, out BaseSerializableData data) 174 | { 175 | data = null; 176 | 177 | if (_dataCache.ContainsKey(tag)) 178 | { 179 | data = _dataCache[tag]; 180 | return true; 181 | } 182 | 183 | return false; 184 | } 185 | 186 | private bool readFile(string folder, string tag, out BaseSerializableData data) 187 | { 188 | data = null; 189 | 190 | string path = folder + "/" + tag + ".bytes"; 191 | 192 | if (File.Exists(path)) 193 | { 194 | FileStream stream = new FileStream(path, FileMode.Open); 195 | if (serializationMethod == SerializationMethod.bin) 196 | { 197 | BinaryFormatter formatter = new BinaryFormatter(); 198 | data = formatter.Deserialize(stream) as BaseSerializableData; 199 | 200 | } 201 | else if(serializationMethod == SerializationMethod.json) 202 | { 203 | 204 | } 205 | 206 | stream.Close(); 207 | return true; 208 | } 209 | 210 | return false; 211 | } 212 | 213 | //private bool readNetwork()//TODO 异步回调 214 | 215 | #endregion 216 | 217 | 218 | } 219 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/PersistData/PersistDataManager.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 5c82fa6ade3657349818201e555ee1ac 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Pool.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: f1c73ae63aaa7f3429eb912b94168bed 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/Pool/GameObjectPool.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections; 3 | using System.Collections.Generic; 4 | using UnityEngine; 5 | 6 | namespace ZTools.Game 7 | { 8 | /// 9 | /// GameObjectPool for Monobehavior. 10 | /// 11 | /// Use 'int' as subType ID. 12 | /// This is useful when put different types of Enemy in same pool 13 | /// 14 | public class GameObjectPool where T : MonoBehaviour 15 | { 16 | public GameObjectPool(Transform root) 17 | { 18 | poolRoot = root; 19 | _pool = new Dictionary>(); 20 | } 21 | 22 | public Transform poolRoot { get; private set; } 23 | private Dictionary> _pool; 24 | 25 | public T getObject(int type, bool needSetActive = true) 26 | { 27 | T retObj = null; 28 | 29 | if (_pool.ContainsKey(type) && _pool[type] != null && _pool[type].Count > 0) 30 | { 31 | retObj = _pool[type][0]; 32 | if (needSetActive) 33 | { 34 | retObj.gameObject.SetActive(true); 35 | } 36 | 37 | _pool[type].RemoveAt(0); 38 | } 39 | 40 | return retObj; 41 | } 42 | 43 | public bool returnObject(int type, T obj) 44 | { 45 | if (obj == null) { return false; } 46 | 47 | obj.transform.SetParent(poolRoot, false); 48 | obj.transform.localPosition = Vector3.zero; 49 | obj.gameObject.SetActive(false); 50 | 51 | if (!_pool.ContainsKey(type)) 52 | { 53 | _pool.Add(type, new List { obj }); 54 | } 55 | else 56 | { 57 | _pool[type].Add(obj); 58 | } 59 | 60 | 61 | 62 | return true; 63 | } 64 | 65 | public void clear() 66 | { 67 | _pool.Clear(); 68 | } 69 | } 70 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/Pool/GameObjectPool.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 44244ccfb6ed65e4eb888b72ff4aac88 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/ReactSystem.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 6aad0fd0caa7aae4c8193656d1ef45e4 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/UI.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 42a71cf114a4e074aab5aed8d8dfd30b 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Game/UI/ButtonGroupClick.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | using UnityEngine.UI; 3 | namespace ZTools.UIUtility 4 | { 5 | /// 6 | /// Multiple buttons share one handler with different data passed into it. 7 | /// 8 | public class ButtonGroupClick : MonoBehaviour 9 | { 10 | public Button[] buttons; 11 | 12 | private void Awake() 13 | { 14 | for (int i = 0; i < buttons.Length; i++) 15 | { 16 | int _i = i;//must do this, or it will always pass buttons.Length into handler(i) 17 | buttons[i].onClick.AddListener(delegate () { hander(_i); }); 18 | } 19 | } 20 | 21 | private void hander(int idx) 22 | { 23 | UnityEngine.Debug.Log("idx = " + idx.ToString()); 24 | UnityEngine.Debug.Log("You clicked button:" + buttons[idx].name); 25 | } 26 | } 27 | } -------------------------------------------------------------------------------- /Assets/ZTools/Game/UI/ButtonGroupClick.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 2311faeffaab39443b3e4cefb5745bcd 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ZTools/Plugin.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: dc6a0b9b4f6a76c40863fdd45f0db038 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Plugin/Animation.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 5be3a29334745fb48917058ab6bb9908 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Plugin/Animation/DOTween Pro 0.9.690.unitypackage: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pps43/ZToolsForUnity/a49170d2a8246b4fec630b65e4b95d6f38d75406/Assets/ZTools/Plugin/Animation/DOTween Pro 0.9.690.unitypackage -------------------------------------------------------------------------------- /Assets/ZTools/Plugin/Animation/DOTween Pro 0.9.690.unitypackage.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: ba5a6cf4afff35941a7b84e8a07e0d29 3 | DefaultImporter: 4 | externalObjects: {} 5 | userData: 6 | assetBundleName: 7 | assetBundleVariant: 8 | -------------------------------------------------------------------------------- /Assets/ZTools/Plugin/Optimize Sprite Mesh.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 8846abef5ee5c3048b830c8979d0cb64 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ZTools/Plugin/Optimize Sprite Mesh/SpriteSharp Mesh Optimizer.unitypackage: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pps43/ZToolsForUnity/a49170d2a8246b4fec630b65e4b95d6f38d75406/Assets/ZTools/Plugin/Optimize Sprite Mesh/SpriteSharp Mesh Optimizer.unitypackage -------------------------------------------------------------------------------- /Assets/ZTools/Plugin/Optimize Sprite Mesh/SpriteSharp Mesh Optimizer.unitypackage.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: b8aa85f293dc39e41ad97be1cb62157e 3 | DefaultImporter: 4 | externalObjects: {} 5 | userData: 6 | assetBundleName: 7 | assetBundleVariant: 8 | -------------------------------------------------------------------------------- /Assets/ZTools/ZToolsAssembly.asmdef: -------------------------------------------------------------------------------- 1 | { 2 | "name": "ZToolsAssembly" 3 | } 4 | -------------------------------------------------------------------------------- /Assets/ZTools/ZToolsAssembly.asmdef.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 7fc9a8723e354c545aa473601a494f5b 3 | AssemblyDefinitionImporter: 4 | externalObjects: {} 5 | userData: 6 | assetBundleName: 7 | assetBundleVariant: 8 | -------------------------------------------------------------------------------- /Packages/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "dependencies": { 3 | "com.unity.2d.sprite": "1.0.0", 4 | "com.unity.2d.tilemap": "1.0.0", 5 | "com.unity.ads": "3.7.5", 6 | "com.unity.analytics": "3.5.3", 7 | "com.unity.collab-proxy": "1.7.1", 8 | "com.unity.ide.rider": "2.0.7", 9 | "com.unity.ide.visualstudio": "2.0.11", 10 | "com.unity.ide.vscode": "1.2.3", 11 | "com.unity.purchasing": "3.2.2", 12 | "com.unity.test-framework": "1.1.27", 13 | "com.unity.textmeshpro": "3.0.6", 14 | "com.unity.timeline": "1.4.8", 15 | "com.unity.ugui": "1.0.0", 16 | "com.unity.xr.legacyinputhelpers": "2.1.8", 17 | "com.unity.modules.ai": "1.0.0", 18 | "com.unity.modules.androidjni": "1.0.0", 19 | "com.unity.modules.animation": "1.0.0", 20 | "com.unity.modules.assetbundle": "1.0.0", 21 | "com.unity.modules.audio": "1.0.0", 22 | "com.unity.modules.cloth": "1.0.0", 23 | "com.unity.modules.director": "1.0.0", 24 | "com.unity.modules.imageconversion": "1.0.0", 25 | "com.unity.modules.imgui": "1.0.0", 26 | "com.unity.modules.jsonserialize": "1.0.0", 27 | "com.unity.modules.particlesystem": "1.0.0", 28 | "com.unity.modules.physics": "1.0.0", 29 | "com.unity.modules.physics2d": "1.0.0", 30 | "com.unity.modules.screencapture": "1.0.0", 31 | "com.unity.modules.terrain": "1.0.0", 32 | "com.unity.modules.terrainphysics": "1.0.0", 33 | "com.unity.modules.tilemap": "1.0.0", 34 | "com.unity.modules.ui": "1.0.0", 35 | "com.unity.modules.uielements": "1.0.0", 36 | "com.unity.modules.umbra": "1.0.0", 37 | "com.unity.modules.unityanalytics": "1.0.0", 38 | "com.unity.modules.unitywebrequest": "1.0.0", 39 | "com.unity.modules.unitywebrequestassetbundle": "1.0.0", 40 | "com.unity.modules.unitywebrequestaudio": "1.0.0", 41 | "com.unity.modules.unitywebrequesttexture": "1.0.0", 42 | "com.unity.modules.unitywebrequestwww": "1.0.0", 43 | "com.unity.modules.vehicles": "1.0.0", 44 | "com.unity.modules.video": "1.0.0", 45 | "com.unity.modules.vr": "1.0.0", 46 | "com.unity.modules.wind": "1.0.0", 47 | "com.unity.modules.xr": "1.0.0" 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /ProjectSettings/AudioManager.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!11 &1 4 | AudioManager: 5 | m_ObjectHideFlags: 0 6 | m_Volume: 1 7 | Rolloff Scale: 1 8 | Doppler Factor: 1 9 | Default Speaker Mode: 2 10 | m_SampleRate: 0 11 | m_DSPBufferSize: 1024 12 | m_VirtualVoiceCount: 512 13 | m_RealVoiceCount: 32 14 | m_SpatializerPlugin: 15 | m_AmbisonicDecoderPlugin: 16 | m_DisableAudio: 0 17 | m_VirtualizeEffects: 1 18 | -------------------------------------------------------------------------------- /ProjectSettings/ClusterInputManager.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!236 &1 4 | ClusterInputManager: 5 | m_ObjectHideFlags: 0 6 | m_Inputs: [] 7 | -------------------------------------------------------------------------------- /ProjectSettings/DynamicsManager.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!55 &1 4 | PhysicsManager: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 8 7 | m_Gravity: {x: 0, y: -9.81, z: 0} 8 | m_DefaultMaterial: {fileID: 0} 9 | m_BounceThreshold: 2 10 | m_SleepThreshold: 0.005 11 | m_DefaultContactOffset: 0.01 12 | m_DefaultSolverIterations: 6 13 | m_DefaultSolverVelocityIterations: 1 14 | m_QueriesHitBackfaces: 0 15 | m_QueriesHitTriggers: 1 16 | m_EnableAdaptiveForce: 0 17 | m_ClothInterCollisionDistance: 0 18 | m_ClothInterCollisionStiffness: 0 19 | m_ContactsGeneration: 1 20 | m_LayerCollisionMatrix: ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 21 | m_AutoSimulation: 1 22 | m_AutoSyncTransforms: 0 23 | m_ReuseCollisionCallbacks: 1 24 | m_ClothInterCollisionSettingsToggle: 0 25 | m_ContactPairsMode: 0 26 | m_BroadphaseType: 0 27 | m_WorldBounds: 28 | m_Center: {x: 0, y: 0, z: 0} 29 | m_Extent: {x: 250, y: 250, z: 250} 30 | m_WorldSubdivisions: 8 31 | -------------------------------------------------------------------------------- /ProjectSettings/EditorBuildSettings.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!1045 &1 4 | EditorBuildSettings: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 2 7 | m_Scenes: 8 | - enabled: 0 9 | path: 10 | guid: 00000000000000000000000000000000 11 | - enabled: 1 12 | path: Assets/Demo/Demo_01/DemoScene.unity 13 | guid: e0935558b019b204a896b31d9d9e1835 14 | m_configObjects: {} 15 | -------------------------------------------------------------------------------- /ProjectSettings/EditorSettings.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!159 &1 4 | EditorSettings: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 7 7 | m_ExternalVersionControlSupport: Visible Meta Files 8 | m_SerializationMode: 2 9 | m_LineEndingsForNewScripts: 2 10 | m_DefaultBehaviorMode: 1 11 | m_SpritePackerMode: 4 12 | m_SpritePackerPaddingPower: 1 13 | m_EtcTextureCompressorBehavior: 1 14 | m_EtcTextureFastCompressor: 1 15 | m_EtcTextureNormalCompressor: 2 16 | m_EtcTextureBestCompressor: 4 17 | m_ProjectGenerationIncludedExtensions: txt;xml;fnt;cd 18 | m_ProjectGenerationRootNamespace: 19 | m_UserGeneratedProjectSuffix: 20 | m_CollabEditorSettings: 21 | inProgressEnabled: 1 22 | -------------------------------------------------------------------------------- /ProjectSettings/GraphicsSettings.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!30 &1 4 | GraphicsSettings: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 12 7 | m_Deferred: 8 | m_Mode: 1 9 | m_Shader: {fileID: 69, guid: 0000000000000000f000000000000000, type: 0} 10 | m_DeferredReflections: 11 | m_Mode: 1 12 | m_Shader: {fileID: 74, guid: 0000000000000000f000000000000000, type: 0} 13 | m_ScreenSpaceShadows: 14 | m_Mode: 1 15 | m_Shader: {fileID: 64, guid: 0000000000000000f000000000000000, type: 0} 16 | m_LegacyDeferred: 17 | m_Mode: 1 18 | m_Shader: {fileID: 63, guid: 0000000000000000f000000000000000, type: 0} 19 | m_DepthNormals: 20 | m_Mode: 1 21 | m_Shader: {fileID: 62, guid: 0000000000000000f000000000000000, type: 0} 22 | m_MotionVectors: 23 | m_Mode: 1 24 | m_Shader: {fileID: 75, guid: 0000000000000000f000000000000000, type: 0} 25 | m_LightHalo: 26 | m_Mode: 1 27 | m_Shader: {fileID: 105, guid: 0000000000000000f000000000000000, type: 0} 28 | m_LensFlare: 29 | m_Mode: 1 30 | m_Shader: {fileID: 102, guid: 0000000000000000f000000000000000, type: 0} 31 | m_AlwaysIncludedShaders: 32 | - {fileID: 10753, guid: 0000000000000000f000000000000000, type: 0} 33 | - {fileID: 10770, guid: 0000000000000000f000000000000000, type: 0} 34 | - {fileID: 10783, guid: 0000000000000000f000000000000000, type: 0} 35 | - {fileID: 16000, guid: 0000000000000000f000000000000000, type: 0} 36 | - {fileID: 17000, guid: 0000000000000000f000000000000000, type: 0} 37 | m_PreloadedShaders: [] 38 | m_SpritesDefaultMaterial: {fileID: 10754, guid: 0000000000000000f000000000000000, 39 | type: 0} 40 | m_CustomRenderPipeline: {fileID: 0} 41 | m_TransparencySortMode: 0 42 | m_TransparencySortAxis: {x: 0, y: 0, z: 1} 43 | m_DefaultRenderingPath: 1 44 | m_DefaultMobileRenderingPath: 1 45 | m_TierSettings: [] 46 | m_LightmapStripping: 0 47 | m_FogStripping: 0 48 | m_InstancingStripping: 0 49 | m_LightmapKeepPlain: 1 50 | m_LightmapKeepDirCombined: 1 51 | m_LightmapKeepDynamicPlain: 1 52 | m_LightmapKeepDynamicDirCombined: 1 53 | m_LightmapKeepShadowMask: 1 54 | m_LightmapKeepSubtractive: 1 55 | m_FogKeepLinear: 1 56 | m_FogKeepExp: 1 57 | m_FogKeepExp2: 1 58 | m_AlbedoSwatchInfos: [] 59 | m_LightsUseLinearIntensity: 0 60 | m_LightsUseColorTemperature: 0 61 | -------------------------------------------------------------------------------- /ProjectSettings/InputManager.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!13 &1 4 | InputManager: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 2 7 | m_Axes: 8 | - serializedVersion: 3 9 | m_Name: Horizontal 10 | descriptiveName: 11 | descriptiveNegativeName: 12 | negativeButton: left 13 | positiveButton: right 14 | altNegativeButton: a 15 | altPositiveButton: d 16 | gravity: 3 17 | dead: 0.001 18 | sensitivity: 3 19 | snap: 1 20 | invert: 0 21 | type: 0 22 | axis: 0 23 | joyNum: 0 24 | - serializedVersion: 3 25 | m_Name: Vertical 26 | descriptiveName: 27 | descriptiveNegativeName: 28 | negativeButton: down 29 | positiveButton: up 30 | altNegativeButton: s 31 | altPositiveButton: w 32 | gravity: 3 33 | dead: 0.001 34 | sensitivity: 3 35 | snap: 1 36 | invert: 0 37 | type: 0 38 | axis: 0 39 | joyNum: 0 40 | - serializedVersion: 3 41 | m_Name: Fire1 42 | descriptiveName: 43 | descriptiveNegativeName: 44 | negativeButton: 45 | positiveButton: left ctrl 46 | altNegativeButton: 47 | altPositiveButton: mouse 0 48 | gravity: 1000 49 | dead: 0.001 50 | sensitivity: 1000 51 | snap: 0 52 | invert: 0 53 | type: 0 54 | axis: 0 55 | joyNum: 0 56 | - serializedVersion: 3 57 | m_Name: Fire2 58 | descriptiveName: 59 | descriptiveNegativeName: 60 | negativeButton: 61 | positiveButton: left alt 62 | altNegativeButton: 63 | altPositiveButton: mouse 1 64 | gravity: 1000 65 | dead: 0.001 66 | sensitivity: 1000 67 | snap: 0 68 | invert: 0 69 | type: 0 70 | axis: 0 71 | joyNum: 0 72 | - serializedVersion: 3 73 | m_Name: Fire3 74 | descriptiveName: 75 | descriptiveNegativeName: 76 | negativeButton: 77 | positiveButton: left shift 78 | altNegativeButton: 79 | altPositiveButton: mouse 2 80 | gravity: 1000 81 | dead: 0.001 82 | sensitivity: 1000 83 | snap: 0 84 | invert: 0 85 | type: 0 86 | axis: 0 87 | joyNum: 0 88 | - serializedVersion: 3 89 | m_Name: Jump 90 | descriptiveName: 91 | descriptiveNegativeName: 92 | negativeButton: 93 | positiveButton: space 94 | altNegativeButton: 95 | altPositiveButton: 96 | gravity: 1000 97 | dead: 0.001 98 | sensitivity: 1000 99 | snap: 0 100 | invert: 0 101 | type: 0 102 | axis: 0 103 | joyNum: 0 104 | - serializedVersion: 3 105 | m_Name: Mouse X 106 | descriptiveName: 107 | descriptiveNegativeName: 108 | negativeButton: 109 | positiveButton: 110 | altNegativeButton: 111 | altPositiveButton: 112 | gravity: 0 113 | dead: 0 114 | sensitivity: 0.1 115 | snap: 0 116 | invert: 0 117 | type: 1 118 | axis: 0 119 | joyNum: 0 120 | - serializedVersion: 3 121 | m_Name: Mouse Y 122 | descriptiveName: 123 | descriptiveNegativeName: 124 | negativeButton: 125 | positiveButton: 126 | altNegativeButton: 127 | altPositiveButton: 128 | gravity: 0 129 | dead: 0 130 | sensitivity: 0.1 131 | snap: 0 132 | invert: 0 133 | type: 1 134 | axis: 1 135 | joyNum: 0 136 | - serializedVersion: 3 137 | m_Name: Mouse ScrollWheel 138 | descriptiveName: 139 | descriptiveNegativeName: 140 | negativeButton: 141 | positiveButton: 142 | altNegativeButton: 143 | altPositiveButton: 144 | gravity: 0 145 | dead: 0 146 | sensitivity: 0.1 147 | snap: 0 148 | invert: 0 149 | type: 1 150 | axis: 2 151 | joyNum: 0 152 | - serializedVersion: 3 153 | m_Name: Horizontal 154 | descriptiveName: 155 | descriptiveNegativeName: 156 | negativeButton: 157 | positiveButton: 158 | altNegativeButton: 159 | altPositiveButton: 160 | gravity: 0 161 | dead: 0.19 162 | sensitivity: 1 163 | snap: 0 164 | invert: 0 165 | type: 2 166 | axis: 0 167 | joyNum: 0 168 | - serializedVersion: 3 169 | m_Name: Vertical 170 | descriptiveName: 171 | descriptiveNegativeName: 172 | negativeButton: 173 | positiveButton: 174 | altNegativeButton: 175 | altPositiveButton: 176 | gravity: 0 177 | dead: 0.19 178 | sensitivity: 1 179 | snap: 0 180 | invert: 1 181 | type: 2 182 | axis: 1 183 | joyNum: 0 184 | - serializedVersion: 3 185 | m_Name: Fire1 186 | descriptiveName: 187 | descriptiveNegativeName: 188 | negativeButton: 189 | positiveButton: joystick button 0 190 | altNegativeButton: 191 | altPositiveButton: 192 | gravity: 1000 193 | dead: 0.001 194 | sensitivity: 1000 195 | snap: 0 196 | invert: 0 197 | type: 0 198 | axis: 0 199 | joyNum: 0 200 | - serializedVersion: 3 201 | m_Name: Fire2 202 | descriptiveName: 203 | descriptiveNegativeName: 204 | negativeButton: 205 | positiveButton: joystick button 1 206 | altNegativeButton: 207 | altPositiveButton: 208 | gravity: 1000 209 | dead: 0.001 210 | sensitivity: 1000 211 | snap: 0 212 | invert: 0 213 | type: 0 214 | axis: 0 215 | joyNum: 0 216 | - serializedVersion: 3 217 | m_Name: Fire3 218 | descriptiveName: 219 | descriptiveNegativeName: 220 | negativeButton: 221 | positiveButton: joystick button 2 222 | altNegativeButton: 223 | altPositiveButton: 224 | gravity: 1000 225 | dead: 0.001 226 | sensitivity: 1000 227 | snap: 0 228 | invert: 0 229 | type: 0 230 | axis: 0 231 | joyNum: 0 232 | - serializedVersion: 3 233 | m_Name: Jump 234 | descriptiveName: 235 | descriptiveNegativeName: 236 | negativeButton: 237 | positiveButton: joystick button 3 238 | altNegativeButton: 239 | altPositiveButton: 240 | gravity: 1000 241 | dead: 0.001 242 | sensitivity: 1000 243 | snap: 0 244 | invert: 0 245 | type: 0 246 | axis: 0 247 | joyNum: 0 248 | - serializedVersion: 3 249 | m_Name: Submit 250 | descriptiveName: 251 | descriptiveNegativeName: 252 | negativeButton: 253 | positiveButton: return 254 | altNegativeButton: 255 | altPositiveButton: joystick button 0 256 | gravity: 1000 257 | dead: 0.001 258 | sensitivity: 1000 259 | snap: 0 260 | invert: 0 261 | type: 0 262 | axis: 0 263 | joyNum: 0 264 | - serializedVersion: 3 265 | m_Name: Submit 266 | descriptiveName: 267 | descriptiveNegativeName: 268 | negativeButton: 269 | positiveButton: enter 270 | altNegativeButton: 271 | altPositiveButton: space 272 | gravity: 1000 273 | dead: 0.001 274 | sensitivity: 1000 275 | snap: 0 276 | invert: 0 277 | type: 0 278 | axis: 0 279 | joyNum: 0 280 | - serializedVersion: 3 281 | m_Name: Cancel 282 | descriptiveName: 283 | descriptiveNegativeName: 284 | negativeButton: 285 | positiveButton: escape 286 | altNegativeButton: 287 | altPositiveButton: joystick button 1 288 | gravity: 1000 289 | dead: 0.001 290 | sensitivity: 1000 291 | snap: 0 292 | invert: 0 293 | type: 0 294 | axis: 0 295 | joyNum: 0 296 | -------------------------------------------------------------------------------- /ProjectSettings/NavMeshAreas.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!126 &1 4 | NavMeshProjectSettings: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 2 7 | areas: 8 | - name: Walkable 9 | cost: 1 10 | - name: Not Walkable 11 | cost: 1 12 | - name: Jump 13 | cost: 2 14 | - name: 15 | cost: 1 16 | - name: 17 | cost: 1 18 | - name: 19 | cost: 1 20 | - name: 21 | cost: 1 22 | - name: 23 | cost: 1 24 | - name: 25 | cost: 1 26 | - name: 27 | cost: 1 28 | - name: 29 | cost: 1 30 | - name: 31 | cost: 1 32 | - name: 33 | cost: 1 34 | - name: 35 | cost: 1 36 | - name: 37 | cost: 1 38 | - name: 39 | cost: 1 40 | - name: 41 | cost: 1 42 | - name: 43 | cost: 1 44 | - name: 45 | cost: 1 46 | - name: 47 | cost: 1 48 | - name: 49 | cost: 1 50 | - name: 51 | cost: 1 52 | - name: 53 | cost: 1 54 | - name: 55 | cost: 1 56 | - name: 57 | cost: 1 58 | - name: 59 | cost: 1 60 | - name: 61 | cost: 1 62 | - name: 63 | cost: 1 64 | - name: 65 | cost: 1 66 | - name: 67 | cost: 1 68 | - name: 69 | cost: 1 70 | - name: 71 | cost: 1 72 | m_LastAgentTypeID: -887442657 73 | m_Settings: 74 | - serializedVersion: 2 75 | agentTypeID: 0 76 | agentRadius: 0.5 77 | agentHeight: 2 78 | agentSlope: 45 79 | agentClimb: 0.75 80 | ledgeDropHeight: 0 81 | maxJumpAcrossDistance: 0 82 | minRegionArea: 2 83 | manualCellSize: 0 84 | cellSize: 0.16666667 85 | manualTileSize: 0 86 | tileSize: 256 87 | accuratePlacement: 0 88 | debug: 89 | m_Flags: 0 90 | m_SettingNames: 91 | - Humanoid 92 | -------------------------------------------------------------------------------- /ProjectSettings/NetworkManager.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!149 &1 4 | NetworkManager: 5 | m_ObjectHideFlags: 0 6 | m_DebugLevel: 0 7 | m_Sendrate: 15 8 | m_AssetToPrefab: {} 9 | -------------------------------------------------------------------------------- /ProjectSettings/PackageManagerSettings.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!114 &1 4 | MonoBehaviour: 5 | m_ObjectHideFlags: 61 6 | m_CorrespondingSourceObject: {fileID: 0} 7 | m_PrefabInstance: {fileID: 0} 8 | m_PrefabAsset: {fileID: 0} 9 | m_GameObject: {fileID: 0} 10 | m_Enabled: 1 11 | m_EditorHideFlags: 0 12 | m_Script: {fileID: 13964, guid: 0000000000000000e000000000000000, type: 0} 13 | m_Name: 14 | m_EditorClassIdentifier: 15 | m_EnablePreviewPackages: 0 16 | m_EnablePackageDependencies: 0 17 | m_AdvancedSettingsExpanded: 1 18 | m_ScopedRegistriesSettingsExpanded: 1 19 | oneTimeWarningShown: 0 20 | m_Registries: 21 | - m_Id: main 22 | m_Name: 23 | m_Url: https://packages.unity.cn 24 | m_Scopes: [] 25 | m_IsDefault: 1 26 | m_Capabilities: 7 27 | m_UserSelectedRegistryName: 28 | m_UserAddingNewScopedRegistry: 0 29 | m_RegistryInfoDraft: 30 | m_ErrorMessage: 31 | m_Original: 32 | m_Id: 33 | m_Name: 34 | m_Url: 35 | m_Scopes: [] 36 | m_IsDefault: 0 37 | m_Capabilities: 0 38 | m_Modified: 0 39 | m_Name: 40 | m_Url: 41 | m_Scopes: 42 | - 43 | m_SelectedScopeIndex: 0 44 | -------------------------------------------------------------------------------- /ProjectSettings/Physics2DSettings.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!19 &1 4 | Physics2DSettings: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 4 7 | m_Gravity: {x: 0, y: -9.81} 8 | m_DefaultMaterial: {fileID: 0} 9 | m_VelocityIterations: 8 10 | m_PositionIterations: 3 11 | m_VelocityThreshold: 1 12 | m_MaxLinearCorrection: 0.2 13 | m_MaxAngularCorrection: 8 14 | m_MaxTranslationSpeed: 100 15 | m_MaxRotationSpeed: 360 16 | m_BaumgarteScale: 0.2 17 | m_BaumgarteTimeOfImpactScale: 0.75 18 | m_TimeToSleep: 0.5 19 | m_LinearSleepTolerance: 0.01 20 | m_AngularSleepTolerance: 2 21 | m_DefaultContactOffset: 0.01 22 | m_JobOptions: 23 | serializedVersion: 2 24 | useMultithreading: 0 25 | useConsistencySorting: 0 26 | m_InterpolationPosesPerJob: 100 27 | m_NewContactsPerJob: 30 28 | m_CollideContactsPerJob: 100 29 | m_ClearFlagsPerJob: 200 30 | m_ClearBodyForcesPerJob: 200 31 | m_SyncDiscreteFixturesPerJob: 50 32 | m_SyncContinuousFixturesPerJob: 50 33 | m_FindNearestContactsPerJob: 100 34 | m_UpdateTriggerContactsPerJob: 100 35 | m_IslandSolverCostThreshold: 100 36 | m_IslandSolverBodyCostScale: 1 37 | m_IslandSolverContactCostScale: 10 38 | m_IslandSolverJointCostScale: 10 39 | m_IslandSolverBodiesPerJob: 50 40 | m_IslandSolverContactsPerJob: 50 41 | m_AutoSimulation: 1 42 | m_QueriesHitTriggers: 1 43 | m_QueriesStartInColliders: 1 44 | m_CallbacksOnDisable: 1 45 | m_ReuseCollisionCallbacks: 1 46 | m_AutoSyncTransforms: 0 47 | m_AlwaysShowColliders: 0 48 | m_ShowColliderSleep: 1 49 | m_ShowColliderContacts: 0 50 | m_ShowColliderAABB: 0 51 | m_ContactArrowScale: 0.2 52 | m_ColliderAwakeColor: {r: 0.5686275, g: 0.95686275, b: 0.54509807, a: 0.7529412} 53 | m_ColliderAsleepColor: {r: 0.5686275, g: 0.95686275, b: 0.54509807, a: 0.36078432} 54 | m_ColliderContactColor: {r: 1, g: 0, b: 1, a: 0.6862745} 55 | m_ColliderAABBColor: {r: 1, g: 1, b: 0, a: 0.2509804} 56 | m_LayerCollisionMatrix: ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 57 | -------------------------------------------------------------------------------- /ProjectSettings/PresetManager.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!1386491679 &1 4 | PresetManager: 5 | m_ObjectHideFlags: 0 6 | m_DefaultList: 7 | - type: 8 | m_NativeTypeID: 20 9 | m_ManagedTypePPtr: {fileID: 0} 10 | m_ManagedTypeFallback: 11 | defaultPresets: 12 | - m_Preset: {fileID: 2655988077585873504, guid: bfcfc320427f8224bbb7a96f3d3aebad, 13 | type: 2} 14 | -------------------------------------------------------------------------------- /ProjectSettings/ProjectVersion.txt: -------------------------------------------------------------------------------- 1 | m_EditorVersion: 2020.3.17f1c1 2 | m_EditorVersionWithRevision: 2020.3.17f1c1 (1f35b2393d76) 3 | -------------------------------------------------------------------------------- /ProjectSettings/QualitySettings.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!47 &1 4 | QualitySettings: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 5 7 | m_CurrentQuality: 3 8 | m_QualitySettings: 9 | - serializedVersion: 2 10 | name: Very Low 11 | pixelLightCount: 0 12 | shadows: 0 13 | shadowResolution: 0 14 | shadowProjection: 1 15 | shadowCascades: 1 16 | shadowDistance: 15 17 | shadowNearPlaneOffset: 3 18 | shadowCascade2Split: 0.33333334 19 | shadowCascade4Split: {x: 0.06666667, y: 0.2, z: 0.46666667} 20 | shadowmaskMode: 0 21 | blendWeights: 1 22 | textureQuality: 1 23 | anisotropicTextures: 0 24 | antiAliasing: 0 25 | softParticles: 0 26 | softVegetation: 0 27 | realtimeReflectionProbes: 0 28 | billboardsFaceCameraPosition: 0 29 | vSyncCount: 0 30 | lodBias: 0.3 31 | maximumLODLevel: 0 32 | particleRaycastBudget: 4 33 | asyncUploadTimeSlice: 2 34 | asyncUploadBufferSize: 16 35 | resolutionScalingFixedDPIFactor: 1 36 | excludedTargetPlatforms: [] 37 | - serializedVersion: 2 38 | name: Low 39 | pixelLightCount: 0 40 | shadows: 0 41 | shadowResolution: 0 42 | shadowProjection: 1 43 | shadowCascades: 1 44 | shadowDistance: 20 45 | shadowNearPlaneOffset: 3 46 | shadowCascade2Split: 0.33333334 47 | shadowCascade4Split: {x: 0.06666667, y: 0.2, z: 0.46666667} 48 | shadowmaskMode: 0 49 | blendWeights: 2 50 | textureQuality: 0 51 | anisotropicTextures: 0 52 | antiAliasing: 0 53 | softParticles: 0 54 | softVegetation: 0 55 | realtimeReflectionProbes: 0 56 | billboardsFaceCameraPosition: 0 57 | vSyncCount: 0 58 | lodBias: 0.4 59 | maximumLODLevel: 0 60 | particleRaycastBudget: 16 61 | asyncUploadTimeSlice: 2 62 | asyncUploadBufferSize: 16 63 | resolutionScalingFixedDPIFactor: 1 64 | excludedTargetPlatforms: [] 65 | - serializedVersion: 2 66 | name: Medium 67 | pixelLightCount: 1 68 | shadows: 0 69 | shadowResolution: 0 70 | shadowProjection: 1 71 | shadowCascades: 1 72 | shadowDistance: 20 73 | shadowNearPlaneOffset: 3 74 | shadowCascade2Split: 0.33333334 75 | shadowCascade4Split: {x: 0.06666667, y: 0.2, z: 0.46666667} 76 | shadowmaskMode: 0 77 | blendWeights: 2 78 | textureQuality: 0 79 | anisotropicTextures: 0 80 | antiAliasing: 0 81 | softParticles: 0 82 | softVegetation: 0 83 | realtimeReflectionProbes: 0 84 | billboardsFaceCameraPosition: 0 85 | vSyncCount: 1 86 | lodBias: 0.7 87 | maximumLODLevel: 0 88 | particleRaycastBudget: 64 89 | asyncUploadTimeSlice: 2 90 | asyncUploadBufferSize: 16 91 | resolutionScalingFixedDPIFactor: 1 92 | excludedTargetPlatforms: [] 93 | - serializedVersion: 2 94 | name: High 95 | pixelLightCount: 2 96 | shadows: 0 97 | shadowResolution: 1 98 | shadowProjection: 1 99 | shadowCascades: 2 100 | shadowDistance: 40 101 | shadowNearPlaneOffset: 3 102 | shadowCascade2Split: 0.33333334 103 | shadowCascade4Split: {x: 0.06666667, y: 0.2, z: 0.46666667} 104 | shadowmaskMode: 1 105 | blendWeights: 2 106 | textureQuality: 0 107 | anisotropicTextures: 0 108 | antiAliasing: 0 109 | softParticles: 0 110 | softVegetation: 1 111 | realtimeReflectionProbes: 0 112 | billboardsFaceCameraPosition: 0 113 | vSyncCount: 1 114 | lodBias: 1 115 | maximumLODLevel: 0 116 | particleRaycastBudget: 256 117 | asyncUploadTimeSlice: 2 118 | asyncUploadBufferSize: 16 119 | resolutionScalingFixedDPIFactor: 1 120 | excludedTargetPlatforms: [] 121 | - serializedVersion: 2 122 | name: Very High 123 | pixelLightCount: 3 124 | shadows: 0 125 | shadowResolution: 2 126 | shadowProjection: 1 127 | shadowCascades: 2 128 | shadowDistance: 70 129 | shadowNearPlaneOffset: 3 130 | shadowCascade2Split: 0.33333334 131 | shadowCascade4Split: {x: 0.06666667, y: 0.2, z: 0.46666667} 132 | shadowmaskMode: 1 133 | blendWeights: 4 134 | textureQuality: 0 135 | anisotropicTextures: 0 136 | antiAliasing: 0 137 | softParticles: 0 138 | softVegetation: 1 139 | realtimeReflectionProbes: 0 140 | billboardsFaceCameraPosition: 0 141 | vSyncCount: 1 142 | lodBias: 1.5 143 | maximumLODLevel: 0 144 | particleRaycastBudget: 1024 145 | asyncUploadTimeSlice: 2 146 | asyncUploadBufferSize: 16 147 | resolutionScalingFixedDPIFactor: 1 148 | excludedTargetPlatforms: [] 149 | - serializedVersion: 2 150 | name: Ultra 151 | pixelLightCount: 4 152 | shadows: 0 153 | shadowResolution: 0 154 | shadowProjection: 1 155 | shadowCascades: 4 156 | shadowDistance: 150 157 | shadowNearPlaneOffset: 3 158 | shadowCascade2Split: 0.33333334 159 | shadowCascade4Split: {x: 0.06666667, y: 0.2, z: 0.46666667} 160 | shadowmaskMode: 1 161 | blendWeights: 4 162 | textureQuality: 0 163 | anisotropicTextures: 0 164 | antiAliasing: 0 165 | softParticles: 0 166 | softVegetation: 1 167 | realtimeReflectionProbes: 0 168 | billboardsFaceCameraPosition: 0 169 | vSyncCount: 1 170 | lodBias: 2 171 | maximumLODLevel: 0 172 | particleRaycastBudget: 4096 173 | asyncUploadTimeSlice: 2 174 | asyncUploadBufferSize: 16 175 | resolutionScalingFixedDPIFactor: 1 176 | excludedTargetPlatforms: [] 177 | m_PerPlatformDefaultQuality: 178 | Android: 2 179 | Nintendo 3DS: 5 180 | Nintendo Switch: 5 181 | PS4: 5 182 | PSM: 5 183 | PSP2: 2 184 | Standalone: 5 185 | Tizen: 2 186 | WebGL: 3 187 | WiiU: 5 188 | Windows Store Apps: 5 189 | XboxOne: 5 190 | iPhone: 2 191 | tvOS: 2 192 | -------------------------------------------------------------------------------- /ProjectSettings/TagManager.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!78 &1 4 | TagManager: 5 | serializedVersion: 2 6 | tags: [] 7 | layers: 8 | - Default 9 | - TransparentFX 10 | - Ignore Raycast 11 | - 12 | - Water 13 | - UI 14 | - 15 | - 16 | - 17 | - 18 | - 19 | - 20 | - 21 | - 22 | - 23 | - 24 | - 25 | - 26 | - 27 | - 28 | - 29 | - 30 | - 31 | - 32 | - 33 | - 34 | - 35 | - 36 | - 37 | - 38 | - 39 | - 40 | m_SortingLayers: 41 | - name: Default 42 | uniqueID: 0 43 | locked: 0 44 | -------------------------------------------------------------------------------- /ProjectSettings/TimeManager.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!5 &1 4 | TimeManager: 5 | m_ObjectHideFlags: 0 6 | Fixed Timestep: 0.02 7 | Maximum Allowed Timestep: 0.1 8 | m_TimeScale: 1 9 | Maximum Particle Timestep: 0.03 10 | -------------------------------------------------------------------------------- /ProjectSettings/UnityConnectSettings.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!310 &1 4 | UnityConnectSettings: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 1 7 | m_Enabled: 1 8 | m_TestMode: 0 9 | m_EventOldUrl: https://api.uca.cloud.unity3d.com/v1/events 10 | m_EventUrl: https://cdp.cloud.unity3d.com/v1/events 11 | m_ConfigUrl: https://config.uca.cloud.unity3d.com 12 | m_TestInitMode: 0 13 | CrashReportingSettings: 14 | m_EventUrl: https://perf-events.cloud.unity3d.com 15 | m_Enabled: 0 16 | m_LogBufferSize: 10 17 | m_CaptureEditorExceptions: 1 18 | UnityPurchasingSettings: 19 | m_Enabled: 0 20 | m_TestMode: 0 21 | UnityAnalyticsSettings: 22 | m_Enabled: 0 23 | m_TestMode: 0 24 | m_InitializeOnStartup: 1 25 | UnityAdsSettings: 26 | m_Enabled: 0 27 | m_InitializeOnStartup: 1 28 | m_TestMode: 0 29 | m_IosGameId: 30 | m_AndroidGameId: 31 | m_GameIds: {} 32 | m_GameId: 33 | PerformanceReportingSettings: 34 | m_Enabled: 0 35 | -------------------------------------------------------------------------------- /ProjectSettings/VFXManager.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!937362698 &1 4 | VFXManager: 5 | m_ObjectHideFlags: 0 6 | m_IndirectShader: {fileID: 0} 7 | m_CopyBufferShader: {fileID: 0} 8 | m_SortShader: {fileID: 0} 9 | m_RenderPipeSettingsPath: 10 | m_FixedTimeStep: 11.1 11 | m_MaxDeltaTime: 0.05 12 | -------------------------------------------------------------------------------- /ProjectSettings/VersionControlSettings.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!890905787 &1 4 | VersionControlSettings: 5 | m_ObjectHideFlags: 0 6 | m_Mode: Visible Meta Files 7 | m_CollabEditorSettings: 8 | inProgressEnabled: 1 9 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # ZToolsForUnity 2 | 3 | 4 | this is for test commit. -------------------------------------------------------------------------------- /UserSettings/EditorUserSettings.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!162 &1 4 | EditorUserSettings: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 4 7 | m_ConfigSettings: 8 | RecentlyUsedScenePath-0: 9 | value: 224247031146467f0803036d3426521f29474965082d2b3f1e2a183de7ae2136ebf32f 10 | flags: 0 11 | vcSharedLogLevel: 12 | value: 0d5e400f0650 13 | flags: 0 14 | m_VCAutomaticAdd: 1 15 | m_VCDebugCom: 0 16 | m_VCDebugCmd: 0 17 | m_VCDebugOut: 0 18 | m_SemanticMergeMode: 2 19 | m_VCShowFailedCheckout: 1 20 | m_VCOverwriteFailedCheckoutAssets: 1 21 | m_VCProjectOverlayIcons: 1 22 | m_VCHierarchyOverlayIcons: 1 23 | m_VCOtherOverlayIcons: 1 24 | m_VCAllowAsyncUpdate: 1 25 | --------------------------------------------------------------------------------