PhantomR
PhantomR

Reputation: 595

Implement an Ellipse Structural Element

I want to implement the following using OpenCV (I'll post my attempt at the bottom of the post). I am aware that OpenCV has a function for something like this, but I want to try to write my own.

In an image (Mat) (the coordinate system is at the top left, since it is an image) of width width and height height, I want to display a filled ellipsewith the following properties:

Ok, so I've found an equation similar to this (https://math.stackexchange.com/a/434482/403961) for my purpose. My code is as follows.. it does seem to do pretty well on the rotation side, but, sadly, depending on the rotation angle, the SIZE (major axis, not sure about the minor) visibly increases/decreases, which is not normal, since I want it to have the same size, independent of the rotation angle.

NOTE The biggest size is seemingly achieved when the angle is 45 or -45 degrees and the smallest for angles like -90, 0, 90.

Code:

inline double sqr(double x)
{
    return x * x;
}

Mat ellipticalElement(double a, double b, double angle, int width, int height)
{
    // just to make sure I don't use some bad values for my parameters
    assert(2 * a < width);
    assert(2 * b < height);

    Mat element = Mat::zeros(height, width, CV_8UC1);

    Point center(width / 2, height / 2);
    for(int x = 0 ; x < width ; x++)
        for(int y = 0 ; y < height ; y++)
        {
            if (sqr((x - center.x) * cos(angle) - (y - center.y) * sin(angle)) / sqr(a) + sqr((x - center.x) * sin(angle) - (y - center.y) * cos(angle)) / sqr(b) <= 1)
                element.at<uchar>(y, x) = 1;
        }

    return element;
}

Upvotes: 0

Views: 296

Answers (1)

kazarey
kazarey

Reputation: 835

A pesky typo sneaked in your inequality. The first summand must be

sqr((x - center.x) * cos(angle) + (y - center.y) * sin(angle)) / sqr(a)

Note the plus sign instead of minus.

Upvotes: 1

Related Questions