public static int DragReorder(Rect position, int elementHeight, List <MonoScript> elements, DrawElementDelegate drawElementDelegate) { Rect rect2; int controlID = GUIUtility.GetControlID(s_DragReorderGUIHash, FocusType.Passive); Rect r = position; r.height = elementHeight; int index = 0; if ((GUIUtility.hotControl == controlID) && (Event.current.type == EventType.Repaint)) { for (int i = 0; i < elements.Count; i++) { if (i != s_ReorderingDraggedElement) { if (IsDefaultTimeElement(elements[i])) { index = i; i++; } else { r.y = position.y + (s_ReorderingPositions[i] * elementHeight); drawElementDelegate(r, elements[i], false); } } } rect2 = new Rect(r.x, position.y + (s_ReorderingPositions[index] * elementHeight), r.width, ((s_ReorderingPositions[index + 1] - s_ReorderingPositions[index]) + 1f) * elementHeight); } else { for (int j = 0; j < elements.Count; j++) { r.y = position.y + (j * elementHeight); if (IsDefaultTimeElement(elements[j])) { index = j; j++; } else { drawElementDelegate(r, elements[j], false); } } rect2 = new Rect(r.x, position.y + (index * elementHeight), r.width, (float)(elementHeight * 2)); } GUI.Label(rect2, ScriptExecutionOrderInspector.m_Styles.defaultTimeContent, ScriptExecutionOrderInspector.m_Styles.defaultTime); bool flag = rect2.height > (elementHeight * 2.5f); if (GUIUtility.hotControl == controlID) { if (flag) { GUI.color = new Color(1f, 1f, 1f, 0.5f); } r.y = position.y + (s_ReorderingPositions[s_ReorderingDraggedElement] * elementHeight); drawElementDelegate(r, elements[s_ReorderingDraggedElement], true); GUI.color = Color.white; } int num5 = -1; switch (Event.current.GetTypeForControl(controlID)) { case EventType.MouseDown: if (position.Contains(Event.current.mousePosition)) { GUIUtility.keyboardControl = 0; EditorGUI.EndEditingActiveTextField(); s_ReorderingDraggedElement = Mathf.FloorToInt((Event.current.mousePosition.y - position.y) / ((float)elementHeight)); if (IsDefaultTimeElement(elements[s_ReorderingDraggedElement])) { return(num5); } s_ReorderingPositions = new float[elements.Count]; s_ReorderingGoals = new int[elements.Count]; for (int k = 0; k < elements.Count; k++) { s_ReorderingGoals[k] = k; s_ReorderingPositions[k] = k; } GUIUtility.hotControl = controlID; Event.current.Use(); } return(num5); case EventType.MouseUp: if (GUIUtility.hotControl == controlID) { if (s_ReorderingGoals[s_ReorderingDraggedElement] != s_ReorderingDraggedElement) { List <MonoScript> list = new List <MonoScript>(elements); for (int m = 0; m < elements.Count; m++) { elements[s_ReorderingGoals[m]] = list[m]; } num5 = s_ReorderingGoals[s_ReorderingDraggedElement]; } s_ReorderingGoals = null; s_ReorderingPositions = null; s_ReorderingDraggedElement = -1; GUIUtility.hotControl = 0; Event.current.Use(); return(num5); } return(num5); case EventType.MouseMove: case EventType.KeyDown: case EventType.KeyUp: case EventType.ScrollWheel: return(num5); case EventType.MouseDrag: if (GUIUtility.hotControl == controlID) { s_ReorderingPositions[s_ReorderingDraggedElement] = ((Event.current.mousePosition.y - position.y) / ((float)elementHeight)) - 0.5f; s_ReorderingPositions[s_ReorderingDraggedElement] = Mathf.Clamp(s_ReorderingPositions[s_ReorderingDraggedElement], 0f, (float)(elements.Count - 1)); int num7 = Mathf.RoundToInt(s_ReorderingPositions[s_ReorderingDraggedElement]); if (num7 != s_ReorderingGoals[s_ReorderingDraggedElement]) { for (int n = 0; n < elements.Count; n++) { s_ReorderingGoals[n] = n; } int num9 = (num7 <= s_ReorderingDraggedElement) ? 1 : -1; for (int num10 = s_ReorderingDraggedElement; num10 != num7; num10 -= num9) { s_ReorderingGoals[num10 - num9] = num10; } s_ReorderingGoals[s_ReorderingDraggedElement] = num7; } Event.current.Use(); return(num5); } return(num5); case EventType.Repaint: if (GUIUtility.hotControl == controlID) { for (int num12 = 0; num12 < elements.Count; num12++) { if (num12 != s_ReorderingDraggedElement) { s_ReorderingPositions[num12] = Mathf.MoveTowards(s_ReorderingPositions[num12], (float)s_ReorderingGoals[num12], 0.075f); } } GUIView.current.Repaint(); } return(num5); } return(num5); }
public static int DragReorder(Rect position, int elementHeight, List <MonoScript> elements, DrawElementDelegate drawElementDelegate) { int id = GUIUtility.GetControlID(s_DragReorderGUIHash, FocusType.Passive); Rect elementRect = position; elementRect.height = elementHeight; int defPos = 0; Rect defRect; // If we're dragging, draw elements based on their animated reordering positions, // but only for repainting. Control event handling does't like to suddenly change order, // so things will screw up if we HANDLE the controls in a different order when dragging. if (GUIUtility.hotControl == id && Event.current.type == EventType.Repaint) { for (int i = 0; i < elements.Count; i++) { // Don't draw the dragged element as part of loop if (i == s_ReorderingDraggedElement) { continue; } if (IsDefaultTimeElement(elements[i])) { defPos = i; i++; continue; } elementRect.y = position.y + s_ReorderingPositions[i] * elementHeight; drawElementDelegate(elementRect, elements[i], false); } defRect = new Rect(elementRect.x, position.y + s_ReorderingPositions[defPos] * elementHeight, elementRect.width, (s_ReorderingPositions[defPos + 1] - s_ReorderingPositions[defPos] + 1) * elementHeight); } // For everything else than repainting while dragging, // draw controls based on their positions in the array. else { for (int i = 0; i < elements.Count; i++) { elementRect.y = position.y + i * elementHeight; if (IsDefaultTimeElement(elements[i])) { defPos = i; i++; continue; } drawElementDelegate(elementRect, elements[i], false); } defRect = new Rect(elementRect.x, position.y + defPos * elementHeight, elementRect.width, elementHeight * 2); } GUI.Label(defRect, Content.defaultTimeContent, Styles.defaultTime); bool isAddingToDefault = defRect.height > elementHeight * 2.5f; if (GUIUtility.hotControl == id) { if (isAddingToDefault) { GUI.color = new Color(1, 1, 1, 0.5f); } // Draw the dragged element after all the other ones elementRect.y = position.y + s_ReorderingPositions[s_ReorderingDraggedElement] * elementHeight; drawElementDelegate(elementRect, elements[s_ReorderingDraggedElement], true); GUI.color = Color.white; } int changed = -1; EventType type = Event.current.GetTypeForControl(id); switch (type) { case EventType.MouseDown: if (position.Contains(Event.current.mousePosition)) { GUIUtility.keyboardControl = 0; EditorGUI.EndEditingActiveTextField(); s_ReorderingDraggedElement = Mathf.FloorToInt((Event.current.mousePosition.y - position.y) / elementHeight); if (!IsDefaultTimeElement(elements[s_ReorderingDraggedElement])) { s_ReorderingPositions = new float[elements.Count]; s_ReorderingGoals = new int[elements.Count]; for (int i = 0; i < elements.Count; i++) { s_ReorderingGoals[i] = i; s_ReorderingPositions[i] = i; } GUIUtility.hotControl = id; Event.current.Use(); } } break; case EventType.MouseDrag: if (GUIUtility.hotControl != id) { break; } // Set reordering position of dragged element based on mouse cursor s_ReorderingPositions[s_ReorderingDraggedElement] = (Event.current.mousePosition.y - position.y) / elementHeight - 0.5f; // Clamp to range of list s_ReorderingPositions[s_ReorderingDraggedElement] = Mathf.Clamp(s_ReorderingPositions[s_ReorderingDraggedElement], 0, elements.Count - 1); // Set draggedToPosition based on dragged position int draggedToPosition = Mathf.RoundToInt(s_ReorderingPositions[s_ReorderingDraggedElement]); // if dragged to a new position, re-assign goals if (draggedToPosition != s_ReorderingGoals[s_ReorderingDraggedElement]) { // Reset for (int i = 0; i < elements.Count; i++) { s_ReorderingGoals[i] = i; } // Find direction that other elements must be moved in int direction = (draggedToPosition > s_ReorderingDraggedElement ? -1 : 1); // Move goals of elements to make room for the dragged one for (int i = s_ReorderingDraggedElement; i != draggedToPosition; i -= direction) { s_ReorderingGoals[i - direction] = i; } // At last, move the goal of the dragged element s_ReorderingGoals[s_ReorderingDraggedElement] = draggedToPosition; } Event.current.Use(); break; case EventType.MouseUp: if (GUIUtility.hotControl != id) { break; } if (s_ReorderingGoals[s_ReorderingDraggedElement] != s_ReorderingDraggedElement) { // Reorder array according to the reordering goals List <MonoScript> reorderedArray = new List <MonoScript>(elements); for (int i = 0; i < elements.Count; i++) { elements[s_ReorderingGoals[i]] = reorderedArray[i]; } // Return which elements was just moved changed = s_ReorderingGoals[s_ReorderingDraggedElement]; } // Reset s_ReorderingGoals = null; s_ReorderingPositions = null; s_ReorderingDraggedElement = -1; GUIUtility.hotControl = 0; Event.current.Use(); break; case EventType.Repaint: // Animate elements to move towards their goals if (GUIUtility.hotControl == id) { for (int i = 0; i < elements.Count; i++) { if (i != s_ReorderingDraggedElement) { s_ReorderingPositions[i] = Mathf.MoveTowards(s_ReorderingPositions[i], s_ReorderingGoals[i], 0.075f); } } GUIView.current.Repaint(); } break; } return(changed); }