Nodes/ComfyUI CV/cv2.ximgproc.rollingGuidanceFilter
ComfyUI Node

cv2.ximgproc.rollingGuidanceFilter

Smoothing that knows what size of detail it's removing

By bmad4ever·Created 3 months ago·Updated 14 days ago· 1
cv2.ximgproc.rollingGuidanceFilter
  • src
  • result
◄d-1►
◄sigmaColor25.0000►
◄sigmaSpace3.0000►
◄numOfIter4►
◄borderTypeBORDER_DEFAULT►

Most edge-preserving filters have an ambiguity problem: run them hard enough to erase texture and they also start eroding the real edges, because "detail" and "structure" look the same to a single pass with a single window. The rolling guidance filter sidesteps that by iterating. Each pass filters the image, then uses its own previous output as the guide for the next pass - small structures get removed and stay removed, while large edges get re-established by the guide. The pack's own note describes the effect neatly: it "progressively removes small-scale structure while restoring large edges."

If you've ever wanted a texture slider where texture and structure are separately controllable, that's this. It's the scale-space member of the family - the pack's edge-aware filter playground puts it next to guidedFilter, l0Smooth and the weighted median filter for exactly that comparison.

Inputs that matter

  • src - the image. 8-bit or float, one or three channels. The result output echoes this input's format, so an IMAGE link comes back as an IMAGE you can preview without bridges.
  • sigmaSpace (3.0) - this is the one to think about. It sets the spatial reach of each pass, i.e. the scale of detail that gets removed. Turn this up to remove bigger texture, not numOfIter.
  • sigmaColor (25.0) - the colour difference (in 0–255 units) below which pixels get averaged together. Too high and it bleeds across genuine edges.
  • numOfIter (4) - the rolling passes. More iterations strengthen the "small stuff stays gone" effect without changing which scale you're targeting; the default 4 is a good place to stop unless you're chasing maximal flattening.
  • d (-1) - the neighbourhood diameter. Non-positive means "derive it from sigmaSpace", which is the sane default here.
  • borderType (BORDER_DEFAULT) - how the pixels outside the frame are synthesised. Leave it unless you're matching another pass.

Defaults are OpenCV's own (25 / 3 / 4), so a fresh node is already in a usable place - the pack only replaces a default when the value isn't actually sensible, and here it is.

Install

cd ComfyUI/custom_nodes
git clone https://github.com/bmad4ever/comfyui_cv

Restart ComfyUI, or install ComfyUI CV from ComfyUI Manager. Python ≥3.12, a recent ComfyUI on the V3 node API, opencv-contrib-python-headless~=5.0.0.93 - no model downloads, no extra dependencies; that one wheel is the entire install. It's a contrib function, so a non-contrib OpenCV install on the same site-packages/cv2 silently removes the node from the menu: tools/repair_opencv_contrib.py --check diagnoses, --apply repairs.

Common issues

The pause before output. This node is on the pack's always-offload list - the cv2 call runs in an interruptible subprocess, so you can cancel a slow run instead of killing ComfyUI, at the cost of about a second of startup per call. Expected, not stuck.

You raised numOfIter and nothing changed much. Right: iterations reinforce the scale you've already set. Change sigmaSpace.

Over-flattening. You've set sigmaSpace above the size of the structure you care about. That's the whole parameter semantics; there's no edge-threshold rescue knob.

Disparity/depth maps. As with every filter in this module, invalid-pixel markers are just values - the −1 in a stereo map gets averaged into its neighbours. The curated disparity nodes in this pack handle validity; the generic smoothers don't.

Cost scales with frame size and iterations. Unlike l0Smooth, this one is at least cancellable - but it's still an iterative filter on the whole frame. Tune at preview resolution.

Categoryimage/CV/low-level/ximgproc

Inputs (6)

NameTypeDefaultDescription
srcCOMFY_MATCHTYPE_V3Source 8-bit or floating-point, 1-channel or 3-channel image. The image output(s) echo this input's format. Accepts a ComfyUI IMAGE/MASK directly (frame 0 of a batch) or an NPARRAY. Arithmetic ops (add, multiply, etc.) process the full IMAGE batch when both inputs have the same batch size.
doptINT-1-2147483648–2147483647Diameter of each pixel neighborhood that is used during filtering. If it is non-positive, it is computed from sigmaSpace . Preset to the OpenCV default (-1).
sigmaColoroptFLOAT25.0000-1e+38–1e+38Filter sigma in the color space. A larger value of the parameter means that farther colors within the pixel neighborhood (see sigmaSpace ) will be mixed together, resulting in larger areas of semi-equal color. Preset to the OpenCV default (25.0).
sigmaSpaceoptFLOAT3.0000-1e+38–1e+38Filter sigma in the coordinate space. A larger value of the parameter means that farther pixels will influence each other as long as their colors are close enough (see sigmaColor ). When d>0 , it specifies the neighborhood size regardless of sigmaSpace . Otherwise, d is proportional to sigmaSpace . Preset to the OpenCV default (3.0).
numOfIteroptINT4-2147483648–2147483647Number of iterations of joint edge-preserving filtering applied on the source image. Preset to the OpenCV default (4).
borderTypeoptCOMBOBORDER_DEFAULT - - -

Outputs (1)

NameTypeDescription
resultCOMFY_MATCHTYPE_V3Echoes the 'src' input's format: an IMAGE link comes back as IMAGE, MASK as MASK, NPARRAY stays NPARRAY.