How to preserve transparent edges in images after image processing?

2 Ansichten (letzte 30 Tage)
Caio
Caio am 21 Aug. 2024
Kommentiert: Walter Roberson am 22 Aug. 2024
Hello, everyone!
I'm facing a problem related to the processing of .png images with transparent edges obtained in a simulation software. Whenever I convert the image (RGB) to grayscale, together with a Graussian filter, the transparent edges become white, and this hinders the reading and training of the neural network model I'm using.

A input (with transparent edges) and output instance (no transparent edges)

Information: size = [480 480]

Notice how in the first image we have transparent edges, and in the following images the edges become white and threrefore suffer from changes.

Code

path = 'C:\Users\W11\OneDrive\Desktop\dataset\pla_50\';
files = dir(fullfile(path,'*.png*'));
sizeImg = 160;
fileSize = [sizeImg, sizeImg];
numFiles = length(files);
file = zeros([fileSize, numFiles], 'like', imread(fullfile(path, files(1).name)));
time = zeros(numFiles, 1);
for i = 1:length(files)
img = imread(fullfile(path, files(i).name));
[~, name, ext] = fileparts(files(i).name);
if size(img, 3) == 3
grayImg = rgb2gray(img);
else
grayImg = img;
end
mean=0; variance=0.01;
noisedImg = imnoise(grayImg, 'gaussian', mean, variance);
imgDeformed = elasticDeform(noisedImg, 8, 30);
file(:, :, 1, i) = imresize(imgDeformed, fileSize);
separatorIndex = strfind(name, '-');
depth(i, 1) = round(str2double(name(1:separatorIndex-1)), 2);
time(i, 1) = round(str2double(name(separatorIndex+1:end)));
end
[train_idx, ~, val_idx] = dividerand(numFiles, 0.7, 0, 0.3);
XTrain = file(:, :, 1, train_idx);
YTrain = depth(train_idx, 1);
XVal = file(:, :, 1, val_idx);
YVal = depth(val_idx, 1);
save('data.mat', 'XTrain', 'XVal', 'YTrain', 'YVal');
Where elasticDeform is:
function imgDeformed = elasticDeform(img, alpha, sigma)
[rows, cols] = size(img);
dx = alpha * randn(rows, cols);
dy = alpha * randn(rows, cols);
dx = imgaussfilt(dx, sigma);
dy = imgaussfilt(dy, sigma);
[X, Y] = meshgrid(1:cols, 1:rows);
X_new = X + dx; Y_new = Y + dy;
imgDeformed = interp2(X, Y, double(img), X_new, Y_new, 'linear', 0);
imgDeformed = uint8(imgDeformed);
end

Saving a 4-D array and the depth

save('data.mat', 'XTrain', 'XVal', 'YTrain', 'YVal');
The data is saved in .mat format.
  4 Kommentare
Caio
Caio am 21 Aug. 2024
@Matt J @Image Analyst I hope the changes in my ask have allowed my problem to be understood.
Matt J
Matt J am 22 Aug. 2024
Bearbeitet: Matt J am 22 Aug. 2024
I hope the changes in my ask have allowed my problem to be understood.
I don't see any changes to the code, nor any image attachments.

Melden Sie sich an, um zu kommentieren.

Antworten (1)

Walter Roberson
Walter Roberson am 22 Aug. 2024
Verschoben: Walter Roberson am 22 Aug. 2024
Notice how in the first image we have transparent edges
img = imread(fullfile(path, files(i).name));
The images are not being treated as if they have transparency. To read transparency, you need
[img, Cmap, Alpha] = imread(fullfile(path, files(i).name));
if ~isempty(Cmap)
img = ind2rgb(img, Cmap);
end
if isempty(Alpha)
Alpha = uint8(255)+zeros(size(img,1), size(img,2),'uint8');
end
Afterwards, Alpha contains the transparency information.
  3 Kommentare
Walter Roberson
Walter Roberson am 22 Aug. 2024
Well... you don't. It is not obvious that the transparency of the image has any effect on the calculations.
But I would suggest,
imgDeformed_cleaned = im2uint8(im2double(imgDeformed) .* im2double(Alpha));
Walter Roberson
Walter Roberson am 22 Aug. 2024
You currently have
imgDeformed = elasticDeform(noisedImg, 8, 30);
What would it mean to "preserve transparency" in imgDeformed?
I mean, you could
imgDeformed = cat(3, imgDeformed, Alpha);
to end up with an RGBA array, but that is of questionable utility, since there isn't much you can do with RGBA images other than use the Tiff library to write them out.
You would have more utility to continue to hold the transparency separately, as at least then you can imwrite('FILENAME.png', imgDeformed, [], Alpha)
You can "clean up" the edges of imgDeformed by weighting it by the Alpha matrix, using the code I already posted,
imgDeformed_cleaned = im2uint8(im2double(imgDeformed) .* im2double(Alpha));
But you then proceed to
file(:, :, 1, i) = imresize(imgDeformed, fileSize);
imresize() is going to mess with edges all over again. You might want to
temp = imresize(imgDeformed, fileSize);
temp_Alpha = imresize(Alpha, fileSize);
cleaned_resized = im2uint8(im2double(temp) .* im2double(temp_Alpha));
file(:, :, 1, i) = cleaned_resized;
but this is likely to still generate edges that are a bit blurry, as the resized Alpha is likely to contain intermediate values between 0 and 255.
You might want to
temp = imresize(imgDeformed, fileSize);
temp_Alpha = round(im2double(imresize(Alpha, fileSize)));
cleaned_resized = im2uint8(im2double(temp) .* temp_Alpha);
file(:, :, 1, i) = cleaned_resized;
This will produce sharp Alpha boundaries in the resized image.

Melden Sie sich an, um zu kommentieren.

Kategorien

Mehr zu Lighting, Transparency, and Shading finden Sie in Help Center und File Exchange

Community Treasure Hunt

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

Start Hunting!

Translated by