Nodes/ComfyUI-bleh/BlehContrastiveOrthoCFG
ComfyUI Node

BlehContrastiveOrthoCFG

Tune positive and negative guidance separately

By blepping·Created 3 years ago·Updated 4 days ago· 143
BlehContrastiveOrthoCFG
  • model
  • MODEL
start_sigma99999.00
end_sigma0.00
positive_scale0.20
negative_scale1.00
patch_modepre_cfg
start_dim1
end_dim1
use_noisefalse
force_uncond_generationfalse

Standard CFG scale is one dial that amplifies the difference between your positive and negative predictions equally. This node splits that into two dials - how much of what's unique to the positive prompt gets added, and how much of what's unique to the negative prompt gets subtracted - computed as orthogonal (non-overlapping) features rather than just the raw difference. The node's own description is refreshingly honest about the baseline case: at the default scales of 1.0 on both sides, "this is just a slower version of CFG." The point of the node only shows up once you pull positive_scale and negative_scale apart.

Three patch modes, and the tooltips here are unusually thorough for this pack, worth reading closely rather than skimming. pre_cfg applies the positive change to the conditioned prediction and the negative change to the unconditioned one, then lets ComfyUI's own CFG math do the combining - which has a real consequence: at CFG 1, only the positive scale does anything, because the unconditioned pass isn't part of the computation at CFG 1 in the first place. post_cfg subtracts the negative-unique features and adds the positive-unique ones directly onto the already-computed CFG result, relative to the original cond/uncond generations. post_cfg_base_denoised is flagged by the author himself as experimental and "generally not recommended" - it can behave strangely if you're stacking other CFG-type effects afterward, like CFG++.

Inputs: model is the only required one. Everything else is optional with defaults tuned toward the safest starting point. positive_scale (0.2 default) is deliberately small - in pre_cfg mode it effectively gets multiplied by whatever your actual CFG value is. negative_scale (1 default) is subtracted, similarly scaled by CFG in pre_cfg mode. patch_mode defaults to pre_cfg, which the tooltip recommends explicitly: "for the most predictable effects, use positive scales and pre_cfg mode with use_noise disabled." start_dim/end_dim (1/1 default) pick which tensor dimensions count as "features" when figuring out what's orthogonal - the default targets the channel dimension, which is right for image models; video models insert an extra frames dimension after channels, so that's worth adjusting if you're patching a video model. use_noise (false default) applies the effect to the noise prediction instead of the clean image - the author calls this the harder case to reason about, since separating orthogonal features is murkier in noise space. force_uncond_generation (false default) overrides the usual CFG-1 shortcut that skips computing the unconditioned pass entirely, useful if you're running at CFG 1 but still want this node's negative-side effect to actually compute.

Output is a patched MODEL.

This is another node with no README section and nothing findable in wider community discussion - everything above comes from the node's own tooltips, which happen to be some of the most detailed in the whole pack, likely because the mechanism genuinely needs that much explaining to use correctly. Start with the recommended combination - pre_cfg, use_noise off, small positive_scale - before pulling any of the other knobs.

Install is standard: ComfyUI Manager, or a manual clone of blepping/ComfyUI-bleh into custom_nodes plus a restart. No extra dependencies.

Categoryadvanced/guidance

Inputs (10)

NameTypeDefaultDescription
modelMODEL
start_sigmaoptFLOAT99999.000–99999
end_sigmaoptFLOAT0.000–99999
positive_scaleoptFLOAT0.20-9999–9999Scale for features unique to the positive prompt (cond). In pre-CFG mode, this gets multiplied by the CFG scale. For example, at CFG 5, the default of 0.2 would result in roughly the same strength as CFG 1.
negative_scaleoptFLOAT1.00-9999–9999Scale for features unique to the negative prompt (uncond). This gets subtracted. In pre-CFG mode the scale is effectively multiplied by CFG.
patch_modeoptCOMBOpre_cfgpre_cfg: This mode applies the positive change to cond and the negative change to uncond and lets the CFG function take care of subtracting the negative part and adding the positive part. Since CFG 1 is normally just cond, at CFG one you will get the positive change applied as expected but the negative side will have no effect. Or in other words, result is basically common + unique_positive * CFG - unique_negative * (CFG - 1). post_cfg: The unique negative features are subtracted at exactly the scale you specify and the unique positive features are added in the same way. However, these are relative to the original cond/uncond generations but are applied to the result of CFG. post_cfg_base_denoised: This is like post_cfg mode except the positive side is what's unique to denoised (the result of CFG) and both parts are added to a common base. The results can be weird if you have other CFG type effects (I.E. CFG++) running afterward because what's unique to denoised will also include the negative side of uncond. Experimental mode, generally not recommended.
start_dimoptINT1-999–999Start dimension (zero-based) for determining orthogonal features. Image models typically use dimensions BATCH, CHANNELS, HEIGHT, WIDTH. Video models insert a FRAMES dimension after CHANNELS. The default is to normalize over channels.
end_dimoptINT1-999–999End dimension (zero-based) for determining orthogonal features. Image models typically use dimensions BATCH, CHANNELS, HEIGHT, WIDTH. Video models insert a FRAMES dimension after CHANNELS. The default is to normalize over channels.
use_noiseoptBOOLEANfalseApply CFG to the noise prediction instead of the clean image. CFG normally uses the clean image. Experimental option and generally it's harder to separate out what's orthogonal from noise compared to a clean latent.
force_uncond_generationoptBOOLEANfalseDisables the normal optimization that skip generating uncond (negative prompt) when CFG is 1.

Outputs (1)

NameTypeDescription
MODELMODEL