mirror of
https://github.com/Comfy-Org/ComfyUI_frontend.git
synced 2026-02-04 23:20:07 +00:00
* [feat] Add formatKeySequence function to format keybindings for commands * [feat] Add lock and unlock canvas commands with keybindings and update localization * feat: Implement canvas scale synchronization and zoom level adjustment * feat: Enhance GraphCanvasMenu with zoom controls and improved button functionality * feat: Refactor MiniMap component layout and remove unused bottomPanelStore * feat: Update zoom control shortcuts to use formatted key sequences * feat: Add tests for ZoomControlsModal and enhance GraphCanvasMenu tests * Update locales [skip ci] * Fix browser tests * ui: align minimap properly * Update locales [skip ci] * feat: focus zoom input when zoom modal loads * style: improve styling of zoom controls and add focus effect * fix styling and tests * styling: add divider to graph canvas menu * styling: position minimap properly * styling: add close button for minimap * styling: add horizontal divider to minimap * styling: update minimap toggle button text and remove old styles * Update locales [skip ci] * Update locales [skip ci] * feat: disable canvas menu in viewport settings after zoom adjustments * Update test expectations [skip ci] * fix: update canvas read-only property access to use state object * Update locales [skip ci] * fix: adjust button group and minimap positioning * feat: enhance zoom controls and adjust minimap positioning per PR comments * feat: implement zoom controls composable * feat: add timeout delays for headless tests * fix: update zoom input validation range in applyZoom function * [refactor] Update positioning and styles for GraphCanvasMenu, MiniMap, and ZoomControlsModal components * [refactor] Adjust z-index and positioning for GraphCanvasMenu, MiniMap, and ZoomControlsModal components * [style] Adjust margin for minimap button styles in GraphCanvasMenu component * [refactor] minimap should show on focus mode * [refactor] Update LiteGraphCanvasSplitterOverlay to conditionally render side and bottom panels based on focus mode * [style] Adjust right positioning for MiniMap and ZoomControlsModal components * [style] Adjust right positioning for MiniMap and ZoomControlsModal components --------- Co-authored-by: github-actions <github-actions@github.com> Co-authored-by: Christian Byrne <cbyrne@comfy.org>
141 lines
4.0 KiB
TypeScript
141 lines
4.0 KiB
TypeScript
import { defineStore } from 'pinia'
|
|
import { computed, ref } from 'vue'
|
|
|
|
import { useErrorHandling } from '@/composables/useErrorHandling'
|
|
import type { ComfyExtension } from '@/types/comfy'
|
|
|
|
import { type KeybindingImpl, useKeybindingStore } from './keybindingStore'
|
|
|
|
export interface ComfyCommand {
|
|
id: string
|
|
function: () => void | Promise<void>
|
|
|
|
label?: string | (() => string)
|
|
icon?: string | (() => string)
|
|
tooltip?: string | (() => string)
|
|
menubarLabel?: string | (() => string) // Menubar item label, if different from command label
|
|
versionAdded?: string
|
|
confirmation?: string // If non-nullish, this command will prompt for confirmation
|
|
source?: string
|
|
active?: () => boolean // Getter to check if the command is active/toggled on
|
|
category?: 'essentials' | 'view-controls' // For shortcuts panel organization
|
|
}
|
|
|
|
export class ComfyCommandImpl implements ComfyCommand {
|
|
id: string
|
|
function: () => void | Promise<void>
|
|
_label?: string | (() => string)
|
|
_icon?: string | (() => string)
|
|
_tooltip?: string | (() => string)
|
|
_menubarLabel?: string | (() => string)
|
|
versionAdded?: string
|
|
confirmation?: string
|
|
source?: string
|
|
active?: () => boolean
|
|
category?: 'essentials' | 'view-controls'
|
|
|
|
constructor(command: ComfyCommand) {
|
|
this.id = command.id
|
|
this.function = command.function
|
|
this._label = command.label
|
|
this._icon = command.icon
|
|
this._tooltip = command.tooltip
|
|
this._menubarLabel = command.menubarLabel ?? command.label
|
|
this.versionAdded = command.versionAdded
|
|
this.confirmation = command.confirmation
|
|
this.source = command.source
|
|
this.active = command.active
|
|
this.category = command.category
|
|
}
|
|
|
|
get label() {
|
|
return typeof this._label === 'function' ? this._label() : this._label
|
|
}
|
|
|
|
get icon() {
|
|
return typeof this._icon === 'function' ? this._icon() : this._icon
|
|
}
|
|
|
|
get tooltip() {
|
|
return typeof this._tooltip === 'function' ? this._tooltip() : this._tooltip
|
|
}
|
|
|
|
get menubarLabel() {
|
|
return typeof this._menubarLabel === 'function'
|
|
? this._menubarLabel()
|
|
: this._menubarLabel
|
|
}
|
|
|
|
get keybinding(): KeybindingImpl | null {
|
|
return useKeybindingStore().getKeybindingByCommandId(this.id)
|
|
}
|
|
}
|
|
|
|
export const useCommandStore = defineStore('command', () => {
|
|
const commandsById = ref<Record<string, ComfyCommandImpl>>({})
|
|
const commands = computed(() => Object.values(commandsById.value))
|
|
|
|
const registerCommand = (command: ComfyCommand) => {
|
|
if (commandsById.value[command.id]) {
|
|
console.warn(`Command ${command.id} already registered`)
|
|
}
|
|
commandsById.value[command.id] = new ComfyCommandImpl(command)
|
|
}
|
|
|
|
const registerCommands = (commands: ComfyCommand[]) => {
|
|
for (const command of commands) {
|
|
registerCommand(command)
|
|
}
|
|
}
|
|
|
|
const getCommand = (command: string) => {
|
|
return commandsById.value[command]
|
|
}
|
|
|
|
const { wrapWithErrorHandlingAsync } = useErrorHandling()
|
|
const execute = async (
|
|
commandId: string,
|
|
errorHandler?: (error: any) => void
|
|
) => {
|
|
const command = getCommand(commandId)
|
|
if (command) {
|
|
await wrapWithErrorHandlingAsync(command.function, errorHandler)()
|
|
} else {
|
|
throw new Error(`Command ${commandId} not found`)
|
|
}
|
|
}
|
|
|
|
const isRegistered = (command: string) => {
|
|
return !!commandsById.value[command]
|
|
}
|
|
|
|
const loadExtensionCommands = (extension: ComfyExtension) => {
|
|
if (extension.commands) {
|
|
for (const command of extension.commands) {
|
|
registerCommand({
|
|
...command,
|
|
source: extension.name
|
|
})
|
|
}
|
|
}
|
|
}
|
|
|
|
const formatKeySequence = (command: ComfyCommandImpl): string => {
|
|
const sequences = command.keybinding?.combo.getKeySequences() || []
|
|
return sequences
|
|
.map((seq) => seq.replace(/Control/g, 'Ctrl').replace(/Shift/g, 'Shift'))
|
|
.join(' + ')
|
|
}
|
|
|
|
return {
|
|
commands,
|
|
execute,
|
|
getCommand,
|
|
registerCommand,
|
|
registerCommands,
|
|
isRegistered,
|
|
loadExtensionCommands,
|
|
formatKeySequence
|
|
}
|
|
})
|