[backport core/1.35] Do not delay fit to view on graph restore (#7678)

Backport of #7645 to core/1.35

## Original PR Summary
Fixes a bug where swapping to a different workflow from the inside of a
subgraph would cause nodes to be in an incorrect position after swapping
back in vue mode.

This is done by not delaying the fitView by a frame (which causes it to
occur after the graph is no longer in the configuring state).

┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-7678-backport-core-1-35-Do-not-delay-fit-to-view-on-graph-restore-2cf6d73d36508101aea2e54c5388a32f)
by [Unito](https://www.unito.io)

Co-authored-by: AustinMroz <austin@comfy.org>
This commit is contained in:
Christian Byrne
2025-12-20 12:37:34 -08:00
committed by GitHub
parent b7b4608e7b
commit a8d0cfe058
3 changed files with 17 additions and 14 deletions

View File

@@ -2000,7 +2000,7 @@ export class LGraphNode
* @param out `x, y, width, height` are written to this array.
* @param ctx The canvas context to use for measuring text.
*/
measure(out: Rect, ctx: CanvasRenderingContext2D): void {
measure(out: Rect, ctx?: CanvasRenderingContext2D): void {
const titleMode = this.title_mode
const renderTitle =
titleMode != TitleMode.TRANSPARENT_TITLE &&
@@ -2013,11 +2013,13 @@ export class LGraphNode
out[2] = this.size[0]
out[3] = this.size[1] + titleHeight
} else {
ctx.font = this.innerFontStyle
if (ctx) ctx.font = this.innerFontStyle
this._collapsed_width = Math.min(
this.size[0],
ctx.measureText(this.getTitle() ?? '').width +
LiteGraph.NODE_TITLE_HEIGHT * 2
ctx
? ctx.measureText(this.getTitle() ?? '').width +
LiteGraph.NODE_TITLE_HEIGHT * 2
: 0
)
out[2] = this._collapsed_width || LiteGraph.NODE_COLLAPSED_WIDTH
out[3] = LiteGraph.NODE_TITLE_HEIGHT
@@ -2047,7 +2049,7 @@ export class LGraphNode
* Calculates the render area of this node, populating both {@link boundingRect} and {@link renderArea}.
* Called automatically at the start of every frame.
*/
updateArea(ctx: CanvasRenderingContext2D): void {
updateArea(ctx?: CanvasRenderingContext2D): void {
const bounds = this.#boundingRect
this.measure(bounds, ctx)
this.onBounding?.(bounds)

View File

@@ -1224,12 +1224,7 @@ export class ComfyApp {
this.canvas.ds.offset = graphData.extra.ds.offset
this.canvas.ds.scale = graphData.extra.ds.scale
} else {
// @note: Set view after the graph has been rendered once. fitView uses
// boundingRect on nodes to calculate the view bounds, which only become
// available after the first render.
requestAnimationFrame(() => {
useLitegraphService().fitView()
})
useLitegraphService().fitView()
}
}
} catch (error) {

View File

@@ -868,6 +868,13 @@ export const useLitegraphService = () => {
app.canvas.animateToBounds(graphNode.boundingRect)
}
function ensureBounds(nodes: LGraphNode[]) {
for (const node of nodes) {
if (!node.boundingRect.every((i) => i === 0)) continue
node.updateArea()
}
}
/**
* Resets the canvas view to the default
*/
@@ -881,11 +888,10 @@ export const useLitegraphService = () => {
}
function fitView() {
const canvas = canvasStore.canvas
if (!canvas) return
const canvas = canvasStore.getCanvas()
const nodes = canvas.graph?.nodes
if (!nodes) return
ensureBounds(nodes)
const bounds = createBounds(nodes)
if (!bounds) return