Nodes/ComfyUI CV/cv2.thresholdWithMask
ComfyUI Node

cv2.thresholdWithMask

Threshold only inside the region you care about

By bmad4ever·Created 4 months ago·Updated 16 days ago· 1
cv2.thresholdWithMask
  • src
  • dst
  • mask
  • float
  • result
◄thresh0.0000►
◄maxval0.0000►
◄typeTHRESH_BINARY►

The honest pitch first: this is one of the least-known functions in OpenCV 5 - a masked variant of threshold - and it exists in this pack only because the pack auto-generates a wrapper for everything cv2 exposes. Nobody's shipping workflows around it. But the shape of what it does is genuinely useful in a mixing graph, and it's simple enough to explain in a paragraph.

threshold binarises the whole frame. thresholdWithMask binarises only where the mask is non-zero and leaves everything else as it was. In a ComfyUI graph that's "sharpen the decision in this region", which is how you binarise a soft mask only inside the subject's bounding area, or cut a local threshold out of a noisy background without touching the rest of the picture.

One of roughly 470 auto-generated raw cv2.* wrappers in ComfyUI CV (bmad4ever/comfyui_cv) - uncurated by design, LLM-generated, per the pack's own disclaimers.

Inputs

Six, and the middle one is the interesting bit.

  • src - NPARRAY, IMAGE or MASK. An IMAGE is auto-grayscaled, because this function wants single-channel input.
  • dst - required, and this is the best thing about the node. In cv2, thresholdWithMask writes its result into dst, and the pixels outside the mask keep whatever dst held. The wrapper's tooltip says it plainly: cv2 writes into this array in place, "but this wrapper passes cv2 a private copy, so your input array is never modified". Meaning: whatever you link into dst is the content that survives outside the mask. Link your original image and only the masked region gets thresholded - a local binarisation brush. Link a black image and the outside goes black.
  • mask - required here (the same-size 8-bit array), which is exactly what makes this a different node from cv2.threshold. Same size as src.
  • thresh, maxval, type - the same trio as plain threshold, with type a dropdown of the THRESH_* flags plus the OTSU/TRIANGLE options pipe-joined onto THRESH_BINARY.

Same units warning as its sibling: an IMAGE is 8-bit, so thresh and maxval are 0..255, not 0..1.

Outputs

result echoes src's socket type (IMAGE → IMAGE, MASK → MASK) and float is the threshold value cv2 settled on - only interesting when you've enabled OTSU or TRIANGLE, in which case it's the histogram's answer and worth reading.

Is it worth using?

Sometimes. The three-step version of the same thing - threshold the frame, then cv2.copyTo or cv2.bitwise_and the result back through the mask - gives you more control and more knobs (you can feather the seam, pick which of several sources survives outside, dilate the mask first to avoid a hard cut). This node does it in one call, and one call is a real advantage when all you want is "don't let the binarisation touch anything outside this box".

What it won't do is give you a soft transition at the mask border, any more than threshold gives you one at the intensity border. If the edge of the region is visible in the result - and on a difference-of-two-results it always is - the fix is to feather the mask before it arrives, not to look for a knob here. The stock binary mask is sharp by nature.

Treat this as a raw building block: there's no shipped example workflow using it, no curated preset, and no author support. Verify on your own data before you build a production graph around it, which the pack's README says about everything in here anyway.

Installing the pack

cd ComfyUI/custom_nodes
git clone https://github.com/bmad4ever/comfyui_cv
cd comfyui_cv && pip install "opencv-contrib-python-headless~=5.0.0.93"

Manager → search ComfyUI CV → install → restart works too. Python ≥ 3.12 and a ComfyUI on the V3 node API are hard requirements - older installations never show these nodes. Keep the OpenCV build contrib: all four distributions share one site-packages/cv2, and installing plain opencv-python over the contrib wheel silently empties the contrib submodules, taking contrib nodes with it. tools/repair_opencv_contrib.py --check diagnoses, --apply repairs. Behaviour is curated against 5.0.0.93.

Watch out for

Forgetting dst is not just a formality - it defines everything outside the mask, so leaving it wired to a black constant gives you a hard black border you didn't intend. Mismatched src/dst/mask sizes raise rather than resize. And a maxval of 0 still produces an all-zero result inside the mask, exactly as in plain threshold.

Categoryimage/CV/low-level/cv2 T

Inputs (6)

NameTypeDefaultDescription
srcCOMFY_MATCHTYPE_V3input array (multiple-channel, 8-bit or 32-bit floating point). 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.
dstNPARRAY,IMAGE,MASKoutput array of the same size and type and the same number of channels as src. The low-level cv2 function writes its result into this array in place, but this wrapper passes cv2 a private copy, so your input array is never modified. 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.
maskNPARRAY,IMAGE,MASKoptional mask (same size as src, 8-bit). 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.
threshFLOAT0.0000-1e+38–1e+38threshold value.
maxvalFLOAT0.0000-1e+38–1e+38maximum value to use with the #THRESH_BINARY and #THRESH_BINARY_INV thresholding types.
typeSTRINGTHRESH_BINARYthresholding type (see #ThresholdTypes). cv2.thresholdWithMask flags: one of THRESH_BINARY, THRESH_BINARY_INV, THRESH_TRUNC, THRESH_TOZERO, THRESH_TOZERO_INV plus any of THRESH_OTSU, THRESH_TRIANGLE, pipe-joined (e.g. "THRESH_BINARY | THRESH_OTSU"). In the UI this renders as a dropdown with one toggle per flag.

Outputs (2)

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