Scan image and crop it to certain size

Hi,
I have two different size of images in one folder
What I am trying to do with these two different size of image is:
  • Trying to scan an image row by row to see the area or section with highest intensity of white pixel.
  • With that data I am trying to crop it to 320x320 image and save it to different folder
Below is my code that I constructed and working with.
I am very new to Matlab and coding it for image processing so hope you understand the mess.
data = '2018.png';
baseFileName = imread(data);
[rows, columns]=size(baseFileName);
% Get the full filename, with path prepended.
fullFileName = fullfile(folder, baseFileName);
originalImage = imread(fullFileName);
binaryImage = originalImage >= 1;
binaryImage = bwareafilt(binaryImage, [1, inf]); % Extract only the largest.
Pixels = sum(binaryImage(:)); % Check total pixel
% Find the bounding box.
[blobRows, blobColumns] = find(binaryImage);
row1 = min(blobRows);
row2 = max(blobRows);
col1 = min(blobColumns);
col2 = max(blobColumns);
if row2 <= 322
for x = 1:160
for y = 1:2
im_buff = binaryImage(y:(y+320-1), x:(x+320-1));
x = x + 1;
% Crop it.
crop = imcrop(im_buff, [row1 col1 320 320]);
img1g_NB = length(crop(crop~=0));
% Display the cropped image.
imshow(crop);
end
end
else
for x = 1:2
for y = 1:160
im_buff = binaryImage(y:(y+320-1), x:(x+320-1));
y = y + 1;
% Crop it.
crop = imcrop(im_buff, [row1 col1 320 320]);
img1g_NB = length(crop(crop~=0));
% Display the cropped image.
imshow(crop);
end
end
end

 Accepted Answer

Those look like binary images so all pixel values are either 0 or 1. Not sure what you mean by finding the brightest pixel.
To scan a grayscale image row by row looking for the brightest row you can do
meanRowIntensities = mean(grayImage, 2);
[maxAveIntensity, rowOfMaxIntensity] = max(meanRowIntensities);
% Get 320 row range centered there.
row1 = rowOfMaxIntensity - 160
if row1 < 1
row1 = 1; % Don't let go off the top of the image.
end
row2 = row1 + 319
subImage = grayImage(row1:row2, :);
If you want, after that you can find the brightest column and do essentially the same thing (crop) so that you have a 320x320 image.
meanColIntensities = mean(subImage, 1);
[maxAveIntensity, colOfMaxIntensity] = max(meanColIntensities);
% Get 320 row range centered there.
col1 = colOfMaxIntensity - 160
if col1 < 1
col1 = 1; % Don't let go off the left of the image.
end
col2 = col1 + 319
subImage = subImage(:, col1:col2);
You'll need to do a little more validation to make sure row2 and col2 are not past the bottom or right side of the image, respectively. And to be super robust, make sure your original images are all bigger than 320 in any dimension.

5 Comments

