Added Support for Riverflow 2.5

This commit is contained in:
Sirshendu Ganguly
2026-06-08 09:27:56 +05:30
parent 85ec73715d
commit 46074fde9c
11 changed files with 468 additions and 22 deletions
+8
View File
@@ -26,6 +26,7 @@ from .modules.ipAdapterCombine import ipAdapterCombine
from .modules.vaeSearch import vaeSearch
from .modules.referenceImages import referenceImages
from .modules.imageInferenceInputs import imageInferenceInputs
from .modules.imageInferenceInputsFonts import RunwareImageInferenceInputsFonts
from .modules.imageInferenceAdvancedFeatures import RunwareImageInferenceAdvancedFeatures
from .modules.imageWatermarkAdvancedFeature import RunwareWatermarkAdvancedFeature
from .modules.imageRegionalPromptingAdvancedFeature import RunwareRegionalPromptingAdvancedFeature
@@ -112,6 +113,10 @@ from .modules.imageInferenceSettingsColorPalette import RunwareImageInferenceSet
from .modules.imageInferenceSettingsMoodboards import RunwareImageInferenceSettingsMoodboards
from .modules.imageInferenceSettingsStructuredPrompt import RunwareImageInferenceSettingsStructuredPrompt
from .modules.imageInferenceSettingsPromptEnhance import RunwareImageInferenceSettingsPromptEnhance
from .modules.imageInferenceSettingsScoringRubric import (
RunwareImageInferenceSettingsScoringRubric,
RunwareImageInferenceSettingsScoringRubricCombine,
)
from .modules.videoAdvancedFeatureInputs import videoAdvancedFeatureInputs
from .modules.advancedFeatureSettings.wanAnimateAdvancedFeatureSettings import RunwareWanAnimateAdvancedFeatureSettings
from .modules.saveImage import RunwareSaveImage
@@ -166,6 +171,7 @@ NODE_CLASS_MAPPINGS = {
"Runware IPAdapters Combine": ipAdapterCombine,
"Runware Reference Images": referenceImages,
"Runware Image Inference Inputs": imageInferenceInputs,
"Runware Image Inference Inputs Fonts": RunwareImageInferenceInputsFonts,
"Runware Image Advanced Feature Input": RunwareImageInferenceAdvancedFeatures,
"Runware Watermark Advanced Feature": RunwareWatermarkAdvancedFeature,
"Runware Regional Prompting Advanced Feature": RunwareRegionalPromptingAdvancedFeature,
@@ -254,6 +260,8 @@ NODE_CLASS_MAPPINGS = {
"Runware Image Inference Settings Moodboards": RunwareImageInferenceSettingsMoodboards,
"Runware Image Inference Settings Structured Prompt": RunwareImageInferenceSettingsStructuredPrompt,
"Runware Image Inference Settings Prompt Enhance": RunwareImageInferenceSettingsPromptEnhance,
"Runware Image Inference Settings Scoring Rubric": RunwareImageInferenceSettingsScoringRubric,
"Runware Image Inference Settings Scoring Rubric Combine": RunwareImageInferenceSettingsScoringRubricCombine,
"Runware Video Advanced Feature Inputs": videoAdvancedFeatureInputs,
"Runware Wan Animate Advanced Feature Settings": RunwareWanAnimateAdvancedFeatureSettings,
"Runware Save Image": RunwareSaveImage,
+3 -1
View File
@@ -1,6 +1,6 @@
import { app } from "../../scripts/app.js";
import { api } from "../../scripts/api.js";
import { promptEnhanceHandler, syncDimensionsNodeHandler, searchNodeHandler, APIKeyHandler, captionNodeHandler, saveTextHandler, mediaUUIDHandler, save3DFilepathHandler, videoTranscriptionHandler, videoOutputsHandler, handleCustomErrors, videoInferenceDimensionsHandler, videoModelSearchFilterHandler, audioModelSearchFilterHandler, textModelSearchFilterHandler, vectorizeModelSearchFilterHandler, vectorizeToggleHandler, useParameterToggleHandler, imageInferenceToggleHandler, imageInferenceAdvancedFeaturesToggleHandler, watermarkAdvancedFeatureToggleHandler, videoInferenceSpeechInputToggleHandler, regionalPromptingRegionsToggleHandler, upscalerToggleHandler, imageUpscalerSettingsToggleHandler, videoUpscalerToggleHandler, audioInferenceToggleHandler, audioInferenceSpeechToggleHandler, audioSettingsToggleHandler, textInferenceSettingsToggleHandler, videoSettingsToggleHandler, videoInferenceSettingsTtsToggleHandler, videoInferenceSettingsActiveSpeakerDetectionToggleHandler, videoInferenceSettingsActiveSpeakerBoundingBoxesToggleHandler, videoInferenceSettingsSegmentsToggleHandler, acceleratorOptionsToggleHandler, bytedanceProviderSettingsToggleHandler, xaiProviderSettingsToggleHandler, viduProviderSettingsToggleHandler, sourcefulProviderSettingsToggleHandler, sourcefulProviderSettingsFontsToggleHandler, threeDInferenceToggleHandler, threeDInferenceSettingsToggleHandler, threeDInferenceSettingsLatToggleHandler, threeDInferenceSettingsMeshClusterToggleHandler, ultralyticsProviderSettingsToggleHandler, openaiProviderSettingsToggleHandler, lightricksProviderSettingsToggleHandler, klingProviderSettingsToggleHandler, lumaProviderSettingsToggleHandler, briaProviderSettingsToggleHandler, pixverseProviderSettingsToggleHandler, alibabaProviderSettingsToggleHandler, mireloProviderSettingsToggleHandler, googleProviderSettingsToggleHandler, syncProviderSettingsToggleHandler, syncSegmentToggleHandler, settingsToggleHandler, outpaintSettingsToggleHandler, safetyInputsToggleHandler, imageInferenceSettingsColorPaletteToggleHandler, imageInferenceSettingsMoodboardsToggleHandler, imageInferenceSettingsStructuredPromptToggleHandler, imageInferenceSettingsPromptEnhanceToggleHandler, audioInputToggleHandler, speechInputToggleHandler, briaProviderMaskToggleHandler, wanAnimateAdvancedFeatureSettingsToggleHandler, videoAdvancedFeatureInputsToggleHandler, audioInferenceInputsToggleHandler, audioInferenceReferenceVoiceToggleHandler, audioInferenceSpeechVoicesToggleHandler, videoInputsFrameToggleHandler, referenceVideosToggleHandler } from "./utils.js";
import { promptEnhanceHandler, syncDimensionsNodeHandler, searchNodeHandler, APIKeyHandler, captionNodeHandler, saveTextHandler, mediaUUIDHandler, save3DFilepathHandler, videoTranscriptionHandler, videoOutputsHandler, handleCustomErrors, videoInferenceDimensionsHandler, videoModelSearchFilterHandler, audioModelSearchFilterHandler, textModelSearchFilterHandler, vectorizeModelSearchFilterHandler, vectorizeToggleHandler, useParameterToggleHandler, imageInferenceToggleHandler, imageInferenceAdvancedFeaturesToggleHandler, watermarkAdvancedFeatureToggleHandler, videoInferenceSpeechInputToggleHandler, regionalPromptingRegionsToggleHandler, upscalerToggleHandler, imageUpscalerSettingsToggleHandler, videoUpscalerToggleHandler, audioInferenceToggleHandler, audioInferenceSpeechToggleHandler, audioSettingsToggleHandler, textInferenceSettingsToggleHandler, videoSettingsToggleHandler, videoInferenceSettingsTtsToggleHandler, videoInferenceSettingsActiveSpeakerDetectionToggleHandler, videoInferenceSettingsActiveSpeakerBoundingBoxesToggleHandler, videoInferenceSettingsSegmentsToggleHandler, acceleratorOptionsToggleHandler, bytedanceProviderSettingsToggleHandler, xaiProviderSettingsToggleHandler, viduProviderSettingsToggleHandler, sourcefulProviderSettingsToggleHandler, sourcefulProviderSettingsFontsToggleHandler, threeDInferenceToggleHandler, threeDInferenceSettingsToggleHandler, threeDInferenceSettingsLatToggleHandler, threeDInferenceSettingsMeshClusterToggleHandler, ultralyticsProviderSettingsToggleHandler, openaiProviderSettingsToggleHandler, lightricksProviderSettingsToggleHandler, klingProviderSettingsToggleHandler, lumaProviderSettingsToggleHandler, briaProviderSettingsToggleHandler, pixverseProviderSettingsToggleHandler, alibabaProviderSettingsToggleHandler, mireloProviderSettingsToggleHandler, googleProviderSettingsToggleHandler, syncProviderSettingsToggleHandler, syncSegmentToggleHandler, settingsToggleHandler, outpaintSettingsToggleHandler, safetyInputsToggleHandler, imageInferenceSettingsColorPaletteToggleHandler, imageInferenceSettingsMoodboardsToggleHandler, imageInferenceSettingsStructuredPromptToggleHandler, imageInferenceSettingsPromptEnhanceToggleHandler, imageInferenceSettingsScoringRubricToggleHandler, audioInputToggleHandler, speechInputToggleHandler, briaProviderMaskToggleHandler, wanAnimateAdvancedFeatureSettingsToggleHandler, videoAdvancedFeatureInputsToggleHandler, audioInferenceInputsToggleHandler, audioInferenceReferenceVoiceToggleHandler, audioInferenceSpeechVoicesToggleHandler, videoInputsFrameToggleHandler, referenceVideosToggleHandler } from "./utils.js";
import { RUNWARE_NODE_TYPES, RUNWARE_NODE_PROPS, SEARCH_TERMS } from "./types.js";
const nodeInitList = [];
@@ -157,6 +157,8 @@ app.registerExtension({
imageInferenceSettingsStructuredPromptToggleHandler(node);
} else if(nodeClass === RUNWARE_NODE_TYPES.IMAGEINFERENCESETTINGSPROMPTENHANCE) {
imageInferenceSettingsPromptEnhanceToggleHandler(node);
} else if(nodeClass === RUNWARE_NODE_TYPES.IMAGEINFERENCESETTINGSSCORINGRUBRIC) {
imageInferenceSettingsScoringRubricToggleHandler(node);
} else if(nodeClass === RUNWARE_NODE_TYPES.AUDIOINPUT) {
audioInputToggleHandler(node);
} else if(nodeClass === RUNWARE_NODE_TYPES.SPEECHINPUT) {
+15
View File
@@ -76,6 +76,7 @@ const RUNWARE_NODE_TYPES = {
VAE: "Runware VAE Search",
REFERENCEIMAGES: "Runware Reference Images",
IMAGEINFERENCEINPUTS: "Runware Image Inference Inputs",
IMAGEINFERENCEINPUTSFONTS: "Runware Image Inference Inputs Fonts",
IMAGEINFERENCEADVANCEDFEATURES: "Runware Image Advanced Feature Input",
VIDEOINFERENCE: "Runware Video Inference",
VIDEOMODELSEARCH: "Runware Video Model Search",
@@ -161,6 +162,8 @@ const RUNWARE_NODE_TYPES = {
IMAGEINFERENCESETTINGSMOODBOARDS: "Runware Image Inference Settings Moodboards",
IMAGEINFERENCESETTINGSSTRUCTUREDPROMPT: "Runware Image Inference Settings Structured Prompt",
IMAGEINFERENCESETTINGSPROMPTENHANCE: "Runware Image Inference Settings Prompt Enhance",
IMAGEINFERENCESETTINGSSCORINGRUBRIC: "Runware Image Inference Settings Scoring Rubric",
IMAGEINFERENCESETTINGSSCORINGRUBRICCOMBINE: "Runware Image Inference Settings Scoring Rubric Combine",
VIDEOADVANCEDFEATUREINPUTS: "Runware Video Advanced Feature Inputs",
WANANIMATEADVANCEDFEATURESETTINGS: "Runware Wan Animate Advanced Feature Settings",
SAVEIMAGE: "Runware Save Image",
@@ -370,6 +373,10 @@ const RUNWARE_NODE_PROPS = {
bgColor: DEFAULT_BGCOLOR,
colorModeOnly: true,
},
[RUNWARE_NODE_TYPES.IMAGEINFERENCEINPUTSFONTS]: {
bgColor: DEFAULT_BGCOLOR,
colorModeOnly: true,
},
[RUNWARE_NODE_TYPES.IMAGEINFERENCEADVANCEDFEATURES]: {
bgColor: DEFAULT_BGCOLOR,
colorModeOnly: true,
@@ -642,6 +649,14 @@ const RUNWARE_NODE_PROPS = {
bgColor: DEFAULT_BGCOLOR,
colorModeOnly: true,
},
[RUNWARE_NODE_TYPES.IMAGEINFERENCESETTINGSSCORINGRUBRIC]: {
bgColor: DEFAULT_BGCOLOR,
colorModeOnly: true,
},
[RUNWARE_NODE_TYPES.IMAGEINFERENCESETTINGSSCORINGRUBRICCOMBINE]: {
bgColor: DEFAULT_BGCOLOR,
colorModeOnly: true,
},
[RUNWARE_NODE_TYPES.VIDEOADVANCEDFEATUREINPUTS]: {
bgColor: DEFAULT_BGCOLOR,
colorModeOnly: true,
+90 -11
View File
@@ -2135,12 +2135,9 @@ function sourcefulProviderSettingsToggleHandler(sourcefulNode) {
}
function sourcefulProviderSettingsFontsToggleHandler(fontsNode) {
const useFont1Widget = fontsNode.widgets.find(w => w.name === "useFont1");
const fontUrl1Widget = fontsNode.widgets.find(w => w.name === "fontUrl1");
const text1Widget = fontsNode.widgets.find(w => w.name === "text1");
const useFont2Widget = fontsNode.widgets.find(w => w.name === "useFont2");
const fontUrl2Widget = fontsNode.widgets.find(w => w.name === "fontUrl2");
const text2Widget = fontsNode.widgets.find(w => w.name === "text2");
if (!fontsNode?.widgets) return;
if (fontsNode._sourcefulProviderSettingsFontsToggleHandlerRegistered) return;
fontsNode._sourcefulProviderSettingsFontsToggleHandlerRegistered = true;
function toggleFontGroup(useWidget, fontUrlWidget, textWidget, fontParamName, textParamName) {
if (!useWidget || !fontUrlWidget || !textWidget) return;
@@ -2180,11 +2177,13 @@ function sourcefulProviderSettingsFontsToggleHandler(fontsNode) {
setTimeout(toggleEnabled, 100);
}
if (useFont1Widget && fontUrl1Widget && text1Widget) {
toggleFontGroup(useFont1Widget, fontUrl1Widget, text1Widget, "fontUrl1", "text1");
}
if (useFont2Widget && fontUrl2Widget && text2Widget) {
toggleFontGroup(useFont2Widget, fontUrl2Widget, text2Widget, "fontUrl2", "text2");
for (let i = 1; i <= 2; i++) {
const useFontWidget = fontsNode.widgets.find(w => w && w.name === `useFont${i}`);
const fontUrlWidget = fontsNode.widgets.find(w => w && w.name === `fontUrl${i}`);
const textWidget = fontsNode.widgets.find(w => w && w.name === `text${i}`);
if (useFontWidget && fontUrlWidget && textWidget) {
toggleFontGroup(useFontWidget, fontUrlWidget, textWidget, `fontUrl${i}`, `text${i}`);
}
}
}
@@ -5260,6 +5259,7 @@ export {
imageInferenceSettingsMoodboardsToggleHandler,
imageInferenceSettingsStructuredPromptToggleHandler,
imageInferenceSettingsPromptEnhanceToggleHandler,
imageInferenceSettingsScoringRubricToggleHandler,
audioInputToggleHandler,
speechInputToggleHandler,
briaProviderMaskToggleHandler,
@@ -5380,6 +5380,14 @@ function settingsToggleHandler(settingsNode) {
const dilatePixelsWidget = settingsNode.widgets.find(w => w.name === "dilatePixels");
const useCreativityWidget = settingsNode.widgets.find(w => w.name === "useCreativity");
const creativityWidget = settingsNode.widgets.find(w => w.name === "creativity");
const useBackgroundModeWidget = settingsNode.widgets.find(w => w.name === "useBackgroundMode");
const backgroundModeWidget = settingsNode.widgets.find(w => w.name === "backgroundMode");
const useBackgroundColorWidget = settingsNode.widgets.find(w => w.name === "useBackgroundColor");
const backgroundColorWidget = settingsNode.widgets.find(w => w.name === "backgroundColor");
const useEnhancePromptWidget = settingsNode.widgets.find(w => w.name === "useEnhancePrompt");
const enhancePromptWidget = settingsNode.widgets.find(w => w.name === "enhancePrompt");
const useScoringPromptWidget = settingsNode.widgets.find(w => w.name === "useScoringPrompt");
const scoringPromptWidget = settingsNode.widgets.find(w => w.name === "scoringPrompt");
// Helper function to toggle widget enabled state
function toggleWidgetState(useWidget, paramWidget, paramName) {
@@ -5481,6 +5489,18 @@ function settingsToggleHandler(settingsNode) {
if (useCreativityWidget && creativityWidget) {
toggleWidgetState(useCreativityWidget, creativityWidget, "creativity");
}
if (useBackgroundModeWidget && backgroundModeWidget) {
toggleWidgetState(useBackgroundModeWidget, backgroundModeWidget, "backgroundMode");
}
if (useBackgroundColorWidget && backgroundColorWidget) {
toggleWidgetState(useBackgroundColorWidget, backgroundColorWidget, "backgroundColor");
}
if (useEnhancePromptWidget && enhancePromptWidget) {
toggleWidgetState(useEnhancePromptWidget, enhancePromptWidget, "enhancePrompt");
}
if (useScoringPromptWidget && scoringPromptWidget) {
toggleWidgetState(useScoringPromptWidget, scoringPromptWidget, "scoringPrompt");
}
}
function outpaintSettingsToggleHandler(settingsNode) {
@@ -5705,6 +5725,65 @@ function imageInferenceSettingsMoodboardsToggleHandler(moodboardsNode) {
setTimeout(toggleStrengthState, 100);
}
function imageInferenceSettingsScoringRubricToggleHandler(rubricNode) {
if (!rubricNode?.widgets) return;
if (rubricNode._imageInferenceSettingsScoringRubricToggleHandlerRegistered) return;
rubricNode._imageInferenceSettingsScoringRubricToggleHandlerRegistered = true;
function toggleWidgetState(useWidget, paramWidgets, paramNames) {
if (!useWidget) return;
const widgets = Array.isArray(paramWidgets) ? paramWidgets : [paramWidgets];
const names = Array.isArray(paramNames) ? paramNames : [paramNames];
function toggleEnabled() {
const enabled = useWidget.value === true;
widgets.forEach((paramWidget, index) => {
if (!paramWidget) return;
toggleWidgetEnabled(paramWidget, enabled, rubricNode);
const paramName = names[index];
if (!paramWidget.inputEl && paramName) {
const nodeElement = rubricNode.htmlElements?.widgetsContainer || rubricNode.htmlElements;
if (nodeElement) {
const input = nodeElement.querySelector(
`input[name="${paramName}"], textarea[name="${paramName}"], select[name="${paramName}"]`
);
if (input) {
input.disabled = !enabled;
input.style.opacity = enabled ? "1" : "0.5";
input.style.pointerEvents = enabled ? "auto" : "none";
}
}
}
});
rubricNode.setDirtyCanvas(true);
}
appendWidgetCB(useWidget, () => setTimeout(toggleEnabled, 50));
setTimeout(toggleEnabled, 100);
}
const usePassingScoreWidget = rubricNode.widgets.find((w) => w && w.name === "usePassingScore");
const passingScoreWidget = rubricNode.widgets.find((w) => w && w.name === "passingScore");
if (usePassingScoreWidget && passingScoreWidget) {
toggleWidgetState(usePassingScoreWidget, passingScoreWidget, "passingScore");
}
for (let i = 1; i <= 5; i++) {
const useScoreGuidanceWidget = rubricNode.widgets.find((w) => w && w.name === `useScoreGuidance${i}`);
const scoreWidget = rubricNode.widgets.find((w) => w && w.name === `score${i}`);
const guidanceDescriptionWidget = rubricNode.widgets.find((w) => w && w.name === `guidanceDescription${i}`);
if (useScoreGuidanceWidget && (scoreWidget || guidanceDescriptionWidget)) {
toggleWidgetState(
useScoreGuidanceWidget,
[scoreWidget, guidanceDescriptionWidget].filter(Boolean),
[`score${i}`, `guidanceDescription${i}`]
);
}
}
}
function imageInferenceSettingsStructuredPromptToggleHandler(node) {
if (!node?.widgets) return;
+1 -1
View File
@@ -204,7 +204,7 @@ class txt2img:
"tooltip": "Connect Runware Safety Inputs node to configure safety and content moderation settings.",
}),
"settings": ("RUNWARESETTINGS", {
"tooltip": "Connect Runware Image Inference Settings for temperature, systemPrompt, topP, layers, quality, background, style, search, promptExtend, editRegions (JSON), thinking, thinkingLevel (high/medium/low), sequential, colorPalette (via Color Palette node), etc.",
"tooltip": "Connect Runware Image Inference Settings for temperature, systemPrompt, topP, layers, quality, backgroundMode, backgroundColor, enhancePrompt, scoringPrompt, background, style, search, promptExtend, editRegions (JSON), thinking, thinkingLevel (low/medium/high/xhigh), sequential, colorPalette (via Color Palette node), etc.",
}),
"ultralytics": ("RUNWAREULTRALYTICSINPUTS", {
"tooltip": "Connect Runware Image Inference Ultralytics node to configure Ultralytics parameters (maskBlur, maskPadding, confidence, prompts, steps, CFGScale, strength).",
+13 -1
View File
@@ -49,12 +49,20 @@ class imageInferenceInputs:
"tooltip": f"Specifies {ordinal.capitalize()} Super Resolution Reference Image for the inputs.",
})
optionalInputs["Fonts"] = ("RUNWAREIMAGEINFERENCEFONTS", {
"tooltip": "Connect Runware Image Inference Inputs Fonts for inputs.fonts (up to 2 font URL + text references).",
})
return {
"required": {},
"optional": optionalInputs
}
DESCRIPTION = "Configure custom inputs for Runware Image Inference, including image/mask, reference images (with optional tag, role, type e.g. 'sketch' for illustrative style models, and strength 0-1 for sketch), and super resolution references."
DESCRIPTION = (
"Configure custom inputs for Runware Image Inference, including image/mask, reference images "
"(with optional tag, role, type e.g. 'sketch' for illustrative style models, and strength 0-1 for sketch), "
"super resolution references, and font references (inputs.fonts)."
)
FUNCTION = "createInputs"
RETURN_TYPES = ("RUNWAREIMAGEINFERENCEINPUTS",)
RETURN_NAMES = ("Inference Inputs",)
@@ -80,6 +88,10 @@ class imageInferenceInputs:
if len(super_resolution_refs) > 0:
inputs["superResolutionReferenceImages"] = super_resolution_refs
fonts = kwargs.get("Fonts", None)
if fonts is not None and isinstance(fonts, list) and len(fonts) > 0:
inputs["fonts"] = fonts
return (inputs,)
def _collectReferences(self, kwargs):
+60
View File
@@ -0,0 +1,60 @@
"""
Runware Image Inference Inputs Fonts node.
Builds inputs.fonts for image inference (up to 2 font references with url and text).
"""
from typing import Any, Dict, List, Tuple
class RunwareImageInferenceInputsFonts:
"""Build inputs.fonts[] for image inference requests."""
MAX_FONTS = 2
@classmethod
def INPUT_TYPES(cls):
optional_inputs = {}
for i in range(1, cls.MAX_FONTS + 1):
optional_inputs[f"fontUrl{i}"] = ("STRING", {
"default": "",
"tooltip": (
f"Font file URL for reference {i}. Must be ttf, otf, woff, or woff2. "
"Included when both fontUrl and text are non-empty."
),
})
optional_inputs[f"text{i}"] = ("STRING", {
"multiline": True,
"default": "",
"tooltip": f"Text to render with font reference {i}. Included when both fontUrl and text are non-empty.",
})
return {
"required": {},
"optional": optional_inputs,
}
RETURN_TYPES = ("RUNWAREIMAGEINFERENCEFONTS",)
RETURN_NAMES = ("fonts",)
FUNCTION = "create_fonts"
CATEGORY = "Runware"
DESCRIPTION = (
"Configure inputs.fonts for Runware Image Inference (up to 2 entries). "
"Each entry: { \"url\": \"<font URL>\", \"text\": \"<text to render>\" }. "
"A slot is included only when both fontUrl and text are non-empty. "
"Connect to Runware Image Inference Inputs."
)
def create_fonts(self, **kwargs) -> Tuple[List[Dict[str, Any]]]:
fonts: List[Dict[str, Any]] = []
for i in range(1, self.MAX_FONTS + 1):
font_url = (kwargs.get(f"fontUrl{i}") or "").strip()
text = (kwargs.get(f"text{i}") or "").strip()
if len(font_url) > 0 and len(text) > 0:
fonts.append({
"url": font_url,
"text": text,
})
return (fonts,)
@@ -0,0 +1,171 @@
"""
Runware Image Inference Settings Scoring Rubric
Builds settings.scoringRubric[] for Riverflow 2.5 (1–8 dimensions).
"""
from typing import Any, Dict, List, Tuple
_MAX_SCORE_GUIDANCE = 5
_MAX_RUBRIC_COMBINE = 4
def _build_score_guidance(kwargs: Dict[str, Any]) -> List[Dict[str, Any]]:
guidance: List[Dict[str, Any]] = []
for i in range(1, _MAX_SCORE_GUIDANCE + 1):
if not kwargs.get(f"useScoreGuidance{i}", False):
continue
score = kwargs.get(f"score{i}")
description = (kwargs.get(f"guidanceDescription{i}") or "").strip()
if score is None or not description:
continue
guidance.append({
"score": float(score),
"description": description,
})
return guidance
def _build_rubric_entry(kwargs: Dict[str, Any]) -> Dict[str, Any]:
entry: Dict[str, Any] = {
"key": (kwargs.get("key") or "").strip(),
"label": (kwargs.get("label") or "").strip(),
"description": (kwargs.get("description") or "").strip(),
"weight": float(kwargs.get("weight", 1.0)),
}
if kwargs.get("usePassingScore", False):
entry["passingScore"] = float(kwargs.get("passingScore", 0.0))
guidance = _build_score_guidance(kwargs)
if guidance:
entry["scoreGuidance"] = guidance
return entry
class RunwareImageInferenceSettingsScoringRubric:
"""Build one scoringRubric dimension for settings.scoringRubric."""
@classmethod
def INPUT_TYPES(cls):
optional: Dict[str, tuple] = {
"usePassingScore": ("BOOLEAN", {
"default": False,
"label_on": "Enabled",
"label_off": "Disabled",
"tooltip": "Include passingScore for this scoring dimension.",
}),
"passingScore": ("FLOAT", {
"default": 0.5,
"min": 0.0,
"max": 1.0,
"step": 0.01,
"tooltip": "Optional dimension floor from 0 to 1. Only used when usePassingScore is enabled.",
}),
}
for i in range(1, _MAX_SCORE_GUIDANCE + 1):
optional[f"useScoreGuidance{i}"] = ("BOOLEAN", {
"default": False,
"label_on": "Enabled",
"label_off": "Disabled",
"tooltip": f"Include scoreGuidance anchor {i} (up to {_MAX_SCORE_GUIDANCE} per dimension).",
})
optional[f"score{i}"] = ("FLOAT", {
"default": 0.0,
"min": 0.0,
"max": 1.0,
"step": 0.01,
"tooltip": f"Normalized score anchor (0–1) for scoreGuidance entry {i}.",
})
optional[f"guidanceDescription{i}"] = ("STRING", {
"multiline": True,
"default": "",
"tooltip": f"What score anchor {i} means for the judge.",
})
return {
"required": {
"key": ("STRING", {
"default": "",
"tooltip": "Unique machine-readable dimension key (e.g. composition, lighting).",
}),
"label": ("STRING", {
"default": "",
"tooltip": "Short human-readable dimension label.",
}),
"description": ("STRING", {
"multiline": True,
"default": "",
"tooltip": "Judging criteria for this score dimension.",
}),
"weight": ("FLOAT", {
"default": 1.0,
"min": 0.01,
"max": 100.0,
"step": 0.01,
"tooltip": "Positive scoring weight. Weights are normalized internally.",
}),
},
"optional": optional,
}
RETURN_TYPES = ("RUNWAREIMAGEINFERENCESCORINGRUBRIC",)
RETURN_NAMES = ("scoringRubric",)
FUNCTION = "build_scoring_rubric"
CATEGORY = "Runware"
DESCRIPTION = (
"Define one settings.scoringRubric[] dimension for Riverflow 2.5 (key, label, description, weight, "
"optional passingScore and up to 5 scoreGuidance anchors). Connect to Runware Image Inference Settings, "
"or use Runware Image Inference Settings Scoring Rubric Combine for up to 4 dimensions."
)
def build_scoring_rubric(self, **kwargs) -> Tuple[List[Dict[str, Any]]]:
return ([_build_rubric_entry(kwargs)],)
class RunwareImageInferenceSettingsScoringRubricCombine:
"""Combine up to 4 Scoring Rubric node outputs into settings.scoringRubric."""
@classmethod
def INPUT_TYPES(cls):
optional: Dict[str, tuple] = {}
for i in range(2, _MAX_RUBRIC_COMBINE + 1):
optional[f"Scoring Rubric {i}"] = ("RUNWAREIMAGEINFERENCESCORINGRUBRIC", {
"tooltip": f"Optional scoring rubric dimension {i} (connect Runware Image Inference Settings Scoring Rubric).",
})
return {
"required": {
"Scoring Rubric 1": ("RUNWAREIMAGEINFERENCESCORINGRUBRIC", {
"tooltip": "First scoring rubric dimension (connect Runware Image Inference Settings Scoring Rubric).",
}),
},
"optional": optional,
}
RETURN_TYPES = ("RUNWAREIMAGEINFERENCESCORINGRUBRIC",)
RETURN_NAMES = ("scoringRubric",)
FUNCTION = "combine_scoring_rubric"
CATEGORY = "Runware"
DESCRIPTION = (
"Combine up to 4 Runware Image Inference Settings Scoring Rubric outputs into settings.scoringRubric. "
"Connect scoringRubric to Runware Image Inference Settings."
)
def combine_scoring_rubric(self, **kwargs) -> Tuple[List[Dict[str, Any]]]:
combined: List[Dict[str, Any]] = []
for i in range(1, _MAX_RUBRIC_COMBINE + 1):
chunk = kwargs.get(f"Scoring Rubric {i}")
if chunk is not None and isinstance(chunk, list):
combined.extend(
entry for entry in chunk
if isinstance(entry, dict) and len(entry) > 0
)
return (combined,)
+105 -7
View File
@@ -2,7 +2,8 @@
Runware Image Inference Settings (registered as Runware Settings for workflow compatibility).
Provides settings for image generation including temperature, systemPrompt, topP, layers,
quality, background, style, search, promptExtend, editRegions, thinking (boolean),
thinkingLevel (high/medium/low), sequential, renderingSpeed (TURBO/DEFAULT/QUALITY),
thinkingLevel (low/medium/high/xhigh), backgroundMode (original/transparent/solid), backgroundColor,
enhancePrompt, scoringPrompt, sequential, renderingSpeed (TURBO/DEFAULT/QUALITY),
magicPrompt (AUTO/ON/OFF), autoCrop, dilatePixels, creativity (raw/low/medium/high), colorPalette,
moodboards (from Runware Image Inference Settings Moodboards),
structuredPrompt (from Runware Image Inference Settings Structured Prompt; Ideogram 4.0),
@@ -127,9 +128,12 @@ class RunwareSettings:
"tooltip": "Enable to include thinkingLevel (string) in settings.",
"default": False,
}),
"thinkingLevel": (["high", "medium", "low"], {
"thinkingLevel": (["high", "medium", "low", "xhigh"], {
"default": "high",
"tooltip": "Reasoning level for visual understanding. Only used when 'Use Thinking Level' is enabled.",
"tooltip": (
"Reasoning level for visual understanding. Riverflow 2.5 also supports xhigh (Pro only). "
"Only used when 'Use Thinking Level' is enabled."
),
}),
"useBackground": ("BOOLEAN", {
"tooltip": "Enable to include background style in API request",
@@ -212,6 +216,60 @@ class RunwareSettings:
"promptEnhance": ("RUNWAREIMAGEINFERENCEPROMPTENHANCE", {
"tooltip": "Connect Runware Image Inference Settings Prompt Enhance. Merged into settings.promptEnhance (temperature, topP). Omit from API when not connected or empty.",
}),
"useBackgroundMode": ("BOOLEAN", {
"tooltip": "Enable to include backgroundMode in settings (Riverflow 2.5 output background handling).",
"default": False,
}),
"backgroundMode": (["original", "transparent", "solid"], {
"default": "original",
"tooltip": (
"settings.backgroundMode: original, transparent, or solid. "
"Only used when 'Use Background Mode' is enabled."
),
}),
"useBackgroundColor": ("BOOLEAN", {
"tooltip": "Enable to include backgroundColor in settings (required when backgroundMode is solid).",
"default": False,
}),
"backgroundColor": ("STRING", {
"default": "#FFFFFF",
"tooltip": (
"Hex color (#RRGGBB) composited when backgroundMode is solid. "
"Only used when 'Use Background Color' is enabled."
),
}),
"useEnhancePrompt": ("BOOLEAN", {
"tooltip": "Enable to include enhancePrompt (boolean) in settings.",
"default": False,
}),
"enhancePrompt": ("BOOLEAN", {
"default": False,
"label_on": "true",
"label_off": "false",
"tooltip": (
"Enhance the prompt with use-case context before generation (Riverflow 2.5). "
"Distinct from settings.promptEnhance (nested object). "
"Only used when 'Use Enhance Prompt' is enabled."
),
}),
"useScoringPrompt": ("BOOLEAN", {
"tooltip": "Enable to include scoringPrompt in settings.",
"default": False,
}),
"scoringPrompt": ("STRING", {
"multiline": True,
"default": "",
"tooltip": (
"Optional quality rubric used when RF 2.5 scores candidate outputs. "
"Only used when 'Use Scoring Prompt' is enabled."
),
}),
"scoringRubric": ("RUNWAREIMAGEINFERENCESCORINGRUBRIC", {
"tooltip": (
"Connect Runware Image Inference Settings Scoring Rubric or Scoring Rubric Combine "
"for settings.scoringRubric (up to 4 dimensions via Combine)."
),
}),
}
}
@@ -220,10 +278,12 @@ class RunwareSettings:
FUNCTION = "createSettings"
CATEGORY = "Runware"
DESCRIPTION = (
"Configure general settings for image generation: temperature, system prompt, top-p, layers, quality, background, style, search, "
"promptExtend, editRegions (JSON), thinking (boolean), thinkingLevel (high/medium/low), sequential, "
"Configure general settings for image generation: temperature, system prompt, top-p, layers, quality, "
"backgroundMode (original/transparent/solid), backgroundColor, enhancePrompt, scoringPrompt, background, style, search, "
"promptExtend, editRegions (JSON), thinking (boolean), thinkingLevel (low/medium/high/xhigh), sequential, "
"renderingSpeed (TURBO/DEFAULT/QUALITY), magicPrompt (AUTO/ON/OFF), autoCrop, dilatePixels, "
"creativity (raw/low/medium/high), and optional colorPalette, moodboards, structuredPrompt, and promptEnhance from dedicated settings nodes."
"creativity (raw/low/medium/high), and optional colorPalette, moodboards, structuredPrompt, promptEnhance, "
"and scoringRubric from dedicated settings nodes."
)
def createSettings(self, **kwargs) -> tuple[Dict[str, Any]]:
@@ -244,6 +304,10 @@ class RunwareSettings:
useEditRegions = kwargs.get("useEditRegions", False)
useThinking = kwargs.get("useThinking", False)
useThinkingLevel = kwargs.get("useThinkingLevel", False)
useBackgroundMode = kwargs.get("useBackgroundMode", False)
useBackgroundColor = kwargs.get("useBackgroundColor", False)
useEnhancePrompt = kwargs.get("useEnhancePrompt", False)
useScoringPrompt = kwargs.get("useScoringPrompt", False)
useSequential = kwargs.get("useSequential", False)
useRenderingSpeed = kwargs.get("useRenderingSpeed", False)
useMagicPrompt = kwargs.get("useMagicPrompt", False)
@@ -304,7 +368,37 @@ class RunwareSettings:
settings["thinking"] = bool(kwargs.get("thinking", False))
if useThinkingLevel:
settings["thinkingLevel"] = str(kwargs.get("thinkingLevel", "high"))
thinking_level = str(kwargs.get("thinkingLevel", "high"))
if thinking_level not in ("low", "medium", "high", "xhigh"):
raise ValueError(
"thinkingLevel must be low, medium, high, or xhigh when useThinkingLevel is enabled."
)
settings["thinkingLevel"] = thinking_level
if useBackgroundMode:
background_mode = str(kwargs.get("backgroundMode", "original"))
if background_mode not in ("original", "transparent", "solid"):
raise ValueError(
"backgroundMode must be original, transparent, or solid when useBackgroundMode is enabled."
)
settings["backgroundMode"] = background_mode
if useBackgroundColor:
background_color = (kwargs.get("backgroundColor") or "").strip()
if background_color:
if not background_color.startswith("#") or len(background_color) != 7:
raise ValueError(
"backgroundColor must be a hex color in #RRGGBB format when useBackgroundColor is enabled."
)
settings["backgroundColor"] = background_color
if useEnhancePrompt:
settings["enhancePrompt"] = bool(kwargs.get("enhancePrompt", False))
if useScoringPrompt:
scoring_prompt = (kwargs.get("scoringPrompt") or "").strip()
if scoring_prompt:
settings["scoringPrompt"] = scoring_prompt
if useSequential:
settings["sequential"] = bool(kwargs.get("sequential", False))
@@ -332,6 +426,10 @@ class RunwareSettings:
):
settings["promptEnhance"] = prompt_enhance
scoring_rubric: Optional[List[Dict[str, Any]]] = kwargs.get("scoringRubric")
if scoring_rubric is not None and isinstance(scoring_rubric, list) and len(scoring_rubric) > 0:
settings["scoringRubric"] = scoring_rubric
if useRenderingSpeed:
settings["renderingSpeed"] = str(renderingSpeed)
if useMagicPrompt:
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long