Effacer les filtres
Effacer les filtres

imcrop not correct problem

4 vues (au cours des 30 derniers jours)
Yu Li
Yu Li le 4 Jan 2019
I export a figure with 2*3 subplot, the unit of each subplot is 'pixel', meanwhile, I export the position of each subplots.
then, I import the figure using 'imread', and use 'imcrop' function to cut it into 6 seperature figures, using the saved position previously. but the result is not what I want. I guess this may be due to the 'pixel' unit from subplot, but I do not know how to fix this problem.
is there any way to solve this problem?
Thanks!
Yu
  2 commentaires
KSSV
KSSV le 4 Jan 2019
YOu can use imcrop to crop manually ....did you try that?
Yu Li
Yu Li le 4 Jan 2019
Modifié(e) : Yu Li le 4 Jan 2019
yes I know I can do it mannually, but I want to export the 2*3 figure, and use the position to seperate it automatically. this may save some workload.
Thanks!
Yu

Connectez-vous pour commenter.

Réponses (1)

Walter Roberson
Walter Roberson le 4 Jan 2019
There is an off-by-one error in the crop boundaries for imcrop. I wrote this up about 15 months ago:
=== begin report
The cropping rectangle used by imcrop does not have the same meaning as any other cropping rectangle in MATLAB.
I = imread('circuit.tif');
mask = I < 29;
stats = regionprops(mask,'bounding');
cropped = imcrop(I, stats(1).BoundingBox);
any(cropped(:,1:end-1)<29,2).'
ans =
1×75 logical array
Columns 1 through 40
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
Columns 41 through 75
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 0
any(cropped(1:end-1,:)<29,1)
ans =
1×31 logical array
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 0
stats(1).BoundingBox
ans =
0.5 0.5 30 74
size(cropped)
ans =
75 31
That is, regionprops determined that the bounding box was 30 wide by 74 high, but when that cropping rectangle is passed into imcrop, a 31 wide by 75 high rectangle is returned. We could hypothesize that the bounding box returned by regionprops does not include the last edge and thus hypothesize that imcrop is extracting the "right" portion to include just the bounding box, but the pair of any() that I show above shows that in fact the last row and the last column extracted are outside the bounding box.
regionprops documents
width specifies the width of the bounding box along each dimension in the form [x_width y_width ...]
Likewise, if you look at the figure Position property documentation
width Distance between the right and left inner edges of the figure.
height Distance between the top and bottom inner edges of the figure.
imcrop documents
Size and position of the crop rectangle, specified as a four-element position vector of the form [xmin ymin width height].
It does not document exactly the width and height measure there, but we are given no reason to expect it would be different than what width and height measures for regionprops or Position properties for graphics objects would measure.
This problem goes back to at least R2012a (just tested.)
I suspect that this issue has to do with the fact that in images on the display, that coordinates refer to pixel _centres_and thus by default an image N pixels wide has a left boundary of 0.5 and a right boundary of N+0.5. Someone might get confused and say that the total distance is 0.5+N+0.5, but that is incorrect: the coordinate distances is (N+0.5)-(0.5) = N.
For example with 5 pixels, let the digits below be number of _halfs_ and the + represent pixel centers and the | represent pixel boundaries:
1 3 5 7 9 11
| + | + | + | + | + |
5 +'s, 5 pixels, left edge 1/2, right edge 11/2, coordinate distance (11/2)-(1/2) = 10/2 = 5
It would be easy to think that one had to add +1 to that to get the right count, but that is not the case for coordinates: distance by coordinates is pure subtraction of coordinates.
If you were to image() a 1 x 5 vector, the XData would be [1 5], and when you want to calculate the width of that you do need to add 1 to the subtraction, but that would be [5 - 1]+1 = 4+1 = 5 same as the distance between the pixel edge coordinates.
Even if there was somehow some good reason to add 1 to the size to compensate for XData and YData representing pixel centers, clearly that +1 should only be applied in the case of interactive cropping or somehow cropping from an image graphics object, and should NOT be applied when the image is passed in as an array.

Community Treasure Hunt

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

Start Hunting!

Translated by