How can I force an image to render on the entire axes of a figure?

8 views (last 30 days)
Sometimes I use imshow to view a dataset that has a very high or very low aspect ratio. imshow faithfully displays it in its correct aspect ratio, but it keeps the original image aspect ratio instead of showing data across the full axes if I zoom in with the mouse wheel.
Example code to show the problem I'm trying to address:
data = rand([10,500]);
imshow(data);
Resize the figure window to be roughly square and you'll see the following figure, showing the full image by default.
Now zoom in with your mouse wheel and the "very short but very wide" aspect ratio forces only a tiny slice of the image to show when it would be more helpful to show data across the full axes. The next image shows this. I've added text in paint to show where I want to see data.
Is there a way to change this behavior to always display data across the full area of the figure regardless of the original aspect ratio of that data? Thanks for any help!

Answers (1)

DGM
DGM on 5 Mar 2024
Edited: DGM on 5 Mar 2024
There are various proposed solutions that I can't remember entirely. If I recall, many don't work consistently across different scenarios, so that's why I never bothered keeping track of them. I don't remember if there's a thread about that. I feel like there was, but I doubt I could find it.
This exact horrible problem is why I made imshow2() part of MIMT. It has practical zoom and pan controls and actually fills the figure area when zooming in. It also lets you zoom out further, and it supports a bunch of things imshow() doesn't support.
Is imshow2() an elegant solution? I wouldn't call it elegant.
EDIT:
I recall one of the simple ways:
image(myimage)
axis equal
That at least lets you zoom in, but the view controls are still clumsy as normal, and you're wasting figure area to excessive padding. You could get rid of most of the padding:
image(myimage)
axis equal off
set(gca,'position',[0 0 1 1])
  2 Comments
Jeff
Jeff on 5 Mar 2024
Thanks for the comment. I was hoping I was missing something obvious but it sounds like this is a fundamental limitation of imshow. Honestly I'm a bit shocked that noone at Mathworks has zoomed in on a high aspect ratio image and said "well this looks stupid, we should fix this"...
I took a look at your imshow2 function and there's something I didn't mention in the main post: I also am building a GUI with uiaxes that uses imshow to display images. Your comment at the top of imshow2 says this won't work well.
Do you think a simplified version of your imshow2 function could support your improved zoom functionality without interfering with ui callbacks?
DGM
DGM on 5 Mar 2024
Edited: DGM on 5 Mar 2024
You could try to simplify it, but that's not a bridge I'd suggest to cross unless you're sure that the simpler use of "image(); axis equal off" isn't appropriate.
EDIT: actually, I think the entire aspect ratio handling I did there is buried in the @onresize callback. Off the top of my head, I don't know of a way to work around that that isn't a bigger problem than just trying to use the snippet above.

Sign in to comment.

Products


Release

R2023b

Community Treasure Hunt

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

Start Hunting!