Migrate groupNode (#35)

This commit is contained in:
Chenlei Hu
2024-06-18 15:02:50 -04:00
committed by GitHub
parent a624d411cb
commit e444a86ffe
3 changed files with 56 additions and 8 deletions

View File

@@ -2,6 +2,7 @@ import { app } from "../../scripts/app";
import { api } from "../../scripts/api";
import { mergeIfValid } from "./widgetInputs";
import { ManageGroupDialog } from "./groupNodeManage";
import type { LGraphNode } from "/types/litegraph";
const GROUP = Symbol();
@@ -14,7 +15,9 @@ const Workflow = {
isInUseGroupNode(name) {
const id = `workflow/${name}`;
// Check if lready registered/in use in this workflow
// @ts-ignore
if (app.graph.extra?.groupNodes?.[name]) {
// @ts-ignore
if (app.graph._nodes.find((n) => n.type === id)) {
return Workflow.InUse.InWorkflow;
} else {
@@ -24,7 +27,9 @@ const Workflow = {
return Workflow.InUse.Free;
},
storeGroupNode(name, data) {
// @ts-ignore
let extra = app.graph.extra;
// @ts-ignore
if (!extra) app.graph.extra = extra = {};
let groupNodes = extra.groupNodes;
if (!groupNodes) extra.groupNodes = groupNodes = {};
@@ -33,6 +38,9 @@ const Workflow = {
};
class GroupNodeBuilder {
nodes: LGraphNode[];
nodeData: any;
constructor(nodes) {
this.nodes = nodes;
}
@@ -120,6 +128,8 @@ class GroupNodeBuilder {
// Use the built in copyToClipboard function to generate the node data we need
const backup = localStorage.getItem("litegrapheditor_clipboard");
try {
// @ts-ignore
// TODO Figure out if copyToClipboard is really taking this param
app.canvas.copyToClipboard(this.nodes);
const config = JSON.parse(localStorage.getItem("litegrapheditor_clipboard"));
@@ -134,6 +144,25 @@ class GroupNodeBuilder {
}
export class GroupNodeConfig {
name: string;
nodeData: any;
inputCount: number;
oldToNewOutputMap: {};
newToOldOutputMap: {};
oldToNewInputMap: {};
oldToNewWidgetMap: {};
newToOldWidgetMap: {};
primitiveDefs: {};
widgetToPrimitive: {};
primitiveToWidget: {};
nodeInputs: {};
outputVisibility: any[];
nodeDef: any;
inputs: any[];
linksFrom: {};
linksTo: {};
externalFrom: {};
constructor(name, nodeData) {
this.name = name;
this.nodeData = nodeData;
@@ -289,6 +318,7 @@ export class GroupNodeConfig {
null,
widget
);
// @ts-ignore
config = res?.customConfig ?? config;
}
}
@@ -312,6 +342,7 @@ export class GroupNodeConfig {
}
}
// @ts-ignore
config.forceInput = true;
return {
input: {
@@ -328,7 +359,7 @@ export class GroupNodeConfig {
console.warn("Skipping virtual node " + node.type + " when building group node " + this.name);
}
getInputConfig(node, inputName, seenInputs, config, extra) {
getInputConfig(node, inputName, seenInputs, config, extra?) {
const customConfig = this.nodeData.config?.[node.index]?.input?.[inputName];
let name = customConfig?.name ?? node.inputs?.find((inp) => inp.name === inputName)?.label ?? inputName;
let key = name;
@@ -580,6 +611,7 @@ export class GroupNodeConfig {
export class GroupNodeHandler {
node;
groupData;
innerNodes: any;
constructor(node) {
this.node = node;
@@ -624,6 +656,8 @@ export class GroupNodeHandler {
let link = app.graph.links[linkId];
// Use the outer link, but update the target to the inner node
// @ts-ignore
// TODO: Fix this
link = {
...link,
target_id: innerNode.id,
@@ -676,6 +710,7 @@ export class GroupNodeHandler {
this.groupData.nodeData.nodes.map((n, i) => {
const innerNode = LiteGraph.createNode(n.type);
innerNode.configure(n);
// @ts-ignore
innerNode.id = `${this.node.id}:${i}`;
return innerNode;
})
@@ -1225,7 +1260,9 @@ function addConvertToGroupOptions() {
}
// Add to canvas
// @ts-ignore
const getCanvasMenuOptions = LGraphCanvas.prototype.getCanvasMenuOptions;
// @ts-ignore
LGraphCanvas.prototype.getCanvasMenuOptions = function () {
const options = getCanvasMenuOptions.apply(this, arguments);
const index = options.findIndex((o) => o?.content === "Add Group") + 1 || options.length;
@@ -1235,7 +1272,9 @@ function addConvertToGroupOptions() {
};
// Add to nodes
// @ts-ignore
const getNodeMenuOptions = LGraphCanvas.prototype.getNodeMenuOptions;
// @ts-ignore
LGraphCanvas.prototype.getNodeMenuOptions = function (node) {
const options = getNodeMenuOptions.apply(this, arguments);
if (!GroupNodeHandler.isGroupNode(node)) {

View File

@@ -158,11 +158,11 @@ export function mergeIfValid(output, config2, forceUpdate, recreateWidget, confi
}
if (config1[0] instanceof Array) {
if (!isValidCombo(config1[0], config2[0])) return false;
if (!isValidCombo(config1[0], config2[0])) return;
} else if (config1[0] !== config2[0]) {
// Types dont match
console.log(`connection rejected: types dont match`, config1[0], config2[0]);
return false;
return;
}
const keys = new Set([...Object.keys(config1[1] ?? {}), ...Object.keys(config2[1] ?? {})]);
@@ -192,7 +192,7 @@ export function mergeIfValid(output, config2, forceUpdate, recreateWidget, confi
const theirMax = config2[1]?.["max"];
if (theirMax != null && v1 > theirMax) {
console.log("connection rejected: min > max", v1, theirMax);
return false;
return;
}
getCustomConfig()[k] = v1 == null ? v2 : v2 == null ? v1 : Math.max(v1, v2);
continue;
@@ -200,7 +200,7 @@ export function mergeIfValid(output, config2, forceUpdate, recreateWidget, confi
const theirMin = config2[1]?.["min"];
if (theirMin != null && v1 < theirMin) {
console.log("connection rejected: max < min", v1, theirMin);
return false;
return;
}
getCustomConfig()[k] = v1 == null ? v2 : v2 == null ? v1 : Math.min(v1, v2);
continue;
@@ -221,7 +221,7 @@ export function mergeIfValid(output, config2, forceUpdate, recreateWidget, confi
}
if (v1 % v2) {
console.log("connection rejected: steps not divisible", "current:", v1, "new:", v2);
return false;
return;
}
step = v1;
@@ -233,7 +233,7 @@ export function mergeIfValid(output, config2, forceUpdate, recreateWidget, confi
}
console.log(`connection rejected: config ${k} values dont match`, v1, v2);
return false;
return;
}
}
@@ -302,7 +302,7 @@ app.registerExtension({
}
}
}
//Convert.. main menu
if (toInput.length) {
if (useConversionSubmenusSetting.value) {

View File

@@ -52,6 +52,9 @@ export type WidgetCallback<T extends IWidget = IWidget> = (
) => void;
export interface IWidget<TValue = any, TOptions = any> {
// linked widgets, e.g. seed+seedControl
linkedWidgets: IWidget[];
name: string | null;
value: TValue;
options?: TOptions;
@@ -162,6 +165,7 @@ export declare class LGraph {
static supported_types: string[];
static STATUS_STOPPED: 1;
static STATUS_RUNNING: 2;
extra: any;
constructor(o?: object);
@@ -407,6 +411,11 @@ export type SerializedLGraphNode<T extends LGraphNode = LGraphNode> = {
/** https://github.com/jagenjo/litegraph.js/blob/master/guides/README.md#lgraphnode */
export declare class LGraphNode {
// Used in group node
setInnerNodes(nodes: any) {
throw new Error("Method not implemented.");
}
static title_color: string;
static title: string;
static type: null | string;