Files
bentoml-comfy-pack/web/dynamic.js
T
2024-11-20 14:42:12 +08:00

76 lines
2.6 KiB
JavaScript

import { app } from "../../scripts/app.js";
function mimicNode(node, target, slot) {
const getWidget = (widget) => {
if (typeof widget.origType === "undefined") return widget;
const newWidget = Object.assign({}, widget);
for (const key in widget) {
if (key.startsWith("orig") || key === "computeSize") {
delete newWidget[key];
}
}
newWidget.type = widget.origType;
newWidget.name = inputName;
return newWidget;
}
const input = target.inputs[slot];
const inputName = node.inputs.length > 0 ? node.inputs[0].name : node.widgets[0].name;
if (typeof input.widget === "undefined") { // This is an input
node.inputs = [{ ...input, name: inputName }];
node.widgets = [];
} else { // This is a widget
node.widgets = [getWidget(target.widgets.find(w => w.name === input.name))];
node.inputs = [];
node.size = node.computeSize();
requestAnimationFrame(() => {
if (node.onResize) {
node.onResize(node.size);
}
});
}
}
app.registerExtension({
name: "Comfy.DynamicInput",
extensionNodes: ["CPackInputValue", "CPackInputFile"],
async beforeRegisterNodeDef(nodeType, nodeData) {
if (!this.extensionNodes.includes(nodeData.name)) return;
nodeType.prototype.onConnectOutput = function () {
if (this.outputs[0].links?.length > 0) return false;
const target = arguments[3];
if (this.type === "CPackInputFile" && !["COMBO", "STRING"].includes(target.inputs[arguments[4]].type))
return false;
mimicNode(this, target, arguments[4]);
this.title = target.inputs[arguments[4]].name;
}
},
async setup(app) {
app.graph.nodes.forEach((node) => {
if (!this.extensionNodes.includes(node.type)) return;
if (node.outputs.length > 0 && node.outputs[0].links.length > 0) {
const link = node.graph.links[node.outputs[0].links[0]];
mimicNode(node, app.graph.getNodeById(link.target_id), link.target_slot);
}
})
},
async init(app) {
const originalToPrompt = app.graphToPrompt;
const self = this;
app.graphToPrompt = async function(graph = app.graph, clean = true) {
const { workflow, output } = await originalToPrompt(graph, clean);
Object.entries(output).forEach(([id, nodeData]) => {
if (!self.extensionNodes.includes(nodeData.class_type)) return;
const node = graph.getNodeById(parseInt(id));
if (node.widgets.length === 0) return;
const widget = node.widgets[0];
nodeData["_meta"] = Object.assign({}, nodeData["_meta"] || {}, { options: widget.options });
});
return { workflow, output };
};
}
});