how to divide image to overlapping blocks
Show older comments
how to divide image to overlapping blocks using blockproc or mat2cell.
Accepted Answer
More Answers (1)
Image Analyst
on 7 Jan 2013
Edited: Image Analyst
on 7 Jan 2013
In my demo (which I've posted several times before) I split a color and a grayscale image into non-overlapping blocks using both methods: blockproc and indexing. It's really straightforward to adapt it to do overlapping blocks - I trust you can do that. Good luck.
% Demo to divide a color image up into blocks.
clc; % Clear the command window.
close all; % Close all figures (except those of imtool.)
workspace; % Make sure the workspace panel is showing.
fontSize = 20;
% Read in a standard MATLAB color demo image.
folder = fullfile(matlabroot, '\toolbox\images\imdemos');
baseFileName = 'peppers.png';
% Get the full filename, with path prepended.
fullFileName = fullfile(folder, baseFileName);
if ~exist(fullFileName, 'file')
% Didn't find it there. Check the search path for it.
fullFileName = baseFileName; % No path this time.
if ~exist(fullFileName, 'file')
% Still didn't find it. Alert user.
errorMessage = sprintf('Error: %s does not exist.', fullFileName);
uiwait(warndlg(errorMessage));
return;
end
end
% Read the image from disk.
rgbImage = imread(fullFileName);
% Test code if you want to try it with a gray scale image.
% Uncomment line below if you want to see how it works with a gray scale image.
% rgbImage = rgb2gray(rgbImage);
% Display image full screen.
imshow(rgbImage);
% Enlarge figure to full screen.
set(gcf, 'units','normalized','outerposition',[0 0 1 1]);
drawnow;
% Get the dimensions of the image. numberOfColorBands should be = 3.
[rows columns numberOfColorBands] = size(rgbImage)
%==========================================================================
% The first way to divide an image up into blocks is by using mat2cell().
blockSizeR = 150; % Rows in block.
blockSizeC = 100; % Columns in block.
% Figure out the size of each block in rows.
% Most will be blockSizeR but there may be a remainder amount of less than that.
wholeBlockRows = floor(rows / blockSizeR);
blockVectorR = [blockSizeR * ones(1, wholeBlockRows), rem(rows, blockSizeR)];
% Figure out the size of each block in columns.
wholeBlockCols = floor(columns / blockSizeC);
blockVectorC = [blockSizeC * ones(1, wholeBlockCols), rem(columns, blockSizeC)];
% Create the cell array, ca.
% Each cell (except for the remainder cells at the end of the image)
% in the array contains a blockSizeR by blockSizeC by 3 color array.
% This line is where the image is actually divided up into blocks.
if numberOfColorBands > 1
% It's a color image.
ca = mat2cell(rgbImage, blockVectorR, blockVectorC, numberOfColorBands);
else
ca = mat2cell(rgbImage, blockVectorR, blockVectorC);
end
% Now display all the blocks.
plotIndex = 1;
numPlotsR = size(ca, 1);
numPlotsC = size(ca, 2);
for r = 1 : numPlotsR
for c = 1 : numPlotsC
fprintf('plotindex = %d, c=%d, r=%d\n', plotIndex, c, r);
% Specify the location for display of the image.
subplot(numPlotsR, numPlotsC, plotIndex);
% Extract the numerical array out of the cell
% just for tutorial purposes.
rgbBlock = ca{r,c};
imshow(rgbBlock); % Could call imshow(ca{r,c}) if you wanted to.
[rowsB columnsB numberOfColorBandsB] = size(rgbBlock);
% Make the caption the block number.
caption = sprintf('Block #%d of %d\n%d rows by %d columns', ...
plotIndex, numPlotsR*numPlotsC, rowsB, columnsB);
title(caption);
drawnow;
% Increment the subplot to the next location.
plotIndex = plotIndex + 1;
end
end
% Display the original image in the upper left.
subplot(4, 6, 1);
imshow(rgbImage);
title('Original Image');
%==============================================================================
% Another way to split the image up into blocks is to use indexing.
% Read in a standard MATLAB gray scale demo image.
folder = fullfile(matlabroot, '\toolbox\images\imdemos');
baseFileName = 'cameraman.tif';
fullFileName = fullfile(folder, baseFileName);
% Get the full filename, with path prepended.
fullFileName = fullfile(folder, baseFileName);
if ~exist(fullFileName, 'file')
% Didn't find it there. Check the search path for it.
fullFileName = baseFileName; % No path this time.
if ~exist(fullFileName, 'file')
% Still didn't find it. Alert user.
errorMessage = sprintf('Error: %s does not exist.', fullFileName);
uiwait(warndlg(errorMessage));
return;
end
end
grayImage = imread(fullFileName);
% Get the dimensions of the image. numberOfColorBands should be = 1.
[rows columns numberOfColorBands] = size(grayImage);
% Display the original gray scale image.
figure;
subplot(2, 2, 1);
imshow(grayImage, []);
title('Original Grayscale Image', 'FontSize', fontSize);
% Enlarge figure to full screen.
set(gcf, 'units','normalized','outerposition',[0 0 1 1]);
% Divide the image up into 4 blocks.
% Let's assume we know the block size and that all blocks will be the same size.
blockSizeR = 128; % Rows in block.
blockSizeC = 128; % Columns in block.
% Figure out the size of each block.
wholeBlockRows = floor(rows / blockSizeR);
wholeBlockCols = floor(columns / blockSizeC);
% Preallocate a 3D image
image3d = zeros(wholeBlockRows, wholeBlockCols, 3);
% Now scan though, getting each block and putting it as a slice of a 3D array.
sliceNumber = 1;
for row = 1 : blockSizeR : rows
for col = 1 : blockSizeC : columns
% Let's be a little explicit here in our variables
% to make it easier to see what's going on.
row1 = row;
row2 = row1 + blockSizeR - 1;
col1 = col;
col2 = col1 + blockSizeC - 1;
% Extract out the block into a single subimage.
oneBlock = grayImage(row1:row2, col1:col2);
% Specify the location for display of the image.
subplot(2, 2, sliceNumber);
imshow(oneBlock);
% Make the caption the block number.
caption = sprintf('Block #%d of 4', sliceNumber);
title(caption);
drawnow;
% Assign this slice to the image we just extracted.
image3D(:, :, sliceNumber) = oneBlock;
sliceNumber = sliceNumber + 1;
end
end
% Now image3D is a 3D image where each slice,
% or plane, is one quadrant of the original 2D image.
msgbox('Done with demo! Check out the two figures.');
14 Comments
Algorithms Analyst
on 6 Mar 2013
can you please further provide how can we create overlapp regions?
Walter Roberson
on 6 Mar 2013
blockproc(YourArray, [6 6], TheFunction, 'BorderSize', [3 3], 'TrimBorder', 0)
would be for an overlap of 3 on blocks that are overlap+6+overlap = 3+6+3 = 12 wide
Algorithms Analyst
on 6 Mar 2013
can I access this overlapped region of blocks....for further processing....coz I want to compute the histgrams of overlapping regions..
Thanks Mr Robertson.
Algorithms Analyst
on 6 Mar 2013
what will happen if i make trimborder=false in BLOCKPROC operation
Image Analyst
on 6 Mar 2013
That's strange. Why would you want the histogram of only the pixels where your block overlapped the previous (and next?) blocks, and not the part of the current block that would not be overlapped?
Walter Roberson
on 6 Mar 2013
trimborder 0 and trimborder false are exactly the same. Both of them tell blockproc to not remove the "bordersize" border from the output calculated by The Function.
Regardless of the setting of trimborder, TheFunction will be passed the block including the overlap.
Algorithms Analyst
on 7 Mar 2013
Image Analyst:
This is the project which I am following....I need to compute the histograms from overlapped regions of block.and then need to compare overlapped block histograms with non-overlapped block histograms.So it means need to compute histograms from these two regions separately. Thanks
Algorithms Analyst
on 7 Mar 2013
Ahhh thank you MR.Roberson...
TUSHAR SURESH MURATKAR 17PHD0024
on 4 Sep 2017
@ image analyst..... i used the code given by you for grayscale image. But i am getting error as "index exceeds number of subplots" . Also image is divided into 4 blocks but it is completely white, nothing is seen on it.
Image Analyst
on 4 Sep 2017
The demo works for me so I need to see how you modified it. Post your image and your code so I can run it and fix the error.
Walter Roberson
on 4 Sep 2017
The code in the demo starting at
% Divide the image up into 4 blocks.
% Let's assume we know the block size and that all blocks will be the same size.
assumes that the original image is 256 by 256; if it were larger then you would end up trying to access an subplot greater than 2 by 2
TUSHAR MURATKAR
on 14 Sep 2017
@ image analyst..... can you tell me how to divide an image into overlapping blocks so that i can perform feature extraction using SVD from each block. My input image is of size 128x128 and block size is 16. My image after division must satisfy the dimension (128-16+1)*(128-16+1). Eagerly waiting for your answer.
Image Analyst
on 14 Sep 2017
And doesn't the code already posted do that?
If you want more demos, including one where you can use your own custom function to do whatever you want to the block, see my attached demos.
TUSHAR MURATKAR
on 16 Sep 2017
@ image analyst.... i had divide the image into overlapping blocks. But now i am stucked up with applying svd to each block. Can you give me suggestion on this
Categories
Find more on Neighborhood and Block Processing in Help Center and File Exchange
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!