Files
ausboss-ComfyUI-AusBoss/js/shared/media_list.mjs
ausboss 74de1107c6 Crop and Pad loaders: list a picture the MaskEditor saved
ComfyUI calls a media input missing when its value is not in the
widget's list. The MaskEditor writes the file it saved into the image
widget, and no list has that file until the lists are refreshed, so
the node was flagged the next time it came out of bypass. Both nodes
now add a picture to their list once it has loaded. Load Image + Pad
also follows a picture written that way, as the crop node does.
2026-10-12 21:48:45 -05:00

51 lines
2.3 KiB
JavaScript

// Pure decisions behind the media picker (media_picker.mjs): which query
// /view needs for a combo value, which values a filter keeps, how a value
// splits into folder and name, and where the highlight moves. No DOM, so
// node:test covers them.
import { parseImageReference } from "./pad_canvas.mjs";
// "pasted/image (2).png" or "clip.mp4 [output]" -> "filename=...&subfolder=...&type=...".
export function mediaViewQuery(value) {
const reference = parseImageReference(value);
return reference ? new URLSearchParams(reference).toString() : "";
}
// Every space-separated term must appear in the value, ignoring case, so
// "night png" finds "pasted/ausboss_night_bridge.png".
export function filterMedia(values, query) {
const list = Array.isArray(values) ? values.map(String) : [];
const terms = String(query ?? "").toLowerCase().split(/\s+/).filter(Boolean);
if (!terms.length) return list;
return list.filter((value) => {
const text = value.toLowerCase();
return terms.every((term) => text.includes(term));
});
}
// The value to add to a media widget's list, or "" when the list has it. A
// value counts as listed with or without its " [input]" tail, which is how
// the frontend looks one up before it calls a picture missing.
export function unlistedMedia(values, value) {
const text = String(value ?? "");
if (!text || !Array.isArray(values)) return "";
const bare = text.replace(/\s+\[(input|output)\]$/, "");
return values.includes(text) || values.includes(bare) ? "" : text;
}
// The dim folder prefix and the name the list shows for one value.
export function mediaLabel(value) {
const reference = parseImageReference(value);
if (!reference) return { folder: "", name: String(value ?? "") };
const where = reference.type === "input" ? "" : ` [${reference.type}]`;
return { folder: reference.subfolder ? `${reference.subfolder}/` : "", name: `${reference.filename}${where}` };
}
// Arrow-key movement that stops at the ends; -1 when there is nothing to
// highlight. From no highlight, down starts at the top and up at the bottom.
export function moveHighlight(index, delta, length) {
if (!(length > 0)) return -1;
if (index < 0 || index >= length) return delta > 0 ? 0 : length - 1;
return Math.max(0, Math.min(length - 1, index + delta));
}