A game about forced loneliness, made by TACStudios
at master 7.6 kB view raw
1using System; 2using System.Collections.Generic; 3using System.IO; 4using UnityEngine; 5using UnityEngine.Tilemaps; 6 7namespace UnityEditor.Tilemaps 8{ 9 /// <summary> This class is in charge of drag'n'drops of Tile assets on scene view </summary> 10 internal class TileDragAndDropManager : ScriptableSingleton<TileDragAndDropManager> 11 { 12 private bool m_RegisteredEventHandlers; 13 private Dictionary<Vector2Int, TileDragAndDropHoverData> m_HoverData; 14 15 [SerializeField] 16 private string m_LastUserTileAssetPath; 17 18 [InitializeOnLoadMethod] 19 static void Initialize() 20 { 21 instance.RegisterEventHandlers(); 22 } 23 24 void OnEnable() 25 { 26 RegisterEventHandlers(); 27 } 28 29 void RegisterEventHandlers() 30 { 31 if (m_RegisteredEventHandlers) 32 return; 33 34 SceneView.duringSceneGui += DuringSceneGui; 35 m_RegisteredEventHandlers = true; 36 } 37 38 void OnDisable() 39 { 40 SceneView.duringSceneGui -= DuringSceneGui; 41 m_RegisteredEventHandlers = false; 42 } 43 44 private void DuringSceneGui(SceneView sceneView) 45 { 46 Event evt = Event.current; 47 if (evt.type != EventType.DragUpdated && evt.type != EventType.DragPerform && evt.type != EventType.DragExited && evt.type != EventType.Repaint) 48 return; 49 50 Grid activeGrid = GetActiveGrid(); 51 if (activeGrid == null || DragAndDrop.objectReferences.Length == 0) 52 return; 53 54 Vector3 localMouse = GridEditorUtility.ScreenToLocal(activeGrid.transform, evt.mousePosition); 55 Vector3Int mouseGridPosition = activeGrid.LocalToCell(localMouse); 56 57 switch (evt.type) 58 { 59 //TODO: Cache this 60 case EventType.DragUpdated: 61 DragAndDrop.visualMode = DragAndDropVisualMode.Copy; 62 List<TileBase> tiles = TileDragAndDrop.GetValidTiles(DragAndDrop.objectReferences); 63 instance.m_HoverData = TileDragAndDrop.CreateHoverData(null, null, tiles, null, activeGrid.cellLayout); 64 if (instance.m_HoverData.Count > 0) 65 { 66 Event.current.Use(); 67 GUI.changed = true; 68 } 69 break; 70 case EventType.DragPerform: 71 if (instance.m_HoverData.Count > 0) 72 { 73 DragAndDrop.visualMode = DragAndDropVisualMode.Copy; 74 var tileSheet = TileDragAndDrop.ConvertToTileSheet(instance.m_HoverData); 75 Tilemap tilemap = GetOrCreateActiveTilemap(); 76 tilemap.ClearAllEditorPreviewTiles(); 77 int i = 0; 78 foreach (KeyValuePair<Vector2Int, TileDragAndDropHoverData> item in instance.m_HoverData) 79 { 80 Vector3Int position = new Vector3Int(mouseGridPosition.x + item.Key.x, mouseGridPosition.y + item.Key.y, 0); 81 tilemap.SetTile(position, tileSheet[i++]); 82 tilemap.SetTransformMatrix(position, Matrix4x4.TRS( 83 item.Value.hasOffset ? item.Value.positionOffset - tilemap.tileAnchor : Vector3.zero 84 , Quaternion.identity 85 , Vector3.one)); 86 } 87 instance.m_HoverData = null; 88 GUI.changed = true; 89 Event.current.Use(); 90 } 91 break; 92 case EventType.Repaint: 93 if (instance.m_HoverData != null) 94 { 95 DragAndDrop.visualMode = DragAndDropVisualMode.Copy; 96 97 var map = Selection.activeGameObject.GetComponentInParent<Tilemap>(); 98 var hasMap = map != null; 99 if (hasMap) 100 { 101 map.ClearAllEditorPreviewTiles(); 102 foreach (KeyValuePair<Vector2Int, TileDragAndDropHoverData> item in instance.m_HoverData) 103 { 104 var gridPos = mouseGridPosition + new Vector3Int(item.Key.x, item.Key.y, 0); 105 if (item.Value.hoverObject is TileBase tile) 106 { 107 map.SetEditorPreviewTile(gridPos, tile); 108 } 109 } 110 } 111 } 112 break; 113 } 114 115 if (instance.m_HoverData != null && ( 116 Event.current.type == EventType.DragExited || 117 Event.current.type == EventType.KeyDown && Event.current.keyCode == KeyCode.Escape)) 118 { 119 if (instance.m_HoverData.Count > 0) 120 { 121 Tilemap map = Selection.activeGameObject.GetComponentInParent<Tilemap>(); 122 if (map != null) 123 map.ClearAllEditorPreviewTiles(); 124 125 Event.current.Use(); 126 } 127 128 instance.m_HoverData = null; 129 } 130 } 131 132 internal static string GetDefaultTileAssetDirectoryPath() 133 { 134 var path = instance.m_LastUserTileAssetPath; 135 if (String.IsNullOrEmpty(path)) 136 { 137 path = ProjectBrowser.s_LastInteractedProjectBrowser != null 138 ? ProjectBrowser.s_LastInteractedProjectBrowser.GetActiveFolderPath() 139 : "Assets"; 140 } 141 return path; 142 } 143 144 internal static void SetUserTileAssetDirectoryPath(string path) 145 { 146 var directoryPath = String.Empty; 147 if (!String.IsNullOrEmpty(path)) 148 { 149 // UUM-29240: UnityGetDirectoryName clips off last directory if path is not a file path 150 if (String.IsNullOrEmpty(FileUtil.GetPathExtension(path)) 151 && !path.EndsWith("/") // MacOS 152 && !File.Exists(path)) 153 { 154 path = FileUtil.CombinePaths(path, ""); 155 } 156 directoryPath = FileUtil.UnityGetDirectoryName(path); 157 } 158 instance.m_LastUserTileAssetPath = directoryPath; 159 } 160 161 static Tilemap GetOrCreateActiveTilemap() 162 { 163 if (Selection.activeGameObject != null) 164 { 165 Tilemap tilemap = Selection.activeGameObject.GetComponentInParent<Tilemap>(); 166 if (tilemap == null) 167 { 168 Grid grid = Selection.activeGameObject.GetComponentInParent<Grid>(); 169 tilemap = CreateNewTilemap(grid); 170 } 171 return tilemap; 172 } 173 return null; 174 } 175 176 static Tilemap CreateNewTilemap(Grid grid) 177 { 178 GameObject go = new GameObject("Tilemap"); 179 go.transform.SetParent(grid.gameObject.transform); 180 Tilemap map = go.AddComponent<Tilemap>(); 181 go.AddComponent<TilemapRenderer>(); 182 return map; 183 } 184 185 static Grid GetActiveGrid() 186 { 187 if (Selection.activeGameObject != null) 188 { 189 return Selection.activeGameObject.GetComponentInParent<Grid>(); 190 } 191 return null; 192 } 193 } 194}