Files
blepping-comfyui_overly_com…/docs/expression.md
T
blepping d8574bae2d Mega update (#8)
* Weird experiments with sampler blending

* Mega sync

* Use ComfyUI union types for wildcard inputs when available

* Add weoon wavelet sampler

* Fix noise sampler caching not considering immiscible settings
Allow specifying alt custom noise/immiscible settings for samplers that internally add noise
AFS support at the merge sampler level
Allow the Weoon internal step to use ETA
Add t_copysign expression function

* Start updating documentation

* Add ImmiscibleReference node, other changes

* Respect factor in ImmiscibleReference noise

* Fixing normalizing in ImmiscibleReference noise

* Handle case where there are no RGB factors (i.e. audio models)

* Fix rectified flow type detection for non-Flux models

* Add more tensor ops, add OCS ApplyExpressionImage/Latent nodes

* Rename ApplyExpression nodes to ApplyFilter, expression QoL improvements

* Fix apply filter nodes definitions

* Make t_noise handler work for image-latents.

* Add t_new_like expression function

* Make it possible to comment out lines with hash in expressions

* Add gradient estimation, pingpong and res_multistep samplers.
Add pingpong group merge method.
Remove model call caching stuff.
Allow defining pre_cfg and post_cfg filters.
Handle filters changing the latent shape better.
Allow disabling detecting out of order sigmas as restart sampling.

* Sync current updates (which I am too lazy to describe individually)

* Add ExpressionFilteredNoise node
Improvements to immiscible noise handling/expanded features
2025-08-09 07:28:10 -06:00

13 KiB

OCS Expressions

See Filters for places where expressions apply.

Expressions

OCS implements a simple expression language.

Supported math operators: +, -, *, /, // (integer division), ** (power)

Supported logic operators: ||, &&, ==, !=, >, <, >=, <=

Operator precedence should generally work the way you'd expect.

You may surround a function name with backticks to turn it into a binary operator (only for functions that take two arguments).

Functions are called via name(param1, param2). Keyword arguments may be passed using the :> operator. Example: name(param1, key :> 123, key2 :> otherfunction(10)).

Symbols (simple string type) are defined using 'symbol_name - note the solitary single quote. They may not contain spaces.

; can be used to sequence operations. I.E. exp1 ; exp2 evaluates exp1, then exp2 and then result of the expression is whatever exp2 returned.

:= is used to assign to a temporary variable (see set_var below).

The expression language supports a C/JavaScript style ternary operator: condition ? true_branch : false_branch is the equivalent of if(condition, true_branch, false_branch).

Like Python, a parenthesized expression with a trailing comma can be used to create an empty tuple. Example: (1,)

Filter Variables

Indexes like step are zero-based: 0 will be the first step.

Basic Variables

  • default: Context specific default value. i.e. if used in an input expression this would be x, if used for output this would be the current result.
  • step: Current step.
  • substep: Current substep.
  • dt: sigma_next - sigma
  • sigma_idx: Index of the current sigma. Note that when using restarts this will be based on the restart sigma chunks, not full sigma list.
  • sigma: The current sigma.
  • sigma_next: The next sigma.
  • sigma_down: The down sigma in ancestral sampling.
  • sigma_up: The up sigma in ancestral sampling.
  • sigma_prev: The previous sigma (may be None).
  • hist_len: Current available history length. "Now" counts as one.
  • sigma_min: The minimum sigma (based on the full list).
  • sigma_max: The maximum sigma (based on the full list).
  • step_pct: Percentage for the current step (based on total steps).
  • total_steps: Total steps to be sampled.

Extended Variables

  • denoised: From the current step or substep. May not be available in model input or group pre_filter.
  • cond: From the current step or substep. May not be available in model input or group pre_filter.
  • uncond: From the current step or substep. May not be available in model input or group pre_filter.
  • denoised_prev: Only available when model history exists.
  • cond_prev: Only available when model history exists.
  • cond_prev: Only available when model history exists.

Model Filter Variables

  • model_call: Only applicable to model filters, will be the model call index. I.E. if the sampler calls the model three times, the filter would be called with model call indexes 0, 1 and 2.

Available in model filters, with the exception of the input filter.

  • denoised_curr
  • cond_curr
  • uncond_curr

Basic Expression Functions

Name Input Output
⬤ all B* B
Evaluates to true if all its arguments evaluate to true.
Example: all(x > 1, y < 1)
⬤ any B* B
Evaluates to true if any of its arguments evaluate to true.
Example: any(x > 1, y < 1)
⬤ between value:N, from:N, to:N B
Boolean range checking.
Example: between(value, low, high)
⬤ comment * null
Ignores any arguments passed to it (they won't be evaluated at all but must parse as a valid expression) and returns None
⬤ dict ** dict
Constructs a dictionary from its keyword arguments. Note: You may not pass positional arguments.
Example: dict(key1 :> value1, keyN :> valueN)
⬤ get name:SY, fallback:* *
Returns a variable if set, otherwise the fallback.
Example: get('somevar, 123)
⬤ if condition:B, then:*, else:* *
Conditional expressions.
Example: if(condition, true_expression, false_expression)
⬤ index index:IDX, value:S | T *
Index function.
⬤ is_set name:SY B
Tests whether a variable is set.
⬤ max values:SN N
Maximum operation. Note: Takes one sequence argument.
Example: min((1, 2, 3))
⬤ min values: SN N
Minimum operation. Note: Takes one sequence argument.
Example: max((1, 2, 3))
⬤ mod lhs:N, rhs:N N
Modulus operation:
Example: mod(5, 2)
⬤ neg N N
Negation.
Example: neg(2)
⬤ not B B
Boolean negation
⬤ s_ start:I(null), end:I(null), step:I(null) slice
Creates a slice object from the start, end, step values. See Numpy s_
⬤ set_var SY, * *
Sets a temporary variable to the specified value and returns the value. Alias for the := assignment operator.
Example: test1 := 2; set_var('test2, 10); test1 * test2
⬤ unsafe_call callable, ** *
Allows calling an arbitrary callable.
Example: unsafe_call(some_callable, arg1, arg2, kwarg1 :> 123)

Legend: B=boolean, N=numeric, NS=scalar numeric, I=integer, F=float, T=tensor, S=sequence, SN=numeric sequence, SY=symbol, *=any -- parenthized values indicate argument defaults. * following the type indicates variable length arguments. For functions that take keyword arguments, the type will be written like "name: TYPE(default_value)".

Tensor Expression Functions

Tensor dimensions hint: Most tensors you'll be dealing with are laid out as batch, channels, height, width. Negative indexes start from the end, so dimension -1 would mean width just the same as 3.

Name Input Output
⬤ t_bleh_enhance tensor:T, mode:SY, scale:N(1.0) T
Available if you have the ComfyUI-bleh node pack installed. See Filtering.
Example: bleh_enhance(some_tensor, 'bandpass, 0.5)
⬤ t_blend tensor1:T, tensor2:T, scale:N(0.5), mode:SY(lerp) T
Tensor blend operation.
Example: t_blend(t1, t2, 0.75, 'lerp)
⬤ t_contrast_adaptive_sharpening tensor:T, scale:N(0.5) T
Contrast adaptive sharpening. Note: Not recommended to call on noisy tensors (so denoised but probably not x).
Example: t_contrast_adaptive_sharpening(some_tensor, 0.1)
⬤ t_flip tensor:T, dim:NS, mirror:B(false) T
Flips a tensor on the specified dimension. If the third argument is true, it will be mirrored around the center in that dimension.
Example: t_flip(some_tensor, -1, true)
⬤ t_mean tensor:T, dim:SN(-3, -2, -1) T
Tensor mean, second argument is dimensions.
Example: t_mean(some_tensor, (-2, -1))
⬤ t_noise tensor:T, type:SY(gaussian) T
Generates un-normalized noise (use t_norm if you want to normalize it). If you have ComfyUI-sonar you can use any noise type that supports, otherwise only gaussian. The generated noise will have the same shape as the supplied tensor (hopefully, may not be true for every exotic noise type but at least should be broadcastable to the tensor).
Example: t_noise(some_tensor, 'pyramid)
⬤ t_norm tensor:T, factor:N(1.0), dim:SN(-3, -2, -1) T
Tensor normalization (subtracts mean, divides by std).
Example: t_norm(some_tensor, 1.0, (-2, -1))
⬤ t_sonar_power_filter tensor:T, filter:dict T
Available if you have ComfyUI-sonar installed. See Filtering. Constructs a power filter from a dictionary argument. Note: May be slow as the filter is reconstructed on every evaluation.
Example: t_sonar_power_filter(some_tensor, dict(alpha :> 0.1, min_freq :> 0.2, max_freq :> 0.6))
⬤ t_roll tensor:T, amount:NS(0.5), dim:SN((-2,)) T
Rolls a tensor along the specified dimensions. If amount is >= -1.0 and < 1.0 this will be interpreted as a percentage.
Example: t_roll(some_tensor, 10, (-2,))
⬤ t_scale tensor:T, scale:SN | NS, mode:SY(bicubic), absolute_scale:B(false) T
Scales a tensor. If scale is a tuple, it will be interpreted as (height, width). When absolute_scale is not set, the scales will be interpreted as percentages otherwise absolute values will be used.
Example: t_scale(some_tensor, (0.75, 0.5), 'bilinear)
⬤ t_scale_nnlatentupscale tensor:T, mode:SY(sd1), scale:SN(2.0) T
Available if you have ComfyUi_NNLatentUpscale installed. mode must be one of sd1 or sdxl. scale should be between 1.0 and 2.0 (may or may not work out of that range).
Example: t_scale_nnlatentupscale(some_tensor, 'sdxl, 1.5)
⬤ t_shape tensor:T SN
Returns a tensor's shape as a tuple.
Example: shp := t_shape(some_tensor); width := shp[-1]; height := shp[-2]
⬤ t_std tensor:T, dim:SN(-3, -2, -1) T
Tensor std, second argument is dimensions.
Example: t_std(some_tensor, (-2, -1))
⬤ t_taesd_decode tensor:T, mode:SY(sd15) T
Decodes a latent tensor used TAESD. Mode must be one of sd15, sdxl. Only works if the appropriate models are in vae_approx
Example: t_taesd_decode(some_tensor, 'sd15)
⬤ unsafe_tensor_method T, SY, ** *
Unsafe tensor method call. See note below.
Example: unsafe_tensor_method(some_tensor, 'mul, 10)
⬤ unsafe_torch path:SY *
Unsafe Torch module attribute access. See note below.
Example: unsafe_torch('nn.functional.interpolate)

Note on unsafe_tensor_method and unsafe_torch: These functions are disabled by default. If the environment variable COMFYUI_OCS_ALLOW_UNSAFE_EXPRESSIONS is set to anything then you can use unsafe_tensor_method with a whitelisted set of methods (best effort to avoid anything actually unsafe). If the environment variable COMFYUI_OCS_ALLOW_ALL_UNSAFE is set to anything then unsafe_torch is enabled and unsafe_tensor_method will allow calling any method. WARNING: Allowing all unsafe with workflows you don't trust is not recommended and a malicious workflow will likely have access to anything ComfyUI can access. It is effectively the same as letting the workflow run an arbitrary script on your system.

Documentation TBD (check the source if you want to use them now): t_copysign, t_gaussianblur2d, t_rgb_latent, t_snf_guidance

Image Expression Functions

IMG used here to donate the type for functions that take an image. This may actually be an image batch rather than a single image.

Name Input Output
⬤ img_pil_resize image:IMG, size:SN | NS, resample_mode:SY(bicubic), absolute_scale:B(false) IMG
Scales an image batch using Pillow's Image.resize function (follow link for information about resample modes, etc). If scale is a tuple, it will be interpreted as (height, width). When absolute_scale is not set, the scales will be interpreted as percentages otherwise absolute values will be used.
Example: img_pil_resize(image_batch, (0.75, 0.5), 'lanczos)
⬤ img_shape image:IMG SN
Returns an image's shape as a tuple. Will fail if all the images in the batch aren't the same size.
Example: shp := img_shape(image_batch); width := shp[-1]; height := shp[-2]
⬤ img_taesd_encode image:IMG, reference_latent: T, mode:SY(sd15) T
Encodes an image batch into a latent tensor. The reference latent is only used to determine what device and type the output should be. Mode must be one of sd15, sdxl. Only works if the appropriate models are in vae_approx.
Example: img_taesd_encode(image_batch, some_tensor, 'sd15)