dominic
dominic on 27 Dec 2022
Edited: dominic on 27 Dec 2022
Thank you!
About the finding the brightest pixel, I meant there are some images only have few white pixels like the image below and I would like to focus on the area with most pixel numbers that counted, or found in the image and crop it in 320x320 image.
To be clear, after the scan the image row by row and count the number of white pixel, I want to crop the area with most white pixel exists centered with 320x320 image.
Also, my images are all bigger than 320 which are 321x481 or 481x321 so I believe it should be fine.
You can use conv2() to count all the pixels in a 320x320 sliding window. Then pick the location with the greatest sum
windowSize = 320;
kernel = ones(windowSize, windowSize);
pixelCounts = conv2(double(binaryImage), kernel, 'same');
maxCount = max(pixelCounts(:));
[row, col] = find(pixelCounts == maxCount);
% Find top left corner
row1 = row(1) - 159
row2 = row1 + 319
col1 = col(1) - 159
col2 = col1 + 319
So to be clear, should I combine two codes you gave and use them?
Like count the pixel first and then scan the images?
I am sorry for the many questions I am very new to matlab and image processing stuff.
Yes. I'm sure you've already gotten it by now but here is how I'd do it:
% Demo by Image Analyst
clc; % Clear the command window.
close all; % Close all figures (except those of imtool.)
clear; % Erase all existing variables. Or clearvars if you want.
workspace; % Make sure the workspace panel is showing.
format long g;
format compact;
fontSize = 22;
markerSize = 40;
%--------------------------------------------------------------------------------------------------------
% READ IN IMAGE
folder = [];
baseFileName = 'dominic.png';
fullFileName = fullfile(folder, baseFileName);
% Check if file exists.
if ~exist(fullFileName, 'file')
% The file doesn't exist -- didn't find it there in that folder.
% Check the entire search path (other folders) for the file by stripping off the folder.
fullFileNameOnSearchPath = baseFileName; % No path this time.
if ~exist(fullFileNameOnSearchPath, 'file')
% Still didn't find it. Alert user.
errorMessage = sprintf('Error: %s does not exist in the search path folders.', fullFileName);
uiwait(warndlg(errorMessage));
return;
end
end
grayImage = imread(fullFileName);
% Get the dimensions of the image.
% numberOfColorChannels should be = 1 for a gray scale image, and 3 for an RGB color image.
[rows, columns, numberOfColorChannels] = size(grayImage)
%--------------------------------------------------------------------------------------------------------
% Display the image.
subplot(2, 2, 1);
imshow(grayImage);
impixelinfo;
axis('on', 'image');
title('Original Image', 'FontSize', fontSize, 'Interpreter', 'None');
if numberOfColorChannels > 1
% It's not really gray scale like we expected - it's color.
fprintf('It is not really gray scale like we expected - it is color\n');
% Extract the blue channel.
grayImage = grayImage(:, :, 3);
% Update the dimensions of the image.
% numberOfColorChannels should be = 1 for a gray scale image, and 3 for an RGB color image.
[rows, columns, numberOfColorChannels] = size(grayImage)
end
% Maximize window.
g = gcf;
g.WindowState = 'maximized';
drawnow;
%--------------------------------------------------------------------------------------------------------
% Count the pixels in a 320x320 sliding window.
subplot(2, 2, 2);
binaryImage = grayImage>0;
histogram(binaryImage, 256);
grid on;
title('Histogram of Image Gray Levels', 'FontSize', fontSize, 'Interpreter', 'None');
windowSize = 320;
kernel = ones(windowSize, windowSize);
pixelCounts = conv2(double(binaryImage), kernel, 'same');
maxCount = max(pixelCounts(:));
subplot(2, 2, 3);
imshow(pixelCounts, [])
colorbar;
caption = sprintf('Count Image. maxCount = %d', maxCount);
title(caption, 'FontSize', fontSize, 'Interpreter', 'None');
axis('on', 'image');
impixelinfo
drawnow;
[rowOfMaxIntensity, col] = find(pixelCounts == maxCount);
% Find top left corner
row1 = rowOfMaxIntensity(1) - floor(windowSize/2 - 1)
row2 = row1 + (windowSize - 1)
col1 = col(1) - floor(windowSize/2 - 1)
col2 = col1 + (windowSize - 1)
% Get 320 row range centered there.
if row1 < 1
row1 = 1; % Don't let go off the top of the image.
end
row2 = row1 + (windowSize - 1)
if row2 > rows
row2 = rows
row1 = row2 - (windowSize - 1)
end
subImage = grayImage(row1:row2, :);
size(subImage)
% Need to crop pixelCounts also.
pixelCounts = pixelCounts(row1:row2, :);
% Now we have a band through the image.
% Find out what columns we need.
meanColIntensities = mean(pixelCounts, 1);
[maxAveIntensity, colOfMaxIntensity] = max(meanColIntensities);
% Get 320 row range centered there.
col1 = colOfMaxIntensity - floor(windowSize/2)
if col1 < 1
col1 = 1; % Don't let go off the left of the image.
end
col2 = col1 + (windowSize - 1)
subImage = subImage(:, col1:col2);
% Get the dimensions of the image.
% numberOfColorChannels should be = 1 for a gray scale image, and 3 for an RGB color image.
[rows, columns, numberOfColorChannels] = size(subImage)
subplot(2, 2, 4);
imshow(subImage, [])
impixelinfo
caption = sprintf('%d by %d Subimage', rows, columns);
title(caption, 'FontSize', fontSize, 'Interpreter', 'None');
axis('on', 'image');
impixelinfo
drawnow;
Yes, I got it to work but it wasnt that neat as yours. I really appreciate your organized code, so i can compare with mine and study bit more with it.
Thank you very much!

Sign in to comment.

More Answers (1)

I = imread('https://www.mathworks.com/matlabcentral/answers/uploaded_files/1243147/image.png') ;
[y,x] = find(I) ;
% Get bounding box
x0 = min(x) ; x1 = max(x) ;
y0 = min(y) ; y1 = max(y) ;
I1 = I(y0:y1,x0:x1) ;
subplot(211)
imshow(I) ;
subplot(212)
imshow(I1)

3 Comments

dominic
dominic on 26 Dec 2022
Edited: dominic on 26 Dec 2022
I tried to use your code but depends on the images that I input (since there are more than 100 of images) it crops in a different size where it should be cropped in 320x320.
Later you can use imresize to get every image to equal size.
imresize will rise the problem with the quailty of training that I will do later due to the forced resizing

Sign in to comment.

Categories

Find more on Deep Learning Toolbox in Help Center and File Exchange

Asked:

on 26 Dec 2022

Edited:

on 30 Dec 2022

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!