Why does MATLAB resample display data for *some* large images and not others? Can this be turned off?

12 views (last 30 days)
When displaying large images (i.e. images with dimension greater than the screen resolution) using IMSHOW, IMAGESC, and similar functions, MATLAB will downsample the displayed image (CData not manipulated). However, this only happens when my image has dimension below 2048 pixels (i.e. images with dimension larger than 2048 do not have display data manipulated). This can be demonstrated by simply padding an image just under 2048 pixels and zooming in on an area of high detail. Why? How can this be avoided? Example below.
% Create image with dimension = 2048
im = zeros(2048);
% Draw line pair down center of image
im(:,[1000,1002]) = 1;
% Display and zoom in (no line pair)
figure; imshow(im)
% Display portion of image with dimensions within screen resolution (line pairs visible)
figure; imshow(im(1:1010,1:1010))
% Create new image with dimension = 2049 (or larger)
im2 = zeros(2049);
% Draw line pair down center of image
im2(:,[1000,1002]) = 1;
% Display and zoom in (line pair now visible)
figure; imshow(im2)

Answers (1)

Image Analyst
Image Analyst on 11 Jan 2017
I think it just depends on what rows and columns it decides to use when it does the resampling. For one case it might decide to use column 1000 with the line and you'll see it, and in another case it might decide to use column 1001 with no line and not use the 1000 line, so the line doesn't show up. It's downsampling in both cases, it's just using different sets of pixels.
  5 Comments
Image Analyst
Image Analyst on 12 Jan 2017
Something's gone wrong with their attachment thing. I definitely attached it and now it's gone. Plus, I've tried 4 times to attach it just now with the paperclip icon, and it won't take it. It doesn't give any error message or anything, it just doesn't do the attachment. It must be a bug. I'll tell Rena about this tomorrow. In the meantime, here is the demo I got from the Mathworks, with slight modifications by me.
clc; % Clear the command window.
close all; % Close all figures (except those of imtool.)
imtool close all; % Close all imtool figures if you have the Image Processing Toolbox.
clear; % Erase all existing variables. Or clearvars if you want.
workspace; % Make sure the workspace panel is showing.
format long g;
format compact;
fontSize = 13;
% IMSHOW has historically had this behavior all the way back to 1993, that is, it shows the whole image.
% If it can show the whole image at “truesize” or more recently called 100, it does,
% but if not, it shows the whole image.
% When we introduced IMTOOL and IMSCROLLPANEL, there’s more flexibility with the display
% because the scroll panel shows you that there is more image there beyond what you can see.
% Have you tried using IMSCROLLPANEL in combination with IMSHOW? See example below or in:
% doc imscrollpanel
%
% It allows you to directly set the magnification, programmatically or through a magnification box.
% When we created IMSCROLLPANEL and the associated magnification controls in IPT5, we hoped that they would satisfy exactly this GUI use case.
%
% Let me know what you think if you try it or if you've tried it in the past, why it doesn't meet your needs.
% We're open to discussing this further with you to see if we can fix the issue or make the better solution easier to discover if it's indeed adequate.
% Here's the example from the documentation:
% Create a scroll panel with a Magnification Box and an Overview tool.
hFig = figure('Toolbar','none',...
'Menubar','none');
hIm = imshow('saturn.png');
hSP = imscrollpanel(hFig,hIm); % Handle to scroll panel.
set(hSP,'Units','normalized',...
'Position',[0 .1 1 .9])
% Add a Magnification Box and an Overview tool.
hMagBox = immagbox(hFig,hIm);
pos = get(hMagBox,'Position');
set(hMagBox,'Position',[0 0 pos(3) pos(4)])
imoverview(hIm)
% Get the scroll panel API to programmatically control the view.
api = iptgetapi(hSP);
% Get the current magnification and position.
mag = api.getMagnification();
r = api.getVisibleImageRect();
% View the top left corner of the image.
message = sprintf('Click OK to view the top left corner of the image');
button = questdlg(message, 'Continue?', 'OK', 'Quit', 'OK');
drawnow; % Refresh screen to get rid of dialog box remnants.
if strcmpi(button, 'Quit')
return;
end
api.setVisibleLocation(0.5,0.5)
% Change the magnification to the value that just fits.
message = sprintf('Click OK to change the magnification to the value that just fits');
button = questdlg(message, 'Continue?', 'OK', 'Quit', 'OK');
drawnow; % Refresh screen to get rid of dialog box remnants.
if strcmpi(button, 'Quit')
return;
end
api.setMagnification(api.findFitMag())
% Zoom in to 1600% on the dark spot.
message = sprintf('Click OK to zoom in to 1600%%on the dark spot.');
button = questdlg(message, 'Continue?', 'OK', 'Quit', 'OK');
drawnow; % Refresh screen to get rid of dialog box remnants.
if strcmpi(button, 'Quit')
return;
end
api.setMagnificationAndCenter(16,306,800)
% Zoom in to 100% with upper left showing.
message = sprintf('Click OK to zoom in to exactly 100%%.');
button = questdlg(message, 'Continue?', 'OK', 'Quit', 'OK');
drawnow; % Refresh screen to get rid of dialog box remnants.
if strcmpi(button, 'Quit')
return;
end
api.setMagnificationAndCenter(1,1,100)
Jered Wells
Jered Wells on 12 Jan 2017
Edited: Jered Wells on 12 Jan 2017
Image Analyst, thank you very much for your suggestion. I tried it with one modification - I used my own (problematic) image. See attachments (if they upload). I completely understand that displayed image quality cannot exceed the resolution limits of the display device. However, zooming to 1:1 (i.e. one image pixel to one display pixel) should provide a displayed image ROI with resolution matching the original image data. The problem (bug?) I've noted is that this only happens when the original image has dimensions greater than 2048 pixels or less than the screen resolution! The attachments show this very problem using the code you provided (1600% zoom). My original (2021x2021) DICOM image (read using DICOMREAD), even with extreme zoom, shows a poorly resolved bar phantom. However, the same image padded with 20 "zeros" on all sides (2061x2061) yields a faithful representation of the original image data when zoomed. There must be an exception built into MATLAB's core image display code - weather intentional or not - since this problem exists with all manner of image display functions (IMTOOL, IMAGESC, IMSHOW, etc.). Furthermore, there is something special about image dimension 2048. I suspect that it has to do with my monitor resolution being 1920x1080 and 2048 being the next highest power of two (2^11). What's even more interesting is that truncating the original 2021x2021 image so that the default display size falls at different %-ages (e.g. 33%, 50%) relative to my display resolution yields different subsampling! At 33% default zoom, I see 3x3 regions of displayed pixels with the same value, and at 50% default zoom, there are 2x2 regions of identical pixel values observed when zooming. I suspect this is a result of some nearest neighbor interpolation of the CData prior to display.
Now, I could just go pad all my images to get them over the 2048 pixel limit (or reduce my monitor resolution to be less than the minimum size of the images I intend to display), but I'm not interested in doing that. I would be more interested in helping to find the root cause of this buggy functionality. I'd be happy to take up the discussion offline with you or MATLAB is that is of more use. Otherwise, happy to continue here. Again, appreciative of your expertise.

Sign in to comment.

Categories

Find more on Convert Image Type in Help Center and File Exchange

Products

Community Treasure Hunt

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

Start Hunting!