ComfyUI/web/assets/index-B1vRdV2i.js.map

1 line
281 KiB
Plaintext

{"version":3,"file":"index-B1vRdV2i.js","sources":["../../src/extensions/core/clipspace.ts","../../src/extensions/core/contextMenuFilter.ts","../../src/extensions/core/dynamicPrompts.ts","../../src/extensions/core/editAttention.ts","../../src/extensions/core/groupNodeManage.ts","../../src/extensions/core/groupNode.ts","../../src/extensions/core/groupOptions.ts","../../src/extensions/core/invertMenuScrolling.ts","../../src/extensions/core/keybinds.ts","../../src/extensions/core/maskeditor.ts","../../src/extensions/core/nodeTemplates.ts","../../src/extensions/core/noteNode.ts","../../src/extensions/core/rerouteNode.ts","../../src/extensions/core/saveImageExtraOutput.ts","../../src/extensions/core/simpleTouchSupport.ts","../../src/extensions/core/slotDefaults.ts","../../src/extensions/core/snapToGrid.ts","../../src/extensions/core/uploadImage.ts","../../src/extensions/core/webcamCapture.ts","../../src/extensions/core/uploadAudio.ts"],"sourcesContent":["import { app } from '../../scripts/app'\nimport { ComfyDialog, $el } from '../../scripts/ui'\nimport { ComfyApp } from '../../scripts/app'\n\nexport class ClipspaceDialog extends ComfyDialog {\n static items: Array<\n HTMLButtonElement & {\n contextPredicate?: () => boolean\n }\n > = []\n static instance: ClipspaceDialog | null = null\n\n static registerButton(\n name: string,\n contextPredicate: () => boolean,\n callback: () => void\n ) {\n const item = $el('button', {\n type: 'button',\n textContent: name,\n contextPredicate: contextPredicate,\n onclick: callback\n })\n\n ClipspaceDialog.items.push(item)\n }\n\n static invalidatePreview() {\n if (\n ComfyApp.clipspace &&\n ComfyApp.clipspace.imgs &&\n ComfyApp.clipspace.imgs.length > 0\n ) {\n const img_preview = document.getElementById(\n 'clipspace_preview'\n ) as HTMLImageElement\n if (img_preview) {\n img_preview.src =\n ComfyApp.clipspace.imgs[ComfyApp.clipspace['selectedIndex']].src\n img_preview.style.maxHeight = '100%'\n img_preview.style.maxWidth = '100%'\n }\n }\n }\n\n static invalidate() {\n if (ClipspaceDialog.instance) {\n const self = ClipspaceDialog.instance\n // allow reconstruct controls when copying from non-image to image content.\n const children = $el('div.comfy-modal-content', [\n self.createImgSettings(),\n ...self.createButtons()\n ])\n\n if (self.element) {\n // update\n if (self.element.firstChild) {\n self.element.removeChild(self.element.firstChild)\n }\n self.element.appendChild(children)\n } else {\n // new\n self.element = $el('div.comfy-modal', { parent: document.body }, [\n children\n ])\n }\n\n if (self.element.children[0].children.length <= 1) {\n self.element.children[0].appendChild(\n $el('p', {}, [\n 'Unable to find the features to edit content of a format stored in the current Clipspace.'\n ])\n )\n }\n\n ClipspaceDialog.invalidatePreview()\n }\n }\n\n constructor() {\n super()\n }\n\n createButtons() {\n const buttons = []\n\n for (let idx in ClipspaceDialog.items) {\n const item = ClipspaceDialog.items[idx]\n if (!item.contextPredicate || item.contextPredicate())\n buttons.push(ClipspaceDialog.items[idx])\n }\n\n buttons.push(\n $el('button', {\n type: 'button',\n textContent: 'Close',\n onclick: () => {\n this.close()\n }\n })\n )\n\n return buttons\n }\n\n createImgSettings() {\n if (ComfyApp.clipspace?.imgs) {\n const combo_items = []\n const imgs = ComfyApp.clipspace.imgs\n\n for (let i = 0; i < imgs.length; i++) {\n combo_items.push($el('option', { value: i }, [`${i}`]))\n }\n\n const combo1 = $el(\n 'select',\n {\n id: 'clipspace_img_selector',\n onchange: (event: Event) => {\n if (event.target && ComfyApp.clipspace) {\n ComfyApp.clipspace['selectedIndex'] = (\n event.target as HTMLSelectElement\n ).selectedIndex\n ClipspaceDialog.invalidatePreview()\n }\n }\n },\n combo_items\n )\n\n const row1 = $el('tr', {}, [\n $el('td', {}, [$el('font', { color: 'white' }, ['Select Image'])]),\n $el('td', {}, [combo1])\n ])\n\n const combo2 = $el(\n 'select',\n {\n id: 'clipspace_img_paste_mode',\n onchange: (event: Event) => {\n if (event.target && ComfyApp.clipspace) {\n ComfyApp.clipspace['img_paste_mode'] = (\n event.target as HTMLSelectElement\n ).value\n }\n }\n },\n [\n $el('option', { value: 'selected' }, 'selected'),\n $el('option', { value: 'all' }, 'all')\n ]\n ) as HTMLSelectElement\n combo2.value = ComfyApp.clipspace['img_paste_mode']\n\n const row2 = $el('tr', {}, [\n $el('td', {}, [$el('font', { color: 'white' }, ['Paste Mode'])]),\n $el('td', {}, [combo2])\n ])\n\n const td = $el(\n 'td',\n { align: 'center', width: '100px', height: '100px', colSpan: '2' },\n [$el('img', { id: 'clipspace_preview', ondragstart: () => false }, [])]\n )\n\n const row3 = $el('tr', {}, [td])\n\n return $el('table', {}, [row1, row2, row3])\n } else {\n return []\n }\n }\n\n createImgPreview() {\n if (ComfyApp.clipspace?.imgs) {\n return $el('img', { id: 'clipspace_preview', ondragstart: () => false })\n } else return []\n }\n\n show() {\n const img_preview = document.getElementById('clipspace_preview')\n ClipspaceDialog.invalidate()\n\n this.element.style.display = 'block'\n }\n}\n\napp.registerExtension({\n name: 'Comfy.Clipspace',\n init(app) {\n app.openClipspace = function () {\n if (!ClipspaceDialog.instance) {\n ClipspaceDialog.instance = new ClipspaceDialog()\n ComfyApp.clipspace_invalidate_handler = ClipspaceDialog.invalidate\n }\n\n if (ComfyApp.clipspace) {\n ClipspaceDialog.instance.show()\n } else app.ui.dialog.show('Clipspace is Empty!')\n }\n }\n})\n","import { LiteGraph, LGraphCanvas } from '@comfyorg/litegraph'\nimport { app } from '../../scripts/app'\n\n// Adds filtering to combo context menus\n\nconst ext = {\n name: 'Comfy.ContextMenuFilter',\n init() {\n const ctxMenu = LiteGraph.ContextMenu\n\n // @ts-expect-error TODO Very hacky way to modify Litegraph behaviour. Fix ctx later.\n LiteGraph.ContextMenu = function (values, options) {\n const ctx = new ctxMenu(values, options)\n\n // If we are a dark menu (only used for combo boxes) then add a filter input\n if (options?.className === 'dark' && values?.length > 4) {\n const filter = document.createElement('input')\n filter.classList.add('comfy-context-menu-filter')\n filter.placeholder = 'Filter list'\n\n ctx.root.prepend(filter)\n\n const items = Array.from(\n ctx.root.querySelectorAll('.litemenu-entry')\n ) as HTMLElement[]\n let displayedItems = [...items]\n let itemCount = displayedItems.length\n\n // We must request an animation frame for the current node of the active canvas to update.\n requestAnimationFrame(() => {\n const currentNode = LGraphCanvas.active_canvas.current_node\n const clickedComboValue = currentNode?.widgets\n ?.filter(\n (w) =>\n w.type === 'combo' && w.options.values?.length === values.length\n )\n .find((w) =>\n w.options.values?.every((v, i) => v === values[i])\n )?.value\n\n let selectedIndex = clickedComboValue\n ? values.findIndex((v: string) => v === clickedComboValue)\n : 0\n if (selectedIndex < 0) {\n selectedIndex = 0\n }\n let selectedItem = displayedItems[selectedIndex]\n updateSelected()\n\n // Apply highlighting to the selected item\n function updateSelected() {\n selectedItem?.style.setProperty('background-color', '')\n selectedItem?.style.setProperty('color', '')\n selectedItem = displayedItems[selectedIndex]\n selectedItem?.style.setProperty(\n 'background-color',\n '#ccc',\n 'important'\n )\n selectedItem?.style.setProperty('color', '#000', 'important')\n }\n\n const positionList = () => {\n const rect = ctx.root.getBoundingClientRect()\n\n // If the top is off-screen then shift the element with scaling applied\n if (rect.top < 0) {\n const scale =\n 1 -\n ctx.root.getBoundingClientRect().height / ctx.root.clientHeight\n\n const shift = (ctx.root.clientHeight * scale) / 2\n\n ctx.root.style.top = -shift + 'px'\n }\n }\n\n // Arrow up/down to select items\n filter.addEventListener('keydown', (event) => {\n switch (event.key) {\n case 'ArrowUp':\n event.preventDefault()\n if (selectedIndex === 0) {\n selectedIndex = itemCount - 1\n } else {\n selectedIndex--\n }\n updateSelected()\n break\n case 'ArrowRight':\n event.preventDefault()\n selectedIndex = itemCount - 1\n updateSelected()\n break\n case 'ArrowDown':\n event.preventDefault()\n if (selectedIndex === itemCount - 1) {\n selectedIndex = 0\n } else {\n selectedIndex++\n }\n updateSelected()\n break\n case 'ArrowLeft':\n event.preventDefault()\n selectedIndex = 0\n updateSelected()\n break\n case 'Enter':\n selectedItem?.click()\n break\n case 'Escape':\n ctx.close()\n break\n }\n })\n\n filter.addEventListener('input', () => {\n // Hide all items that don't match our filter\n const term = filter.value.toLocaleLowerCase()\n // When filtering, recompute which items are visible for arrow up/down and maintain selection.\n displayedItems = items.filter((item) => {\n const isVisible =\n !term || item.textContent?.toLocaleLowerCase().includes(term)\n item.style.display = isVisible ? 'block' : 'none'\n return isVisible\n })\n\n selectedIndex = 0\n if (displayedItems.includes(selectedItem)) {\n selectedIndex = displayedItems.findIndex(\n (d) => d === selectedItem\n )\n }\n itemCount = displayedItems.length\n\n updateSelected()\n\n // If we have an event then we can try and position the list under the source\n if (options.event) {\n let top = options.event.clientY - 10\n\n const bodyRect = document.body.getBoundingClientRect()\n\n const rootRect = ctx.root.getBoundingClientRect()\n if (\n bodyRect.height &&\n top > bodyRect.height - rootRect.height - 10\n ) {\n top = Math.max(0, bodyRect.height - rootRect.height - 10)\n }\n\n ctx.root.style.top = top + 'px'\n positionList()\n }\n })\n\n requestAnimationFrame(() => {\n // Focus the filter box when opening\n filter.focus()\n\n positionList()\n })\n })\n }\n\n return ctx\n }\n\n LiteGraph.ContextMenu.prototype = ctxMenu.prototype\n }\n}\n\napp.registerExtension(ext)\n","// @ts-strict-ignore\nimport { app } from '../../scripts/app'\n\n// Allows for simple dynamic prompt replacement\n// Inputs in the format {a|b} will have a random value of a or b chosen when the prompt is queued.\n\n/*\n * Strips C-style line and block comments from a string\n */\nfunction stripComments(str) {\n return str.replace(/\\/\\*[\\s\\S]*?\\*\\/|\\/\\/.*/g, '')\n}\n\napp.registerExtension({\n name: 'Comfy.DynamicPrompts',\n nodeCreated(node) {\n if (node.widgets) {\n // Locate dynamic prompt text widgets\n // Include any widgets with dynamicPrompts set to true, and customtext\n const widgets = node.widgets.filter((n) => n.dynamicPrompts)\n for (const widget of widgets) {\n // Override the serialization of the value to resolve dynamic prompts for all widgets supporting it in this node\n widget.serializeValue = (workflowNode, widgetIndex) => {\n let prompt = stripComments(widget.value)\n while (\n prompt.replace('\\\\{', '').includes('{') &&\n prompt.replace('\\\\}', '').includes('}')\n ) {\n const startIndex = prompt.replace('\\\\{', '00').indexOf('{')\n const endIndex = prompt.replace('\\\\}', '00').indexOf('}')\n\n const optionsString = prompt.substring(startIndex + 1, endIndex)\n const options = optionsString.split('|')\n\n const randomIndex = Math.floor(Math.random() * options.length)\n const randomOption = options[randomIndex]\n\n prompt =\n prompt.substring(0, startIndex) +\n randomOption +\n prompt.substring(endIndex + 1)\n }\n\n // Overwrite the value in the serialized workflow pnginfo\n if (workflowNode?.widgets_values)\n workflowNode.widgets_values[widgetIndex] = prompt\n\n return prompt\n }\n }\n }\n }\n})\n","import { app } from '../../scripts/app'\n\n// Allows you to edit the attention weight by holding ctrl (or cmd) and using the up/down arrow keys\n\napp.registerExtension({\n name: 'Comfy.EditAttention',\n init() {\n const editAttentionDelta = app.ui.settings.addSetting({\n id: 'Comfy.EditAttention.Delta',\n name: 'Ctrl+up/down precision',\n type: 'slider',\n attrs: {\n min: 0.01,\n max: 0.5,\n step: 0.01\n },\n defaultValue: 0.05\n })\n\n function incrementWeight(weight: string, delta: number): string {\n const floatWeight = parseFloat(weight)\n if (isNaN(floatWeight)) return weight\n const newWeight = floatWeight + delta\n return String(Number(newWeight.toFixed(10)))\n }\n\n type Enclosure = {\n start: number\n end: number\n }\n\n function findNearestEnclosure(\n text: string,\n cursorPos: number\n ): Enclosure | null {\n let start = cursorPos,\n end = cursorPos\n let openCount = 0,\n closeCount = 0\n\n // Find opening parenthesis before cursor\n while (start >= 0) {\n start--\n if (text[start] === '(' && openCount === closeCount) break\n if (text[start] === '(') openCount++\n if (text[start] === ')') closeCount++\n }\n if (start < 0) return null\n\n openCount = 0\n closeCount = 0\n\n // Find closing parenthesis after cursor\n while (end < text.length) {\n if (text[end] === ')' && openCount === closeCount) break\n if (text[end] === '(') openCount++\n if (text[end] === ')') closeCount++\n end++\n }\n if (end === text.length) return null\n\n return { start: start + 1, end: end }\n }\n\n function addWeightToParentheses(text: string): string {\n const parenRegex = /^\\((.*)\\)$/\n const parenMatch = text.match(parenRegex)\n\n const floatRegex = /:([+-]?(\\d*\\.)?\\d+([eE][+-]?\\d+)?)/\n const floatMatch = text.match(floatRegex)\n\n if (parenMatch && !floatMatch) {\n return `(${parenMatch[1]}:1.0)`\n } else {\n return text\n }\n }\n\n function editAttention(event: KeyboardEvent) {\n // @ts-expect-error Runtime narrowing not impl.\n const inputField: HTMLTextAreaElement = event.composedPath()[0]\n const delta = parseFloat(editAttentionDelta.value)\n\n if (inputField.tagName !== 'TEXTAREA') return\n if (!(event.key === 'ArrowUp' || event.key === 'ArrowDown')) return\n if (!event.ctrlKey && !event.metaKey) return\n\n event.preventDefault()\n\n let start = inputField.selectionStart\n let end = inputField.selectionEnd\n let selectedText = inputField.value.substring(start, end)\n\n // If there is no selection, attempt to find the nearest enclosure, or select the current word\n if (!selectedText) {\n const nearestEnclosure = findNearestEnclosure(inputField.value, start)\n if (nearestEnclosure) {\n start = nearestEnclosure.start\n end = nearestEnclosure.end\n selectedText = inputField.value.substring(start, end)\n } else {\n // Select the current word, find the start and end of the word\n const delimiters = ' .,\\\\/!?%^*;:{}=-_`~()\\r\\n\\t'\n\n while (\n !delimiters.includes(inputField.value[start - 1]) &&\n start > 0\n ) {\n start--\n }\n\n while (\n !delimiters.includes(inputField.value[end]) &&\n end < inputField.value.length\n ) {\n end++\n }\n\n selectedText = inputField.value.substring(start, end)\n if (!selectedText) return\n }\n }\n\n // If the selection ends with a space, remove it\n if (selectedText[selectedText.length - 1] === ' ') {\n selectedText = selectedText.substring(0, selectedText.length - 1)\n end -= 1\n }\n\n // If there are parentheses left and right of the selection, select them\n if (\n inputField.value[start - 1] === '(' &&\n inputField.value[end] === ')'\n ) {\n start -= 1\n end += 1\n selectedText = inputField.value.substring(start, end)\n }\n\n // If the selection is not enclosed in parentheses, add them\n if (\n selectedText[0] !== '(' ||\n selectedText[selectedText.length - 1] !== ')'\n ) {\n selectedText = `(${selectedText})`\n }\n\n // If the selection does not have a weight, add a weight of 1.0\n selectedText = addWeightToParentheses(selectedText)\n\n // Increment the weight\n const weightDelta = event.key === 'ArrowUp' ? delta : -delta\n const updatedText = selectedText.replace(\n /\\((.*):([+-]?\\d+(?:\\.\\d+)?)\\)/,\n (match, text, weight) => {\n weight = incrementWeight(weight, weightDelta)\n if (weight == 1) {\n return text\n } else {\n return `(${text}:${weight})`\n }\n }\n )\n\n inputField.setSelectionRange(start, end)\n // Intentional use of deprecated: https://developer.mozilla.org/docs/Web/API/Document/execCommand#using_inserttext\n document.execCommand('insertText', false, updatedText)\n inputField.setSelectionRange(start, start + updatedText.length)\n }\n window.addEventListener('keydown', editAttention)\n }\n})\n","// @ts-strict-ignore\nimport { $el, ComfyDialog } from '../../scripts/ui'\nimport { DraggableList } from '../../scripts/ui/draggableList'\nimport { GroupNodeConfig, GroupNodeHandler } from './groupNode'\nimport './groupNodeManage.css'\nimport { app, type ComfyApp } from '../../scripts/app'\nimport {\n LiteGraph,\n type LGraphNode,\n type LGraphNodeConstructor\n} from '@comfyorg/litegraph'\nimport { useToastStore } from '@/stores/toastStore'\n\nconst ORDER: symbol = Symbol()\nconst PREFIX = 'workflow'\nconst SEPARATOR = '>'\n\nfunction merge(target, source) {\n if (typeof target === 'object' && typeof source === 'object') {\n for (const key in source) {\n const sv = source[key]\n if (typeof sv === 'object') {\n let tv = target[key]\n if (!tv) tv = target[key] = {}\n merge(tv, source[key])\n } else {\n target[key] = sv\n }\n }\n }\n\n return target\n}\n\nexport class ManageGroupDialog extends ComfyDialog<HTMLDialogElement> {\n tabs: Record<\n 'Inputs' | 'Outputs' | 'Widgets',\n { tab: HTMLAnchorElement; page: HTMLElement }\n >\n selectedNodeIndex: number | null | undefined\n selectedTab: keyof ManageGroupDialog['tabs'] = 'Inputs'\n selectedGroup: string | undefined\n modifications: Record<\n string,\n Record<\n string,\n Record<\n string,\n { name?: string | undefined; visible?: boolean | undefined }\n >\n >\n > = {}\n nodeItems: any[]\n app: ComfyApp\n groupNodeType: LGraphNodeConstructor<LGraphNode>\n groupNodeDef: any\n groupData: any\n\n innerNodesList: HTMLUListElement\n widgetsPage: HTMLElement\n inputsPage: HTMLElement\n outputsPage: HTMLElement\n draggable: any\n\n get selectedNodeInnerIndex() {\n return +this.nodeItems[this.selectedNodeIndex].dataset.nodeindex\n }\n\n constructor(app) {\n super()\n this.app = app\n this.element = $el('dialog.comfy-group-manage', {\n parent: document.body\n }) as HTMLDialogElement\n }\n\n changeTab(tab) {\n this.tabs[this.selectedTab].tab.classList.remove('active')\n this.tabs[this.selectedTab].page.classList.remove('active')\n this.tabs[tab].tab.classList.add('active')\n this.tabs[tab].page.classList.add('active')\n this.selectedTab = tab\n }\n\n changeNode(index, force?) {\n if (!force && this.selectedNodeIndex === index) return\n\n if (this.selectedNodeIndex != null) {\n this.nodeItems[this.selectedNodeIndex].classList.remove('selected')\n }\n this.nodeItems[index].classList.add('selected')\n this.selectedNodeIndex = index\n\n if (!this.buildInputsPage() && this.selectedTab === 'Inputs') {\n this.changeTab('Widgets')\n }\n if (!this.buildWidgetsPage() && this.selectedTab === 'Widgets') {\n this.changeTab('Outputs')\n }\n if (!this.buildOutputsPage() && this.selectedTab === 'Outputs') {\n this.changeTab('Inputs')\n }\n\n this.changeTab(this.selectedTab)\n }\n\n getGroupData() {\n this.groupNodeType =\n LiteGraph.registered_node_types[\n `${PREFIX}${SEPARATOR}` + this.selectedGroup\n ]\n this.groupNodeDef = this.groupNodeType.nodeData\n this.groupData = GroupNodeHandler.getGroupData(this.groupNodeType)\n }\n\n changeGroup(group, reset = true) {\n this.selectedGroup = group\n this.getGroupData()\n\n const nodes = this.groupData.nodeData.nodes\n this.nodeItems = nodes.map((n, i) =>\n $el(\n 'li.draggable-item',\n {\n dataset: {\n nodeindex: n.index + ''\n },\n onclick: () => {\n this.changeNode(i)\n }\n },\n [\n $el('span.drag-handle'),\n $el(\n 'div',\n {\n textContent: n.title ?? n.type\n },\n n.title\n ? $el('span', {\n textContent: n.type\n })\n : []\n )\n ]\n )\n )\n\n this.innerNodesList.replaceChildren(...this.nodeItems)\n\n if (reset) {\n this.selectedNodeIndex = null\n this.changeNode(0)\n } else {\n const items = this.draggable.getAllItems()\n let index = items.findIndex((item) => item.classList.contains('selected'))\n if (index === -1) index = this.selectedNodeIndex\n this.changeNode(index, true)\n }\n\n const ordered = [...nodes]\n this.draggable?.dispose()\n this.draggable = new DraggableList(this.innerNodesList, 'li')\n this.draggable.addEventListener(\n 'dragend',\n ({ detail: { oldPosition, newPosition } }) => {\n if (oldPosition === newPosition) return\n ordered.splice(newPosition, 0, ordered.splice(oldPosition, 1)[0])\n for (let i = 0; i < ordered.length; i++) {\n this.storeModification({\n nodeIndex: ordered[i].index,\n section: ORDER,\n prop: 'order',\n value: i\n })\n }\n }\n )\n }\n\n storeModification(props: {\n nodeIndex?: number\n section: symbol\n prop: string\n value: any\n }) {\n const { nodeIndex, section, prop, value } = props\n const groupMod = (this.modifications[this.selectedGroup] ??= {})\n const nodesMod = (groupMod.nodes ??= {})\n const nodeMod = (nodesMod[nodeIndex ?? this.selectedNodeInnerIndex] ??= {})\n const typeMod = (nodeMod[section] ??= {})\n if (typeof value === 'object') {\n const objMod = (typeMod[prop] ??= {})\n Object.assign(objMod, value)\n } else {\n typeMod[prop] = value\n }\n }\n\n getEditElement(section, prop, value, placeholder, checked, checkable = true) {\n if (value === placeholder) value = ''\n\n const mods =\n this.modifications[this.selectedGroup]?.nodes?.[\n this.selectedNodeInnerIndex\n ]?.[section]?.[prop]\n if (mods) {\n if (mods.name != null) {\n value = mods.name\n }\n if (mods.visible != null) {\n checked = mods.visible\n }\n }\n\n return $el('div', [\n $el('input', {\n value,\n placeholder,\n type: 'text',\n onchange: (e) => {\n this.storeModification({\n section,\n prop,\n value: { name: e.target.value }\n })\n }\n }),\n $el('label', { textContent: 'Visible' }, [\n $el('input', {\n type: 'checkbox',\n checked,\n disabled: !checkable,\n onchange: (e) => {\n this.storeModification({\n section,\n prop,\n value: { visible: !!e.target.checked }\n })\n }\n })\n ])\n ])\n }\n\n buildWidgetsPage() {\n const widgets =\n this.groupData.oldToNewWidgetMap[this.selectedNodeInnerIndex]\n const items = Object.keys(widgets ?? {})\n const type = app.graph.extra.groupNodes[this.selectedGroup]\n const config = type.config?.[this.selectedNodeInnerIndex]?.input\n this.widgetsPage.replaceChildren(\n ...items.map((oldName) => {\n return this.getEditElement(\n 'input',\n oldName,\n widgets[oldName],\n oldName,\n config?.[oldName]?.visible !== false\n )\n })\n )\n return !!items.length\n }\n\n buildInputsPage() {\n const inputs = this.groupData.nodeInputs[this.selectedNodeInnerIndex]\n const items = Object.keys(inputs ?? {})\n const type = app.graph.extra.groupNodes[this.selectedGroup]\n const config = type.config?.[this.selectedNodeInnerIndex]?.input\n this.inputsPage.replaceChildren(\n ...items\n .map((oldName) => {\n let value = inputs[oldName]\n if (!value) {\n return\n }\n\n return this.getEditElement(\n 'input',\n oldName,\n value,\n oldName,\n config?.[oldName]?.visible !== false\n )\n })\n .filter(Boolean)\n )\n return !!items.length\n }\n\n buildOutputsPage() {\n const nodes = this.groupData.nodeData.nodes\n const innerNodeDef = this.groupData.getNodeDef(\n nodes[this.selectedNodeInnerIndex]\n )\n const outputs = innerNodeDef?.output ?? []\n const groupOutputs =\n this.groupData.oldToNewOutputMap[this.selectedNodeInnerIndex]\n\n const type = app.graph.extra.groupNodes[this.selectedGroup]\n const config = type.config?.[this.selectedNodeInnerIndex]?.output\n const node = this.groupData.nodeData.nodes[this.selectedNodeInnerIndex]\n const checkable = node.type !== 'PrimitiveNode'\n this.outputsPage.replaceChildren(\n ...outputs\n .map((type, slot) => {\n const groupOutputIndex = groupOutputs?.[slot]\n const oldName = innerNodeDef.output_name?.[slot] ?? type\n let value = config?.[slot]?.name\n const visible = config?.[slot]?.visible || groupOutputIndex != null\n if (!value || value === oldName) {\n value = ''\n }\n return this.getEditElement(\n 'output',\n slot,\n value,\n oldName,\n visible,\n checkable\n )\n })\n .filter(Boolean)\n )\n return !!outputs.length\n }\n\n show(type?) {\n const groupNodes = Object.keys(app.graph.extra?.groupNodes ?? {}).sort(\n (a, b) => a.localeCompare(b)\n )\n\n this.innerNodesList = $el(\n 'ul.comfy-group-manage-list-items'\n ) as HTMLUListElement\n this.widgetsPage = $el('section.comfy-group-manage-node-page')\n this.inputsPage = $el('section.comfy-group-manage-node-page')\n this.outputsPage = $el('section.comfy-group-manage-node-page')\n const pages = $el('div', [\n this.widgetsPage,\n this.inputsPage,\n this.outputsPage\n ])\n\n this.tabs = [\n ['Inputs', this.inputsPage],\n ['Widgets', this.widgetsPage],\n ['Outputs', this.outputsPage]\n ].reduce((p, [name, page]: [string, HTMLElement]) => {\n p[name] = {\n tab: $el('a', {\n onclick: () => {\n this.changeTab(name)\n },\n textContent: name\n }),\n page\n }\n return p\n }, {}) as any\n\n const outer = $el('div.comfy-group-manage-outer', [\n $el('header', [\n $el('h2', 'Group Nodes'),\n $el(\n 'select',\n {\n onchange: (e) => {\n this.changeGroup(e.target.value)\n }\n },\n groupNodes.map((g) =>\n $el('option', {\n textContent: g,\n selected: `${PREFIX}${SEPARATOR}` + g === type,\n value: g\n })\n )\n )\n ]),\n $el('main', [\n $el('section.comfy-group-manage-list', this.innerNodesList),\n $el('section.comfy-group-manage-node', [\n $el(\n 'header',\n Object.values(this.tabs).map((t) => t.tab)\n ),\n pages\n ])\n ]),\n $el('footer', [\n $el(\n 'button.comfy-btn',\n {\n onclick: (e) => {\n const node = app.graph.nodes.find(\n (n) => n.type === `${PREFIX}${SEPARATOR}` + this.selectedGroup\n )\n if (node) {\n useToastStore().addAlert(\n 'This group node is in use in the current workflow, please first remove these.'\n )\n return\n }\n if (\n confirm(\n `Are you sure you want to remove the node: \"${this.selectedGroup}\"`\n )\n ) {\n delete app.graph.extra.groupNodes[this.selectedGroup]\n LiteGraph.unregisterNodeType(\n `${PREFIX}${SEPARATOR}` + this.selectedGroup\n )\n }\n this.show()\n }\n },\n 'Delete Group Node'\n ),\n $el(\n 'button.comfy-btn',\n {\n onclick: async () => {\n let nodesByType\n let recreateNodes = []\n const types = {}\n for (const g in this.modifications) {\n const type = app.graph.extra.groupNodes[g]\n let config = (type.config ??= {})\n\n let nodeMods = this.modifications[g]?.nodes\n if (nodeMods) {\n const keys = Object.keys(nodeMods)\n if (nodeMods[keys[0]][ORDER]) {\n // If any node is reordered, they will all need sequencing\n const orderedNodes = []\n const orderedMods = {}\n const orderedConfig = {}\n\n for (const n of keys) {\n const order = nodeMods[n][ORDER].order\n orderedNodes[order] = type.nodes[+n]\n orderedMods[order] = nodeMods[n]\n orderedNodes[order].index = order\n }\n\n // Rewrite links\n for (const l of type.links) {\n if (l[0] != null) l[0] = type.nodes[l[0]].index\n if (l[2] != null) l[2] = type.nodes[l[2]].index\n }\n\n // Rewrite externals\n if (type.external) {\n for (const ext of type.external) {\n ext[0] = type.nodes[ext[0]]\n }\n }\n\n // Rewrite modifications\n for (const id of keys) {\n if (config[id]) {\n orderedConfig[type.nodes[id].index] = config[id]\n }\n delete config[id]\n }\n\n type.nodes = orderedNodes\n nodeMods = orderedMods\n type.config = config = orderedConfig\n }\n\n merge(config, nodeMods)\n }\n\n types[g] = type\n\n if (!nodesByType) {\n nodesByType = app.graph.nodes.reduce((p, n) => {\n p[n.type] ??= []\n p[n.type].push(n)\n return p\n }, {})\n }\n\n const nodes = nodesByType[`${PREFIX}${SEPARATOR}` + g]\n if (nodes) recreateNodes.push(...nodes)\n }\n\n await GroupNodeConfig.registerFromWorkflow(types, {})\n\n for (const node of recreateNodes) {\n node.recreate()\n }\n\n this.modifications = {}\n this.app.graph.setDirtyCanvas(true, true)\n this.changeGroup(this.selectedGroup, false)\n }\n },\n 'Save'\n ),\n $el(\n 'button.comfy-btn',\n { onclick: () => this.element.close() },\n 'Close'\n )\n ])\n ])\n\n this.element.replaceChildren(outer)\n this.changeGroup(\n type\n ? groupNodes.find((g) => `${PREFIX}${SEPARATOR}` + g === type)\n : groupNodes[0]\n )\n this.element.showModal()\n\n this.element.addEventListener('close', () => {\n this.draggable?.dispose()\n })\n }\n}\n","// @ts-strict-ignore\nimport { app } from '../../scripts/app'\nimport { api } from '../../scripts/api'\nimport { mergeIfValid } from './widgetInputs'\nimport { ManageGroupDialog } from './groupNodeManage'\nimport { LGraphCanvas, LiteGraph, type LGraph } from '@comfyorg/litegraph'\nimport { LGraphNode, type NodeId } from '@comfyorg/litegraph/dist/LGraphNode'\nimport { useNodeDefStore } from '@/stores/nodeDefStore'\nimport { ComfyLink, ComfyNode, ComfyWorkflowJSON } from '@/types/comfyWorkflow'\nimport { useToastStore } from '@/stores/toastStore'\nimport { ComfyExtension } from '@/types/comfy'\nimport {\n deserialiseAndCreate,\n serialise\n} from '@/extensions/core/vintageClipboard'\n\ntype GroupNodeWorkflowData = {\n external: ComfyLink[]\n links: ComfyLink[]\n nodes: ComfyNode[]\n}\n\nconst GROUP = Symbol()\n\n// v1 Prefix + Separator: workflow/\n// v2 Prefix + Separator: workflow> (ComfyUI_frontend v1.2.63)\nconst PREFIX = 'workflow'\nconst SEPARATOR = '>'\n\nconst Workflow = {\n InUse: {\n Free: 0,\n Registered: 1,\n InWorkflow: 2\n },\n isInUseGroupNode(name) {\n const id = `${PREFIX}${SEPARATOR}${name}`\n // Check if lready registered/in use in this workflow\n if (app.graph.extra?.groupNodes?.[name]) {\n if (app.graph.nodes.find((n) => n.type === id)) {\n return Workflow.InUse.InWorkflow\n } else {\n return Workflow.InUse.Registered\n }\n }\n return Workflow.InUse.Free\n },\n storeGroupNode(name: string, data: GroupNodeWorkflowData) {\n let extra = app.graph.extra\n if (!extra) app.graph.extra = extra = {}\n let groupNodes = extra.groupNodes\n if (!groupNodes) extra.groupNodes = groupNodes = {}\n groupNodes[name] = data\n }\n}\n\nclass GroupNodeBuilder {\n nodes: LGraphNode[]\n nodeData: any\n\n constructor(nodes: LGraphNode[]) {\n this.nodes = nodes\n }\n\n build() {\n const name = this.getName()\n if (!name) return\n\n // Sort the nodes so they are in execution order\n // this allows for widgets to be in the correct order when reconstructing\n this.sortNodes()\n\n this.nodeData = this.getNodeData()\n Workflow.storeGroupNode(name, this.nodeData)\n\n return { name, nodeData: this.nodeData }\n }\n\n getName() {\n const name = prompt('Enter group name')\n if (!name) return\n const used = Workflow.isInUseGroupNode(name)\n switch (used) {\n case Workflow.InUse.InWorkflow:\n useToastStore().addAlert(\n 'An in use group node with this name already exists embedded in this workflow, please remove any instances or use a new name.'\n )\n return\n case Workflow.InUse.Registered:\n if (\n !confirm(\n 'A group node with this name already exists embedded in this workflow, are you sure you want to overwrite it?'\n )\n ) {\n return\n }\n break\n }\n return name\n }\n\n sortNodes() {\n // Gets the builders nodes in graph execution order\n const nodesInOrder = app.graph.computeExecutionOrder(false)\n this.nodes = this.nodes\n .map((node) => ({ index: nodesInOrder.indexOf(node), node }))\n // @ts-expect-error id might be string\n .sort((a, b) => a.index - b.index || a.node.id - b.node.id)\n .map(({ node }) => node)\n }\n\n getNodeData() {\n const storeLinkTypes = (config) => {\n // Store link types for dynamically typed nodes e.g. reroutes\n for (const link of config.links) {\n const origin = app.graph.getNodeById(link[4])\n const type = origin.outputs[link[1]].type\n link.push(type)\n }\n }\n\n const storeExternalLinks = (config) => {\n // Store any external links to the group in the config so when rebuilding we add extra slots\n config.external = []\n for (let i = 0; i < this.nodes.length; i++) {\n const node = this.nodes[i]\n if (!node.outputs?.length) continue\n for (let slot = 0; slot < node.outputs.length; slot++) {\n let hasExternal = false\n const output = node.outputs[slot]\n let type = output.type\n if (!output.links?.length) continue\n for (const l of output.links) {\n const link = app.graph.links[l]\n if (!link) continue\n if (type === '*') type = link.type\n\n if (!app.canvas.selected_nodes[link.target_id]) {\n hasExternal = true\n break\n }\n }\n if (hasExternal) {\n config.external.push([i, slot, type])\n }\n }\n }\n }\n\n // Use the built in copyToClipboard function to generate the node data we need\n try {\n const serialised = serialise(this.nodes, app.canvas.graph)\n const config = JSON.parse(serialised)\n\n storeLinkTypes(config)\n storeExternalLinks(config)\n\n return config\n } finally {\n }\n }\n}\n\nexport class GroupNodeConfig {\n name: string\n nodeData: any\n inputCount: number\n oldToNewOutputMap: {}\n newToOldOutputMap: {}\n oldToNewInputMap: {}\n oldToNewWidgetMap: {}\n newToOldWidgetMap: {}\n primitiveDefs: {}\n widgetToPrimitive: {}\n primitiveToWidget: {}\n nodeInputs: {}\n outputVisibility: any[]\n nodeDef: any\n inputs: any[]\n linksFrom: {}\n linksTo: {}\n externalFrom: {}\n\n constructor(name, nodeData) {\n this.name = name\n this.nodeData = nodeData\n this.getLinks()\n\n this.inputCount = 0\n this.oldToNewOutputMap = {}\n this.newToOldOutputMap = {}\n this.oldToNewInputMap = {}\n this.oldToNewWidgetMap = {}\n this.newToOldWidgetMap = {}\n this.primitiveDefs = {}\n this.widgetToPrimitive = {}\n this.primitiveToWidget = {}\n this.nodeInputs = {}\n this.outputVisibility = []\n }\n\n async registerType(source = PREFIX) {\n this.nodeDef = {\n output: [],\n output_name: [],\n output_is_list: [],\n output_is_hidden: [],\n name: source + SEPARATOR + this.name,\n display_name: this.name,\n category: 'group nodes' + (SEPARATOR + source),\n input: { required: {} },\n description: `Group node combining ${this.nodeData.nodes\n .map((n) => n.type)\n .join(', ')}`,\n python_module: 'custom_nodes.' + this.name,\n\n [GROUP]: this\n }\n\n this.inputs = []\n const seenInputs = {}\n const seenOutputs = {}\n for (let i = 0; i < this.nodeData.nodes.length; i++) {\n const node = this.nodeData.nodes[i]\n node.index = i\n this.processNode(node, seenInputs, seenOutputs)\n }\n\n for (const p of this.#convertedToProcess) {\n p()\n }\n this.#convertedToProcess = null\n await app.registerNodeDef(`${PREFIX}${SEPARATOR}` + this.name, this.nodeDef)\n useNodeDefStore().addNodeDef(this.nodeDef)\n }\n\n getLinks() {\n this.linksFrom = {}\n this.linksTo = {}\n this.externalFrom = {}\n\n // Extract links for easy lookup\n for (const l of this.nodeData.links) {\n const [sourceNodeId, sourceNodeSlot, targetNodeId, targetNodeSlot] = l\n\n // Skip links outside the copy config\n if (sourceNodeId == null) continue\n\n if (!this.linksFrom[sourceNodeId]) {\n this.linksFrom[sourceNodeId] = {}\n }\n if (!this.linksFrom[sourceNodeId][sourceNodeSlot]) {\n this.linksFrom[sourceNodeId][sourceNodeSlot] = []\n }\n this.linksFrom[sourceNodeId][sourceNodeSlot].push(l)\n\n if (!this.linksTo[targetNodeId]) {\n this.linksTo[targetNodeId] = {}\n }\n this.linksTo[targetNodeId][targetNodeSlot] = l\n }\n\n if (this.nodeData.external) {\n for (const ext of this.nodeData.external) {\n if (!this.externalFrom[ext[0]]) {\n this.externalFrom[ext[0]] = { [ext[1]]: ext[2] }\n } else {\n this.externalFrom[ext[0]][ext[1]] = ext[2]\n }\n }\n }\n }\n\n processNode(node, seenInputs, seenOutputs) {\n const def = this.getNodeDef(node)\n if (!def) return\n\n const inputs = { ...def.input?.required, ...def.input?.optional }\n\n this.inputs.push(this.processNodeInputs(node, seenInputs, inputs))\n if (def.output?.length) this.processNodeOutputs(node, seenOutputs, def)\n }\n\n getNodeDef(node) {\n const def = globalDefs[node.type]\n if (def) return def\n\n const linksFrom = this.linksFrom[node.index]\n if (node.type === 'PrimitiveNode') {\n // Skip as its not linked\n if (!linksFrom) return\n\n let type = linksFrom['0'][0][5]\n if (type === 'COMBO') {\n // Use the array items\n const source = node.outputs[0].widget.name\n const fromTypeName = this.nodeData.nodes[linksFrom['0'][0][2]].type\n const fromType = globalDefs[fromTypeName]\n const input =\n fromType.input.required[source] ?? fromType.input.optional[source]\n type = input[0]\n }\n\n const def = (this.primitiveDefs[node.index] = {\n input: {\n required: {\n value: [type, {}]\n }\n },\n output: [type],\n output_name: [],\n output_is_list: []\n })\n return def\n } else if (node.type === 'Reroute') {\n const linksTo = this.linksTo[node.index]\n if (linksTo && linksFrom && !this.externalFrom[node.index]?.[0]) {\n // Being used internally\n return null\n }\n\n let config = {}\n let rerouteType = '*'\n if (linksFrom) {\n for (const [, , id, slot] of linksFrom['0']) {\n const node = this.nodeData.nodes[id]\n const input = node.inputs[slot]\n if (rerouteType === '*') {\n rerouteType = input.type\n }\n if (input.widget) {\n const targetDef = globalDefs[node.type]\n const targetWidget =\n targetDef.input.required[input.widget.name] ??\n targetDef.input.optional[input.widget.name]\n\n const widget = [targetWidget[0], config]\n const res = mergeIfValid(\n {\n widget\n },\n targetWidget,\n false,\n null,\n widget\n )\n config = res?.customConfig ?? config\n }\n }\n } else if (linksTo) {\n const [id, slot] = linksTo['0']\n rerouteType = this.nodeData.nodes[id].outputs[slot].type\n } else {\n // Reroute used as a pipe\n for (const l of this.nodeData.links) {\n if (l[2] === node.index) {\n rerouteType = l[5]\n break\n }\n }\n if (rerouteType === '*') {\n // Check for an external link\n const t = this.externalFrom[node.index]?.[0]\n if (t) {\n rerouteType = t\n }\n }\n }\n\n // @ts-expect-error\n config.forceInput = true\n return {\n input: {\n required: {\n [rerouteType]: [rerouteType, config]\n }\n },\n output: [rerouteType],\n output_name: [],\n output_is_list: []\n }\n }\n\n console.warn(\n 'Skipping virtual node ' +\n node.type +\n ' when building group node ' +\n this.name\n )\n }\n\n getInputConfig(node, inputName, seenInputs, config, extra?) {\n const customConfig = this.nodeData.config?.[node.index]?.input?.[inputName]\n let name =\n customConfig?.name ??\n node.inputs?.find((inp) => inp.name === inputName)?.label ??\n inputName\n let key = name\n let prefix = ''\n // Special handling for primitive to include the title if it is set rather than just \"value\"\n if ((node.type === 'PrimitiveNode' && node.title) || name in seenInputs) {\n prefix = `${node.title ?? node.type} `\n key = name = `${prefix}${inputName}`\n if (name in seenInputs) {\n name = `${prefix}${seenInputs[name]} ${inputName}`\n }\n }\n seenInputs[key] = (seenInputs[key] ?? 1) + 1\n\n if (inputName === 'seed' || inputName === 'noise_seed') {\n if (!extra) extra = {}\n extra.control_after_generate = `${prefix}control_after_generate`\n }\n if (config[0] === 'IMAGEUPLOAD') {\n if (!extra) extra = {}\n extra.widget =\n this.oldToNewWidgetMap[node.index]?.[config[1]?.widget ?? 'image'] ??\n 'image'\n }\n\n if (extra) {\n config = [config[0], { ...config[1], ...extra }]\n }\n\n return { name, config, customConfig }\n }\n\n processWidgetInputs(inputs, node, inputNames, seenInputs) {\n const slots = []\n const converted = new Map()\n const widgetMap = (this.oldToNewWidgetMap[node.index] = {})\n for (const inputName of inputNames) {\n let widgetType = app.getWidgetType(inputs[inputName], inputName)\n if (widgetType) {\n const convertedIndex = node.inputs?.findIndex(\n (inp) => inp.name === inputName && inp.widget?.name === inputName\n )\n if (convertedIndex > -1) {\n // This widget has been converted to a widget\n // We need to store this in the correct position so link ids line up\n converted.set(convertedIndex, inputName)\n widgetMap[inputName] = null\n } else {\n // Normal widget\n const { name, config } = this.getInputConfig(\n node,\n inputName,\n seenInputs,\n inputs[inputName]\n )\n this.nodeDef.input.required[name] = config\n widgetMap[inputName] = name\n this.newToOldWidgetMap[name] = { node, inputName }\n }\n } else {\n // Normal input\n slots.push(inputName)\n }\n }\n return { converted, slots }\n }\n\n checkPrimitiveConnection(link, inputName, inputs) {\n const sourceNode = this.nodeData.nodes[link[0]]\n if (sourceNode.type === 'PrimitiveNode') {\n // Merge link configurations\n const [sourceNodeId, _, targetNodeId, __] = link\n const primitiveDef = this.primitiveDefs[sourceNodeId]\n const targetWidget = inputs[inputName]\n const primitiveConfig = primitiveDef.input.required.value\n const output = { widget: primitiveConfig }\n const config = mergeIfValid(\n output,\n targetWidget,\n false,\n null,\n primitiveConfig\n )\n primitiveConfig[1] =\n config?.customConfig ?? inputs[inputName][1]\n ? { ...inputs[inputName][1] }\n : {}\n\n let name = this.oldToNewWidgetMap[sourceNodeId]['value']\n name = name.substr(0, name.length - 6)\n primitiveConfig[1].control_after_generate = true\n primitiveConfig[1].control_prefix = name\n\n let toPrimitive = this.widgetToPrimitive[targetNodeId]\n if (!toPrimitive) {\n toPrimitive = this.widgetToPrimitive[targetNodeId] = {}\n }\n if (toPrimitive[inputName]) {\n toPrimitive[inputName].push(sourceNodeId)\n }\n toPrimitive[inputName] = sourceNodeId\n\n let toWidget = this.primitiveToWidget[sourceNodeId]\n if (!toWidget) {\n toWidget = this.primitiveToWidget[sourceNodeId] = []\n }\n toWidget.push({ nodeId: targetNodeId, inputName })\n }\n }\n\n processInputSlots(inputs, node, slots, linksTo, inputMap, seenInputs) {\n this.nodeInputs[node.index] = {}\n for (let i = 0; i < slots.length; i++) {\n const inputName = slots[i]\n if (linksTo[i]) {\n this.checkPrimitiveConnection(linksTo[i], inputName, inputs)\n // This input is linked so we can skip it\n continue\n }\n\n const { name, config, customConfig } = this.getInputConfig(\n node,\n inputName,\n seenInputs,\n inputs[inputName]\n )\n\n this.nodeInputs[node.index][inputName] = name\n if (customConfig?.visible === false) continue\n\n this.nodeDef.input.required[name] = config\n inputMap[i] = this.inputCount++\n }\n }\n\n processConvertedWidgets(\n inputs,\n node,\n slots,\n converted,\n linksTo,\n inputMap,\n seenInputs\n ) {\n // Add converted widgets sorted into their index order (ordered as they were converted) so link ids match up\n const convertedSlots = [...converted.keys()]\n .sort()\n .map((k) => converted.get(k))\n for (let i = 0; i < convertedSlots.length; i++) {\n const inputName = convertedSlots[i]\n if (linksTo[slots.length + i]) {\n this.checkPrimitiveConnection(\n linksTo[slots.length + i],\n inputName,\n inputs\n )\n // This input is linked so we can skip it\n continue\n }\n\n const { name, config } = this.getInputConfig(\n node,\n inputName,\n seenInputs,\n inputs[inputName],\n {\n defaultInput: true\n }\n )\n\n this.nodeDef.input.required[name] = config\n this.newToOldWidgetMap[name] = { node, inputName }\n\n if (!this.oldToNewWidgetMap[node.index]) {\n this.oldToNewWidgetMap[node.index] = {}\n }\n this.oldToNewWidgetMap[node.index][inputName] = name\n\n inputMap[slots.length + i] = this.inputCount++\n }\n }\n\n #convertedToProcess = []\n processNodeInputs(node, seenInputs, inputs) {\n const inputMapping = []\n\n const inputNames = Object.keys(inputs)\n if (!inputNames.length) return\n\n const { converted, slots } = this.processWidgetInputs(\n inputs,\n node,\n inputNames,\n seenInputs\n )\n const linksTo = this.linksTo[node.index] ?? {}\n const inputMap = (this.oldToNewInputMap[node.index] = {})\n this.processInputSlots(inputs, node, slots, linksTo, inputMap, seenInputs)\n\n // Converted inputs have to be processed after all other nodes as they'll be at the end of the list\n this.#convertedToProcess.push(() =>\n this.processConvertedWidgets(\n inputs,\n node,\n slots,\n converted,\n linksTo,\n inputMap,\n seenInputs\n )\n )\n\n return inputMapping\n }\n\n processNodeOutputs(node, seenOutputs, def) {\n const oldToNew = (this.oldToNewOutputMap[node.index] = {})\n\n // Add outputs\n for (let outputId = 0; outputId < def.output.length; outputId++) {\n const linksFrom = this.linksFrom[node.index]\n // If this output is linked internally we flag it to hide\n const hasLink =\n linksFrom?.[outputId] && !this.externalFrom[node.index]?.[outputId]\n const customConfig =\n this.nodeData.config?.[node.index]?.output?.[outputId]\n const visible = customConfig?.visible ?? !hasLink\n this.outputVisibility.push(visible)\n if (!visible) {\n continue\n }\n\n oldToNew[outputId] = this.nodeDef.output.length\n this.newToOldOutputMap[this.nodeDef.output.length] = {\n node,\n slot: outputId\n }\n this.nodeDef.output.push(def.output[outputId])\n this.nodeDef.output_is_list.push(def.output_is_list[outputId])\n\n let label = customConfig?.name\n if (!label) {\n label = def.output_name?.[outputId] ?? def.output[outputId]\n const output = node.outputs.find((o) => o.name === label)\n if (output?.label) {\n label = output.label\n }\n }\n\n let name = label\n if (name in seenOutputs) {\n const prefix = `${node.title ?? node.type} `\n name = `${prefix}${label}`\n if (name in seenOutputs) {\n name = `${prefix}${node.index} ${label}`\n }\n }\n seenOutputs[name] = 1\n\n this.nodeDef.output_name.push(name)\n }\n }\n\n static async registerFromWorkflow(groupNodes, missingNodeTypes) {\n for (const g in groupNodes) {\n const groupData = groupNodes[g]\n\n let hasMissing = false\n for (const n of groupData.nodes) {\n // Find missing node types\n if (!(n.type in LiteGraph.registered_node_types)) {\n missingNodeTypes.push({\n type: n.type,\n hint: ` (In group node '${PREFIX}${SEPARATOR}${g}')`\n })\n\n missingNodeTypes.push({\n type: `${PREFIX}${SEPARATOR}` + g,\n action: {\n text: 'Remove from workflow',\n callback: (e) => {\n delete groupNodes[g]\n e.target.textContent = 'Removed'\n e.target.style.pointerEvents = 'none'\n e.target.style.opacity = 0.7\n }\n }\n })\n\n hasMissing = true\n }\n }\n\n if (hasMissing) continue\n\n const config = new GroupNodeConfig(g, groupData)\n await config.registerType()\n }\n }\n}\n\nexport class GroupNodeHandler {\n node\n groupData\n innerNodes: any\n\n constructor(node) {\n this.node = node\n this.groupData = node.constructor?.nodeData?.[GROUP]\n\n this.node.setInnerNodes = (innerNodes) => {\n this.innerNodes = innerNodes\n\n for (\n let innerNodeIndex = 0;\n innerNodeIndex < this.innerNodes.length;\n innerNodeIndex++\n ) {\n const innerNode = this.innerNodes[innerNodeIndex]\n\n for (const w of innerNode.widgets ?? []) {\n if (w.type === 'converted-widget') {\n w.serializeValue = w.origSerializeValue\n }\n }\n\n innerNode.index = innerNodeIndex\n innerNode.getInputNode = (slot) => {\n // Check if this input is internal or external\n const externalSlot =\n this.groupData.oldToNewInputMap[innerNode.index]?.[slot]\n if (externalSlot != null) {\n return this.node.getInputNode(externalSlot)\n }\n\n // Internal link\n const innerLink = this.groupData.linksTo[innerNode.index]?.[slot]\n if (!innerLink) return null\n\n const inputNode = innerNodes[innerLink[0]]\n // Primitives will already apply their values\n if (inputNode.type === 'PrimitiveNode') return null\n\n return inputNode\n }\n\n innerNode.getInputLink = (slot) => {\n const externalSlot =\n this.groupData.oldToNewInputMap[innerNode.index]?.[slot]\n if (externalSlot != null) {\n // The inner node is connected via the group node inputs\n const linkId = this.node.inputs[externalSlot].link\n let link = app.graph.links[linkId]\n\n // Use the outer link, but update the target to the inner node\n // @ts-expect-error\n // TODO: Fix this\n link = {\n ...link,\n target_id: innerNode.id,\n target_slot: +slot\n }\n return link\n }\n\n let link = this.groupData.linksTo[innerNode.index]?.[slot]\n if (!link) return null\n // Use the inner link, but update the origin node to be inner node id\n link = {\n origin_id: innerNodes[link[0]].id,\n origin_slot: link[1],\n target_id: innerNode.id,\n target_slot: +slot\n }\n return link\n }\n }\n }\n\n this.node.updateLink = (link) => {\n // Replace the group node reference with the internal node\n link = { ...link }\n const output = this.groupData.newToOldOutputMap[link.origin_slot]\n let innerNode = this.innerNodes[output.node.index]\n let l\n while (innerNode?.type === 'Reroute') {\n l = innerNode.getInputLink(0)\n innerNode = innerNode.getInputNode(0)\n }\n\n if (!innerNode) {\n return null\n }\n\n if (l && GroupNodeHandler.isGroupNode(innerNode)) {\n return innerNode.updateLink(l)\n }\n\n link.origin_id = innerNode.id\n link.origin_slot = l?.origin_slot ?? output.slot\n return link\n }\n\n this.node.getInnerNodes = () => {\n if (!this.innerNodes) {\n this.node.setInnerNodes(\n this.groupData.nodeData.nodes.map((n, i) => {\n const innerNode = LiteGraph.createNode(n.type)\n innerNode.configure(n)\n innerNode.id = `${this.node.id}:${i}`\n return innerNode\n })\n )\n }\n\n this.updateInnerWidgets()\n\n return this.innerNodes\n }\n\n this.node.recreate = async () => {\n const id = this.node.id\n const sz = this.node.size\n const nodes = this.node.convertToNodes()\n\n const groupNode = LiteGraph.createNode(this.node.type)\n groupNode.id = id\n\n // Reuse the existing nodes for this instance\n groupNode.setInnerNodes(nodes)\n groupNode[GROUP].populateWidgets()\n app.graph.add(groupNode)\n groupNode.size = [\n Math.max(groupNode.size[0], sz[0]),\n Math.max(groupNode.size[1], sz[1])\n ]\n\n // Remove all converted nodes and relink them\n const builder = new GroupNodeBuilder(nodes)\n const nodeData = builder.getNodeData()\n groupNode[GROUP].groupData.nodeData.links = nodeData.links\n groupNode[GROUP].replaceNodes(nodes)\n return groupNode\n }\n\n this.node.convertToNodes = () => {\n const addInnerNodes = () => {\n // Clone the node data so we dont mutate it for other nodes\n const c = { ...this.groupData.nodeData }\n c.nodes = [...c.nodes]\n const innerNodes = this.node.getInnerNodes()\n let ids = []\n for (let i = 0; i < c.nodes.length; i++) {\n let id = innerNodes?.[i]?.id\n // Use existing IDs if they are set on the inner nodes\n if (id == null || isNaN(id)) {\n id = undefined\n } else {\n ids.push(id)\n }\n c.nodes[i] = { ...c.nodes[i], id }\n }\n deserialiseAndCreate(JSON.stringify(c), app.canvas)\n\n const [x, y] = this.node.pos\n let top\n let left\n // Configure nodes with current widget data\n const selectedIds = ids.length\n ? ids\n : Object.keys(app.canvas.selected_nodes)\n const newNodes = []\n for (let i = 0; i < selectedIds.length; i++) {\n const id = selectedIds[i]\n const newNode = app.graph.getNodeById(id)\n const innerNode = innerNodes[i]\n newNodes.push(newNode)\n\n if (left == null || newNode.pos[0] < left) {\n left = newNode.pos[0]\n }\n if (top == null || newNode.pos[1] < top) {\n top = newNode.pos[1]\n }\n\n if (!newNode.widgets) continue\n\n const map = this.groupData.oldToNewWidgetMap[innerNode.index]\n if (map) {\n const widgets = Object.keys(map)\n\n for (const oldName of widgets) {\n const newName = map[oldName]\n if (!newName) continue\n\n const widgetIndex = this.node.widgets.findIndex(\n (w) => w.name === newName\n )\n if (widgetIndex === -1) continue\n\n // Populate the main and any linked widgets\n if (innerNode.type === 'PrimitiveNode') {\n for (let i = 0; i < newNode.widgets.length; i++) {\n newNode.widgets[i].value =\n this.node.widgets[widgetIndex + i].value\n }\n } else {\n const outerWidget = this.node.widgets[widgetIndex]\n const newWidget = newNode.widgets.find(\n (w) => w.name === oldName\n )\n if (!newWidget) continue\n\n newWidget.value = outerWidget.value\n for (let w = 0; w < outerWidget.linkedWidgets?.length; w++) {\n newWidget.linkedWidgets[w].value =\n outerWidget.linkedWidgets[w].value\n }\n }\n }\n }\n }\n\n // Shift each node\n for (const newNode of newNodes) {\n newNode.pos[0] -= left - x\n newNode.pos[1] -= top - y\n }\n\n return { newNodes, selectedIds }\n }\n\n const reconnectInputs = (selectedIds) => {\n for (const innerNodeIndex in this.groupData.oldToNewInputMap) {\n const id = selectedIds[innerNodeIndex]\n const newNode = app.graph.getNodeById(id)\n const map = this.groupData.oldToNewInputMap[innerNodeIndex]\n for (const innerInputId in map) {\n const groupSlotId = map[innerInputId]\n if (groupSlotId == null) continue\n const slot = node.inputs[groupSlotId]\n if (slot.link == null) continue\n const link = app.graph.links[slot.link]\n if (!link) continue\n // connect this node output to the input of another node\n const originNode = app.graph.getNodeById(link.origin_id)\n originNode.connect(link.origin_slot, newNode, +innerInputId)\n }\n }\n }\n\n const reconnectOutputs = (selectedIds) => {\n for (\n let groupOutputId = 0;\n groupOutputId < node.outputs?.length;\n groupOutputId++\n ) {\n const output = node.outputs[groupOutputId]\n if (!output.links) continue\n const links = [...output.links]\n for (const l of links) {\n const slot = this.groupData.newToOldOutputMap[groupOutputId]\n const link = app.graph.links[l]\n const targetNode = app.graph.getNodeById(link.target_id)\n const newNode = app.graph.getNodeById(selectedIds[slot.node.index])\n newNode.connect(slot.slot, targetNode, link.target_slot)\n }\n }\n }\n\n app.canvas.emitBeforeChange()\n\n const { newNodes, selectedIds } = addInnerNodes()\n reconnectInputs(selectedIds)\n reconnectOutputs(selectedIds)\n app.graph.remove(this.node)\n\n app.canvas.emitAfterChange()\n\n return newNodes\n }\n\n const getExtraMenuOptions = this.node.getExtraMenuOptions\n this.node.getExtraMenuOptions = function (_, options) {\n getExtraMenuOptions?.apply(this, arguments)\n\n let optionIndex = options.findIndex((o) => o.content === 'Outputs')\n if (optionIndex === -1) optionIndex = options.length\n else optionIndex++\n options.splice(\n optionIndex,\n 0,\n null,\n {\n content: 'Convert to nodes',\n callback: () => {\n return this.convertToNodes()\n }\n },\n {\n content: 'Manage Group Node',\n callback: manageGroupNodes\n }\n )\n }\n\n // Draw custom collapse icon to identity this as a group\n const onDrawTitleBox = this.node.onDrawTitleBox\n this.node.onDrawTitleBox = function (ctx, height, size, scale) {\n onDrawTitleBox?.apply(this, arguments)\n\n const fill = ctx.fillStyle\n ctx.beginPath()\n ctx.rect(11, -height + 11, 2, 2)\n ctx.rect(14, -height + 11, 2, 2)\n ctx.rect(17, -height + 11, 2, 2)\n ctx.rect(11, -height + 14, 2, 2)\n ctx.rect(14, -height + 14, 2, 2)\n ctx.rect(17, -height + 14, 2, 2)\n ctx.rect(11, -height + 17, 2, 2)\n ctx.rect(14, -height + 17, 2, 2)\n ctx.rect(17, -height + 17, 2, 2)\n\n ctx.fillStyle = this.boxcolor || LiteGraph.NODE_DEFAULT_BOXCOLOR\n ctx.fill()\n ctx.fillStyle = fill\n }\n\n // Draw progress label\n const onDrawForeground = node.onDrawForeground\n const groupData = this.groupData.nodeData\n node.onDrawForeground = function (ctx) {\n const r = onDrawForeground?.apply?.(this, arguments)\n if (\n +app.runningNodeId === this.id &&\n this.runningInternalNodeId !== null\n ) {\n const n = groupData.nodes[this.runningInternalNodeId]\n if (!n) return\n const message = `Running ${n.title || n.type} (${this.runningInternalNodeId}/${groupData.nodes.length})`\n ctx.save()\n ctx.font = '12px sans-serif'\n const sz = ctx.measureText(message)\n ctx.fillStyle = node.boxcolor || LiteGraph.NODE_DEFAULT_BOXCOLOR\n ctx.beginPath()\n ctx.roundRect(\n 0,\n -LiteGraph.NODE_TITLE_HEIGHT - 20,\n sz.width + 12,\n 20,\n 5\n )\n ctx.fill()\n\n ctx.fillStyle = '#fff'\n ctx.fillText(message, 6, -LiteGraph.NODE_TITLE_HEIGHT - 6)\n ctx.restore()\n }\n }\n\n // Flag this node as needing to be reset\n const onExecutionStart = this.node.onExecutionStart\n this.node.onExecutionStart = function () {\n this.resetExecution = true\n return onExecutionStart?.apply(this, arguments)\n }\n\n const self = this\n const onNodeCreated = this.node.onNodeCreated\n this.node.onNodeCreated = function () {\n if (!this.widgets) {\n return\n }\n const config = self.groupData.nodeData.config\n if (config) {\n for (const n in config) {\n const inputs = config[n]?.input\n for (const w in inputs) {\n if (inputs[w].visible !== false) continue\n const widgetName = self.groupData.oldToNewWidgetMap[n][w]\n const widget = this.widgets.find((w) => w.name === widgetName)\n if (widget) {\n widget.type = 'hidden'\n widget.computeSize = () => [0, -4]\n }\n }\n }\n }\n\n return onNodeCreated?.apply(this, arguments)\n }\n\n function handleEvent(type, getId, getEvent) {\n const handler = ({ detail }) => {\n const id = getId(detail)\n if (!id) return\n const node = app.graph.getNodeById(id)\n if (node) return\n\n const innerNodeIndex = this.innerNodes?.findIndex((n) => n.id == id)\n if (innerNodeIndex > -1) {\n this.node.runningInternalNodeId = innerNodeIndex\n api.dispatchEvent(\n new CustomEvent(type, {\n detail: getEvent(detail, this.node.id + '', this.node)\n })\n )\n }\n }\n api.addEventListener(type, handler)\n return handler\n }\n\n const executing = handleEvent.call(\n this,\n 'executing',\n (d) => d,\n (d, id, node) => id\n )\n\n const executed = handleEvent.call(\n this,\n 'executed',\n (d) => d?.display_node || d?.node,\n (d, id, node) => ({\n ...d,\n node: id,\n display_node: id,\n merge: !node.resetExecution\n })\n )\n\n const onRemoved = node.onRemoved\n this.node.onRemoved = function () {\n onRemoved?.apply(this, arguments)\n api.removeEventListener('executing', executing)\n api.removeEventListener('executed', executed)\n }\n\n this.node.refreshComboInNode = (defs) => {\n // Update combo widget options\n for (const widgetName in this.groupData.newToOldWidgetMap) {\n const widget = this.node.widgets.find((w) => w.name === widgetName)\n if (widget?.type === 'combo') {\n const old = this.groupData.newToOldWidgetMap[widgetName]\n const def = defs[old.node.type]\n const input =\n def?.input?.required?.[old.inputName] ??\n def?.input?.optional?.[old.inputName]\n if (!input) continue\n\n widget.options.values = input[0]\n\n if (\n old.inputName !== 'image' &&\n !widget.options.values.includes(widget.value)\n ) {\n widget.value = widget.options.values[0]\n widget.callback(widget.value)\n }\n }\n }\n }\n }\n\n updateInnerWidgets() {\n for (const newWidgetName in this.groupData.newToOldWidgetMap) {\n const newWidget = this.node.widgets.find((w) => w.name === newWidgetName)\n if (!newWidget) continue\n\n const newValue = newWidget.value\n const old = this.groupData.newToOldWidgetMap[newWidgetName]\n let innerNode = this.innerNodes[old.node.index]\n\n if (innerNode.type === 'PrimitiveNode') {\n innerNode.primitiveValue = newValue\n const primitiveLinked = this.groupData.primitiveToWidget[old.node.index]\n for (const linked of primitiveLinked ?? []) {\n const node = this.innerNodes[linked.nodeId]\n const widget = node.widgets.find((w) => w.name === linked.inputName)\n\n if (widget) {\n widget.value = newValue\n }\n }\n continue\n } else if (innerNode.type === 'Reroute') {\n const rerouteLinks = this.groupData.linksFrom[old.node.index]\n if (rerouteLinks) {\n for (const [_, , targetNodeId, targetSlot] of rerouteLinks['0']) {\n const node = this.innerNodes[targetNodeId]\n const input = node.inputs[targetSlot]\n if (input.widget) {\n const widget = node.widgets?.find(\n (w) => w.name === input.widget.name\n )\n if (widget) {\n widget.value = newValue\n }\n }\n }\n }\n }\n\n const widget = innerNode.widgets?.find((w) => w.name === old.inputName)\n if (widget) {\n widget.value = newValue\n }\n }\n }\n\n populatePrimitive(node, nodeId, oldName, i, linkedShift) {\n // Converted widget, populate primitive if linked\n const primitiveId = this.groupData.widgetToPrimitive[nodeId]?.[oldName]\n if (primitiveId == null) return\n const targetWidgetName =\n this.groupData.oldToNewWidgetMap[primitiveId]['value']\n const targetWidgetIndex = this.node.widgets.findIndex(\n (w) => w.name === targetWidgetName\n )\n if (targetWidgetIndex > -1) {\n const primitiveNode = this.innerNodes[primitiveId]\n let len = primitiveNode.widgets.length\n if (\n len - 1 !==\n this.node.widgets[targetWidgetIndex].linkedWidgets?.length\n ) {\n // Fallback handling for if some reason the primitive has a different number of widgets\n // we dont want to overwrite random widgets, better to leave blank\n len = 1\n }\n for (let i = 0; i < len; i++) {\n this.node.widgets[targetWidgetIndex + i].value =\n primitiveNode.widgets[i].value\n }\n }\n return true\n }\n\n populateReroute(node, nodeId, map) {\n if (node.type !== 'Reroute') return\n\n const link = this.groupData.linksFrom[nodeId]?.[0]?.[0]\n if (!link) return\n const [, , targetNodeId, targetNodeSlot] = link\n const targetNode = this.groupData.nodeData.nodes[targetNodeId]\n const inputs = targetNode.inputs\n const targetWidget = inputs?.[targetNodeSlot]?.widget\n if (!targetWidget) return\n\n const offset = inputs.length - (targetNode.widgets_values?.length ?? 0)\n const v = targetNode.widgets_values?.[targetNodeSlot - offset]\n if (v == null) return\n\n const widgetName = Object.values(map)[0]\n const widget = this.node.widgets.find((w) => w.name === widgetName)\n if (widget) {\n widget.value = v\n }\n }\n\n populateWidgets() {\n if (!this.node.widgets) return\n\n for (\n let nodeId = 0;\n nodeId < this.groupData.nodeData.nodes.length;\n nodeId++\n ) {\n const node = this.groupData.nodeData.nodes[nodeId]\n const map = this.groupData.oldToNewWidgetMap[nodeId] ?? {}\n const widgets = Object.keys(map)\n\n if (!node.widgets_values?.length) {\n // special handling for populating values into reroutes\n // this allows primitives connect to them to pick up the correct value\n this.populateReroute(node, nodeId, map)\n continue\n }\n\n let linkedShift = 0\n for (let i = 0; i < widgets.length; i++) {\n const oldName = widgets[i]\n const newName = map[oldName]\n const widgetIndex = this.node.widgets.findIndex(\n (w) => w.name === newName\n )\n const mainWidget = this.node.widgets[widgetIndex]\n if (\n this.populatePrimitive(node, nodeId, oldName, i, linkedShift) ||\n widgetIndex === -1\n ) {\n // Find the inner widget and shift by the number of linked widgets as they will have been removed too\n const innerWidget = this.innerNodes[nodeId].widgets?.find(\n (w) => w.name === oldName\n )\n linkedShift += innerWidget?.linkedWidgets?.length ?? 0\n }\n if (widgetIndex === -1) {\n continue\n }\n\n // Populate the main and any linked widget\n mainWidget.value = node.widgets_values[i + linkedShift]\n for (let w = 0; w < mainWidget.linkedWidgets?.length; w++) {\n this.node.widgets[widgetIndex + w + 1].value =\n node.widgets_values[i + ++linkedShift]\n }\n }\n }\n }\n\n replaceNodes(nodes) {\n let top\n let left\n\n for (let i = 0; i < nodes.length; i++) {\n const node = nodes[i]\n if (left == null || node.pos[0] < left) {\n left = node.pos[0]\n }\n if (top == null || node.pos[1] < top) {\n top = node.pos[1]\n }\n\n this.linkOutputs(node, i)\n app.graph.remove(node)\n }\n\n this.linkInputs()\n this.node.pos = [left, top]\n }\n\n linkOutputs(originalNode, nodeId) {\n if (!originalNode.outputs) return\n\n for (const output of originalNode.outputs) {\n if (!output.links) continue\n // Clone the links as they'll be changed if we reconnect\n const links = [...output.links]\n for (const l of links) {\n const link = app.graph.links[l]\n if (!link) continue\n\n const targetNode = app.graph.getNodeById(link.target_id)\n const newSlot =\n this.groupData.oldToNewOutputMap[nodeId]?.[link.origin_slot]\n if (newSlot != null) {\n this.node.connect(newSlot, targetNode, link.target_slot)\n }\n }\n }\n }\n\n linkInputs() {\n for (const link of this.groupData.nodeData.links ?? []) {\n const [, originSlot, targetId, targetSlot, actualOriginId] = link\n const originNode = app.graph.getNodeById(actualOriginId)\n if (!originNode) continue // this node is in the group\n originNode.connect(\n originSlot,\n this.node.id,\n this.groupData.oldToNewInputMap[targetId][targetSlot]\n )\n }\n }\n\n static getGroupData(node) {\n return (node.nodeData ?? node.constructor?.nodeData)?.[GROUP]\n }\n\n static isGroupNode(node: LGraphNode) {\n return !!node.constructor?.nodeData?.[GROUP]\n }\n\n static async fromNodes(nodes: LGraphNode[]) {\n // Process the nodes into the stored workflow group node data\n const builder = new GroupNodeBuilder(nodes)\n const res = builder.build()\n if (!res) return\n\n const { name, nodeData } = res\n\n // Convert this data into a LG node definition and register it\n const config = new GroupNodeConfig(name, nodeData)\n await config.registerType()\n\n const groupNode = LiteGraph.createNode(`${PREFIX}${SEPARATOR}${name}`)\n // Reuse the existing nodes for this instance\n groupNode.setInnerNodes(builder.nodes)\n groupNode[GROUP].populateWidgets()\n app.graph.add(groupNode)\n\n // Remove all converted nodes and relink them\n groupNode[GROUP].replaceNodes(builder.nodes)\n return groupNode\n }\n}\n\nfunction addConvertToGroupOptions() {\n function addConvertOption(options, index) {\n const selected = Object.values(app.canvas.selected_nodes ?? {})\n const disabled =\n selected.length < 2 ||\n selected.find((n) => GroupNodeHandler.isGroupNode(n))\n options.splice(index + 1, null, {\n content: `Convert to Group Node`,\n disabled,\n callback: convertSelectedNodesToGroupNode\n })\n }\n\n function addManageOption(options, index) {\n const groups = app.graph.extra?.groupNodes\n const disabled = !groups || !Object.keys(groups).length\n options.splice(index + 1, null, {\n content: `Manage Group Nodes`,\n disabled,\n callback: manageGroupNodes\n })\n }\n\n // Add to canvas\n const getCanvasMenuOptions = LGraphCanvas.prototype.getCanvasMenuOptions\n LGraphCanvas.prototype.getCanvasMenuOptions = function () {\n const options = getCanvasMenuOptions.apply(this, arguments)\n const index =\n options.findIndex((o) => o?.content === 'Add Group') + 1 || options.length\n addConvertOption(options, index)\n addManageOption(options, index + 1)\n return options\n }\n\n // Add to nodes\n const getNodeMenuOptions = LGraphCanvas.prototype.getNodeMenuOptions\n LGraphCanvas.prototype.getNodeMenuOptions = function (node) {\n const options = getNodeMenuOptions.apply(this, arguments)\n if (!GroupNodeHandler.isGroupNode(node)) {\n const index =\n options.findIndex((o) => o?.content === 'Outputs') + 1 ||\n options.length - 1\n addConvertOption(options, index)\n }\n return options\n }\n}\n\nconst replaceLegacySeparators = (nodes: ComfyNode[]): void => {\n for (const node of nodes) {\n if (typeof node.type === 'string' && node.type.startsWith('workflow/')) {\n node.type = node.type.replace(/^workflow\\//, `${PREFIX}${SEPARATOR}`)\n }\n }\n}\n\n/**\n * Convert selected nodes to a group node\n * @throws {Error} if no nodes are selected\n * @throws {Error} if a group node is already selected\n * @throws {Error} if a group node is selected\n *\n * The context menu item should not be available if any of the above conditions are met.\n * The error is automatically handled by the commandStore when the command is executed.\n */\nasync function convertSelectedNodesToGroupNode() {\n const nodes = Object.values(app.canvas.selected_nodes ?? {})\n if (nodes.length === 0) {\n throw new Error('No nodes selected')\n }\n if (nodes.length === 1) {\n throw new Error('Please select multiple nodes to convert to group node')\n }\n if (nodes.some((n) => GroupNodeHandler.isGroupNode(n))) {\n throw new Error('Selected nodes contain a group node')\n }\n return await GroupNodeHandler.fromNodes(nodes)\n}\n\nfunction ungroupSelectedGroupNodes() {\n const nodes = Object.values(app.canvas.selected_nodes ?? {})\n for (const node of nodes) {\n if (GroupNodeHandler.isGroupNode(node)) {\n node['convertToNodes']?.()\n }\n }\n}\n\nfunction manageGroupNodes() {\n new ManageGroupDialog(app).show()\n}\n\nconst id = 'Comfy.GroupNode'\nlet globalDefs\nconst ext: ComfyExtension = {\n name: id,\n commands: [\n {\n id: 'Comfy.GroupNode.ConvertSelectedNodesToGroupNode',\n label: 'Convert selected nodes to group node',\n icon: 'pi pi-sitemap',\n versionAdded: '1.3.17',\n function: convertSelectedNodesToGroupNode\n },\n {\n id: 'Comfy.GroupNode.UngroupSelectedGroupNodes',\n label: 'Ungroup selected group nodes',\n icon: 'pi pi-sitemap',\n versionAdded: '1.3.17',\n function: ungroupSelectedGroupNodes\n },\n {\n id: 'Comfy.GroupNode.ManageGroupNodes',\n label: 'Manage group nodes',\n icon: 'pi pi-cog',\n versionAdded: '1.3.17',\n function: manageGroupNodes\n }\n ],\n keybindings: [\n {\n commandId: 'Comfy.GroupNode.ConvertSelectedNodesToGroupNode',\n combo: {\n alt: true,\n key: 'g'\n }\n },\n {\n commandId: 'Comfy.GroupNode.UngroupSelectedGroupNodes',\n combo: {\n alt: true,\n shift: true,\n key: 'G'\n }\n }\n ],\n setup() {\n addConvertToGroupOptions()\n },\n async beforeConfigureGraph(\n graphData: ComfyWorkflowJSON,\n missingNodeTypes: string[]\n ) {\n const nodes = graphData?.extra?.groupNodes\n if (nodes) {\n replaceLegacySeparators(graphData.nodes)\n await GroupNodeConfig.registerFromWorkflow(nodes, missingNodeTypes)\n }\n },\n addCustomNodeDefs(defs) {\n // Store this so we can mutate it later with group nodes\n globalDefs = defs\n },\n nodeCreated(node) {\n if (GroupNodeHandler.isGroupNode(node)) {\n node[GROUP] = new GroupNodeHandler(node)\n\n // Ensure group nodes pasted from other workflows are stored\n if (node.title && node[GROUP]?.groupData?.nodeData) {\n Workflow.storeGroupNode(node.title, node[GROUP].groupData.nodeData)\n }\n }\n },\n async refreshComboInNodes(defs) {\n // Re-register group nodes so new ones are created with the correct options\n Object.assign(globalDefs, defs)\n const nodes = app.graph.extra?.groupNodes\n if (nodes) {\n await GroupNodeConfig.registerFromWorkflow(nodes, {})\n }\n }\n}\n\napp.registerExtension(ext)\n","// @ts-strict-ignore\nimport { LGraphGroup } from '@comfyorg/litegraph'\nimport { app } from '../../scripts/app'\nimport { LGraphCanvas } from '@comfyorg/litegraph'\nimport type { Positionable } from '@comfyorg/litegraph/dist/interfaces'\nimport type { LGraphNode } from '@comfyorg/litegraph'\n\nfunction setNodeMode(node: LGraphNode, mode: number) {\n node.mode = mode\n node.graph?.change()\n}\n\nfunction addNodesToGroup(group: LGraphGroup, items: Iterable<Positionable>) {\n group.resizeTo([...group.children, ...items])\n}\n\napp.registerExtension({\n name: 'Comfy.GroupOptions',\n setup() {\n const orig = LGraphCanvas.prototype.getCanvasMenuOptions\n // graph_mouse\n LGraphCanvas.prototype.getCanvasMenuOptions = function (\n this: LGraphCanvas\n ) {\n const options = orig.apply(this, arguments)\n const group = this.graph.getGroupOnPos(\n this.graph_mouse[0],\n this.graph_mouse[1]\n )\n if (!group) {\n options.push({\n content: 'Add Group For Selected Nodes',\n disabled: !this.selectedItems?.size,\n callback: () => {\n const group = new LGraphGroup()\n addNodesToGroup(group, this.selectedItems)\n this.graph.add(group)\n this.graph.change()\n }\n })\n\n return options\n }\n\n // Group nodes aren't recomputed until the group is moved, this ensures the nodes are up-to-date\n group.recomputeInsideNodes()\n const nodesInGroup = group.nodes\n\n options.push({\n content: 'Add Selected Nodes To Group',\n disabled: !this.selectedItems?.size,\n callback: () => {\n addNodesToGroup(group, this.selectedItems)\n this.graph.change()\n }\n })\n\n // No nodes in group, return default options\n if (nodesInGroup.length === 0) {\n return options\n } else {\n // Add a separator between the default options and the group options\n options.push(null)\n }\n\n // Check if all nodes are the same mode\n let allNodesAreSameMode = true\n for (let i = 1; i < nodesInGroup.length; i++) {\n if (nodesInGroup[i].mode !== nodesInGroup[0].mode) {\n allNodesAreSameMode = false\n break\n }\n }\n\n options.push({\n content: 'Fit Group To Nodes',\n callback: () => {\n group.recomputeInsideNodes()\n group.resizeTo(group.children)\n this.graph.change()\n }\n })\n\n options.push({\n content: 'Select Nodes',\n callback: () => {\n this.selectNodes(nodesInGroup)\n this.graph.change()\n this.canvas.focus()\n }\n })\n\n // Modes\n // 0: Always\n // 1: On Event\n // 2: Never\n // 3: On Trigger\n // 4: Bypass\n // If all nodes are the same mode, add a menu option to change the mode\n if (allNodesAreSameMode) {\n const mode = nodesInGroup[0].mode\n switch (mode) {\n case 0:\n // All nodes are always, option to disable, and bypass\n options.push({\n content: 'Set Group Nodes to Never',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 2)\n }\n }\n })\n options.push({\n content: 'Bypass Group Nodes',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 4)\n }\n }\n })\n break\n case 2:\n // All nodes are never, option to enable, and bypass\n options.push({\n content: 'Set Group Nodes to Always',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 0)\n }\n }\n })\n options.push({\n content: 'Bypass Group Nodes',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 4)\n }\n }\n })\n break\n case 4:\n // All nodes are bypass, option to enable, and disable\n options.push({\n content: 'Set Group Nodes to Always',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 0)\n }\n }\n })\n options.push({\n content: 'Set Group Nodes to Never',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 2)\n }\n }\n })\n break\n default:\n // All nodes are On Trigger or On Event(Or other?), option to disable, set to always, or bypass\n options.push({\n content: 'Set Group Nodes to Always',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 0)\n }\n }\n })\n options.push({\n content: 'Set Group Nodes to Never',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 2)\n }\n }\n })\n options.push({\n content: 'Bypass Group Nodes',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 4)\n }\n }\n })\n break\n }\n } else {\n // Nodes are not all the same mode, add a menu option to change the mode to always, never, or bypass\n options.push({\n content: 'Set Group Nodes to Always',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 0)\n }\n }\n })\n options.push({\n content: 'Set Group Nodes to Never',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 2)\n }\n }\n })\n options.push({\n content: 'Bypass Group Nodes',\n callback: () => {\n for (const node of nodesInGroup) {\n setNodeMode(node, 4)\n }\n }\n })\n }\n\n return options\n }\n }\n})\n","// @ts-strict-ignore\nimport { LiteGraph } from '@comfyorg/litegraph'\nimport { app } from '../../scripts/app'\n\n// Inverts the scrolling of context menus\n\nconst id = 'Comfy.InvertMenuScrolling'\napp.registerExtension({\n name: id,\n init() {\n const ctxMenu = LiteGraph.ContextMenu\n const replace = () => {\n // @ts-expect-error\n LiteGraph.ContextMenu = function (values, options) {\n options = options || {}\n if (options.scroll_speed) {\n options.scroll_speed *= -1\n } else {\n options.scroll_speed = -0.1\n }\n return ctxMenu.call(this, values, options)\n }\n LiteGraph.ContextMenu.prototype = ctxMenu.prototype\n }\n app.ui.settings.addSetting({\n id,\n category: ['Comfy', 'Graph', 'InvertMenuScrolling'],\n name: 'Invert Context Menu Scrolling',\n type: 'boolean',\n defaultValue: false,\n onChange(value) {\n if (value) {\n replace()\n } else {\n LiteGraph.ContextMenu = ctxMenu\n }\n }\n })\n }\n})\n","import { app } from '../../scripts/app'\nimport { KeyComboImpl, useKeybindingStore } from '@/stores/keybindingStore'\nimport { useCommandStore } from '@/stores/commandStore'\n\napp.registerExtension({\n name: 'Comfy.Keybinds',\n init() {\n const keybindListener = async function (event: KeyboardEvent) {\n // Ignore keybindings for legacy jest tests as jest tests don't have\n // a Vue app instance or pinia stores.\n if (!app.vueAppReady) return\n\n const keyCombo = KeyComboImpl.fromEvent(event)\n if (keyCombo.isModifier) {\n return\n }\n\n // Ignore non-modifier keybindings if typing in input fields\n const target = event.composedPath()[0] as HTMLElement\n if (\n !keyCombo.hasModifier &&\n (target.tagName === 'TEXTAREA' ||\n target.tagName === 'INPUT' ||\n (target.tagName === 'SPAN' &&\n target.classList.contains('property_value')))\n ) {\n return\n }\n\n const keybindingStore = useKeybindingStore()\n const commandStore = useCommandStore()\n const keybinding = keybindingStore.getKeybinding(keyCombo)\n if (keybinding && keybinding.targetSelector !== '#graph-canvas') {\n // Prevent default browser behavior first, then execute the command\n event.preventDefault()\n await commandStore.execute(keybinding.commandId)\n return\n }\n\n // Finished Handling all modifier keybinds, now handle the rest\n if (event.ctrlKey || event.altKey || event.metaKey) {\n return\n }\n\n // Close out of modals using escape\n if (event.key === 'Escape') {\n const modals = document.querySelectorAll<HTMLElement>('.comfy-modal')\n const modal = Array.from(modals).find(\n (modal) =>\n window.getComputedStyle(modal).getPropertyValue('display') !==\n 'none'\n )\n if (modal) {\n modal.style.display = 'none'\n }\n\n ;[...document.querySelectorAll('dialog')].forEach((d) => {\n d.close()\n })\n }\n }\n\n window.addEventListener('keydown', keybindListener)\n }\n})\n","// @ts-strict-ignore\nimport { app } from '../../scripts/app'\nimport { ComfyDialog, $el } from '../../scripts/ui'\nimport { ComfyApp } from '../../scripts/app'\nimport { api } from '../../scripts/api'\nimport { ClipspaceDialog } from './clipspace'\n\n// Helper function to convert a data URL to a Blob object\nfunction dataURLToBlob(dataURL) {\n const parts = dataURL.split(';base64,')\n const contentType = parts[0].split(':')[1]\n const byteString = atob(parts[1])\n const arrayBuffer = new ArrayBuffer(byteString.length)\n const uint8Array = new Uint8Array(arrayBuffer)\n for (let i = 0; i < byteString.length; i++) {\n uint8Array[i] = byteString.charCodeAt(i)\n }\n return new Blob([arrayBuffer], { type: contentType })\n}\n\nfunction loadedImageToBlob(image) {\n const canvas = document.createElement('canvas')\n\n canvas.width = image.width\n canvas.height = image.height\n\n const ctx = canvas.getContext('2d')\n\n ctx.drawImage(image, 0, 0)\n\n const dataURL = canvas.toDataURL('image/png', 1)\n const blob = dataURLToBlob(dataURL)\n\n return blob\n}\n\nfunction loadImage(imagePath) {\n return new Promise((resolve, reject) => {\n const image = new Image()\n\n image.onload = function () {\n resolve(image)\n }\n\n image.src = imagePath\n })\n}\n\nasync function uploadMask(filepath, formData) {\n await api\n .fetchApi('/upload/mask', {\n method: 'POST',\n body: formData\n })\n .then((response) => {})\n .catch((error) => {\n console.error('Error:', error)\n })\n\n ComfyApp.clipspace.imgs[ComfyApp.clipspace['selectedIndex']] = new Image()\n ComfyApp.clipspace.imgs[ComfyApp.clipspace['selectedIndex']].src = api.apiURL(\n '/view?' +\n new URLSearchParams(filepath).toString() +\n app.getPreviewFormatParam() +\n app.getRandParam()\n )\n\n if (ComfyApp.clipspace.images)\n ComfyApp.clipspace.images[ComfyApp.clipspace['selectedIndex']] = filepath\n\n ClipspaceDialog.invalidatePreview()\n}\n\nfunction prepare_mask(image, maskCanvas, maskCtx, maskColor) {\n // paste mask data into alpha channel\n maskCtx.drawImage(image, 0, 0, maskCanvas.width, maskCanvas.height)\n const maskData = maskCtx.getImageData(\n 0,\n 0,\n maskCanvas.width,\n maskCanvas.height\n )\n\n // invert mask\n for (let i = 0; i < maskData.data.length; i += 4) {\n if (maskData.data[i + 3] == 255) maskData.data[i + 3] = 0\n else maskData.data[i + 3] = 255\n\n maskData.data[i] = maskColor.r\n maskData.data[i + 1] = maskColor.g\n maskData.data[i + 2] = maskColor.b\n }\n\n maskCtx.globalCompositeOperation = 'source-over'\n maskCtx.putImageData(maskData, 0, 0)\n}\n\n// Define the PointerType enum\nenum PointerType {\n Arc = 'arc',\n Rect = 'rect'\n}\n\nenum CompositionOperation {\n SourceOver = 'source-over',\n DestinationOut = 'destination-out'\n}\n\nclass MaskEditorDialog extends ComfyDialog {\n static instance = null\n static mousedown_x: number | null = null\n static mousedown_y: number | null = null\n\n brush: HTMLDivElement\n maskCtx: any\n maskCanvas: HTMLCanvasElement\n brush_size_slider: HTMLDivElement\n brush_opacity_slider: HTMLDivElement\n colorButton: HTMLButtonElement\n saveButton: HTMLButtonElement\n zoom_ratio: number\n pan_x: number\n pan_y: number\n imgCanvas: HTMLCanvasElement\n last_display_style: string\n is_visible: boolean\n image: HTMLImageElement\n handler_registered: boolean\n brush_slider_input: HTMLInputElement\n cursorX: number\n cursorY: number\n mousedown_pan_x: number\n mousedown_pan_y: number\n last_pressure: number\n pointer_type: PointerType\n brush_pointer_type_select: HTMLDivElement\n\n static getInstance() {\n if (!MaskEditorDialog.instance) {\n MaskEditorDialog.instance = new MaskEditorDialog()\n }\n\n return MaskEditorDialog.instance\n }\n\n is_layout_created = false\n\n constructor() {\n super()\n this.element = $el('div.comfy-modal', { parent: document.body }, [\n $el('div.comfy-modal-content', [...this.createButtons()])\n ])\n }\n\n createButtons() {\n return []\n }\n\n createButton(name, callback): HTMLButtonElement {\n var button = document.createElement('button')\n button.style.pointerEvents = 'auto'\n button.innerText = name\n button.addEventListener('click', callback)\n return button\n }\n\n createLeftButton(name, callback) {\n var button = this.createButton(name, callback)\n button.style.cssFloat = 'left'\n button.style.marginRight = '4px'\n return button\n }\n\n createRightButton(name, callback) {\n var button = this.createButton(name, callback)\n button.style.cssFloat = 'right'\n button.style.marginLeft = '4px'\n return button\n }\n\n createLeftSlider(self, name, callback): HTMLDivElement {\n const divElement = document.createElement('div')\n divElement.id = 'maskeditor-slider'\n divElement.style.cssFloat = 'left'\n divElement.style.fontFamily = 'sans-serif'\n divElement.style.marginRight = '4px'\n divElement.style.color = 'var(--input-text)'\n divElement.style.backgroundColor = 'var(--comfy-input-bg)'\n divElement.style.borderRadius = '8px'\n divElement.style.borderColor = 'var(--border-color)'\n divElement.style.borderStyle = 'solid'\n divElement.style.fontSize = '15px'\n divElement.style.height = '25px'\n divElement.style.padding = '1px 6px'\n divElement.style.display = 'flex'\n divElement.style.position = 'relative'\n divElement.style.top = '2px'\n divElement.style.pointerEvents = 'auto'\n self.brush_slider_input = document.createElement('input')\n self.brush_slider_input.setAttribute('type', 'range')\n self.brush_slider_input.setAttribute('min', '1')\n self.brush_slider_input.setAttribute('max', '100')\n self.brush_slider_input.setAttribute('value', '10')\n const labelElement = document.createElement('label')\n labelElement.textContent = name\n\n divElement.appendChild(labelElement)\n divElement.appendChild(self.brush_slider_input)\n\n self.brush_slider_input.addEventListener('change', callback)\n\n return divElement\n }\n\n createOpacitySlider(self, name, callback): HTMLDivElement {\n const divElement = document.createElement('div')\n divElement.id = 'maskeditor-opacity-slider'\n divElement.style.cssFloat = 'left'\n divElement.style.fontFamily = 'sans-serif'\n divElement.style.marginRight = '4px'\n divElement.style.color = 'var(--input-text)'\n divElement.style.backgroundColor = 'var(--comfy-input-bg)'\n divElement.style.borderRadius = '8px'\n divElement.style.borderColor = 'var(--border-color)'\n divElement.style.borderStyle = 'solid'\n divElement.style.fontSize = '15px'\n divElement.style.height = '25px'\n divElement.style.padding = '1px 6px'\n divElement.style.display = 'flex'\n divElement.style.position = 'relative'\n divElement.style.top = '2px'\n divElement.style.pointerEvents = 'auto'\n self.opacity_slider_input = document.createElement('input')\n self.opacity_slider_input.setAttribute('type', 'range')\n self.opacity_slider_input.setAttribute('min', '0.1')\n self.opacity_slider_input.setAttribute('max', '1.0')\n self.opacity_slider_input.setAttribute('step', '0.01')\n self.opacity_slider_input.setAttribute('value', '0.7')\n const labelElement = document.createElement('label')\n labelElement.textContent = name\n\n divElement.appendChild(labelElement)\n divElement.appendChild(self.opacity_slider_input)\n\n self.opacity_slider_input.addEventListener('input', callback)\n\n return divElement\n }\n\n createPointerTypeSelect(self: any): HTMLDivElement {\n const divElement = document.createElement('div')\n divElement.id = 'maskeditor-pointer-type'\n divElement.style.cssFloat = 'left'\n divElement.style.fontFamily = 'sans-serif'\n divElement.style.marginRight = '4px'\n divElement.style.color = 'var(--input-text)'\n divElement.style.backgroundColor = 'var(--comfy-input-bg)'\n divElement.style.borderRadius = '8px'\n divElement.style.borderColor = 'var(--border-color)'\n divElement.style.borderStyle = 'solid'\n divElement.style.fontSize = '15px'\n divElement.style.height = '25px'\n divElement.style.padding = '1px 6px'\n divElement.style.display = 'flex'\n divElement.style.position = 'relative'\n divElement.style.top = '2px'\n divElement.style.pointerEvents = 'auto'\n\n const labelElement = document.createElement('label')\n labelElement.textContent = 'Pointer Type:'\n\n const selectElement = document.createElement('select')\n selectElement.style.borderRadius = '0'\n selectElement.style.borderColor = 'transparent'\n selectElement.style.borderStyle = 'unset'\n selectElement.style.fontSize = '0.9em'\n\n const optionArc = document.createElement('option')\n optionArc.value = 'arc'\n optionArc.text = 'Circle'\n optionArc.selected = true // Fix for TypeScript, \"selected\" should be boolean\n\n const optionRect = document.createElement('option')\n optionRect.value = 'rect'\n optionRect.text = 'Square'\n\n selectElement.appendChild(optionArc)\n selectElement.appendChild(optionRect)\n\n selectElement.addEventListener('change', (event: Event) => {\n const target = event.target as HTMLSelectElement\n self.pointer_type = target.value\n this.setBrushBorderRadius(self)\n })\n\n divElement.appendChild(labelElement)\n divElement.appendChild(selectElement)\n\n return divElement\n }\n\n setBrushBorderRadius(self: any): void {\n if (self.pointer_type === PointerType.Rect) {\n this.brush.style.borderRadius = '0%'\n // @ts-expect-error\n this.brush.style.MozBorderRadius = '0%'\n // @ts-expect-error\n this.brush.style.WebkitBorderRadius = '0%'\n } else {\n this.brush.style.borderRadius = '50%'\n // @ts-expect-error\n this.brush.style.MozBorderRadius = '50%'\n // @ts-expect-error\n this.brush.style.WebkitBorderRadius = '50%'\n }\n }\n\n setlayout(imgCanvas: HTMLCanvasElement, maskCanvas: HTMLCanvasElement) {\n const self = this\n self.pointer_type = PointerType.Arc\n\n // If it is specified as relative, using it only as a hidden placeholder for padding is recommended\n // to prevent anomalies where it exceeds a certain size and goes outside of the window.\n var bottom_panel = document.createElement('div')\n bottom_panel.style.position = 'absolute'\n bottom_panel.style.bottom = '0px'\n bottom_panel.style.left = '20px'\n bottom_panel.style.right = '20px'\n bottom_panel.style.height = '50px'\n bottom_panel.style.pointerEvents = 'none'\n\n var brush = document.createElement('div')\n brush.id = 'brush'\n brush.style.backgroundColor = 'transparent'\n brush.style.outline = '1px dashed black'\n brush.style.boxShadow = '0 0 0 1px white'\n brush.style.position = 'absolute'\n brush.style.zIndex = '8889'\n brush.style.pointerEvents = 'none'\n this.brush = brush\n this.setBrushBorderRadius(self)\n this.element.appendChild(imgCanvas)\n this.element.appendChild(maskCanvas)\n this.element.appendChild(bottom_panel)\n document.body.appendChild(brush)\n\n var clearButton = this.createLeftButton('Clear', () => {\n self.maskCtx.clearRect(\n 0,\n 0,\n self.maskCanvas.width,\n self.maskCanvas.height\n )\n })\n\n this.brush_size_slider = this.createLeftSlider(\n self,\n 'Thickness',\n (event) => {\n self.brush_size = event.target.value\n self.updateBrushPreview(self)\n }\n )\n\n this.brush_opacity_slider = this.createOpacitySlider(\n self,\n 'Opacity',\n (event) => {\n self.brush_opacity = event.target.value\n if (self.brush_color_mode !== 'negative') {\n self.maskCanvas.style.opacity = self.brush_opacity.toString()\n }\n }\n )\n\n this.brush_pointer_type_select = this.createPointerTypeSelect(self)\n this.colorButton = this.createLeftButton(this.getColorButtonText(), () => {\n if (self.brush_color_mode === 'black') {\n self.brush_color_mode = 'white'\n } else if (self.brush_color_mode === 'white') {\n self.brush_color_mode = 'negative'\n } else {\n self.brush_color_mode = 'black'\n }\n\n self.updateWhenBrushColorModeChanged()\n })\n\n var cancelButton = this.createRightButton('Cancel', () => {\n document.removeEventListener('keydown', MaskEditorDialog.handleKeyDown)\n self.close()\n })\n\n this.saveButton = this.createRightButton('Save', () => {\n document.removeEventListener('keydown', MaskEditorDialog.handleKeyDown)\n self.save()\n })\n\n this.element.appendChild(imgCanvas)\n this.element.appendChild(maskCanvas)\n this.element.appendChild(bottom_panel)\n\n bottom_panel.appendChild(clearButton)\n bottom_panel.appendChild(this.saveButton)\n bottom_panel.appendChild(cancelButton)\n bottom_panel.appendChild(this.brush_size_slider)\n bottom_panel.appendChild(this.brush_opacity_slider)\n bottom_panel.appendChild(this.brush_pointer_type_select)\n bottom_panel.appendChild(this.colorButton)\n\n imgCanvas.style.position = 'absolute'\n maskCanvas.style.position = 'absolute'\n\n imgCanvas.style.top = '200'\n imgCanvas.style.left = '0'\n\n maskCanvas.style.top = imgCanvas.style.top\n maskCanvas.style.left = imgCanvas.style.left\n\n const maskCanvasStyle = this.getMaskCanvasStyle()\n maskCanvas.style.mixBlendMode = maskCanvasStyle.mixBlendMode\n maskCanvas.style.opacity = maskCanvasStyle.opacity.toString()\n }\n\n async show() {\n this.zoom_ratio = 1.0\n this.pan_x = 0\n this.pan_y = 0\n\n if (!this.is_layout_created) {\n // layout\n const imgCanvas = document.createElement('canvas')\n const maskCanvas = document.createElement('canvas')\n\n imgCanvas.id = 'imageCanvas'\n maskCanvas.id = 'maskCanvas'\n\n this.setlayout(imgCanvas, maskCanvas)\n\n // prepare content\n this.imgCanvas = imgCanvas\n this.maskCanvas = maskCanvas\n this.maskCtx = maskCanvas.getContext('2d', { willReadFrequently: true })\n\n this.setEventHandler(maskCanvas)\n\n this.is_layout_created = true\n\n // replacement of onClose hook since close is not real close\n const self = this\n const observer = new MutationObserver(function (mutations) {\n mutations.forEach(function (mutation) {\n if (\n mutation.type === 'attributes' &&\n mutation.attributeName === 'style'\n ) {\n if (\n self.last_display_style &&\n self.last_display_style != 'none' &&\n self.element.style.display == 'none'\n ) {\n self.brush.style.display = 'none'\n ComfyApp.onClipspaceEditorClosed()\n }\n\n self.last_display_style = self.element.style.display\n }\n })\n })\n\n const config = { attributes: true }\n observer.observe(this.element, config)\n }\n\n // The keydown event needs to be reconfigured when closing the dialog as it gets removed.\n document.addEventListener('keydown', MaskEditorDialog.handleKeyDown)\n\n if (ComfyApp.clipspace_return_node) {\n this.saveButton.innerText = 'Save to node'\n } else {\n this.saveButton.innerText = 'Save'\n }\n this.saveButton.disabled = false\n\n this.element.style.display = 'block'\n this.element.style.width = '85%'\n this.element.style.margin = '0 7.5%'\n this.element.style.height = '100vh'\n this.element.style.top = '50%'\n this.element.style.left = '42%'\n this.element.style.zIndex = '8888' // NOTE: alert dialog must be high priority.\n\n await this.setImages(this.imgCanvas)\n\n this.is_visible = true\n }\n\n isOpened() {\n return this.element.style.display == 'block'\n }\n\n invalidateCanvas(orig_image, mask_image) {\n this.imgCanvas.width = orig_image.width\n this.imgCanvas.height = orig_image.height\n\n this.maskCanvas.width = orig_image.width\n this.maskCanvas.height = orig_image.height\n\n let imgCtx = this.imgCanvas.getContext('2d', { willReadFrequently: true })\n let maskCtx = this.maskCanvas.getContext('2d', {\n willReadFrequently: true\n })\n\n imgCtx.drawImage(orig_image, 0, 0, orig_image.width, orig_image.height)\n prepare_mask(mask_image, this.maskCanvas, maskCtx, this.getMaskColor())\n }\n\n async setImages(imgCanvas) {\n let self = this\n\n const imgCtx = imgCanvas.getContext('2d', { willReadFrequently: true })\n const maskCtx = this.maskCtx\n const maskCanvas = this.maskCanvas\n\n imgCtx.clearRect(0, 0, this.imgCanvas.width, this.imgCanvas.height)\n maskCtx.clearRect(0, 0, this.maskCanvas.width, this.maskCanvas.height)\n\n // image load\n const filepath = ComfyApp.clipspace.images\n\n const alpha_url = new URL(\n ComfyApp.clipspace.imgs[ComfyApp.clipspace['selectedIndex']].src\n )\n alpha_url.searchParams.delete('channel')\n alpha_url.searchParams.delete('preview')\n alpha_url.searchParams.set('channel', 'a')\n let mask_image = await loadImage(alpha_url)\n\n // original image load\n const rgb_url = new URL(\n ComfyApp.clipspace.imgs[ComfyApp.clipspace['selectedIndex']].src\n )\n rgb_url.searchParams.delete('channel')\n rgb_url.searchParams.set('channel', 'rgb')\n this.image = new Image()\n this.image.onload = function () {\n maskCanvas.width = self.image.width\n maskCanvas.height = self.image.height\n\n self.invalidateCanvas(self.image, mask_image)\n self.initializeCanvasPanZoom()\n }\n this.image.src = rgb_url.toString()\n }\n\n initializeCanvasPanZoom() {\n // set initialize\n let drawWidth = this.image.width\n let drawHeight = this.image.height\n\n let width = this.element.clientWidth\n let height = this.element.clientHeight\n\n if (this.image.width > width) {\n drawWidth = width\n drawHeight = (drawWidth / this.image.width) * this.image.height\n }\n\n if (drawHeight > height) {\n drawHeight = height\n drawWidth = (drawHeight / this.image.height) * this.image.width\n }\n\n this.zoom_ratio = drawWidth / this.image.width\n\n const canvasX = (width - drawWidth) / 2\n const canvasY = (height - drawHeight) / 2\n this.pan_x = canvasX\n this.pan_y = canvasY\n\n this.invalidatePanZoom()\n }\n\n invalidatePanZoom() {\n let raw_width = this.image.width * this.zoom_ratio\n let raw_height = this.image.height * this.zoom_ratio\n\n if (this.pan_x + raw_width < 10) {\n this.pan_x = 10 - raw_width\n }\n\n if (this.pan_y + raw_height < 10) {\n this.pan_y = 10 - raw_height\n }\n\n let width = `${raw_width}px`\n let height = `${raw_height}px`\n\n let left = `${this.pan_x}px`\n let top = `${this.pan_y}px`\n\n this.maskCanvas.style.width = width\n this.maskCanvas.style.height = height\n this.maskCanvas.style.left = left\n this.maskCanvas.style.top = top\n\n this.imgCanvas.style.width = width\n this.imgCanvas.style.height = height\n this.imgCanvas.style.left = left\n this.imgCanvas.style.top = top\n }\n\n setEventHandler(maskCanvas) {\n const self = this\n\n if (!this.handler_registered) {\n maskCanvas.addEventListener('contextmenu', (event) => {\n event.preventDefault()\n })\n\n this.element.addEventListener('wheel', (event) =>\n this.handleWheelEvent(self, event)\n )\n this.element.addEventListener('pointermove', (event) =>\n this.pointMoveEvent(self, event)\n )\n this.element.addEventListener('touchmove', (event) =>\n this.pointMoveEvent(self, event)\n )\n\n this.element.addEventListener('dragstart', (event) => {\n if (event.ctrlKey) {\n event.preventDefault()\n }\n })\n\n maskCanvas.addEventListener('pointerdown', (event) =>\n this.handlePointerDown(self, event)\n )\n maskCanvas.addEventListener('pointermove', (event) =>\n this.draw_move(self, event)\n )\n maskCanvas.addEventListener('touchmove', (event) =>\n this.draw_move(self, event)\n )\n maskCanvas.addEventListener('pointerover', (event) => {\n this.brush.style.display = 'block'\n })\n maskCanvas.addEventListener('pointerleave', (event) => {\n this.brush.style.display = 'none'\n })\n\n document.addEventListener('pointerup', MaskEditorDialog.handlePointerUp)\n\n this.handler_registered = true\n }\n }\n\n getMaskCanvasStyle() {\n if (this.brush_color_mode === 'negative') {\n return {\n mixBlendMode: 'difference',\n opacity: '1'\n }\n } else {\n return {\n mixBlendMode: 'initial',\n opacity: this.brush_opacity\n }\n }\n }\n\n getMaskColor() {\n if (this.brush_color_mode === 'black') {\n return { r: 0, g: 0, b: 0 }\n }\n if (this.brush_color_mode === 'white') {\n return { r: 255, g: 255, b: 255 }\n }\n if (this.brush_color_mode === 'negative') {\n // negative effect only works with white color\n return { r: 255, g: 255, b: 255 }\n }\n\n return { r: 0, g: 0, b: 0 }\n }\n\n getMaskFillStyle() {\n const maskColor = this.getMaskColor()\n\n return 'rgb(' + maskColor.r + ',' + maskColor.g + ',' + maskColor.b + ')'\n }\n\n getColorButtonText() {\n let colorCaption = 'unknown'\n\n if (this.brush_color_mode === 'black') {\n colorCaption = 'black'\n } else if (this.brush_color_mode === 'white') {\n colorCaption = 'white'\n } else if (this.brush_color_mode === 'negative') {\n colorCaption = 'negative'\n }\n\n return 'Color: ' + colorCaption\n }\n\n updateWhenBrushColorModeChanged() {\n this.colorButton.innerText = this.getColorButtonText()\n\n // update mask canvas css styles\n\n const maskCanvasStyle = this.getMaskCanvasStyle()\n this.maskCanvas.style.mixBlendMode = maskCanvasStyle.mixBlendMode\n this.maskCanvas.style.opacity = maskCanvasStyle.opacity.toString()\n\n // update mask canvas rgb colors\n\n const maskColor = this.getMaskColor()\n\n const maskData = this.maskCtx.getImageData(\n 0,\n 0,\n this.maskCanvas.width,\n this.maskCanvas.height\n )\n\n for (let i = 0; i < maskData.data.length; i += 4) {\n maskData.data[i] = maskColor.r\n maskData.data[i + 1] = maskColor.g\n maskData.data[i + 2] = maskColor.b\n }\n\n this.maskCtx.putImageData(maskData, 0, 0)\n }\n\n brush_opacity = 0.7\n brush_size = 10\n brush_color_mode = 'black'\n drawing_mode = false\n lastx = -1\n lasty = -1\n lasttime = 0\n\n static handleKeyDown(event) {\n const self = MaskEditorDialog.instance\n if (event.key === ']') {\n self.brush_size = Math.min(self.brush_size + 2, 100)\n self.brush_slider_input.value = self.brush_size\n } else if (event.key === '[') {\n self.brush_size = Math.max(self.brush_size - 2, 1)\n self.brush_slider_input.value = self.brush_size\n } else if (event.key === 'Enter') {\n self.save()\n }\n\n self.updateBrushPreview(self)\n }\n\n static handlePointerUp(event) {\n event.preventDefault()\n\n this.mousedown_x = null\n this.mousedown_y = null\n\n MaskEditorDialog.instance.drawing_mode = false\n }\n\n updateBrushPreview(self) {\n const brush = self.brush\n\n var centerX = self.cursorX\n var centerY = self.cursorY\n\n brush.style.width = self.brush_size * 2 * this.zoom_ratio + 'px'\n brush.style.height = self.brush_size * 2 * this.zoom_ratio + 'px'\n brush.style.left = centerX - self.brush_size * this.zoom_ratio + 'px'\n brush.style.top = centerY - self.brush_size * this.zoom_ratio + 'px'\n }\n\n handleWheelEvent(self, event) {\n event.preventDefault()\n\n if (event.ctrlKey) {\n // zoom canvas\n if (event.deltaY < 0) {\n this.zoom_ratio = Math.min(10.0, this.zoom_ratio + 0.2)\n } else {\n this.zoom_ratio = Math.max(0.2, this.zoom_ratio - 0.2)\n }\n\n this.invalidatePanZoom()\n } else {\n // adjust brush size\n if (event.deltaY < 0) this.brush_size = Math.min(this.brush_size + 2, 100)\n else this.brush_size = Math.max(this.brush_size - 2, 1)\n\n this.brush_slider_input.value = this.brush_size.toString()\n\n this.updateBrushPreview(this)\n }\n }\n\n pointMoveEvent(self, event) {\n this.cursorX = event.pageX\n this.cursorY = event.pageY\n\n self.updateBrushPreview(self)\n\n if (event.ctrlKey) {\n event.preventDefault()\n self.pan_move(self, event)\n }\n\n let left_button_down =\n (window.TouchEvent && event instanceof TouchEvent) || event.buttons == 1\n\n if (event.shiftKey && left_button_down) {\n self.drawing_mode = false\n\n const y = event.clientY\n let delta = (self.zoom_lasty - y) * 0.005\n self.zoom_ratio = Math.max(\n Math.min(10.0, self.last_zoom_ratio - delta),\n 0.2\n )\n\n this.invalidatePanZoom()\n return\n }\n }\n\n pan_move(self, event) {\n if (event.buttons == 1) {\n if (MaskEditorDialog.mousedown_x) {\n let deltaX = MaskEditorDialog.mousedown_x - event.clientX\n let deltaY = MaskEditorDialog.mousedown_y - event.clientY\n\n self.pan_x = this.mousedown_pan_x - deltaX\n self.pan_y = this.mousedown_pan_y - deltaY\n\n self.invalidatePanZoom()\n }\n }\n }\n\n draw_move(self, event) {\n if (event.ctrlKey || event.shiftKey) {\n return\n }\n\n event.preventDefault()\n\n this.cursorX = event.pageX\n this.cursorY = event.pageY\n\n self.updateBrushPreview(self)\n\n let left_button_down =\n (window.TouchEvent && event instanceof TouchEvent) || event.buttons == 1\n let right_button_down = [2, 5, 32].includes(event.buttons)\n\n if (!event.altKey && left_button_down) {\n var diff = performance.now() - self.lasttime\n\n const maskRect = self.maskCanvas.getBoundingClientRect()\n\n var x = event.offsetX\n var y = event.offsetY\n\n if (event.offsetX == null) {\n x = event.targetTouches[0].clientX - maskRect.left\n }\n\n if (event.offsetY == null) {\n y = event.targetTouches[0].clientY - maskRect.top\n }\n\n x /= self.zoom_ratio\n y /= self.zoom_ratio\n\n var brush_size = this.brush_size\n if (event instanceof PointerEvent && event.pointerType == 'pen') {\n brush_size *= event.pressure\n this.last_pressure = event.pressure\n } else if (\n window.TouchEvent &&\n event instanceof TouchEvent &&\n diff < 20\n ) {\n // The firing interval of PointerEvents in Pen is unreliable, so it is supplemented by TouchEvents.\n brush_size *= this.last_pressure\n } else {\n brush_size = this.brush_size\n }\n\n if (diff > 20 && !this.drawing_mode)\n requestAnimationFrame(() => {\n self.init_shape(self, CompositionOperation.SourceOver)\n self.draw_shape(self, x, y, brush_size)\n self.lastx = x\n self.lasty = y\n })\n else\n requestAnimationFrame(() => {\n self.init_shape(self, CompositionOperation.SourceOver)\n\n var dx = x - self.lastx\n var dy = y - self.lasty\n\n var distance = Math.sqrt(dx * dx + dy * dy)\n var directionX = dx / distance\n var directionY = dy / distance\n\n for (var i = 0; i < distance; i += 5) {\n var px = self.lastx + directionX * i\n var py = self.lasty + directionY * i\n self.draw_shape(self, px, py, brush_size)\n }\n self.lastx = x\n self.lasty = y\n })\n\n self.lasttime = performance.now()\n } else if ((event.altKey && left_button_down) || right_button_down) {\n const maskRect = self.maskCanvas.getBoundingClientRect()\n const x =\n (event.offsetX || event.targetTouches[0].clientX - maskRect.left) /\n self.zoom_ratio\n const y =\n (event.offsetY || event.targetTouches[0].clientY - maskRect.top) /\n self.zoom_ratio\n\n var brush_size = this.brush_size\n if (event instanceof PointerEvent && event.pointerType == 'pen') {\n brush_size *= event.pressure\n this.last_pressure = event.pressure\n } else if (\n window.TouchEvent &&\n event instanceof TouchEvent &&\n diff < 20\n ) {\n brush_size *= this.last_pressure\n } else {\n brush_size = this.brush_size\n }\n\n if (diff > 20 && !this.drawing_mode)\n // cannot tracking drawing_mode for touch event\n requestAnimationFrame(() => {\n self.init_shape(self, CompositionOperation.DestinationOut)\n self.draw_shape(self, x, y, brush_size)\n self.lastx = x\n self.lasty = y\n })\n else\n requestAnimationFrame(() => {\n self.init_shape(self, CompositionOperation.DestinationOut)\n\n var dx = x - self.lastx\n var dy = y - self.lasty\n\n var distance = Math.sqrt(dx * dx + dy * dy)\n var directionX = dx / distance\n var directionY = dy / distance\n\n for (var i = 0; i < distance; i += 5) {\n var px = self.lastx + directionX * i\n var py = self.lasty + directionY * i\n self.draw_shape(self, px, py, brush_size)\n }\n self.lastx = x\n self.lasty = y\n })\n\n self.lasttime = performance.now()\n }\n }\n\n handlePointerDown(self, event) {\n if (event.ctrlKey) {\n if (event.buttons == 1) {\n MaskEditorDialog.mousedown_x = event.clientX\n MaskEditorDialog.mousedown_y = event.clientY\n\n this.mousedown_pan_x = this.pan_x\n this.mousedown_pan_y = this.pan_y\n }\n return\n }\n\n var brush_size = this.brush_size\n if (event instanceof PointerEvent && event.pointerType == 'pen') {\n brush_size *= event.pressure\n this.last_pressure = event.pressure\n }\n\n if ([0, 2, 5].includes(event.button)) {\n self.drawing_mode = true\n\n event.preventDefault()\n\n if (event.shiftKey) {\n self.zoom_lasty = event.clientY\n self.last_zoom_ratio = self.zoom_ratio\n return\n }\n\n const maskRect = self.maskCanvas.getBoundingClientRect()\n const x =\n (event.offsetX || event.targetTouches[0].clientX - maskRect.left) /\n self.zoom_ratio\n const y =\n (event.offsetY || event.targetTouches[0].clientY - maskRect.top) /\n self.zoom_ratio\n\n if (!event.altKey && event.button == 0) {\n self.init_shape(self, CompositionOperation.SourceOver)\n } else {\n self.init_shape(self, CompositionOperation.DestinationOut)\n }\n self.draw_shape(self, x, y, brush_size)\n self.lastx = x\n self.lasty = y\n self.lasttime = performance.now()\n }\n }\n\n init_shape(self, compositionOperation) {\n self.maskCtx.beginPath()\n if (compositionOperation == CompositionOperation.SourceOver) {\n self.maskCtx.fillStyle = this.getMaskFillStyle()\n self.maskCtx.globalCompositeOperation = CompositionOperation.SourceOver\n } else if (compositionOperation == CompositionOperation.DestinationOut) {\n self.maskCtx.globalCompositeOperation =\n CompositionOperation.DestinationOut\n }\n }\n\n draw_shape(self, x, y, brush_size) {\n if (self.pointer_type === PointerType.Rect) {\n self.maskCtx.rect(\n x - brush_size,\n y - brush_size,\n brush_size * 2,\n brush_size * 2\n )\n } else {\n self.maskCtx.arc(x, y, brush_size, 0, Math.PI * 2, false)\n }\n self.maskCtx.fill()\n }\n\n async save() {\n const backupCanvas = document.createElement('canvas')\n const backupCtx = backupCanvas.getContext('2d', {\n willReadFrequently: true\n })\n backupCanvas.width = this.image.width\n backupCanvas.height = this.image.height\n\n backupCtx.clearRect(0, 0, backupCanvas.width, backupCanvas.height)\n backupCtx.drawImage(\n this.maskCanvas,\n 0,\n 0,\n this.maskCanvas.width,\n this.maskCanvas.height,\n 0,\n 0,\n backupCanvas.width,\n backupCanvas.height\n )\n\n // paste mask data into alpha channel\n const backupData = backupCtx.getImageData(\n 0,\n 0,\n backupCanvas.width,\n backupCanvas.height\n )\n\n // refine mask image\n for (let i = 0; i < backupData.data.length; i += 4) {\n if (backupData.data[i + 3] == 255) backupData.data[i + 3] = 0\n else backupData.data[i + 3] = 255\n\n backupData.data[i] = 0\n backupData.data[i + 1] = 0\n backupData.data[i + 2] = 0\n }\n\n backupCtx.globalCompositeOperation = CompositionOperation.SourceOver\n backupCtx.putImageData(backupData, 0, 0)\n\n const formData = new FormData()\n const filename = 'clipspace-mask-' + performance.now() + '.png'\n\n const item = {\n filename: filename,\n subfolder: 'clipspace',\n type: 'input'\n }\n\n if (ComfyApp.clipspace.images) ComfyApp.clipspace.images[0] = item\n\n if (ComfyApp.clipspace.widgets) {\n const index = ComfyApp.clipspace.widgets.findIndex(\n (obj) => obj.name === 'image'\n )\n\n if (index >= 0) ComfyApp.clipspace.widgets[index].value = item\n }\n\n const dataURL = backupCanvas.toDataURL()\n const blob = dataURLToBlob(dataURL)\n\n let original_url = new URL(this.image.src)\n\n type Ref = { filename: string; subfolder?: string; type?: string }\n\n const original_ref: Ref = {\n filename: original_url.searchParams.get('filename')\n }\n\n let original_subfolder = original_url.searchParams.get('subfolder')\n if (original_subfolder) original_ref.subfolder = original_subfolder\n\n let original_type = original_url.searchParams.get('type')\n if (original_type) original_ref.type = original_type\n\n formData.append('image', blob, filename)\n formData.append('original_ref', JSON.stringify(original_ref))\n formData.append('type', 'input')\n formData.append('subfolder', 'clipspace')\n\n this.saveButton.innerText = 'Saving...'\n this.saveButton.disabled = true\n await uploadMask(item, formData)\n ComfyApp.onClipspaceEditorSave()\n this.close()\n }\n}\n\napp.registerExtension({\n name: 'Comfy.MaskEditor',\n init(app) {\n ComfyApp.open_maskeditor = function () {\n const dlg = MaskEditorDialog.getInstance()\n if (!dlg.isOpened()) {\n dlg.show()\n }\n }\n\n const context_predicate = () =>\n ComfyApp.clipspace &&\n ComfyApp.clipspace.imgs &&\n ComfyApp.clipspace.imgs.length > 0\n ClipspaceDialog.registerButton(\n 'MaskEditor',\n context_predicate,\n ComfyApp.open_maskeditor\n )\n }\n})\n","// @ts-strict-ignore\nimport { app } from '../../scripts/app'\nimport { api } from '../../scripts/api'\nimport { ComfyDialog, $el } from '../../scripts/ui'\nimport { GroupNodeConfig, GroupNodeHandler } from './groupNode'\nimport { LGraphCanvas } from '@comfyorg/litegraph'\nimport { useToastStore } from '@/stores/toastStore'\nimport { deserialiseAndCreate } from '@/extensions/core/vintageClipboard'\n\n// Adds the ability to save and add multiple nodes as a template\n// To save:\n// Select multiple nodes (ctrl + drag to select a region or ctrl+click individual nodes)\n// Right click the canvas\n// Save Node Template -> give it a name\n//\n// To add:\n// Right click the canvas\n// Node templates -> click the one to add\n//\n// To delete/rename:\n// Right click the canvas\n// Node templates -> Manage\n//\n// To rearrange:\n// Open the manage dialog and Drag and drop elements using the \"Name:\" label as handle\n\nconst id = 'Comfy.NodeTemplates'\nconst file = 'comfy.templates.json'\n\nclass ManageTemplates extends ComfyDialog {\n templates: any[]\n draggedEl: HTMLElement | null\n saveVisualCue: number | null\n emptyImg: HTMLImageElement\n importInput: HTMLInputElement\n\n constructor() {\n super()\n this.load().then((v) => {\n this.templates = v\n })\n\n this.element.classList.add('comfy-manage-templates')\n this.draggedEl = null\n this.saveVisualCue = null\n this.emptyImg = new Image()\n this.emptyImg.src =\n 'data:image/gif;base64,R0lGODlhAQABAIAAAAUEBAAAACwAAAAAAQABAAACAkQBADs='\n\n this.importInput = $el('input', {\n type: 'file',\n accept: '.json',\n multiple: true,\n style: { display: 'none' },\n parent: document.body,\n onchange: () => this.importAll()\n }) as HTMLInputElement\n }\n\n createButtons() {\n const btns = super.createButtons()\n btns[0].textContent = 'Close'\n btns[0].onclick = (e) => {\n clearTimeout(this.saveVisualCue)\n this.close()\n }\n btns.unshift(\n $el('button', {\n type: 'button',\n textContent: 'Export',\n onclick: () => this.exportAll()\n })\n )\n btns.unshift(\n $el('button', {\n type: 'button',\n textContent: 'Import',\n onclick: () => {\n this.importInput.click()\n }\n })\n )\n return btns\n }\n\n async load() {\n let templates = []\n if (app.storageLocation === 'server') {\n if (app.isNewUserSession) {\n // New user so migrate existing templates\n const json = localStorage.getItem(id)\n if (json) {\n templates = JSON.parse(json)\n }\n await api.storeUserData(file, json, { stringify: false })\n } else {\n const res = await api.getUserData(file)\n if (res.status === 200) {\n try {\n templates = await res.json()\n } catch (error) {}\n } else if (res.status !== 404) {\n console.error(res.status + ' ' + res.statusText)\n }\n }\n } else {\n const json = localStorage.getItem(id)\n if (json) {\n templates = JSON.parse(json)\n }\n }\n\n return templates ?? []\n }\n\n async store() {\n if (app.storageLocation === 'server') {\n const templates = JSON.stringify(this.templates, undefined, 4)\n localStorage.setItem(id, templates) // Backwards compatibility\n try {\n await api.storeUserData(file, templates, { stringify: false })\n } catch (error) {\n console.error(error)\n useToastStore().addAlert(error.message)\n }\n } else {\n localStorage.setItem(id, JSON.stringify(this.templates))\n }\n }\n\n async importAll() {\n for (const file of this.importInput.files) {\n if (file.type === 'application/json' || file.name.endsWith('.json')) {\n const reader = new FileReader()\n reader.onload = async () => {\n const importFile = JSON.parse(reader.result as string)\n if (importFile?.templates) {\n for (const template of importFile.templates) {\n if (template?.name && template?.data) {\n this.templates.push(template)\n }\n }\n await this.store()\n }\n }\n await reader.readAsText(file)\n }\n }\n\n this.importInput.value = null\n\n this.close()\n }\n\n exportAll() {\n if (this.templates.length == 0) {\n useToastStore().addAlert('No templates to export.')\n return\n }\n\n const json = JSON.stringify({ templates: this.templates }, null, 2) // convert the data to a JSON string\n const blob = new Blob([json], { type: 'application/json' })\n const url = URL.createObjectURL(blob)\n const a = $el('a', {\n href: url,\n download: 'node_templates.json',\n style: { display: 'none' },\n parent: document.body\n })\n a.click()\n setTimeout(function () {\n a.remove()\n window.URL.revokeObjectURL(url)\n }, 0)\n }\n\n show() {\n // Show list of template names + delete button\n super.show(\n $el(\n 'div',\n {},\n this.templates.flatMap((t, i) => {\n let nameInput\n return [\n $el(\n 'div',\n {\n dataset: { id: i.toString() },\n className: 'templateManagerRow',\n style: {\n display: 'grid',\n gridTemplateColumns: '1fr auto',\n border: '1px dashed transparent',\n gap: '5px',\n backgroundColor: 'var(--comfy-menu-bg)'\n },\n ondragstart: (e) => {\n this.draggedEl = e.currentTarget\n e.currentTarget.style.opacity = '0.6'\n e.currentTarget.style.border = '1px dashed yellow'\n e.dataTransfer.effectAllowed = 'move'\n e.dataTransfer.setDragImage(this.emptyImg, 0, 0)\n },\n ondragend: (e) => {\n e.target.style.opacity = '1'\n e.currentTarget.style.border = '1px dashed transparent'\n e.currentTarget.removeAttribute('draggable')\n\n // rearrange the elements\n this.element\n .querySelectorAll('.templateManagerRow')\n .forEach((el: HTMLElement, i) => {\n var prev_i = Number.parseInt(el.dataset.id)\n\n if (el == this.draggedEl && prev_i != i) {\n this.templates.splice(\n i,\n 0,\n this.templates.splice(prev_i, 1)[0]\n )\n }\n el.dataset.id = i.toString()\n })\n this.store()\n },\n ondragover: (e) => {\n e.preventDefault()\n if (e.currentTarget == this.draggedEl) return\n\n let rect = e.currentTarget.getBoundingClientRect()\n if (e.clientY > rect.top + rect.height / 2) {\n e.currentTarget.parentNode.insertBefore(\n this.draggedEl,\n e.currentTarget.nextSibling\n )\n } else {\n e.currentTarget.parentNode.insertBefore(\n this.draggedEl,\n e.currentTarget\n )\n }\n }\n },\n [\n $el(\n 'label',\n {\n textContent: 'Name: ',\n style: {\n cursor: 'grab'\n },\n onmousedown: (e) => {\n // enable dragging only from the label\n if (e.target.localName == 'label')\n e.currentTarget.parentNode.draggable = 'true'\n }\n },\n [\n $el('input', {\n value: t.name,\n dataset: { name: t.name },\n style: {\n transitionProperty: 'background-color',\n transitionDuration: '0s'\n },\n onchange: (e) => {\n clearTimeout(this.saveVisualCue)\n var el = e.target\n var row = el.parentNode.parentNode\n this.templates[row.dataset.id].name =\n el.value.trim() || 'untitled'\n this.store()\n el.style.backgroundColor = 'rgb(40, 95, 40)'\n el.style.transitionDuration = '0s'\n // @ts-expect-error\n // In browser env the return value is number.\n this.saveVisualCue = setTimeout(function () {\n el.style.transitionDuration = '.7s'\n el.style.backgroundColor = 'var(--comfy-input-bg)'\n }, 15)\n },\n onkeypress: (e) => {\n var el = e.target\n clearTimeout(this.saveVisualCue)\n el.style.transitionDuration = '0s'\n el.style.backgroundColor = 'var(--comfy-input-bg)'\n },\n $: (el) => (nameInput = el)\n })\n ]\n ),\n $el('div', {}, [\n $el('button', {\n textContent: 'Export',\n style: {\n fontSize: '12px',\n fontWeight: 'normal'\n },\n onclick: (e) => {\n const json = JSON.stringify({ templates: [t] }, null, 2) // convert the data to a JSON string\n const blob = new Blob([json], {\n type: 'application/json'\n })\n const url = URL.createObjectURL(blob)\n const a = $el('a', {\n href: url,\n download: (nameInput.value || t.name) + '.json',\n style: { display: 'none' },\n parent: document.body\n })\n a.click()\n setTimeout(function () {\n a.remove()\n window.URL.revokeObjectURL(url)\n }, 0)\n }\n }),\n $el('button', {\n textContent: 'Delete',\n style: {\n fontSize: '12px',\n color: 'red',\n fontWeight: 'normal'\n },\n onclick: (e) => {\n const item = e.target.parentNode.parentNode\n item.parentNode.removeChild(item)\n this.templates.splice(item.dataset.id * 1, 1)\n this.store()\n // update the rows index, setTimeout ensures that the list is updated\n var that = this\n setTimeout(function () {\n that.element\n .querySelectorAll('.templateManagerRow')\n .forEach((el: HTMLElement, i) => {\n el.dataset.id = i.toString()\n })\n }, 0)\n }\n })\n ])\n ]\n )\n ]\n })\n )\n )\n }\n}\n\napp.registerExtension({\n name: id,\n setup() {\n const manage = new ManageTemplates()\n\n const clipboardAction = async (cb) => {\n // We use the clipboard functions but dont want to overwrite the current user clipboard\n // Restore it after we've run our callback\n const old = localStorage.getItem('litegrapheditor_clipboard')\n await cb()\n localStorage.setItem('litegrapheditor_clipboard', old)\n }\n\n const orig = LGraphCanvas.prototype.getCanvasMenuOptions\n LGraphCanvas.prototype.getCanvasMenuOptions = function () {\n const options = orig.apply(this, arguments)\n\n options.push(null)\n options.push({\n content: `Save Selected as Template`,\n disabled: !Object.keys(app.canvas.selected_nodes || {}).length,\n callback: () => {\n const name = prompt('Enter name')\n if (!name?.trim()) return\n\n clipboardAction(() => {\n app.canvas.copyToClipboard()\n let data = localStorage.getItem('litegrapheditor_clipboard')\n data = JSON.parse(data)\n const nodeIds = Object.keys(app.canvas.selected_nodes)\n for (let i = 0; i < nodeIds.length; i++) {\n const node = app.graph.getNodeById(nodeIds[i])\n const nodeData = node?.constructor.nodeData\n\n let groupData = GroupNodeHandler.getGroupData(node)\n if (groupData) {\n groupData = groupData.nodeData\n // @ts-expect-error\n if (!data.groupNodes) {\n // @ts-expect-error\n data.groupNodes = {}\n }\n // @ts-expect-error\n data.groupNodes[nodeData.name] = groupData\n // @ts-expect-error\n data.nodes[i].type = nodeData.name\n }\n }\n\n manage.templates.push({\n name,\n data: JSON.stringify(data)\n })\n manage.store()\n })\n }\n })\n\n // Map each template to a menu item\n const subItems = manage.templates.map((t) => {\n return {\n content: t.name,\n callback: () => {\n clipboardAction(async () => {\n const data = JSON.parse(t.data)\n await GroupNodeConfig.registerFromWorkflow(data.groupNodes, {})\n\n // Check for old clipboard format\n if (!data.reroutes) {\n deserialiseAndCreate(t.data, app.canvas)\n } else {\n localStorage.setItem('litegrapheditor_clipboard', t.data)\n app.canvas.pasteFromClipboard()\n }\n })\n }\n }\n })\n\n subItems.push(null, {\n content: 'Manage',\n callback: () => manage.show()\n })\n\n options.push({\n content: 'Node Templates',\n submenu: {\n options: subItems\n }\n })\n\n return options\n }\n }\n})\n","// @ts-strict-ignore\nimport { LiteGraph, LGraphCanvas } from '@comfyorg/litegraph'\nimport { app } from '../../scripts/app'\nimport { ComfyWidgets } from '../../scripts/widgets'\nimport { LGraphNode } from '@comfyorg/litegraph'\n// Node that add notes to your project\n\napp.registerExtension({\n name: 'Comfy.NoteNode',\n registerCustomNodes() {\n class NoteNode extends LGraphNode {\n static category: string\n\n color = LGraphCanvas.node_colors.yellow.color\n bgcolor = LGraphCanvas.node_colors.yellow.bgcolor\n groupcolor = LGraphCanvas.node_colors.yellow.groupcolor\n isVirtualNode: boolean\n collapsable: boolean\n title_mode: number\n\n constructor(title?: string) {\n super(title)\n if (!this.properties) {\n this.properties = { text: '' }\n }\n ComfyWidgets.STRING(\n // Should we extends LGraphNode? Yesss\n this,\n '',\n ['', { default: this.properties.text, multiline: true }],\n app\n )\n\n this.serialize_widgets = true\n this.isVirtualNode = true\n }\n }\n\n // Load default visibility\n\n LiteGraph.registerNodeType(\n 'Note',\n Object.assign(NoteNode, {\n title_mode: LiteGraph.NORMAL_TITLE,\n title: 'Note',\n collapsable: true\n })\n )\n\n NoteNode.category = 'utils'\n }\n})\n","// @ts-strict-ignore\nimport type { IContextMenuValue } from '@comfyorg/litegraph'\nimport { app } from '../../scripts/app'\nimport { mergeIfValid, getWidgetConfig, setWidgetConfig } from './widgetInputs'\nimport { LiteGraph, LGraphCanvas, LGraphNode } from '@comfyorg/litegraph'\n\n// Node that allows you to redirect connections for cleaner graphs\n\napp.registerExtension({\n name: 'Comfy.RerouteNode',\n registerCustomNodes(app) {\n interface RerouteNode extends LGraphNode {\n __outputType?: string\n }\n\n class RerouteNode extends LGraphNode {\n static category: string | undefined\n static defaultVisibility = false\n\n constructor(title?: string) {\n super(title)\n if (!this.properties) {\n this.properties = {}\n }\n this.properties.showOutputText = RerouteNode.defaultVisibility\n this.properties.horizontal = false\n\n this.addInput('', '*')\n this.addOutput(this.properties.showOutputText ? '*' : '', '*')\n\n this.onAfterGraphConfigured = function () {\n requestAnimationFrame(() => {\n this.onConnectionsChange(LiteGraph.INPUT, null, true, null)\n })\n }\n\n this.onConnectionsChange = (type, index, connected, link_info) => {\n this.applyOrientation()\n\n // Prevent multiple connections to different types when we have no input\n if (connected && type === LiteGraph.OUTPUT) {\n // Ignore wildcard nodes as these will be updated to real types\n const types = new Set(\n this.outputs[0].links\n .map((l) => app.graph.links[l].type)\n .filter((t) => t !== '*')\n )\n if (types.size > 1) {\n const linksToDisconnect = []\n for (let i = 0; i < this.outputs[0].links.length - 1; i++) {\n const linkId = this.outputs[0].links[i]\n const link = app.graph.links[linkId]\n linksToDisconnect.push(link)\n }\n for (const link of linksToDisconnect) {\n const node = app.graph.getNodeById(link.target_id)\n node.disconnectInput(link.target_slot)\n }\n }\n }\n\n // Find root input\n let currentNode: LGraphNode | null = this\n let updateNodes = []\n let inputType = null\n let inputNode = null\n while (currentNode) {\n updateNodes.unshift(currentNode)\n const linkId = currentNode.inputs[0].link\n if (linkId !== null) {\n const link = app.graph.links[linkId]\n if (!link) return\n const node = app.graph.getNodeById(link.origin_id)\n const type = node.constructor.type\n if (type === 'Reroute') {\n if (node === this) {\n // We've found a circle\n currentNode.disconnectInput(link.target_slot)\n currentNode = null\n } else {\n // Move the previous node\n currentNode = node\n }\n } else {\n // We've found the end\n inputNode = currentNode\n inputType = node.outputs[link.origin_slot]?.type ?? null\n break\n }\n } else {\n // This path has no input node\n currentNode = null\n break\n }\n }\n\n // Find all outputs\n const nodes: LGraphNode[] = [this]\n let outputType = null\n while (nodes.length) {\n currentNode = nodes.pop()\n const outputs =\n (currentNode.outputs ? currentNode.outputs[0].links : []) || []\n if (outputs.length) {\n for (const linkId of outputs) {\n const link = app.graph.links[linkId]\n\n // When disconnecting sometimes the link is still registered\n if (!link) continue\n\n const node = app.graph.getNodeById(link.target_id)\n const type = node.constructor.type\n\n if (type === 'Reroute') {\n // Follow reroute nodes\n nodes.push(node)\n updateNodes.push(node)\n } else {\n // We've found an output\n const nodeOutType =\n node.inputs &&\n node.inputs[link?.target_slot] &&\n node.inputs[link.target_slot].type\n ? node.inputs[link.target_slot].type\n : null\n if (\n inputType &&\n !LiteGraph.isValidConnection(inputType, nodeOutType)\n ) {\n // The output doesnt match our input so disconnect it\n node.disconnectInput(link.target_slot)\n } else {\n outputType = nodeOutType\n }\n }\n }\n } else {\n // No more outputs for this path\n }\n }\n\n const displayType = inputType || outputType || '*'\n const color = LGraphCanvas.link_type_colors[displayType]\n\n let widgetConfig\n let targetWidget\n let widgetType\n // Update the types of each node\n for (const node of updateNodes) {\n // If we dont have an input type we are always wildcard but we'll show the output type\n // This lets you change the output link to a different type and all nodes will update\n node.outputs[0].type = inputType || '*'\n node.__outputType = displayType\n node.outputs[0].name = node.properties.showOutputText\n ? displayType\n : ''\n node.size = node.computeSize()\n node.applyOrientation()\n\n for (const l of node.outputs[0].links || []) {\n const link = app.graph.links[l]\n if (link) {\n link.color = color\n\n if (app.configuringGraph) continue\n const targetNode = app.graph.getNodeById(link.target_id)\n const targetInput = targetNode.inputs?.[link.target_slot]\n if (targetInput?.widget) {\n const config = getWidgetConfig(targetInput)\n if (!widgetConfig) {\n widgetConfig = config[1] ?? {}\n widgetType = config[0]\n }\n if (!targetWidget) {\n targetWidget = targetNode.widgets?.find(\n (w) => w.name === (targetInput.widget as any).name\n )\n }\n\n const merged = mergeIfValid(targetInput, [\n config[0],\n widgetConfig\n ])\n if (merged.customConfig) {\n widgetConfig = merged.customConfig\n }\n }\n }\n }\n }\n\n for (const node of updateNodes) {\n if (widgetConfig && outputType) {\n node.inputs[0].widget = { name: 'value' }\n setWidgetConfig(\n node.inputs[0],\n [widgetType ?? displayType, widgetConfig],\n targetWidget\n )\n } else {\n setWidgetConfig(node.inputs[0], null)\n }\n }\n\n if (inputNode) {\n const link = app.graph.links[inputNode.inputs[0].link]\n if (link) {\n link.color = color\n }\n }\n }\n\n this.clone = function () {\n const cloned = RerouteNode.prototype.clone.apply(this)\n cloned.removeOutput(0)\n cloned.addOutput(this.properties.showOutputText ? '*' : '', '*')\n cloned.size = cloned.computeSize()\n return cloned\n }\n\n // This node is purely frontend and does not impact the resulting prompt so should not be serialized\n this.isVirtualNode = true\n }\n\n getExtraMenuOptions(_, options): IContextMenuValue[] {\n options.unshift(\n {\n content:\n (this.properties.showOutputText ? 'Hide' : 'Show') + ' Type',\n callback: () => {\n this.properties.showOutputText = !this.properties.showOutputText\n if (this.properties.showOutputText) {\n this.outputs[0].name =\n this.__outputType || (this.outputs[0].type as string)\n } else {\n this.outputs[0].name = ''\n }\n this.size = this.computeSize()\n this.applyOrientation()\n app.graph.setDirtyCanvas(true, true)\n }\n },\n {\n content:\n (RerouteNode.defaultVisibility ? 'Hide' : 'Show') +\n ' Type By Default',\n callback: () => {\n RerouteNode.setDefaultTextVisibility(\n !RerouteNode.defaultVisibility\n )\n }\n },\n {\n // naming is inverted with respect to LiteGraphNode.horizontal\n // LiteGraphNode.horizontal == true means that\n // each slot in the inputs and outputs are laid out horizontally,\n // which is the opposite of the visual orientation of the inputs and outputs as a node\n content:\n 'Set ' + (this.properties.horizontal ? 'Horizontal' : 'Vertical'),\n callback: () => {\n this.properties.horizontal = !this.properties.horizontal\n this.applyOrientation()\n }\n }\n )\n return []\n }\n applyOrientation() {\n this.horizontal = this.properties.horizontal\n if (this.horizontal) {\n // we correct the input position, because LiteGraphNode.horizontal\n // doesn't account for title presence\n // which reroute nodes don't have\n this.inputs[0].pos = [this.size[0] / 2, 0]\n } else {\n delete this.inputs[0].pos\n }\n app.graph.setDirtyCanvas(true, true)\n }\n\n computeSize(): [number, number] {\n return [\n this.properties.showOutputText && this.outputs && this.outputs.length\n ? Math.max(\n 75,\n LiteGraph.NODE_TEXT_SIZE * this.outputs[0].name.length * 0.6 +\n 40\n )\n : 75,\n 26\n ]\n }\n\n static setDefaultTextVisibility(visible) {\n RerouteNode.defaultVisibility = visible\n if (visible) {\n localStorage['Comfy.RerouteNode.DefaultVisibility'] = 'true'\n } else {\n delete localStorage['Comfy.RerouteNode.DefaultVisibility']\n }\n }\n }\n\n // Load default visibility\n RerouteNode.setDefaultTextVisibility(\n !!localStorage['Comfy.RerouteNode.DefaultVisibility']\n )\n\n LiteGraph.registerNodeType(\n 'Reroute',\n Object.assign(RerouteNode, {\n title_mode: LiteGraph.NO_TITLE,\n title: 'Reroute',\n collapsable: false\n })\n )\n\n RerouteNode.category = 'utils'\n }\n})\n","// @ts-strict-ignore\nimport { app } from '../../scripts/app'\nimport { applyTextReplacements } from '../../scripts/utils'\n// Use widget values and dates in output filenames\n\napp.registerExtension({\n name: 'Comfy.SaveImageExtraOutput',\n async beforeRegisterNodeDef(nodeType, nodeData, app) {\n if (nodeData.name === 'SaveImage' || nodeData.name === 'SaveAnimatedWEBP') {\n const onNodeCreated = nodeType.prototype.onNodeCreated\n // When the SaveImage node is created we want to override the serialization of the output name widget to run our S&R\n nodeType.prototype.onNodeCreated = function () {\n const r = onNodeCreated\n ? onNodeCreated.apply(this, arguments)\n : undefined\n\n const widget = this.widgets.find((w) => w.name === 'filename_prefix')\n widget.serializeValue = () => {\n return applyTextReplacements(app, widget.value)\n }\n\n return r\n }\n } else {\n // When any other node is created add a property to alias the node\n const onNodeCreated = nodeType.prototype.onNodeCreated\n nodeType.prototype.onNodeCreated = function () {\n const r = onNodeCreated\n ? onNodeCreated.apply(this, arguments)\n : undefined\n\n if (!this.properties || !('Node name for S&R' in this.properties)) {\n this.addProperty('Node name for S&R', this.constructor.type, 'string')\n }\n\n return r\n }\n }\n }\n})\n","// @ts-strict-ignore\nimport { app } from '../../scripts/app'\nimport { LGraphCanvas, LiteGraph } from '@comfyorg/litegraph'\n\nlet touchZooming\nlet touchCount = 0\n\napp.registerExtension({\n name: 'Comfy.SimpleTouchSupport',\n setup() {\n let touchDist\n let touchTime\n let lastTouch\n let lastScale\n function getMultiTouchPos(e) {\n return Math.hypot(\n e.touches[0].clientX - e.touches[1].clientX,\n e.touches[0].clientY - e.touches[1].clientY\n )\n }\n\n function getMultiTouchCenter(e) {\n return {\n clientX: (e.touches[0].clientX + e.touches[1].clientX) / 2,\n clientY: (e.touches[0].clientY + e.touches[1].clientY) / 2\n }\n }\n\n app.canvasEl.parentElement.addEventListener(\n 'touchstart',\n (e: TouchEvent) => {\n touchCount++\n lastTouch = null\n lastScale = null\n if (e.touches?.length === 1) {\n // Store start time for press+hold for context menu\n touchTime = new Date()\n lastTouch = e.touches[0]\n } else {\n touchTime = null\n if (e.touches?.length === 2) {\n // Store center pos for zoom\n lastScale = app.canvas.ds.scale\n lastTouch = getMultiTouchCenter(e)\n\n touchDist = getMultiTouchPos(e)\n app.canvas.pointer_is_down = false\n }\n }\n },\n true\n )\n\n app.canvasEl.parentElement.addEventListener('touchend', (e: TouchEvent) => {\n touchCount--\n\n if (e.touches?.length !== 1) touchZooming = false\n if (touchTime && !e.touches?.length) {\n if (new Date().getTime() - touchTime > 600) {\n if (e.target === app.canvasEl) {\n app.canvasEl.dispatchEvent(\n new PointerEvent('pointerdown', {\n button: 2,\n clientX: e.changedTouches[0].clientX,\n clientY: e.changedTouches[0].clientY\n })\n )\n e.preventDefault()\n }\n }\n touchTime = null\n }\n })\n\n app.canvasEl.parentElement.addEventListener(\n 'touchmove',\n (e) => {\n touchTime = null\n if (e.touches?.length === 2 && lastTouch && !e.ctrlKey && !e.shiftKey) {\n e.preventDefault() // Prevent browser from zooming when two textareas are touched\n app.canvas.pointer_is_down = false\n touchZooming = true\n\n LiteGraph.closeAllContextMenus(window)\n // @ts-expect-error\n app.canvas.search_box?.close()\n const newTouchDist = getMultiTouchPos(e)\n\n const center = getMultiTouchCenter(e)\n\n let scale = (lastScale * newTouchDist) / touchDist\n\n const newX = (center.clientX - lastTouch.clientX) / scale\n const newY = (center.clientY - lastTouch.clientY) / scale\n\n // Code from LiteGraph\n if (scale < app.canvas.ds.min_scale) {\n scale = app.canvas.ds.min_scale\n } else if (scale > app.canvas.ds.max_scale) {\n scale = app.canvas.ds.max_scale\n }\n\n const oldScale = app.canvas.ds.scale\n\n app.canvas.ds.scale = scale\n\n // Code from LiteGraph\n if (Math.abs(app.canvas.ds.scale - 1) < 0.01) {\n app.canvas.ds.scale = 1\n }\n\n const newScale = app.canvas.ds.scale\n\n const convertScaleToOffset = (scale) => [\n center.clientX / scale - app.canvas.ds.offset[0],\n center.clientY / scale - app.canvas.ds.offset[1]\n ]\n var oldCenter = convertScaleToOffset(oldScale)\n var newCenter = convertScaleToOffset(newScale)\n\n app.canvas.ds.offset[0] += newX + newCenter[0] - oldCenter[0]\n app.canvas.ds.offset[1] += newY + newCenter[1] - oldCenter[1]\n\n lastTouch.clientX = center.clientX\n lastTouch.clientY = center.clientY\n\n app.canvas.setDirty(true, true)\n }\n },\n true\n )\n }\n})\n\nconst processMouseDown = LGraphCanvas.prototype.processMouseDown\nLGraphCanvas.prototype.processMouseDown = function (e) {\n if (touchZooming || touchCount) {\n return\n }\n app.canvas.pointer_is_down = false // Prevent context menu from opening on second tap\n return processMouseDown.apply(this, arguments)\n}\n\nconst processMouseMove = LGraphCanvas.prototype.processMouseMove\nLGraphCanvas.prototype.processMouseMove = function (e) {\n if (touchZooming || touchCount > 1) {\n return\n }\n return processMouseMove.apply(this, arguments)\n}\n","import { app } from '../../scripts/app'\nimport { ComfyWidgets } from '../../scripts/widgets'\nimport { LiteGraph } from '@comfyorg/litegraph'\n// Adds defaults for quickly adding nodes with middle click on the input/output\n\napp.registerExtension({\n name: 'Comfy.SlotDefaults',\n suggestionsNumber: null,\n init() {\n LiteGraph.search_filter_enabled = true\n LiteGraph.middle_click_slot_add_default_node = true\n this.suggestionsNumber = app.ui.settings.addSetting({\n id: 'Comfy.NodeSuggestions.number',\n category: ['Comfy', 'Node Search Box', 'NodeSuggestions'],\n name: 'Number of nodes suggestions',\n tooltip: 'Only for litegraph searchbox/context menu',\n type: 'slider',\n attrs: {\n min: 1,\n max: 100,\n step: 1\n },\n defaultValue: 5,\n onChange: (newVal, oldVal) => {\n this.setDefaults(newVal)\n }\n })\n },\n slot_types_default_out: {},\n slot_types_default_in: {},\n async beforeRegisterNodeDef(nodeType, nodeData, app) {\n var nodeId = nodeData.name\n const inputs = nodeData['input']?.['required'] //only show required inputs to reduce the mess also not logical to create node with optional inputs\n for (const inputKey in inputs) {\n var input = inputs[inputKey]\n if (typeof input[0] !== 'string') continue\n\n var type = input[0]\n if (type in ComfyWidgets) {\n var customProperties = input[1]\n if (!customProperties?.forceInput) continue //ignore widgets that don't force input\n }\n\n if (!(type in this.slot_types_default_out)) {\n this.slot_types_default_out[type] = ['Reroute']\n }\n if (this.slot_types_default_out[type].includes(nodeId)) continue\n this.slot_types_default_out[type].push(nodeId)\n\n // Input types have to be stored as lower case\n // Store each node that can handle this input type\n const lowerType = type.toLocaleLowerCase()\n if (!(lowerType in LiteGraph.registered_slot_in_types)) {\n LiteGraph.registered_slot_in_types[lowerType] = { nodes: [] }\n }\n LiteGraph.registered_slot_in_types[lowerType].nodes.push(\n nodeType.comfyClass\n )\n }\n\n var outputs = nodeData['output'] ?? []\n for (const el of outputs) {\n const type = el as string\n if (!(type in this.slot_types_default_in)) {\n this.slot_types_default_in[type] = ['Reroute'] // [\"Reroute\", \"Primitive\"]; primitive doesn't always work :'()\n }\n\n this.slot_types_default_in[type].push(nodeId)\n\n // Store each node that can handle this output type\n if (!(type in LiteGraph.registered_slot_out_types)) {\n LiteGraph.registered_slot_out_types[type] = { nodes: [] }\n }\n LiteGraph.registered_slot_out_types[type].nodes.push(nodeType.comfyClass)\n\n if (!LiteGraph.slot_types_out.includes(type)) {\n LiteGraph.slot_types_out.push(type)\n }\n }\n\n var maxNum = this.suggestionsNumber.value\n this.setDefaults(maxNum)\n },\n setDefaults(maxNum?: number | null) {\n LiteGraph.slot_types_default_out = {}\n LiteGraph.slot_types_default_in = {}\n\n for (const type in this.slot_types_default_out) {\n LiteGraph.slot_types_default_out[type] = this.slot_types_default_out[\n type\n ].slice(0, maxNum)\n }\n for (const type in this.slot_types_default_in) {\n LiteGraph.slot_types_default_in[type] = this.slot_types_default_in[\n type\n ].slice(0, maxNum)\n }\n }\n})\n","// @ts-strict-ignore\nimport type { SettingParams } from '@/types/settingTypes'\nimport { app } from '../../scripts/app'\nimport {\n LGraphCanvas,\n LGraphNode,\n LGraphGroup,\n LiteGraph\n} from '@comfyorg/litegraph'\n\n// Shift + drag/resize to snap to grid\n\n/** Rounds a Vector2 in-place to the current CANVAS_GRID_SIZE. */\nfunction roundVectorToGrid(vec) {\n vec[0] =\n LiteGraph.CANVAS_GRID_SIZE * Math.round(vec[0] / LiteGraph.CANVAS_GRID_SIZE)\n vec[1] =\n LiteGraph.CANVAS_GRID_SIZE * Math.round(vec[1] / LiteGraph.CANVAS_GRID_SIZE)\n return vec\n}\n\napp.registerExtension({\n name: 'Comfy.SnapToGrid',\n init() {\n // Add setting to control grid size\n app.ui.settings.addSetting({\n id: 'Comfy.SnapToGrid.GridSize',\n category: ['Comfy', 'Graph', 'GridSize'],\n name: 'Snap to grid size',\n type: 'slider',\n attrs: {\n min: 1,\n max: 500\n },\n tooltip:\n 'When dragging and resizing nodes while holding shift they will be aligned to the grid, this controls the size of that grid.',\n defaultValue: LiteGraph.CANVAS_GRID_SIZE,\n onChange(value) {\n LiteGraph.CANVAS_GRID_SIZE = +value || 10\n }\n })\n // Keep the 'pysssss.SnapToGrid' setting id so we don't need to migrate setting values.\n // Using a new setting id can cause existing users to lose their existing settings.\n const alwaysSnapToGrid = app.ui.settings.addSetting({\n id: 'pysssss.SnapToGrid',\n category: ['Comfy', 'Graph', 'AlwaysSnapToGrid'],\n name: 'Always snap to grid',\n type: 'boolean',\n defaultValue: false,\n versionAdded: '1.3.13'\n } as SettingParams)\n\n const shouldSnapToGrid = () => app.shiftDown || alwaysSnapToGrid.value\n\n // After moving a node, if the shift key is down align it to grid\n const onNodeMoved = app.canvas.onNodeMoved\n app.canvas.onNodeMoved = function (node) {\n const r = onNodeMoved?.apply(this, arguments)\n\n if (shouldSnapToGrid()) {\n // Ensure all selected nodes are realigned\n for (const id in this.selected_nodes) {\n this.selected_nodes[id].alignToGrid()\n }\n }\n\n return r\n }\n\n // When a node is added, add a resize handler to it so we can fix align the size with the grid\n const onNodeAdded = app.graph.onNodeAdded\n app.graph.onNodeAdded = function (node) {\n const onResize = node.onResize\n node.onResize = function () {\n if (shouldSnapToGrid()) {\n roundVectorToGrid(node.size)\n }\n return onResize?.apply(this, arguments)\n }\n return onNodeAdded?.apply(this, arguments)\n }\n\n // Draw a preview of where the node will go if holding shift and the node is selected\n const origDrawNode = LGraphCanvas.prototype.drawNode\n LGraphCanvas.prototype.drawNode = function (node, ctx) {\n if (\n shouldSnapToGrid() &&\n this.node_dragged &&\n node.id in this.selected_nodes\n ) {\n const [x, y] = roundVectorToGrid([...node.pos])\n const shiftX = x - node.pos[0]\n let shiftY = y - node.pos[1]\n\n let w, h\n if (node.flags.collapsed) {\n w = node._collapsed_width\n h = LiteGraph.NODE_TITLE_HEIGHT\n shiftY -= LiteGraph.NODE_TITLE_HEIGHT\n } else {\n w = node.size[0]\n h = node.size[1]\n const titleMode = node.constructor.title_mode\n if (\n titleMode !== LiteGraph.TRANSPARENT_TITLE &&\n titleMode !== LiteGraph.NO_TITLE\n ) {\n h += LiteGraph.NODE_TITLE_HEIGHT\n shiftY -= LiteGraph.NODE_TITLE_HEIGHT\n }\n }\n const f = ctx.fillStyle\n ctx.fillStyle = 'rgba(100, 100, 100, 0.5)'\n ctx.fillRect(shiftX, shiftY, w, h)\n ctx.fillStyle = f\n }\n\n return origDrawNode.apply(this, arguments)\n }\n\n /**\n * The currently moving, selected group only. Set after the `selected_group` has actually started\n * moving.\n */\n let selectedAndMovingGroup: LGraphGroup | null = null\n\n /**\n * Handles moving a group; tracking when a group has been moved (to show the ghost in `drawGroups`\n * below) as well as handle the last move call from LiteGraph's `processMouseUp`.\n */\n const groupMove = LGraphGroup.prototype.move\n LGraphGroup.prototype.move = function (deltax, deltay, ignore_nodes) {\n const v = groupMove.apply(this, arguments)\n // When we've started moving, set `selectedAndMovingGroup` as LiteGraph sets `selected_group`\n // too eagerly and we don't want to behave like we're moving until we get a delta.\n if (\n !selectedAndMovingGroup &&\n app.canvas.selected_group === this &&\n (deltax || deltay)\n ) {\n selectedAndMovingGroup = this\n }\n\n // LiteGraph will call group.move both on mouse-move as well as mouse-up though we only want\n // to snap on a mouse-up which we can determine by checking if `app.canvas.last_mouse_dragging`\n // has been set to `false`. Essentially, this check here is the equivalent to calling an\n // `LGraphGroup.prototype.onNodeMoved` if it had existed.\n if (app.canvas.last_mouse_dragging === false && shouldSnapToGrid()) {\n // After moving a group (while shouldSnapToGrid()), snap all the child nodes and, finally,\n // align the group itself.\n this.recomputeInsideNodes()\n for (const node of this.nodes) {\n node.alignToGrid()\n }\n LGraphNode.prototype.alignToGrid.apply(this)\n }\n return v\n }\n\n /**\n * Handles drawing a group when, snapping the size when one is actively being resized tracking and/or\n * drawing a ghost box when one is actively being moved. This mimics the node snapping behavior for\n * both.\n */\n const drawGroups = LGraphCanvas.prototype.drawGroups\n LGraphCanvas.prototype.drawGroups = function (canvas, ctx) {\n if (this.selected_group && shouldSnapToGrid()) {\n if (this.selected_group_resizing) {\n roundVectorToGrid(this.selected_group.size)\n } else if (selectedAndMovingGroup) {\n const [x, y] = roundVectorToGrid([...selectedAndMovingGroup.pos])\n const f = ctx.fillStyle\n const s = ctx.strokeStyle\n ctx.fillStyle = 'rgba(100, 100, 100, 0.33)'\n ctx.strokeStyle = 'rgba(100, 100, 100, 0.66)'\n ctx.rect(x, y, ...(selectedAndMovingGroup.size as [number, number]))\n ctx.fill()\n ctx.stroke()\n ctx.fillStyle = f\n ctx.strokeStyle = s\n }\n } else if (!this.selected_group) {\n selectedAndMovingGroup = null\n }\n return drawGroups.apply(this, arguments)\n }\n\n /** Handles adding a group in a snapping-enabled state. */\n const onGroupAdd = LGraphCanvas.onGroupAdd\n LGraphCanvas.onGroupAdd = function () {\n const v = onGroupAdd.apply(app.canvas, arguments)\n if (shouldSnapToGrid()) {\n const lastGroup = app.graph.groups[app.graph.groups.length - 1]\n if (lastGroup) {\n roundVectorToGrid(lastGroup.pos)\n roundVectorToGrid(lastGroup.size)\n }\n }\n return v\n }\n }\n})\n","import { app } from '../../scripts/app'\nimport { ComfyNodeDef } from '@/types/apiTypes'\n\n// Adds an upload button to the nodes\n\napp.registerExtension({\n name: 'Comfy.UploadImage',\n beforeRegisterNodeDef(nodeType, nodeData: ComfyNodeDef) {\n if (nodeData?.input?.required?.image?.[1]?.image_upload === true) {\n nodeData.input.required.upload = ['IMAGEUPLOAD']\n }\n }\n})\n","// @ts-strict-ignore\nimport { app } from '../../scripts/app'\nimport { api } from '../../scripts/api'\nimport { useToastStore } from '@/stores/toastStore'\n\nconst WEBCAM_READY = Symbol()\n\napp.registerExtension({\n name: 'Comfy.WebcamCapture',\n getCustomWidgets(app) {\n return {\n WEBCAM(node, inputName) {\n let res\n node[WEBCAM_READY] = new Promise((resolve) => (res = resolve))\n\n const container = document.createElement('div')\n container.style.background = 'rgba(0,0,0,0.25)'\n container.style.textAlign = 'center'\n\n const video = document.createElement('video')\n video.style.height = video.style.width = '100%'\n\n const loadVideo = async () => {\n try {\n const stream = await navigator.mediaDevices.getUserMedia({\n video: true,\n audio: false\n })\n container.replaceChildren(video)\n\n setTimeout(() => res(video), 500) // Fallback as loadedmetadata doesnt fire sometimes?\n video.addEventListener('loadedmetadata', () => res(video), false)\n video.srcObject = stream\n video.play()\n } catch (error) {\n const label = document.createElement('div')\n label.style.color = 'red'\n label.style.overflow = 'auto'\n label.style.maxHeight = '100%'\n label.style.whiteSpace = 'pre-wrap'\n\n if (window.isSecureContext) {\n label.textContent =\n 'Unable to load webcam, please ensure access is granted:\\n' +\n error.message\n } else {\n label.textContent =\n 'Unable to load webcam. A secure context is required, if you are not accessing ComfyUI on localhost (127.0.0.1) you will have to enable TLS (https)\\n\\n' +\n error.message\n }\n\n container.replaceChildren(label)\n }\n }\n\n loadVideo()\n\n return { widget: node.addDOMWidget(inputName, 'WEBCAM', container) }\n }\n }\n },\n nodeCreated(node) {\n if ((node.type, node.constructor.comfyClass !== 'WebcamCapture')) return\n\n let video\n const camera = node.widgets.find((w) => w.name === 'image')\n const w = node.widgets.find((w) => w.name === 'width')\n const h = node.widgets.find((w) => w.name === 'height')\n const captureOnQueue = node.widgets.find(\n (w) => w.name === 'capture_on_queue'\n )\n\n const canvas = document.createElement('canvas')\n\n const capture = () => {\n canvas.width = w.value\n canvas.height = h.value\n const ctx = canvas.getContext('2d')\n ctx.drawImage(video, 0, 0, w.value, h.value)\n const data = canvas.toDataURL('image/png')\n\n const img = new Image()\n img.onload = () => {\n node.imgs = [img]\n app.graph.setDirtyCanvas(true)\n requestAnimationFrame(() => {\n node.setSizeForImage?.()\n })\n }\n img.src = data\n }\n\n const btn = node.addWidget(\n 'button',\n 'waiting for camera...',\n 'capture',\n capture\n )\n btn.disabled = true\n btn.serializeValue = () => undefined\n\n camera.serializeValue = async () => {\n if (captureOnQueue.value) {\n capture()\n } else if (!node.imgs?.length) {\n const err = `No webcam image captured`\n useToastStore().addAlert(err)\n throw new Error(err)\n }\n\n // Upload image to temp storage\n const blob = await new Promise<Blob>((r) => canvas.toBlob(r))\n const name = `${+new Date()}.png`\n const file = new File([blob], name)\n const body = new FormData()\n body.append('image', file)\n body.append('subfolder', 'webcam')\n body.append('type', 'temp')\n const resp = await api.fetchApi('/upload/image', {\n method: 'POST',\n body\n })\n if (resp.status !== 200) {\n const err = `Error uploading camera image: ${resp.status} - ${resp.statusText}`\n useToastStore().addAlert(err)\n throw new Error(err)\n }\n return `webcam/${name} [temp]`\n }\n\n node[WEBCAM_READY].then((v) => {\n video = v\n // If width isnt specified then use video output resolution\n if (!w.value) {\n w.value = video.videoWidth || 640\n h.value = video.videoHeight || 480\n }\n btn.disabled = false\n btn.label = 'capture'\n })\n }\n})\n","// @ts-strict-ignore\nimport { app } from '../../scripts/app'\nimport { api } from '../../scripts/api'\nimport type { IWidget } from '@comfyorg/litegraph'\nimport type { DOMWidget } from '@/scripts/domWidget'\nimport { ComfyNodeDef } from '@/types/apiTypes'\nimport { useToastStore } from '@/stores/toastStore'\n\ntype FolderType = 'input' | 'output' | 'temp'\n\nfunction splitFilePath(path: string): [string, string] {\n const folder_separator = path.lastIndexOf('/')\n if (folder_separator === -1) {\n return ['', path]\n }\n return [\n path.substring(0, folder_separator),\n path.substring(folder_separator + 1)\n ]\n}\n\nfunction getResourceURL(\n subfolder: string,\n filename: string,\n type: FolderType = 'input'\n): string {\n const params = [\n 'filename=' + encodeURIComponent(filename),\n 'type=' + type,\n 'subfolder=' + subfolder,\n app.getRandParam().substring(1)\n ].join('&')\n\n return `/view?${params}`\n}\n\nasync function uploadFile(\n audioWidget: IWidget,\n audioUIWidget: DOMWidget<HTMLAudioElement, string>,\n file: File,\n updateNode: boolean,\n pasted: boolean = false\n) {\n try {\n // Wrap file in formdata so it includes filename\n const body = new FormData()\n body.append('image', file)\n if (pasted) body.append('subfolder', 'pasted')\n const resp = await api.fetchApi('/upload/image', {\n method: 'POST',\n body\n })\n\n if (resp.status === 200) {\n const data = await resp.json()\n // Add the file to the dropdown list and update the widget value\n let path = data.name\n if (data.subfolder) path = data.subfolder + '/' + path\n\n if (!audioWidget.options.values.includes(path)) {\n audioWidget.options.values.push(path)\n }\n\n if (updateNode) {\n audioUIWidget.element.src = api.apiURL(\n getResourceURL(...splitFilePath(path))\n )\n audioWidget.value = path\n }\n } else {\n useToastStore().addAlert(resp.status + ' - ' + resp.statusText)\n }\n } catch (error) {\n useToastStore().addAlert(error)\n }\n}\n\n// AudioWidget MUST be registered first, as AUDIOUPLOAD depends on AUDIO_UI to be\n// present.\napp.registerExtension({\n name: 'Comfy.AudioWidget',\n async beforeRegisterNodeDef(nodeType, nodeData) {\n if (\n ['LoadAudio', 'SaveAudio', 'PreviewAudio'].includes(nodeType.comfyClass)\n ) {\n nodeData.input.required.audioUI = ['AUDIO_UI']\n }\n },\n getCustomWidgets() {\n return {\n AUDIO_UI(node, inputName: string) {\n const audio = document.createElement('audio')\n audio.controls = true\n audio.classList.add('comfy-audio')\n audio.setAttribute('name', 'media')\n\n const audioUIWidget: DOMWidget<HTMLAudioElement, string> =\n node.addDOMWidget(inputName, /* name=*/ 'audioUI', audio, {\n serialize: false\n })\n\n const isOutputNode = node.constructor.nodeData.output_node\n if (isOutputNode) {\n // Hide the audio widget when there is no audio initially.\n audioUIWidget.element.classList.add('empty-audio-widget')\n // Populate the audio widget UI on node execution.\n const onExecuted = node.onExecuted\n node.onExecuted = function (message: any) {\n onExecuted?.apply(this, arguments)\n const audios = message.audio\n if (!audios) return\n const audio = audios[0]\n audioUIWidget.element.src = api.apiURL(\n getResourceURL(audio.subfolder, audio.filename, audio.type)\n )\n audioUIWidget.element.classList.remove('empty-audio-widget')\n }\n }\n return { widget: audioUIWidget }\n }\n }\n },\n onNodeOutputsUpdated(nodeOutputs: Record<number, any>) {\n for (const [nodeId, output] of Object.entries(nodeOutputs)) {\n const node = app.graph.getNodeById(nodeId)\n if ('audio' in output) {\n const audioUIWidget = node.widgets.find(\n (w) => w.name === 'audioUI'\n ) as unknown as DOMWidget<HTMLAudioElement, string>\n const audio = output.audio[0]\n audioUIWidget.element.src = api.apiURL(\n getResourceURL(audio.subfolder, audio.filename, audio.type)\n )\n audioUIWidget.element.classList.remove('empty-audio-widget')\n }\n }\n }\n})\n\napp.registerExtension({\n name: 'Comfy.UploadAudio',\n async beforeRegisterNodeDef(nodeType, nodeData: ComfyNodeDef) {\n if (nodeData?.input?.required?.audio?.[1]?.audio_upload === true) {\n nodeData.input.required.upload = ['AUDIOUPLOAD']\n }\n },\n getCustomWidgets() {\n return {\n AUDIOUPLOAD(node, inputName: string) {\n // The widget that allows user to select file.\n const audioWidget: IWidget = node.widgets.find(\n (w: IWidget) => w.name === 'audio'\n )\n const audioUIWidget = node.widgets.find(\n (w: IWidget) => w.name === 'audioUI'\n ) as unknown as DOMWidget<HTMLAudioElement, string>\n\n const onAudioWidgetUpdate = () => {\n audioUIWidget.element.src = api.apiURL(\n getResourceURL(...splitFilePath(audioWidget.value as string))\n )\n }\n // Initially load default audio file to audioUIWidget.\n if (audioWidget.value) {\n onAudioWidgetUpdate()\n }\n audioWidget.callback = onAudioWidgetUpdate\n\n // Load saved audio file widget values if restoring from workflow\n const onGraphConfigured = node.onGraphConfigured\n node.onGraphConfigured = function () {\n onGraphConfigured?.apply(this, arguments)\n if (audioWidget.value) {\n onAudioWidgetUpdate()\n }\n }\n\n const fileInput = document.createElement('input')\n fileInput.type = 'file'\n fileInput.accept = 'audio/*'\n fileInput.style.display = 'none'\n fileInput.onchange = () => {\n if (fileInput.files.length) {\n uploadFile(audioWidget, audioUIWidget, fileInput.files[0], true)\n }\n }\n // The widget to pop up the upload dialog.\n const uploadWidget = node.addWidget(\n 'button',\n inputName,\n /* value=*/ '',\n () => {\n fileInput.click()\n },\n { serialize: false }\n )\n uploadWidget.label = 'choose file to upload'\n\n return { widget: uploadWidget }\n }\n }\n }\n})\n"],"names":["app","ext","prompt","PREFIX","SEPARATOR","type","id","def","node","link","selectedIds","newNodes","i","w","widget","group","modal","PointerType","CompositionOperation","x","y","file","scale","audio"],"mappings":"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"}