Gaussian blurring with OpenCV: only blurring a subregion of an image?

To blur the whole image, assuming you want to overwrite the original (In-place filtering is supported by cv::GaussianBlur), you will have something like

 cv::GaussianBlur(image, image, Size(0, 0), 4);

To blur just a region use Mat::operator()(const Rect& roi) to extract the region:

 cv::Rect region(x, y, w, h);
 cv::GaussianBlur(image(region), image(region), Size(0, 0), 4);

Or if you want the blurred output in a separate image:

 cv::Rect region(x, y, w, h);
 cv::Mat blurred_region;
 cv::GaussianBlur(image(region), blurred_region, Size(0, 0), 4);

The above uses the default BORDER_CONSTANT option that just assumes everything outside the image is 0 when doing the blurring. I am not sure what it does with pixels at the edge of a region. You can force it to ignore pixels outside the region (BORDER_CONSTANT|BORDER_ISOLATE). SO it think it probably does use the pixels outside the region. You need to compare the results from above with:

 const int bsize = 10;
 cv::Rect region(x, y, w, h);
 cv::Rect padded_region(x - bsize, y - bsize, w + 2 * bsize, h + 2 * bsize)
 cv::Mat blurred_padded_region;
 cv::GaussianBlur(image(padded_region), blurred_padded_region, Size(0, 0), 4);

 cv::Mat blurred_region = blurred_padded_region(cv::Rect(bsize, bsize, w, h));
 // and you can then copy that back into the original image if you want: 
 blurred_region.copyTo(image(region));

If you are using javacv provided by bytecode

then you can do like this way. It will only blur particular ROI.

Mat src = imread("xyz.jpg",IMREAD_COLOR);
Rect rect = new Rect(50,50,src.size().width()/3,100);
GaussianBlur(new Mat(src, rect), new Mat(src, rect), new Size(23,23), 30);

Yes it is possible to blur a Region Of Interest in OpenCV.

size( 120, 160 ); 
OpenCV opencv = new OpenCV(this);
opencv.loadImage("myPicture.jpg");
opencv.ROI( 60, 0, 60, 160 );
opencv.blur( OpenCV.BLUR, 13 );   
image( opencv.image(), 0, 0 );

For more information, check out this link. Good luck,


Here's how to do it in Python. The idea is to select a ROI, blur it, then insert it back into the image

import cv2

# Read in image
image = cv2.imread('1.png')

# Create ROI coordinates
topLeft = (60, 140)
bottomRight = (340, 250)
x, y = topLeft[0], topLeft[1]
w, h = bottomRight[0] - topLeft[0], bottomRight[1] - topLeft[1]

# Grab ROI with Numpy slicing and blur
ROI = image[y:y+h, x:x+w]
blur = cv2.GaussianBlur(ROI, (51,51), 0) 

# Insert ROI back into image
image[y:y+h, x:x+w] = blur

cv2.imshow('blur', blur)
cv2.imshow('image', image)
cv2.waitKey()

Before -> After

Tags:

Opencv