// UI components for command list (Client-Side) import { showNotification } from './notifications.js'; // REMOVED: import { showLearningDialog, hideLearningDialog } from './dialogs.js'; // REMOVED: import { contextProvider } from '../core/contextProvider.js'; import { startMappingCommand } from '../core/learningManager.js'; // Keep this import // REMOVED style imports // Access the global instance instead // const getMappingEngine = () => window.controlFreakMappingEngine; // Define common ComfyUI commands - these would typically be fetched from the server // but we can define them directly in the client for our simplified architecture const COMFY_UI_COMMANDS = [ // Workflow execution { id: "Comfy.QueuePrompt", label: "Queue Prompt" }, { id: "Comfy.QueuePromptFront", label: "Queue Prompt (Front)" }, { id: "Comfy.Interrupt", label: "Interrupt" }, // Workflow management { id: "Comfy.OpenWorkflow", label: "Open Workflow" }, { id: "Comfy.ClearWorkflow", label: "Clear Workflow" }, // Canvas controls { id: "Comfy.Canvas.ZoomIn", label: "Canvas Zoom In" }, { id: "Comfy.Canvas.ZoomOut", label: "Canvas Zoom Out" }, { id: "Comfy.Canvas.FitView", label: "Canvas Fit View" }, // UI panels { id: "Workspace.ToggleSidebarTab.queue", label: "Toggle Queue Panel" }, { id: "Workspace.ToggleSidebarTab.workflows", label: "Toggle Workflows Panel" }, { id: "Workspace.ToggleSidebarTab.node-library", label: "Toggle Node Library Panel" } ]; /** * Loads and displays available commands * @param {HTMLElement} panel - The panel to render commands in */ export function loadCommandsData(panel) { panel.innerHTML = '
Loading commands...
'; try { // Use the predefined commands instead of fetching from server const commands = COMFY_UI_COMMANDS; panel.innerHTML = ''; if (commands.length === 0) { panel.innerHTML = '
No commands available. ComfyUI commands system may not be accessible.
'; return; } // Create a container for the commands list const container = document.createElement('div'); container.className = 'commands-container'; // Create a header with instructions const header = document.createElement('div'); header.className = 'commands-panel-header'; header.innerHTML = '

Map Controllers to UI Commands

' + '

Select a command to map it to a controller input.

'; container.appendChild(header); // Group commands by category const commandsByCategory = groupCommandsByCategory(commands); // Create command sections for each category for (const [category, categoryCommands] of Object.entries(commandsByCategory)) { createCommandCategorySection(container, category, categoryCommands); } panel.appendChild(container); } catch (error) { console.error('Error loading commands data:', error); panel.innerHTML = '
Error loading commands: ' + error.message + '
'; } } /** * Groups commands by category based on their id prefix * @param {Array} commands - List of all commands * @returns {Object} Commands grouped by category */ function groupCommandsByCategory(commands) { const groupedCommands = {}; for (const command of commands) { let category = 'Other'; // Extract category from command ID (e.g., "Comfy.Canvas.ZoomIn" -> "Comfy.Canvas") if (command.id && command.id.includes('.')) { const parts = command.id.split('.'); if (parts.length >= 2) { category = `${parts[0]}.${parts[1]}`; } } if (!groupedCommands[category]) { groupedCommands[category] = []; } groupedCommands[category].push(command); } return groupedCommands; } /** * Creates a section for commands in a specific category * @param {HTMLElement} container - Container to append to * @param {String} category - Category name * @param {Array} commands - Commands in this category */ function createCommandCategorySection(container, category, commands) { const section = document.createElement('div'); section.className = 'command-category-section'; // Add a header for this category const header = document.createElement('h4'); header.className = 'category-header'; header.textContent = formatCategoryName(category); section.appendChild(header); // Create the command list const commandList = document.createElement('div'); commandList.className = 'command-list'; // Add each command commands.forEach(command => { const commandItem = createCommandItem(command); commandList.appendChild(commandItem); }); section.appendChild(commandList); container.appendChild(section); } /** * Format category name for display * @param {String} category - Raw category name * @returns {String} Formatted category name */ function formatCategoryName(category) { return category.replace(/\./g, ' / '); } /** * Create a single command item * @param {Object} command - The command data * @returns {HTMLElement} The command item element */ function createCommandItem(command) { const item = document.createElement('div'); item.className = 'command-item'; // Command info const info = document.createElement('div'); info.className = 'command-info'; // Command label const label = document.createElement('div'); label.className = 'command-label'; label.textContent = command.label || command.id.split('.').pop(); info.appendChild(label); // Command ID (smaller text below) const id = document.createElement('div'); id.className = 'command-id'; id.textContent = command.id; info.appendChild(id); item.appendChild(info); // Map button const mapBtn = document.createElement('button'); mapBtn.textContent = 'Map'; mapBtn.className = 'command-map-btn'; mapBtn.onclick = () => initiateCommandMapping(command); item.appendChild(mapBtn); return item; } /** * Start mapping a command to a controller * @param {Object} command - The command to map */ function initiateCommandMapping(command) { try { // Call the centralized function from learningManager startMappingCommand(command.id, { label: command.label || command.id, description: `Execute "${command.label}" command` }); // Notification is handled by startMappingCommand/showLearningDialog now // showNotification(`Move a controller to map to "${command.label}"`); } catch (error) { console.error("Error starting command mapping:", error); showNotification(`Failed to start mapping for "${command.label}"`, true); } } /** * Execute a ComfyUI command * @param {String} commandId - The ID of the command to execute */ // This function is replaced by the mappingEngine.executeCommand method /* function executeCommand(commandId) { // Based on the command ID, perform different actions switch (commandId) { case "Comfy.QueuePrompt": app.queuePrompt(); break; case "Comfy.QueuePromptFront": app.queuePrompt(true); // true for front of queue break; case "Comfy.Interrupt": app.interrupt(); break; case "Comfy.ClearPendingTasks": if (typeof app.clearQueueInProgress === 'function') app.clearQueueInProgress(); break; // Other command implementations can be added as needed // Many can be accessed via the app API or dispatched as events default: console.warn(`ControlFreak: Command ${commandId} not implemented`); } } */ /** * Register default command handlers (if needed) */ (function registerDefaultCommandHandlers() { // Example of registering a handler directly using the CommandExecutor /* const commandExecutor = contextProvider.get('commandExecutor'); if (commandExecutor) { commandExecutor.registerCommandHandler('MyCustomCommand.Action', () => { console.log("My custom command handler executed!"); }); } */ })();