RotatedRect ROI in OpenCV

vancexu picture vancexu · Oct 26, 2012 · Viewed 14.6k times · Source

I have a RotatedRect, I want to do some image processing in the rotated region (say extract the color histogram). How can I get the ROI? I mean get the region(pixels) so that I can do processing.

I find this, but it changes the region by using getRotationMatrix2D and warpAffine, so it doesn't work for my situation (I need to process the original image pixels).
Then I find this suggests using mask, which sounds reasonable, but can anyone teach me how to get the mask as the green RotatedRect below.
The green RotatedRect is the ROI I want to do some processing

Excepts the mask, is there any other solutions ?
Thanks for any hint

Answer

vancexu picture vancexu · Oct 31, 2012

Here is my solution, using mask:
The idea is construct a Mat mask by assigning 255 to my RotatedRect ROI.

How to know which point is in ROI (which should be assign to 255)?
I use the following function isInROI to address the problem.

/** decide whether point p is in the ROI.
*** The ROI is a rotated rectange whose 4 corners are stored in roi[] 
**/
bool isInROI(Point p, Point2f roi[])
{
    double pro[4];
    for(int i=0; i<4; ++i)
    {
        pro[i] = computeProduct(p, roi[i], roi[(i+1)%4]);
    }
    if(pro[0]*pro[2]<0 && pro[1]*pro[3]<0)
    {
        return true;
    }
    return false;
}

/** function pro = kx-y+j, take two points a and b,
*** compute the line argument k and j, then return the pro value
*** so that can be used to determine whether the point p is on the left or right
*** of the line ab
**/
double computeProduct(Point p, Point2f a, Point2f b)
{
    double k = (a.y-b.y) / (a.x-b.x);
    double j = a.y - k*a.x;
    return k*p.x - p.y + j;
}

How to construct the mask?
Using the following code.

Mat mask = Mat(image.size(), CV_8U, Scalar(0));
for(int i=0; i<image.rows; ++i)
{
    for(int j=0; j<image.cols; ++j)
    {
        Point p = Point(j,i);   // pay attention to the cordination
        if(isInROI(p,vertices))
        {
            mask.at<uchar>(i,j) = 255;
        }
    }
}

Done,
vancexu