Nodes/CMK Flow/CMK Face Mask
ComfyUI Node

CMK Face Mask

A soft ellipse over the face, and a coverage number to prove it

By CMKFlow·Created 3 months ago·Updated 2 days ago· 6
CMK Face Mask
  • image
  • selected_face
  • image
  • selected_face
  • mask
  • diagnostic
◄shapeEllipse►
◄padding0.25►
◄feather24►
◄invertfalse►
◄preview_modeOverlay►
◄preview_opacity0.50►

Inpainting a face is 90% mask quality. Too tight and you get a visible rectangle of different skin; too loose and the model rebuilds the hair, the earring and the background behind it. CMK Face Mask gives you a feathered shape derived from the face box, and - the part I actually like - tells you what percentage of the frame you just selected.

What it is

A toolbox node: image and a selected_face in, then image (passed through untouched), selected_face (passed through), mask, and a diagnostic. Category CMK/Toolbox/Face.

The pass-throughs are deliberate. It's a mask builder, not an image operation, so the image and the face payload come out the other side identical and you can chain it in the middle of a face pipeline without rewiring.

The controls

  • shape - Ellipse (default) or Box. Ellipse hugs a face far better than a rectangle; a box-shaped mask is what you use when the face is against the frame edge or you're deliberately being generous.
  • padding - default 0.25, range 0–2, as a fraction of the face box. This is the main dial: it decides whether you're masking the face or the head.
  • feather - default 24, range 0–256. Softens the mask edge so the composite seam fades. This is the difference between a blended result and a visible oval.
  • invert - flip it and you mask everything except the face, which is the shape you want when the job is "re-generate the surroundings, leave the person alone."
  • preview_mode - Off, Mask, Overlay, Outline or Coverage, default Overlay. And preview_opacity (0.5) to taste.

The preview modes are the sell here. Coverage renders a coverage readout over the image; the diagnostic's summary and metrics carry that number (coverage_avg, as a percentage of the frame) plus the shape, padding, feather and invert state. So after one run you know your mask covers 4.2% of a 1024×1024 frame, and you know that because the node measured it, not because you eyeballed a black-and-white thumbnail.

How it works

For each frame it builds the mask from the face bounding box expanded by padding, as either an ellipse or a rectangle, applies the feather radius, optionally inverts, and stacks the result into a batch. padding, feather and preview_opacity are clamped at execution time - there's a comment in the source about stale widget values in older workflows, so a saved graph that predates a range change gets quietly brought back into range instead of producing something absurd. shape and preview_mode fall back to their defaults if a stored value isn't recognised. That's a small thing that saves a class of "my old workflow went weird" bug reports.

One behaviour to note: the outputs are a batch matched to the input image batch, so a 4-frame batch gives you 4 masks. If a downstream node takes a single mask, take the first frame.

Install

Ships with the pack. Manager: search CMK Flow, install the CMKFlow entry, restart. Manual, from the folder with main.py:

git clone https://github.com/CMKFlow/cmk_nodes.git custom_nodes/cmk_nodes
python3 custom_nodes/cmk_nodes/scripts/install_cmk_requirements.py

CMK dependency check: OK is what you're waiting for, and it's the step people miss after a manual clone - git clone never runs pip on its own. The environment it installs into is a shared one, and this pack is not shy about it: ultralytics, onnxruntime, insightface, segment-anything, imageio-ffmpeg, opencv-python, nudenet==3.4.2. No Impact Pack needed for the SEGS side, though - CMK ships its own.

Detector weights (YOLO face models) belong under models/ultralytics/bbox; the resource checker audits the filenames the bundled workflows expect:

python3 custom_nodes/cmk_nodes/scripts/check_cmk_resources.py --models-root "/path/to/shared/models"

Issues worth knowing

Feather is in pixels, not a percentage, so it doesn't scale with resolution. A feather of 24 that looks perfect at 1024×1024 is a hard edge at 2048. Bump it when you upscale.

And the classic: if your inpainted face has a visible halo, the seam is the mask, not the model. Turn preview_mode to Coverage, look at where the mask actually ends, and increase padding before you touch denoise. More often than not the ellipse was cutting through the jawline.

CategoryCMK/Toolbox/Face

Inputs (8)

NameTypeDefaultDescription
imageIMAGE—
selected_faceCMK_SELECTED_FACE—
shapeCOMBOEllipse2 options: Ellipse, Box
paddingFLOAT0.250–2—
featherINT240–256—
invertBOOLEANfalse—
preview_modeCOMBOOverlay5 options: Off, Mask, Overlay, Outline, Coverage
preview_opacityFLOAT0.500–10—

Outputs (4)

NameTypeDescription
imageIMAGE—
selected_faceCMK_SELECTED_FACE—
maskMASK—
diagnosticCMK_DIAGNOSTIC—