OpenCV fitEllipse_0
Fit an ellipse to your blob in one step
- points
- literal
You've got a blob - a mask region, a contour, a cluster of points - and you want to know its shape as an ellipse. cv2.fitEllipse does a least-squares fit of an ellipse to a set of 2D points and hands back the center, the two axis lengths, and the rotation angle. OpenCV fitEllipse_0 wraps that in ComfyUI, and it's the node you want when "it's roughly elliptical, how roughly, and where?" is the question.
Classic uses: measuring objects in inspection-style workflows, tracking an elliptical region over frames, getting a stable center and bounding ellipse for a detection, or normalizing a tilted blob before further processing. Combined with findNonZero (which turns a mask into point coordinates), this is a two-node "describe my mask" pipeline.
Input and output
The schema is gloriously small:
points- anNPARRAYof 2D points, shapeNx1x2orNx2(float). At least 5 points, or OpenCV refuses. Where do you get those in this pack?findNonZerooff a thresholded mask is the easiest path - it turns a mask into exactly the point list this node wants.
Output: a single literal (STRING) - the fitted ellipse as a RotatedRect, serialized as ((center_x, center_y), (width, height), angle). This is worth being precise about: it's not an image and not a matrix you can warp - it's a compact description of the ellipse. You read the values off it, and you can feed them (as a literal, same (…) syntax) into this pack's ellipse node to draw the fitted ellipse back onto the image.
What trips people
The output is a value, not a picture. The pack's standard 'NoneType' object has no attribute 'shape' error is what greets you if you try to render it. The literal type exists because RotatedRect is a composite OpenCV type, and this pack passes composites around as Python literals (parsed with literal_eval). Expect text you can read, not a wire you can preview.
Points must be floats, and there must be enough of them. Fewer than 5 points → assertion. Integer coordinate arrays → cast to float first (np.float32), which any NPARRAY you hand-build can be.
Ellipse fit is a shape statement, not a mask. A concave or multi-blob point set gets an ellipse fitted anyway - the node doesn't know your geometry is weird. Garbage points in, meaningless ellipse out.
Install
Part of geroldmeisinger/opencv-comfyui. ComfyUI Manager → search opencv-comfyui → install → restart, or:
cd ComfyUI/custom_nodes
git clone https://github.com/geroldmeisinger/opencv-comfyui
requirements.txt installs opencv-contrib-python, numpy, torch. The pack imports cv2 at startup; if OpenCV is missing or duplicated (the guidedFilter import error is the tell), none of its nodes register.
Verdict
fitEllipse_0 is a quiet little utility that earns its place once you're measuring anything in a mask. _1 is its byte-identical twin. And when you want a more robust ellipse estimate - one that handles outliers better - fitEllipseAMS_0 is the "Approximate Mean Square" variant of the same idea.
Inputs (1)
| Name | Type | Default | Description |
|---|---|---|---|
| points | NPARRAY | — |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| literal | STRING | — |