using System; using System.Diagnostics; using System.IO; using System.Linq; using System.Runtime.InteropServices; using UnityEditor; using UnityEditor.UIElements; // For Unity 2021 compatibility using UnityEngine; using UnityEngine.UIElements; using MCPForUnity.Editor.Data; using MCPForUnity.Editor.Helpers; using MCPForUnity.Editor.Models; using MCPForUnity.Editor.Services; namespace MCPForUnity.Editor.Windows { public class MCPForUnityEditorWindowNew : EditorWindow { // Protocol enum for future HTTP support private enum ConnectionProtocol { Stdio, // HTTPStreaming // Future } // Settings UI Elements private Label versionLabel; private Toggle debugLogsToggle; private EnumField validationLevelField; private Label validationDescription; private Foldout advancedSettingsFoldout; private TextField mcpServerPathOverride; private TextField uvPathOverride; private Button browsePythonButton; private Button clearPythonButton; private Button browseUvButton; private Button clearUvButton; private VisualElement mcpServerPathStatus; private VisualElement uvPathStatus; // Connection UI Elements private EnumField protocolDropdown; private TextField unityPortField; private TextField serverPortField; private VisualElement statusIndicator; private Label connectionStatusLabel; private Button connectionToggleButton; private VisualElement healthIndicator; private Label healthStatusLabel; private Button testConnectionButton; private VisualElement serverStatusBanner; private Label serverStatusMessage; private Button downloadServerButton; private Button rebuildServerButton; // Client UI Elements private DropdownField clientDropdown; private Button configureAllButton; private VisualElement clientStatusIndicator; private Label clientStatusLabel; private Button configureButton; private VisualElement claudeCliPathRow; private TextField claudeCliPath; private Button browseClaudeButton; private Foldout manualConfigFoldout; private TextField configPathField; private Button copyPathButton; private Button openFileButton; private TextField configJsonField; private Button copyJsonButton; private Label installationStepsLabel; // Data private readonly McpClients mcpClients = new(); private int selectedClientIndex = 0; private ValidationLevel currentValidationLevel = ValidationLevel.Standard; // Validation levels matching the existing enum private enum ValidationLevel { Basic, Standard, Comprehensive, Strict } public static void ShowWindow() { var window = GetWindow("MCP For Unity"); window.minSize = new Vector2(500, 600); } public void CreateGUI() { // Determine base path (Package Manager vs Asset Store install) string basePath = AssetPathUtility.GetMcpPackageRootPath(); // Load UXML var visualTree = AssetDatabase.LoadAssetAtPath( $"{basePath}/Editor/Windows/MCPForUnityEditorWindowNew.uxml" ); if (visualTree == null) { McpLog.Error($"Failed to load UXML at: {basePath}/Editor/Windows/MCPForUnityEditorWindowNew.uxml"); return; } visualTree.CloneTree(rootVisualElement); // Load USS var styleSheet = AssetDatabase.LoadAssetAtPath( $"{basePath}/Editor/Windows/MCPForUnityEditorWindowNew.uss" ); if (styleSheet != null) { rootVisualElement.styleSheets.Add(styleSheet); } // Cache UI elements CacheUIElements(); // Initialize UI InitializeUI(); // Register callbacks RegisterCallbacks(); // Initial update UpdateConnectionStatus(); UpdateServerStatusBanner(); UpdateClientStatus(); UpdatePathOverrides(); // Technically not required to connect, but if we don't do this, the UI will be blank UpdateManualConfiguration(); UpdateClaudeCliPathVisibility(); } private void OnEnable() { EditorApplication.update += OnEditorUpdate; } private void OnDisable() { EditorApplication.update -= OnEditorUpdate; } private void OnFocus() { // Only refresh data if UI is built if (rootVisualElement == null || rootVisualElement.childCount == 0) return; RefreshAllData(); } private void OnEditorUpdate() { // Only update UI if it's built if (rootVisualElement == null || rootVisualElement.childCount == 0) return; UpdateConnectionStatus(); } private void RefreshAllData() { // Update connection status UpdateConnectionStatus(); // Auto-verify bridge health if connected if (MCPServiceLocator.Bridge.IsRunning) { VerifyBridgeConnection(); } // Update path overrides UpdatePathOverrides(); // Refresh selected client (may have been configured externally) if (selectedClientIndex >= 0 && selectedClientIndex < mcpClients.clients.Count) { var client = mcpClients.clients[selectedClientIndex]; MCPServiceLocator.Client.CheckClientStatus(client); UpdateClientStatus(); UpdateManualConfiguration(); UpdateClaudeCliPathVisibility(); } } private void CacheUIElements() { // Settings versionLabel = rootVisualElement.Q