Smallest mask enclosing a polygon
Afficher commentaires plus anciens
I want to find the smallest mask that contains a given polygon (for example the shape of a country).
X = longitude;
Y = latitude;
[Y,X] = meshgrid(Y,X);
shape = some_polygon;
mask = zeros(size(X));
for i =1:size(X,1)
for j = 1:size(X,2)
if inpolygon(X(i,j),Y(i,j),shape(1,:),shape(2,:))
mask(i,j)=1;
end
end
end
X and Y are lon/lat grids.
This would only give me the coordinates that are in or on the polygon, so if I were to plot the given mask and the polygon overlapped, I may have areas inside the polygon that are not filled.
Example of what that would give me :

I'd like to have the (smallest) mask that would completly enclose the polygon and thus not have any white space.
Is there a function for that
2 commentaires
Dyuman Joshi
le 29 Août 2023
Déplacé(e) : Dyuman Joshi
le 30 Août 2023
"Is there a function for that "
Philippe EAR
le 29 Août 2023
Déplacé(e) : Dyuman Joshi
le 30 Août 2023
Réponse acceptée
Plus de réponses (3)
Image Analyst
le 30 Août 2023
1 vote
Perhaps you'd be interested in the attached paper on "Minimum Perimeter Polygon"

KSSV
le 29 Août 2023
You need not to use a loop. If you want fine mask, increase the resolution.
X = longitude;
Y = latitude;
[Y,X] = meshgrid(Y,X);
shape = some_polygon;
% mask = zeros(size(X));
[in,on] = inpolygon(X,Y,shape(1,:),shape(2,:)) ;
mask(i,j)=in|on;
1 commentaire
Philippe EAR
le 29 Août 2023
Image Analyst
le 29 Août 2023
0 votes
Not sure what you're calling mask and what you're calling polygon, but the smallest shape that would enclose the blue shape without any white space would be the blue shape itself.
If you want to smooth boundaries, there is a variety of ways to do that, like with activecontour or by simply blurring the shape and thresholding, or by using imclose
5 commentaires
Philippe EAR
le 29 Août 2023
Image Analyst
le 29 Août 2023
Modifié(e) : Image Analyst
le 29 Août 2023
OK, so the polygon is the perimeter of the blue shape, not the black line.
So the smallest shape is the blue shape itself. That is the shape that will have the smallest area. To have the shape with the smallest perimeter, use convhull.
Is your data a matrix? And do you want the perimeter of the blue shape? If so you can treat the blue France as an image and use bwboundaries to get a list of (x,y) coordinates of the perimeter of the blue, or use bwperim to get the perimeter as an image where it's 1 along the perimeter and zero everywhere else, including inside.
Attach your data in a .mat file if you can.
Dyuman Joshi
le 29 Août 2023
You said this in the problem statement -
"I'd like to have the (smallest) mask that would completly enclose the polygon and thus not have any white space."
And you said this above -
"What I would like is the smallest shape made of square (corresponding to my lon/lat resolution) that completely include the outline of France."
We can't help you if you keep changing what you want to obtain.
What is it that you want? Clarify it properly once.
Also, it will be better to show a rough image of what you want to achieve.
Philippe EAR
le 29 Août 2023
There are 3 shapes separated by a NaN in the list.
This is what I have so far but I don't think we have enough resolution on the grid.
s = load('example.mat')
x = s.example.X;
y = s.example.Y;
shape = s.example.shape;
xs = shape(:, 1);
ys = shape(:, 2);
subplot(1, 2, 1);
plot(xs, ys, 'r-', 'LineWidth', 2)
grid on;
axis equal;
legend
% Shift so that min ia 1 so we can make an image.
xs = xs - min(xs) + 1;
ys = ys - min(ys) + 1;
% Get a digital image
[rows, columns] = size(x)
binaryImage = false(rows, columns);
[rowss, columnss] = size(xs)
% xs and ys are broken into groups separated by NaN. So find each groups.
nanLocations = [1; find(isnan(xs)); rowss]
for k = 1 : length(nanLocations) - 1
index1 = nanLocations(k) + 1;
index2 = nanLocations(k+1) - 1;
fprintf('Getting boundary #%d between %d and %d\n', k, index1, index2);
thisx = xs(index1 : index2);
thisy = ys(index1 : index2);
binaryImage = binaryImage | poly2mask(thisx, thisy, rows, columns);
subplot(1, 2, 2);
imshow(binaryImage)
axis('on', 'xy')
drawnow
end
Catégories
En savoir plus sur Programming dans Centre d'aide et File Exchange
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!






