📄 rest_sliceviewer.m
字号:
AConfig.hAxesColorbar =hAxesColorbar;
AConfig.hImageColorbar =hImageColorbar;
%Overlay Configuration
%Data for Overlay
AConfig.Overlay.Filename ='';
AConfig.Overlay.Volume =zeros(61, 73, 61);
AConfig.Overlay.VolumeThrd =AConfig.Overlay.Volume;%Volume Thresholded by Cluster Size
AConfig.Overlay.VoxelSize=[3 3 3];
AConfig.Overlay.Origin =[31 43 25];
%Overlay's Info - statistics
Result.Overlay.MinNegative =-Inf;
Result.Overlay.MaxNegative =0;
Result.Overlay.MinPositive =0;
Result.Overlay.MaxPositive =Inf;
Result.Overlay.AbsMin =0;
Result.Overlay.AbsMax =Inf;
%Options for Overlay
AConfig.Overlay.Colormap =jet(64);
AConfig.Overlay.ColorbarCmd ='jet(64)';
%[0 0 1;1 0 0]; %Pure Blue and Pure Red
%[0 0 0.5625;0 0 0.875;0 0 1;1 0 0;0.875 0 0;0.5 0 0];
AConfig.Overlay.Opacity =1; %Default, 50% Opacity
AConfig.Overlay.LabelColor ='white';
AConfig.Overlay.ValueThrdAbsolute =0; %Default, show all
AConfig.Overlay.ValueThrdMin = -Inf; %Default, show all, not absolute, may be negative
AConfig.Overlay.ValueThrdMax = Inf; %Default, show all, not absolute , may be negative, this allows me to set a range such as showing negative values only or positives only
AConfig.Overlay.ValueThrdSeries = NaN; %Default, show all
AConfig.Overlay.ClusterSizeThrd =0; %Default, 0 voxels, for not confining cluster-size
AConfig.Overlay.ClusterRadiusThrd =0; %Default radius(mm) for Cluster size definition
AConfig.Overlay.InfoAal='None'; %AAL descriptions
%Load Recent Images/brains
AConfig =InitRecent(AConfig);
%Save Axes's handles
AConfig.hAxesSagittal =-1;
AConfig.hAxesCoronal =-1;
AConfig.hAxesTransverse =-1;
%Save Images' handles
AConfig.hImageSagittal =-1;
AConfig.hImageCoronal =-1;
AConfig.hImageTransverse =-1;
%Save Lines' handles
AConfig.hXLineSagittal =-1; %x
AConfig.hYLineSagittal =-1; %y
AConfig.hXLineCoronal =-1; %x
AConfig.hYLineCoronal =-1; %y
AConfig.hXLineTransverse =-1; %x
AConfig.hYLineTransverse =-1; %y
AConfig.LastPosition =[90 126 72]; %Default
AConfig.LastAxes ='Transverse'; %For slice previous/next by pressing up/down left/right j/k ... on keyboard
AConfig.LastSavedMask =''; %For ROI define callback
AConfig =InitUnderlay(AConfig);
%Move Auto-Balance out of initialization just for speeding up for starting this slice-viewer
%Save Maping Image parameters, Auto balance 20070911 revised
% theSatMin=0; theSatMax =0; nBins=2^16; %Satuation Min/Max
% theMaxVal=max(AConfig.Volume(:));
% if theMaxVal<257,
% nBins =256;
% else
% nBins =theMaxVal;
% end
% theSum =histc(AConfig.Volume(:), [1:nBins]);
% theSum =cumsum(theSum);
% theCdf =theSum/theSum(end);
% if rest_misc('GetMatlabVersion')>=7.3
% idxSatMin =find(theCdf>0.01, 1, 'first');
% idxSatMax =find(theCdf>=0.99, 1, 'first');
% else
% idxSatMin =find(theCdf>0.01);
% idxSatMin =idxSatMin(1);
% idxSatMax =find(theCdf>=0.99);
% idxSatMax =idxSatMax(1);
% end
% idxSatMin =find(theCdf>0.01, 1, 'first');
% idxSatMax =find(theCdf>=0.99, 1, 'first');
% theSatMin =(idxSatMin-1)/(nBins-1) *theMaxVal;
% theSatMax =(idxSatMax-1)/(nBins-1) *theMaxVal;
% AConfig.Contrast.GrayDepth =256;
% AConfig.Contrast.SatMax =theSatMax;
% AConfig.Contrast.SatMin =theSatMin;
%20070911, AutoBalance for contrast
% AConfig.Contrast.WindowWidth =theSatMax -theSatMin;
% AConfig.Contrast.WindowCenter=(theSatMax +theSatMin)/2;
%For debugging, 20070911
% disp(AConfig.Contrast);
%%Update the figure, the follow function called order shouldn't change
%Display Images
AConfig =SetImage(AConfig);
Result =AConfig;
return;
function Result =DeleteFigure(AGlobalConfig, AFigHandle)
x =ExistViewer(AGlobalConfig, AFigHandle);
if x>0,
theDisplayCount =GetDisplayCount(AGlobalConfig);
isExistFig =rest_misc( 'ForceCheckExistFigure' , AGlobalConfig.Config(x).hFig);
if isExistFig,
%Save the recent menu
rest_sliceviewer('SaveRecent', AFigHandle);
%Delete the figure and rearrange the queue
delete(AGlobalConfig.Config(x).hFig);
if theDisplayCount>x
for y=x:theDisplayCount-1
AGlobalConfig.Config(x) =AGlobalConfig.Config(x+1);
end
end
AGlobalConfig.Config(theDisplayCount)=[];
end
end
Result =AGlobalConfig;
function Result =GetDisplayCount(AGlobalConfig)
%Get the Count of display, this program allow multi-view of brain like MRIcro
if isempty(AGlobalConfig) || isempty(AGlobalConfig.Config),
Result =0;
else
Result =length(AGlobalConfig.Config);
end
return;
function Result =ListViewerFigure(AGlobalConfig, AFilename)
Result =[];
if (isstruct(AGlobalConfig) && isstruct(AGlobalConfig.Config))
for x=1:length(AGlobalConfig.Config)
if strcmpi( AGlobalConfig.Config(x).Filename, AFilename)
Result =[Result; AGlobalConfig.Config(x).hFig];
end
end
else
return;
end
function Result =ExistViewer(AGlobalConfig, AFigureHandle)
Result =0;
if (isstruct(AGlobalConfig) && isstruct(AGlobalConfig.Config))
for x=1:length(AGlobalConfig.Config)
if AGlobalConfig.Config(x).hFig==AFigureHandle,
Result =x;
return;
end
end
else
return;
end
function Result =SetImage(AConfig)
if strcmpi(AConfig.ViewMode, 'Orthogonal'),
Result =SetView_Orthogonal(AConfig);
elseif strcmpi(AConfig.ViewMode, 'Transverse'),
Result =SetView_Transverse(AConfig);
elseif strcmpi(AConfig.ViewMode, 'Sagittal'),
Result =SetView_Sagittal(AConfig);
elseif strcmpi(AConfig.ViewMode, 'Coronal'),
Result =SetView_Coronal(AConfig);
end
%Draw the color bar
Result =DrawColorbar(Result);
set(AConfig.hFig, 'Name', sprintf('Slice Viewer -- REST %s',rest_misc( 'GetRestVersion')));
%Display Underlay Filename
set(AConfig.hUnderlayFile, 'String', sprintf('%s', AConfig.Filename));
%Display Overlay Filename
set(AConfig.hOverlayFile, 'String', sprintf('%s', AConfig.Overlay.Filename));
%Show Voxel's position [x y z]
ShowPositionInEdit(AConfig);
%Update the message
SetMessage(AConfig);
%Resize figure width and height
ResizeFigure(AConfig);
function Result =SetView_Orthogonal(AConfig)
%Underlay Image manuplication, 20070913
theSagittalImg =GetGrayImage('Sagittal', AConfig.Volume, AConfig.LastPosition(1)); %x
theCoronalImg =GetGrayImage('Coronal', AConfig.Volume, AConfig.LastPosition(2)); %y
theTransverseImg =GetGrayImage('Transverse', AConfig.Volume, AConfig.LastPosition(3));%z
%Auto balance
theSagittalImg =SaturateContrast(theSagittalImg, AConfig.Contrast.SatMin, AConfig.Contrast.SatMax);
theCoronalImg =SaturateContrast(theCoronalImg, AConfig.Contrast.SatMin, AConfig.Contrast.SatMax);
theTransverseImg =SaturateContrast(theTransverseImg, AConfig.Contrast.SatMin, AConfig.Contrast.SatMax);
%Calculate the Result Image after Magnifying
theMagnifyCoefficient =GetMagnifyCoefficient(AConfig);
if license('test','image_toolbox')==1 && theMagnifyCoefficient~=1,
theSagittalImg =imresize(theSagittalImg, theMagnifyCoefficient);
theCoronalImg =imresize(theCoronalImg, theMagnifyCoefficient);
theTransverseImg=imresize(theTransverseImg, theMagnifyCoefficient);
end
% Revise the Axes position to make it comfort to Magnify
theFramePosParamSet =get(AConfig.hFrameSetPos, 'Position');
theLeft =theFramePosParamSet(1) +theFramePosParamSet(3) +5;
theBottom =10; %theFramePosParamSet(2);
theLeftTransverse =theLeft;
theLeftCoronal =theLeftTransverse;
theLeftSagittal =theLeftCoronal +size(theCoronalImg,2)+ 2;
theBottomTransverse =theBottom;
theBottomCoronal =theBottomTransverse +size(theTransverseImg,1) +2;
theBottomSagittal =theBottomCoronal;
thePosTransverse =[theLeftTransverse, theBottomTransverse, size(theTransverseImg,2), size(theTransverseImg,1)];
thePosCoronal =[theLeftCoronal, theBottomCoronal, size(theCoronalImg,2), size(theCoronalImg,1)];
thePosSagittal =[theLeftSagittal, theBottomSagittal, size(theSagittalImg,2), size(theSagittalImg,1)];
clear theFramePosParamSet theLeft theBottom
clear theLeftTransverse theLeftCoronal theLeftSagittal
clear theBottomTransverse theBottomCoronal theBottomSagittal
% Show Images
%Clear Text labels first
ClearTextLabels(AConfig);
%Set Default color map for only Underlay
%colormap(gray(AConfig.Contrast.GrayDepth));
%Map images to true color
theSagittalImg =repmat(theSagittalImg, [1 1 3]);
theCoronalImg =repmat(theCoronalImg, [1 1 3]);
theTransverseImg =repmat(theTransverseImg, [1 1 3]);
%Add Overlay Images
if SeeOverlay(AConfig),
theSagittalImg =AddOverlay('Sagittal' ,AConfig, theSagittalImg);
theCoronalImg =AddOverlay('Coronal', AConfig, theCoronalImg);
theTransverseImg =AddOverlay('Transverse', AConfig, theTransverseImg);
end
%Sagittal
set(AConfig.hImageSagittal, 'CData', (theSagittalImg), 'HitTest', 'off','Visible', 'on');
set(AConfig.hAxesSagittal,'Visible', 'on', ...
'XLim', [1 size(theSagittalImg,2)], ...
'YLim', [1 size(theSagittalImg,1)] , ...
'Position', thePosSagittal);
set(AConfig.hXLineSagittal, 'HitTest','off','Visible', IsCrosshairChecked(AConfig), ...
'XData', [1 size(theSagittalImg,2)] , ...
'YData', [1 1]*AConfig.LastPosition(3) * theMagnifyCoefficient);%Parallel to X-axis
set(AConfig.hYLineSagittal, 'HitTest','off','Visible', IsCrosshairChecked(AConfig), ...
'XData', [1 1]*AConfig.LastPosition(2) * theMagnifyCoefficient, ...
'YData', [1 size(theSagittalImg,1)] );%Parallel to Y-axis
%Coronal
set(AConfig.hImageCoronal, 'CData', (theCoronalImg), 'HitTest', 'off','Visible', 'on');
%colormap(gray(AConfig.Contrast.GrayDepth));
set(AConfig.hAxesCoronal, 'Visible', 'on',...
'XLim', [1 size(theCoronalImg,1)], ...
'YLim', [1 size(theCoronalImg,2)], ...
'Position', thePosCoronal);
set(AConfig.hXLineCoronal, 'HitTest','off','Visible', IsCrosshairChecked(AConfig), ...
'XData', [1 size(theCoronalImg,2)] , ...
'YData', [1 1]*AConfig.LastPosition(3) * theMagnifyCoefficient );%Parallel to X-axis
set(AConfig.hYLineCoronal, 'HitTest','off','Visible', IsCrosshairChecked(AConfig), ...
'XData', [1 1]*AConfig.LastPosition(1) * theMagnifyCoefficient , ...
'YData', [1 size(theCoronalImg,1)] );%Parallel to Y-axis
%Transverse
set(AConfig.hImageTransverse, 'CData', (theTransverseImg), 'HitTest', 'off','Visible', 'on');
% colormap(gray(AConfig.Contrast.GrayDepth));
set(AConfig.hAxesTransverse,'Visible', 'on', ...
'XLim', [1 size(theTransverseImg,2)], ...
'YLim', [1 size(theTransverseImg,1)], ...
'Position', thePosTransverse);
set(AConfig.hXLineTransverse, 'HitTest','off','Visible', IsCrosshairChecked(AConfig), ...
'XData', [1 size(theTransverseImg,2)] , ...
'YData', [1 1]*AConfig.LastPosition(2) * theMagnifyCoefficient );%Parallel to X-axis
set(AConfig.hYLineTransverse, 'HitTest','off','Visible', IsCrosshairChecked(AConfig), ...
'XData', [1 1]*AConfig.LastPosition(1) * theMagnifyCoefficient , ...
'YData', [1 size(theTransverseImg,1)] );%Parallel to Y-axis
%Reset View Series
AConfig.ViewSeries =[];
Result =AConfig;
function Result =SetView_Transverse(AConfig)
[nDim1 nDim2 nDim3] =size(AConfig.Volume);
theCenterZ =AConfig.LastPosition(3);
theCount =AConfig.Montage.Across *AConfig.Montage.Down ;
theZSeries =theCenterZ -([(floor(theCount/2)) : -1 :(ceil(-theCount/2))]) *AConfig.Montage.Spacing;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -