ComfyUI Extension: LF Nodes

Authored by lucafoscili

Created

Updated

42 stars

Custom nodes with a touch of extra UX, including: history for primitives, JSON manipulation, logic switches with visual feedback, LLM chat... and more!

Custom Nodes (0)

    README

    <!-- markdownlint-disable MD033 -->

    LF Nodes for ComfyUI

    <div align="center">

    LF Nodes

    </div> <div align="center">

    LFNodes

    </div> <div align="center">

    GitHub last commit

    </div>

    Overview

    A suite of custom nodes for ComfyUI aimed at enhancing user experience with more interactive and visually engaging widgets.

    Whether you're after quality-of-life improvements or specific functionalities, this collection has something for everyone.

    Most UI elements used by the widgets come from the Ketchup Lite web components library.

    LoRA tester workflow

    What kind of nodes does it offer?

    That's a tough one—the nodes span quite a few categories. Here's a quick breakdown:

    • Analytics nodes: Visualize and track data, like checkpoint/LoRA usage or image histograms.
    • Configuration nodes: Manage CivitAI metadata, and control the suite via the Control Panel.
    • Image manipulation nodes: Tools to manipulate images, such as filter and resize nodes.
    • IO Operations nodes: Load and save files to/from the file system.
    • JSON nodes: Tools to manipulate and display JSON data.
    • LLM nodes: Interface with locally running LLMs, like the Messenger node, which also manages characters.
    • Logic nodes: Control flow using simple switches.
    • Primitive nodes: Work with primitive data types, offering features like history.
    • Seed generation nodes: Generate seeds for complex workflows.
    • Selector nodes: Resource selection widgets with metadata display for models.

    CICD

    Table of Contents

    Analytics nodes (analytics.py)

    ImageHistogram

    Displays a widget that plots the RGB channels of a photo in tensor format on a line chart. ImageHistogram

    KeywordCounter

    Counts the number of each keyword in a prompt and displays a bar chart showing their distribution, a chip-shaped widget will also allow to copy one or more keywords in the clipboard. KeywordCounter

    UpdateUsageStatistics

    Keep tracks of the resources used by saving datasets in the input folder of ComfyUI. The datasets will be plotted on area/scatter charts inside the twin node UsageStatistics. UpdateUsageStatistics

    UsageStatistics

    Displays datasets tracking the usage of resources saved with the UpdateUsageStatistics node. UsageStatistics

    Configuration nodes (configuration.py)

    CivitAIMetadataSetup

    Allows to setup and generate CivitAI-compatible metadata information usable in the node SaveImageForCivitAI. CivitAIMetadataSetup

    ControlPanel

    Utilities to debug nodes and to change the theme of Ketchup Lite webcomponents. ControlPanel

    LoadLoraTags

    LoRA models are loaded in tag format, with a status widget displayed at the bottom indicating the loading progress. LoadLoraTags

    Lora2Prompt

    Converts a prompt and LoRAs to a formatted string. Lora2Prompt

    LoraTag2Prompt

    Processes a LoRA tag to extract keywords and count them. This node is useful for preparing prompts based on LoRA file names. LoraTag2Prompt

    Notify

    Triggers a browser notification when executed. Optionally, when clicked, it can queue a new prompt or focus the workflow's tab. Notify

    Image manipulation nodes (image.py)

    BlurImages

    Applies the gaussian blur filter to a list of images and edits the filename of each image by adding the '_Blur' suffix. Blurimages

    ClarityEffect

    Applies a filter mimicking the clarity effect of Lightroom and Camera Raw. ClarityEffect

    MultipleImageResizeForWeb

    The node takes a list of images as input and generates eight additional images, each resized to common web resolutions (256px, 320px, 512px, 640px, 1024px, 1280px, 2048px, 2560px) along the longest edge. MultipleImageResizeForWeb

    ResizeImageByEdge

    Resizes one or more images in tensor format's longest or shortest edge to the specified size. ResizeImageByEdge

    ResizeImageToDimension

    Resizes an image to the longest dimension and then crops it/pads it to fit the canvas. ResizeImageToDimension

    ResizeImageToSquare

    Resizes one or more images in tensor format to fit a square (by cropping when the image is rectangular). ResizeImageToSquare

    IO Operations nodes (io.py)

    LoadFileOnce

    Loads a file from a directory and then saves the name to the history. Files present in the history are skipped. LoadFileOnce

    LoadImages

    Node used to load multiple images from the disk given a directory. Optionally, it can fetch images from subdirectories. LoadImages

    LoadMetadata

    Enables uploading files to the input directory of ComfyUI, then on the workflow's execution the metadata will be extracted from the files included in the uploading process. LoadMetadata

    SaveImageForCivitAI

    Saves images with CivitAI-compatible metadata generated by the node CivitAIMetadataSetup. SaveImageForCivitAI

    SaveJSON

    Saves a JSON file at the specified path. SaveJSON

    JSON nodes (json.py)

    DisplayJSON

    Displays JSON data with a handy button to copy the content. DisplayJSON

    GetRandomKeyFromJSON

    Extracts a random key from a given JSON object. This can be used to introduce variability or select random elements from JSON data. GetRandomKeyFromJSON

    GetValueFromJSON

    Extracts a specific value from a JSON object based on a provided key. This node supports extracting various types of values including JSON objects, strings, numbers, integers, floats, and booleans. GetValueFromJSON

    ImageListFromJSON

    Creates a list of images with the number set by the number of keys inside the input JSON. It also outputs the list of keys themselves. ImageListFromJSON

    KeywordToggleFromJSON

    Allows the selection of keywords received from a Ketchup Lite compatible JSON dataset. Values are refreshed every time the input changes. KeywordToggleFromJSON

    LoadLocalJSON

    Loads JSON data from a local file specified by a URL. This node is useful for importing static JSON configurations or datasets directly into ComfyUI workflows. LoadLocalJSON

    SetValueInJSON

    Sets a new key or updates an existing one with a new value. SetValueInJSON

    ShuffleJSONKeys

    Sorts the keys at root level of a JSON, returning the sorted object. Optionally it can also sort the input JSON in place without making a copy of it. ShuffleJSONKeys

    SortJSONKeys

    Sorts the keys at root level of a JSON, returning the sorted object. Optionally it can also sort the input JSON in place without making a copy of it. SortJSONKeys

    StringToJSON

    Converts a string to a JSON object. StringToJSON

    WriteJSON

    A simple text area that lets the user input a JSON file which will be validated when the workflow is queued. Each 2500ms the text is formatted, if there is an error it will be displayed in the title of the textarea (visible on mouseover).

    WriteJSON

    Large Language Model nodes (llm.py)

    CharacterImpersonator

    Utilizes a large language model to generate text responses as if coming from a character described by a provided biography. This node can be used for creative writing, role-playing scenarios, or generating dynamic content based on character traits. CharacterImpersonator

    ImageClassifier

    Utilizes a large language model to generate descriptions of images portraying characters. ImageClassifier

    LLMChat

    Real-time chat with an LLM model served through Koboldcpp (http://localhost:5001). It's possible to select the last messages as an output, sending them to the next node. LLMChat

    LLMMessenger

    A user interface capable of loading characters through a Ketchup Lite-compatible JSON and then connects to your local Koboldcpp instance (http://localhost:5001). The location, outfit and timeframe options are included in the system prompt to give more context to the LLM. Together with the biography, they define the identity of the LLM. LLMMessenger

    Logic nodes (logic.py)

    MathOperation

    Performs mathematical operations involving up to four variables. MathOperation

    ResolutionSwitcher

    Selects a random resolution between portrait and landscape orientations. The chances for landscape to occur can be set with a percentage. ResolutionSwitcher

    SwitchFloat

    Returns one of two float values depending on a boolean condition. SwitchFloat

    SwitchImage

    Returns one of two images in tensor format based on a boolean condition. SwitchImage

    SwitchInteger

    Returns one of two integer values depending on a boolean condition. SwitchInteger

    SwitchJSON

    Returns one of two JSON objects depending on a boolean condition. SwitchJSON

    SwitchString

    Returns one of two string values based on a boolean condition. SwitchString

    Primitive nodes (primitives.py)

    Boolean

    Used to select a boolean. It keeps record of old values, displaying a clickable list below the widget. Boolean

    DisplayBoolean

    Displays the value of a boolean in a widget. DisplayBoolean

    DisplayFloat

    Displays the value of a float in a widget. DisplayFloat

    DisplayInteger

    Displays the value of a integer in a widget. DisplayInteger

    DisplayPrimitiveAsJSON

    Displays different primitive values as a JSON output or directly in-widget through a tree-like view. DisplayPrimitiveAsJSON

    DisplayString

    Displays the value of a string in a widget. DisplayString

    Extractor

    Extracts text enclosed by a starting and ending delimiter. Extractor

    Float

    Used to select a float. It keeps record of old values, displaying a clickable list below the widget. Float

    Integer

    Used to select an integer. It keeps record of old values, displaying a clickable list below the widget. Integer

    RandomBoolean

    Outputs False or True depending on the chances specified by the percentage widget. 0 always false, 100 always true. RandomBoolean

    Something2Number

    Converts multiple inputs to integers and floats, handling nested structures and mixed types. If multiple numbers are sent to the node, they are summed. Something2Number

    Something2String

    Converts multiple inputs to strings, handling nested structures and mixed types. Something2String

    String

    Used to select a string. It keeps record of old prompts, displaying a clickable list below the textarea. String

    WallOfText

    Concatenates up to 10 strings, with the optional toggle to shuffle the order of concatenation. WallOfText

    Seed generation nodes (seeds.py)

    SequentialSeedsGenerator

    Generates a series of unique seeds based on a global seed value. This node is useful for creating reproducible random sequences in workflows. SequentialSeedsGenerator

    UrandomSeedGenerator

    Generates up to 20 different seeds through the use of the Python urandom function which leverages CPU generated entropy for increased randomness. UrandomSeedGenerator

    Selector nodes (selectors.py)

    CheckpointSelector

    Used to select a checkpoint. It's possible to fetch additional data from CivitAI or by loading the related cover inside the checkpoints folder. CheckpointSelector

    EmbeddingSelector

    Used to select an embedding. It's possible to fetch additional data from CivitAI or by loading the related cover inside the embeddings folder. EmbeddingSelector

    LoraSelector

    Used to select a LoRA. It's possible to fetch additional data from CivitAI or by loading the related cover inside the loras folder. LoraSelector

    LoraAndEmbeddingSelector

    Using a LoRA name as pilot, it also selects its related embedding (it must have the same name). Useful for models trained with pivotal training. LoraAndEmbeddingSelector

    SamplerSelector

    Used to select a sampler, the history widget allows for a quick swap between the most used samplers. SamplerSelector

    SchedulerSelector

    Used to select a scheduler, the history widget allows for a quick swap between the most used schedulers. SchedulerSelector

    UpscaleModelSelector

    Used to select an upscale model, the history widget allows for a quick swap between the most used upscale models. UpscaleModelSelector

    VAESelector

    Used to select a VAE, the history widget allows for a quick swap between the most used VAEs. VAESelector

    Installation

    Using ComfyUI Manager

    • Open ComfyUI Manager.
    • Search LF Nodes.
    • Install the node suite and restart ComfyUI.

    Manual

    • Go to the ComfyUI/custom_nodes folder.
    • Open a terminal.
    • Copy and paste this command git clone https://github.com/lucafoscili/comfyui-lf.git.

    Notes

    The LLM nodes are designed to work with Koboldcpp. The model used in the workflows samples is UCLA-AGI/Llama-3-Instruct-8B-SPPO-Iter3 with ChaoticNeutrals/LLaVA-Llama-3-8B-mmproj-Updated.

    Contributing

    Contributions to this repository are welcome, feel free to submit pull requests or open issues for discussion! To setup the environment clone this repository, then from the root open a terminal and run the command

    pip install -r requirements.txt

    This will install all the required dependencies for the Python back-end.

    npm run setup

    This command will install all the frontend dependencies. Note that the repository includes the compiled files directly to allow Comfy to load them, dependencies are only needed for actual development.

    npm run build

    This command will compile all the frontend sources and generate/refresh the actual web directory.

    License

    MIT License