mirror of
https://github.com/Comfy-Org/ComfyUI_frontend.git
synced 2026-04-28 10:12:11 +00:00
[Refactor] Split node slot code out to base class (#994)
Foundational work for subgraph.
This commit is contained in:
@@ -3521,7 +3521,7 @@ export class LGraphNode implements Positionable, IPinnable, IColorable {
|
|||||||
isValidTarget ||
|
isValidTarget ||
|
||||||
!slot.isWidgetInputSlot ||
|
!slot.isWidgetInputSlot ||
|
||||||
this.#isMouseOverWidget(this.getWidgetFromSlot(slot)) ||
|
this.#isMouseOverWidget(this.getWidgetFromSlot(slot)) ||
|
||||||
slot.isConnected()
|
slot.isConnected
|
||||||
) {
|
) {
|
||||||
ctx.globalAlpha = isValid ? editorAlpha : 0.4 * editorAlpha
|
ctx.globalAlpha = isValid ? editorAlpha : 0.4 * editorAlpha
|
||||||
slot.draw(ctx, {
|
slot.draw(ctx, {
|
||||||
|
|||||||
@@ -38,7 +38,7 @@ export interface HasBoundingRect {
|
|||||||
*
|
*
|
||||||
* Used for various calculations, such as overlap, selective rendering, and click checks.
|
* Used for various calculations, such as overlap, selective rendering, and click checks.
|
||||||
* For most items, this is cached position & size as `x, y, width, height`.
|
* For most items, this is cached position & size as `x, y, width, height`.
|
||||||
* Some items (such as nodes) may extend above and/or to the left of their {@link pos}.
|
* Some items (such as nodes and slots) may extend above and/or to the left of their {@link pos}.
|
||||||
* @readonly
|
* @readonly
|
||||||
* @see {@link move}
|
* @see {@link move}
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -22,7 +22,7 @@ export class NodeInputSlot extends NodeSlot implements INodeInputSlot {
|
|||||||
this.link = slot.link
|
this.link = slot.link
|
||||||
}
|
}
|
||||||
|
|
||||||
override isConnected(): boolean {
|
override get isConnected(): boolean {
|
||||||
return this.link != null
|
return this.link != null
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -31,7 +31,7 @@ export class NodeInputSlot extends NodeSlot implements INodeInputSlot {
|
|||||||
}
|
}
|
||||||
|
|
||||||
override draw(ctx: CanvasRenderingContext2D, options: Omit<IDrawOptions, "doStroke" | "labelPosition">) {
|
override draw(ctx: CanvasRenderingContext2D, options: Omit<IDrawOptions, "doStroke" | "labelPosition">) {
|
||||||
const originalTextAlign = ctx.textAlign
|
const { textAlign } = ctx
|
||||||
ctx.textAlign = "left"
|
ctx.textAlign = "left"
|
||||||
|
|
||||||
super.draw(ctx, {
|
super.draw(ctx, {
|
||||||
@@ -40,6 +40,6 @@ export class NodeInputSlot extends NodeSlot implements INodeInputSlot {
|
|||||||
doStroke: false,
|
doStroke: false,
|
||||||
})
|
})
|
||||||
|
|
||||||
ctx.textAlign = originalTextAlign
|
ctx.textAlign = textAlign
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -36,13 +36,12 @@ export class NodeOutputSlot extends NodeSlot implements INodeOutputSlot {
|
|||||||
return "link" in fromSlot && LiteGraph.isValidConnection(this.type, fromSlot.type)
|
return "link" in fromSlot && LiteGraph.isValidConnection(this.type, fromSlot.type)
|
||||||
}
|
}
|
||||||
|
|
||||||
override isConnected(): boolean {
|
override get isConnected(): boolean {
|
||||||
return this.links != null && this.links.length > 0
|
return this.links != null && this.links.length > 0
|
||||||
}
|
}
|
||||||
|
|
||||||
override draw(ctx: CanvasRenderingContext2D, options: Omit<IDrawOptions, "doStroke" | "labelPosition">) {
|
override draw(ctx: CanvasRenderingContext2D, options: Omit<IDrawOptions, "doStroke" | "labelPosition">) {
|
||||||
const originalTextAlign = ctx.textAlign
|
const { textAlign, strokeStyle } = ctx
|
||||||
const originalStrokeStyle = ctx.strokeStyle
|
|
||||||
ctx.textAlign = "right"
|
ctx.textAlign = "right"
|
||||||
ctx.strokeStyle = "black"
|
ctx.strokeStyle = "black"
|
||||||
|
|
||||||
@@ -52,7 +51,7 @@ export class NodeOutputSlot extends NodeSlot implements INodeOutputSlot {
|
|||||||
doStroke: true,
|
doStroke: true,
|
||||||
})
|
})
|
||||||
|
|
||||||
ctx.textAlign = originalTextAlign
|
ctx.textAlign = textAlign
|
||||||
ctx.strokeStyle = originalStrokeStyle
|
ctx.strokeStyle = strokeStyle
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import type { CanvasColour, DefaultConnectionColors, INodeInputSlot, INodeOutputSlot, INodeSlot, ISlotType, IWidgetLocator, OptionalProps, Point, ReadOnlyPoint, Rect } from "@/interfaces"
|
import type { CanvasColour, DefaultConnectionColors, INodeInputSlot, INodeOutputSlot, INodeSlot, OptionalProps, Point, ReadOnlyPoint } from "@/interfaces"
|
||||||
import type { LGraphNode } from "@/LGraphNode"
|
import type { LGraphNode } from "@/LGraphNode"
|
||||||
|
|
||||||
import { LabelPosition, SlotShape, SlotType } from "@/draw"
|
import { LabelPosition, SlotShape, SlotType } from "@/draw"
|
||||||
@@ -7,6 +7,7 @@ import { getCentre } from "@/measure"
|
|||||||
import { LinkDirection, RenderShape } from "@/types/globalEnums"
|
import { LinkDirection, RenderShape } from "@/types/globalEnums"
|
||||||
|
|
||||||
import { NodeInputSlot } from "./NodeInputSlot"
|
import { NodeInputSlot } from "./NodeInputSlot"
|
||||||
|
import { SlotBase } from "./SlotBase"
|
||||||
|
|
||||||
export interface IDrawOptions {
|
export interface IDrawOptions {
|
||||||
colorContext: DefaultConnectionColors
|
colorContext: DefaultConnectionColors
|
||||||
@@ -16,22 +17,9 @@ export interface IDrawOptions {
|
|||||||
highlight?: boolean
|
highlight?: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
export abstract class NodeSlot implements INodeSlot {
|
/** Shared base class for {@link LGraphNode} input and output slots. */
|
||||||
name: string
|
export abstract class NodeSlot extends SlotBase implements INodeSlot {
|
||||||
localized_name?: string
|
|
||||||
label?: string
|
|
||||||
type: ISlotType
|
|
||||||
dir?: LinkDirection
|
|
||||||
removable?: boolean
|
|
||||||
shape?: RenderShape
|
|
||||||
color_off?: CanvasColour
|
|
||||||
color_on?: CanvasColour
|
|
||||||
locked?: boolean
|
|
||||||
nameLocked?: boolean
|
|
||||||
pos?: Point
|
pos?: Point
|
||||||
widget?: IWidgetLocator
|
|
||||||
hasErrors?: boolean
|
|
||||||
readonly boundingRect: Rect
|
|
||||||
|
|
||||||
/** The offset from the parent node to the centre point of this slot. */
|
/** The offset from the parent node to the centre point of this slot. */
|
||||||
get #centreOffset(): ReadOnlyPoint {
|
get #centreOffset(): ReadOnlyPoint {
|
||||||
@@ -64,10 +52,9 @@ export abstract class NodeSlot implements INodeSlot {
|
|||||||
abstract get isWidgetInputSlot(): boolean
|
abstract get isWidgetInputSlot(): boolean
|
||||||
|
|
||||||
constructor(slot: OptionalProps<INodeSlot, "boundingRect">, node: LGraphNode) {
|
constructor(slot: OptionalProps<INodeSlot, "boundingRect">, node: LGraphNode) {
|
||||||
|
super(slot.name, slot.type, slot.boundingRect ?? [0, 0, 0, 0])
|
||||||
|
|
||||||
Object.assign(this, slot)
|
Object.assign(this, slot)
|
||||||
this.name = slot.name
|
|
||||||
this.type = slot.type
|
|
||||||
this.boundingRect = slot.boundingRect ?? [0, 0, 0, 0]
|
|
||||||
this.#node = node
|
this.#node = node
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -84,14 +71,6 @@ export abstract class NodeSlot implements INodeSlot {
|
|||||||
return this.label || this.localized_name || this.name || ""
|
return this.label || this.localized_name || this.name || ""
|
||||||
}
|
}
|
||||||
|
|
||||||
abstract isConnected(): boolean
|
|
||||||
|
|
||||||
renderingColor(colorContext: DefaultConnectionColors): CanvasColour {
|
|
||||||
return this.isConnected()
|
|
||||||
? this.color_on || colorContext.getConnectedColor(this.type)
|
|
||||||
: this.color_off || colorContext.getDisconnectedColor(this.type)
|
|
||||||
}
|
|
||||||
|
|
||||||
draw(
|
draw(
|
||||||
ctx: CanvasRenderingContext2D,
|
ctx: CanvasRenderingContext2D,
|
||||||
{
|
{
|
||||||
|
|||||||
41
src/node/SlotBase.ts
Normal file
41
src/node/SlotBase.ts
Normal file
@@ -0,0 +1,41 @@
|
|||||||
|
import type { CanvasColour, DefaultConnectionColors, INodeSlot, ISlotType, IWidgetLocator, Point, Rect } from "@/interfaces"
|
||||||
|
import type { LLink } from "@/LLink"
|
||||||
|
import type { RenderShape } from "@/types/globalEnums"
|
||||||
|
import type { LinkDirection } from "@/types/globalEnums"
|
||||||
|
|
||||||
|
/** Base class for all input & output slots. */
|
||||||
|
|
||||||
|
export abstract class SlotBase implements INodeSlot {
|
||||||
|
name: string
|
||||||
|
localized_name?: string
|
||||||
|
label?: string
|
||||||
|
type: ISlotType
|
||||||
|
dir?: LinkDirection
|
||||||
|
removable?: boolean
|
||||||
|
shape?: RenderShape
|
||||||
|
color_off?: CanvasColour
|
||||||
|
color_on?: CanvasColour
|
||||||
|
locked?: boolean
|
||||||
|
nameLocked?: boolean
|
||||||
|
widget?: IWidgetLocator
|
||||||
|
_floatingLinks?: Set<LLink>
|
||||||
|
hasErrors?: boolean
|
||||||
|
|
||||||
|
/** The centre point of the slot. */
|
||||||
|
abstract pos?: Point
|
||||||
|
readonly boundingRect: Rect
|
||||||
|
|
||||||
|
constructor(name: string, type: ISlotType, boundingRect: Rect) {
|
||||||
|
this.name = name
|
||||||
|
this.type = type
|
||||||
|
this.boundingRect = boundingRect
|
||||||
|
}
|
||||||
|
|
||||||
|
abstract get isConnected(): boolean
|
||||||
|
|
||||||
|
renderingColor(colorContext: DefaultConnectionColors): CanvasColour {
|
||||||
|
return this.isConnected
|
||||||
|
? this.color_on || colorContext.getConnectedColor(this.type)
|
||||||
|
: this.color_off || colorContext.getDisconnectedColor(this.type)
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user