OpenCV copyTo_0
Mask-aware copying, the compositing glue you're missing
- src
- mask
- dst
- nparray
copyTo_0 is the mask-aware copy node: it copies pixels from src but only where a mask is nonzero, and leaves everything else alone. In one node it does the two things you end up hand-building otherwise - "keep only this masked region" and "paste these pixels back into a bigger image." It's the compositing glue that belongs in any workflow where a mask meets an image.
The inputs are src (NPARRAY) and mask (NPARRAY); output is a single nparray. Two behaviors, depending on whether you wire the optional dst:
- No
dst(the common case): you get a new array equal tosrcwherever the mask is nonzero, and zeros (black) everywhere else. That's masking out - extracting the masked region onto a black background. - With
dst: pixels fromsrcare written intodstwherever the mask is nonzero, anddststays unchanged everywhere else. That's compositing - pasting a crop back onto a canvas, or restoring original pixels into a region you'd modified.
The optional dst input is one of those OpenCV out-parameters, but here it's actually meaningful: leaving it empty gives you the extract behavior, feeding one gives you the paste behavior. That's the one genuine design fork on this node.
Where it fits in real workflows
This is squarely in the "get a mask, act on it" territory the detection/inpainting docs describe. Classic uses: extracting just the detected face region for a detailer pass, then pasting the refined crop back over the original with dst - or, after an inpainting pass, using a mask to copy the original pixels back into areas you don't want touched. It's the low-level compositor that makes "only this region changed" possible.
One practical note: the mask should be a single-channel uint8 array (0s and 255s) the same size as src. A grayscale mask works as a binary gate here - nonzero is "copy," zero is "skip." If your mask comes out of a ComfyUI masking node, it may arrive as a float tensor, so route it through Image2Nparray (batch 1 only) and check it's actually single-channel before feeding it in.
Install
cd ComfyUI/custom_nodes
git clone https://github.com/geroldmeisinger/opencv-comfyui
pip install opencv-python-contrib
Or ComfyUI Manager → opencv-comfyui → restart. No models.
Troubleshooting
- Size mismatch between
srcandmask→ assertion error. Same dimensions required. - The BGR thing again: this pack works in BGR, so convert colors with
cvtColorif you're inspecting results, and remember theImage2Nparray/Nparrays2Imagebridge is howIMAGEgets in and out. copyTo_0andcopyTo_1are the identical overload pair (MatLike vs UMat). Same node, either works.
Inputs (3)
| Name | Type | Default | Description |
|---|---|---|---|
| src | NPARRAY | — | |
| mask | NPARRAY | — | |
| dstopt | NPARRAY | — |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| nparray | NPARRAY | — |