36c0a433956ee512e36cfbf14523634494c7ffa8
The tokenizer now emits comfy's standard List[List[(token, weight)]] format with one extension: a token entry may also be a lazy Action instance. PromptLangSDClipModel shrinks to a single process_tokens override that resolves Actions to tensors and otherwise defers to the stock SDClipModel.process_tokens for embedding lookup, mask construction, TI splice, and num_tokens accounting. This deletes _build_embeddings, _build_attention_mask, and the custom encode_token_weights override (which were re-implementing what comfy already does), and means stock encode_token_weights / forward handle everything else. posScale/postPos still work via the (modified - default) pre-bake in _apply_pos_modifiers; that's unchanged. Also: - SDXL parses the Lark tree once and transforms per-CLIP, instead of re-parsing the same text for both clip_l and clip_g - Drop Action.get_all_segments (was only needed by the old set_up_textual_embeddings path) - Inline get_embedding into embedding_tensor (no external callers) - SpecialClipLoader: load full cond_stage_model state_dict instead of per-transformer copies - Add pyproject.toml with [tool.comfy] metadata; drop packaging dep (was only for HF version sniffing in fun_clip_stuff.py) - Add tokenizer tests covering native-format emission and slot accounting (logical post-splice length == max_length)
KepPromptLang
A small DSL for ComfyUI that lets you do math on CLIP token embeddings before they're fed into the text transformer.
sum(diff(king|man)|woman)
norm(sum(cat | dog | horse | parrot))
A slerp(cat|dog|0.5) is happy
Install
Clone into ComfyUI/custom_nodes/:
cd ComfyUI/custom_nodes
git clone <repo-url> KepPromptLang
pip install -r KepPromptLang/requirements.txt
Usage
- Add a Special CLIP Loader node and feed it the CLIP output from your Load Checkpoint.
- Pass the wrapped CLIP into a standard CLIP Text Encode node.
- Use the DSL syntax in your prompt.
See examples/WIP_Example_workflow.json for a working workflow.
Syntax
| Element | Syntax | Example |
|---|---|---|
| Plain word | alphanumeric (with ,_.-) |
cat, dog_face |
| Quoted string | single or double quotes | "hello world", 'it\'s sunny' |
| Embedding (textual inversion) | embedding:NAME |
embedding:face_vector |
| Function | name(arg | arg | ...) |
sum(king | woman) |
Arguments inside a function are separated by |. Each arg can itself be plain text, an embedding, a quoted string, or another function call.
Quick examples
- Average two prompts:
avg(The cat is | The dog is | 0.5) - Normalize a sum:
norm(sum(cat | dog | horse)) - King − Man + Woman:
sum(diff(king|man)|woman)(orsum(king | neg(man) | woman)) - Negate an embedding:
neg(embedding:body_vector)
Functions
| Display Name | Action Name | Description | Usage Examples |
|---|---|---|---|
| Average | avg | Performs a weighted average between two segments or actions. The recommended weight is 0 - 1. |
|
| Difference | diff | Subtracts the segments in the order they are given. The first segment is subtracted from the second, then the third from the result, and so on. |
|
| Multiply | mult | Multiplies the provided segments or actions by the multiplier. |
|
| Negate | neg | Negates the provided segments or actions. |
|
| Normalize | norm | Normalizes the provided segments or actions. |
|
| Positional Embedding Scale | posScale | Scales (multiplies) the positional embeddings of the provided segments or actions by the multiplier. |
|
| Ignore Positional Embeddings | postPos | Prevents positional embeddings from being applied to the provided segments or actions. |
|
| Random Embedding | rand | Returns a random embedding of the specified token length, with the values optionally bounded by the second and third arguments. |
|
| Scale Dimensions | scaleDims | Scales the specified dimensions of the input embeddings by the specified amount |
|
| Set Dimensions | setDims | Sets the specified dimensions of the input embeddings to the specified value |
|
| Slerp | slerp | Performs a slerp (interpolation) between two segments or actions, with the given weight. The recommended weight is 0 - 1. |
|
| Sum | sum | Adds the embeddings of the provided segments or actions. |
|
Regenerate the table with python tools/build_docs.py.
Development
Tests are pytest-based and don't require ComfyUI:
pip install -e ".[dev]"
python -m pytest
Compatibility
- SD1.x (CLIP-L) and SDXL (CLIP-L + CLIP-G).
- SD2 is not supported.
- Two pooler-output actions (
_exp-pooler,_exp-pooledAvg) from earlier versions were experimental and have been removed; they relied on direct HuggingFace transformer access that is no longer how ComfyUI structures its CLIP encoders.
Languages
Python
100%
