mirror of
https://github.com/Comfy-Org/ComfyUI_frontend.git
synced 2026-03-14 09:27:41 +00:00
fix: subgraph output slot labels not updating in v2 renderer (#9266)
## Summary Custom names set on subgraph output nodes are ignored in the v2 renderer — it always shows the data type name (e.g. "texts") instead of the user-defined label. Works correctly in v1. ## Changes - **What**: Made `outputs` in `extractVueNodeData` reactive via `shallowReactive` + `defineProperty` (matching the existing `inputs` pattern). Added a `node:slot-label:changed` graph trigger that `SubgraphNode` fires when input/output labels are renamed, so the Vue layer picks up the change. ## Review Focus - The `outputs` reactivity mirrors `inputs` exactly — same `shallowReactive` + setter pattern. The new trigger event forces `shallowReactive` to detect the deep property change by re-assigning the array. - Also handles input label renames for consistency, even though the current bug report is output-specific. ## Screenshots **v1 — output correctly shows custom label "output_text":** <img width="1076" height="628" alt="Screenshot 2026-02-26 at 4 43 00 PM" src="https://github.com/user-attachments/assets/b4d6ae4c-9970-4d99-a872-4ce1b28522f2" /> **v2 before fix — output shows type name "texts" instead of custom label:** <img width="808" height="298" alt="Screenshot 2026-02-26 at 4 43 30 PM" src="https://github.com/user-attachments/assets/cf06aa6c-6d4d-4be9-9bcd-dcc072ed1907" /> **v2 after fix — output correctly shows "output_text":** <img width="1013" height="292" alt="Screenshot 2026-02-26 at 5 14 44 PM" src="https://github.com/user-attachments/assets/3c43fa9b-0615-4758-bee6-be3481168675" /> ┆Issue is synchronized with this [Notion page](https://www.notion.so/PR-9266-fix-subgraph-output-slot-labels-not-updating-in-v2-renderer-3146d73d365081979327fd775a6ef62b) by [Unito](https://www.unito.io)
This commit is contained in:
committed by
GitHub
parent
9447a1f5d6
commit
5640eb7d92
@@ -396,7 +396,9 @@ export function extractVueNodeData(node: LGraphNode): VueNodeData {
|
||||
},
|
||||
set(v) {
|
||||
reactiveWidgets.splice(0, reactiveWidgets.length, ...v)
|
||||
}
|
||||
},
|
||||
configurable: true,
|
||||
enumerable: true
|
||||
})
|
||||
}
|
||||
const reactiveInputs = shallowReactive<INodeInputSlot[]>(node.inputs ?? [])
|
||||
@@ -406,7 +408,20 @@ export function extractVueNodeData(node: LGraphNode): VueNodeData {
|
||||
},
|
||||
set(v) {
|
||||
reactiveInputs.splice(0, reactiveInputs.length, ...v)
|
||||
}
|
||||
},
|
||||
configurable: true,
|
||||
enumerable: true
|
||||
})
|
||||
const reactiveOutputs = shallowReactive<INodeOutputSlot[]>(node.outputs ?? [])
|
||||
Object.defineProperty(node, 'outputs', {
|
||||
get() {
|
||||
return reactiveOutputs
|
||||
},
|
||||
set(v) {
|
||||
reactiveOutputs.splice(0, reactiveOutputs.length, ...v)
|
||||
},
|
||||
configurable: true,
|
||||
enumerable: true
|
||||
})
|
||||
|
||||
const safeWidgets = reactiveComputed<SafeWidgetData[]>(() => {
|
||||
@@ -448,7 +463,7 @@ export function extractVueNodeData(node: LGraphNode): VueNodeData {
|
||||
hasErrors: !!node.has_errors,
|
||||
widgets: safeWidgets,
|
||||
inputs: reactiveInputs,
|
||||
outputs: node.outputs ? [...node.outputs] : undefined,
|
||||
outputs: reactiveOutputs,
|
||||
flags: node.flags ? { ...node.flags } : undefined,
|
||||
color: node.color || undefined,
|
||||
bgcolor: node.bgcolor || undefined,
|
||||
@@ -746,6 +761,20 @@ export function useGraphNodeManager(graph: LGraph): GraphNodeManager {
|
||||
if (slotLinksEvent.slotType === NodeSlotType.INPUT) {
|
||||
refreshNodeSlots(String(slotLinksEvent.nodeId))
|
||||
}
|
||||
},
|
||||
'node:slot-label:changed': (slotLabelEvent) => {
|
||||
const nodeId = String(slotLabelEvent.nodeId)
|
||||
const nodeRef = nodeRefs.get(nodeId)
|
||||
if (!nodeRef) return
|
||||
|
||||
// Force shallowReactive to detect the deep property change
|
||||
// by re-assigning the affected array through the defineProperty setter.
|
||||
if (slotLabelEvent.slotType !== NodeSlotType.OUTPUT && nodeRef.inputs) {
|
||||
nodeRef.inputs = [...nodeRef.inputs]
|
||||
}
|
||||
if (slotLabelEvent.slotType !== NodeSlotType.INPUT && nodeRef.outputs) {
|
||||
nodeRef.outputs = [...nodeRef.outputs]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -760,6 +789,9 @@ export function useGraphNodeManager(graph: LGraph): GraphNodeManager {
|
||||
case 'node:slot-links:changed':
|
||||
triggerHandlers['node:slot-links:changed'](event)
|
||||
break
|
||||
case 'node:slot-label:changed':
|
||||
triggerHandlers['node:slot-label:changed'](event)
|
||||
break
|
||||
}
|
||||
|
||||
// Chain to original handler
|
||||
|
||||
Reference in New Issue
Block a user