Authored by Francois Tadel

Massive code scrubbing

Too many changes to show.

To preserve performance only 15 of 15+ files are displayed.

... ... @@ -78,10 +78,10 @@ Fmenu = figure('IntegerHandle','off',...
'Color',[1 1 1]*.8,...
'UserData',struct('SPMver',SPMver,'SPMc',SPMc),...
'MenuBar','none',...
'DefaultTextFontName',PF.helvetica,...
'DefaultTextFontSize',FS(10),...
'DefaultUicontrolFontName',PF.helvetica,...
'DefaultUicontrolFontSize',FS(12),...
... 'DefaultTextFontName',PF.helvetica,...
'DefaultTextFontSize',FS(8),...
... 'DefaultUicontrolFontName',PF.helvetica,...
'DefaultUicontrolFontSize',FS(8),...
'DefaultUicontrolInterruptible','on',...
'Renderer','painters',...
'Visible','on', ...
... ... @@ -100,7 +100,6 @@ uicontrol(Fmenu,'Style','Text',...
'Position',[025 410 350 020].*WS,...
'ForegroundColor','k',...
'FontAngle','Italic',...
'FontSize',FS(10),...
'HorizontalAlignment','Left',...
'Tag', 'EEG')
... ... @@ -112,7 +111,6 @@ uicontrol(Fmenu,'Style','Text',...
'Position',[025 315 350 020].*WS,...
'ForegroundColor','k',...
'FontAngle','Italic',...
'FontSize',FS(10),...
'HorizontalAlignment','Left',...
'Tag', 'EEG')
... ... @@ -124,7 +122,6 @@ uicontrol(Fmenu,'Style','Text',...
'String','Display',...
'Position',[025 270 350 020].*WS,...
'ForegroundColor','k',...
'FontSize',FS(10),...
'FontAngle','Italic',...
'HorizontalAlignment','Left',...
'Tag', 'EEG')
... ... @@ -137,7 +134,6 @@ uicontrol(Fmenu,'Style','Text',...
'Position',[025 175 350 020].*WS,...
'ForegroundColor','k',...
'FontAngle','Italic',...
'FontSize',FS(10),...
'HorizontalAlignment','Left',...
'Tag', 'EEG')
... ... @@ -145,7 +141,7 @@ uicontrol(Fmenu,'Style','Text',...
'String','SPM Intracerebral EEG Toolbox',...
'ToolTipString','modality & defaults set for EEG/MEG',...
'ForegroundColor',[1 1 1]*.6,'BackgroundColor',[1 1 1]*.8,...
'FontName',PF.times,'FontAngle','Italic','FontWeight','Bold',...
'FontAngle','Italic','FontWeight','Normal','FontSize',FS(10),...
'HorizontalAlignment','center',...
'Position',[020 122 360 020].*WS,...
'Tag','EEG','Visible','on')
... ... @@ -161,7 +157,6 @@ uicontrol(Fmenu,'Style','Text','String',SPMc,...
'ForegroundColor',[1 1 1]*.6,...
'BackgroundColor',[1 1 1]*.8,...
'FontName',PF.times,...
'FontSize',FS(10),...
'HorizontalAlignment','center',...
'Position',[020 002 360 008].*WS)
... ... @@ -170,59 +165,56 @@ uicontrol(Fmenu,'Style','Text','String',SPMc,...
%-Data
%-----------------------------------------------------------------------
uicontrol(Fmenu,'String','Convert',...
'Position',[035 380 100 030].*WS,...
'ToolTipString','Convert data in SPM EEG format',...
'FontSize',FS(10),...
'UserData','ImaGIN_spm_eeg_converteeg2mat',...
'CallBack','ImaGIN_spm_eeg_converteeg2mat;',...
'Tag', 'EEG',...
'Visible','on')
uicontrol(Fmenu,'Style','PopUp',...
'String','Import| Convert| Events| Electrodes positions| Bipolar montage',...
'Position',[035 380 100 030].*WS,...
'FontSize', FS(9), ...
'ToolTipString', 'Convert data in SPM EEG format',...
'CallBack','spm(''PopUpCB'',gcbo)',...
'UserData',{'ImaGIN_spm_eeg_converteeg2mat;','ImaGIN_Events;','ImaGIN_Electrode;','ImaGIN_BipolarMontage;'},...
'Tag', 'EEG');
uicontrol(Fmenu,'String','Montage',...
'Position',[035 345 100 030].*WS,...
'ToolTipString',['Create a new SPM montage file from two text files' 10 '(names and positions of the electrodes)'],...
'FontSize',FS(10),...
'UserData','ImaGIN_Montage',...
'CallBack','ImaGIN_Montage(1);',...
'Tag', 'EEG',...
'Visible','on');
uicontrol(Fmenu,'String','Events',...
'Position',[150 380 100 030].*WS,...
'ToolTipString','Add or remove events',...
'FontSize',FS(10),...
'UserData','ImaGIN_Events',...
'CallBack','ImaGIN_Events;',...
'Tag', 'EEG',...
'Visible','on');
uicontrol(Fmenu,'Style','PopUp',...
'String','Preprocess| Bandpass filter| Notch filter| Downsample',...
'Position',[150 380 100 030].*WS,...
'FontSize', FS(9), ...
'ToolTipString','Other preprocessing functions',...
'CallBack','spm(''PopUpCB'',gcbo)',...
'UserData',{'ImaGIN_BPFilter;','ImaGIN_NotchFilter;','ImaGIN_spm_eeg_downsample;'},...
'Tag', 'EEG')
uicontrol(Fmenu,'Style','PopUp',...
'String','Display| ImaGIN viewer| SPM viewer',...
'Position',[265 380 100 030].*WS,...
'FontSize', FS(9), ...
'ToolTipString','Other preprocessing functions',...
'CallBack','spm(''PopUpCB'',gcbo)',...
'UserData',{'ImaGIN_DispData;','spm_eeg_review;'},...
'Tag', 'EEG')
uicontrol(Fmenu,'String','Time zero',...
'Position',[150 345 100 030].*WS,...
'Position',[035 345 100 030].*WS,...
'ToolTipString','Define time origin compared to a pre-defined event',...
'FontSize',FS(10),...
'UserData','ImaGIN_TimeZero',...
'CallBack','ImaGIN_TimeZero;',...
'Tag', 'EEG',...
'Visible','on');
uicontrol(Fmenu,'String','Epoch',...
'Position',[265 380 100 030].*WS,...
'Position',[150 345 100 030].*WS,...
'ToolTipString','Select a time window according to pre-defined events and overwrite a new (smaller) data set',...
'FontSize',FS(10),...
'UserData','ImaGIN_Crop',...
'CallBack','ImaGIN_Crop;',...
'Tag', 'EEG',...
'Visible','on');
uicontrol(Fmenu,'Style','PopUp',...
'String','Pre-process...| Bandpass filter| Notch filter| Downsample',...
'Position',[265 345 100 030].*WS,...
'ToolTipString','Other preprocessing functions',...
'FontSize',FS(10),...
'CallBack','spm(''PopUpCB'',gcbo)',...
'UserData',{'ImaGIN_BPFilter;','ImaGIN_NotchFilter;','ImaGIN_spm_eeg_downsample;'},...
'Tag', 'EEG')
uicontrol(Fmenu,'String','Montage',...
'Position',[265 345 100 030].*WS,...
'ToolTipString',['Create a new SPM montage file from two text files' 10 '(names and positions of the electrodes)'],...
'UserData','ImaGIN_Montage',...
'CallBack','ImaGIN_Montage(1);',...
'Tag', 'EEG',...
'Visible','on');
% Spatial EEG
%-----------------------------------------------------------------------
... ... @@ -230,7 +222,6 @@ uicontrol(Fmenu,'Style','PopUp',...
'String','FFT| Compute',...
'Position',[25 290 50 030].*WS,...
'ToolTipString','Power spectrum density',...
'FontSize',FS(10),...
'CallBack','spm(''PopUpCB'',gcbo)',...
'UserData',{'ImaGIN_FFT;'},...
'Tag', 'EEG')
... ... @@ -239,33 +230,29 @@ uicontrol(Fmenu,'Style','PopUp',...
'String','Time Freq| Compute| Normalise| Rescale| Average',...
'Position',[85 290 65 030].*WS,...
'ToolTipString','Time frequency analysis (power and synchrony)',...
'FontSize',FS(10),...
'CallBack','spm(''PopUpCB'',gcbo)',...
'UserData',{'ImaGIN_spm_eeg_tf;','ImaGIN_NormaliseTF;','ImaGIN_RescaleTF;','ImaGIN_AverageTF;'},...
'Tag', 'EEG')
uicontrol(Fmenu,'Style','PopUp',...
'String','Causality| Compute| Normalise| Average',...
'String','Causality| Compute| Average',...
'Position',[160 290 65 030].*WS,...
'ToolTipString','Causality analysis',...
'FontSize',FS(10),...
'CallBack','spm(''PopUpCB'',gcbo)',...
'UserData',{'ImaGIN_causality_compute;','ImaGIN_causality_normalise;','ImaGIN_causality_average;'},...
'UserData',{'ImaGIN_causality_compute;','ImaGIN_causality_average;'},...
'Tag', 'EEG')
uicontrol(Fmenu,'Style','PopUp',...
'String','Firing rate| Compute| Normalise| Average',...
'String','Firing rate| Compute',...
'Position',[235 290 65 030].*WS,...
'ToolTipString','Firing rate',...
'FontSize',FS(10),...
'CallBack','spm(''PopUpCB'',gcbo)',...
'UserData',{'ImaGIN_spike_compute;','ImaGIN_spike_normalise;','ImaGIN_spike_average;'},...
'UserData',{'ImaGIN_spike_compute;'},...
'Tag', 'EEG')
uicontrol(Fmenu,'String','3D interpolation',...
'Position',[310 300 65 030].*WS,...
'ToolTipString', '3D interpolation of EEG intracerebral data',...
'FontSize',FS(10),...
'UserData','ImaGIN_spm_eeg_TF_images_3D;',...
'CallBack','ImaGIN_spm_eeg_TF_images_3D;',...
'Visible','on',...
... ... @@ -275,7 +262,6 @@ uicontrol(Fmenu,'String','3D interpolation',...
%-----------------------------------------------------------------------
uicontrol(Fmenu,'String','Montage',...
'Position',[25 240 110 030].*WS,...
'FontSize',FS(10),...
'ToolTipString','Display montage',...
'UserData','ImaGIN_Montage',...
'CallBack','ImaGIN_Montage(2);',...
... ... @@ -283,7 +269,6 @@ uicontrol(Fmenu,'String','Montage',...
uicontrol(Fmenu,'String','Data',...
'Position',[25 205 110 030].*WS,...
'FontSize',FS(10),...
'ToolTipString','Display data',...
'UserData','ImaGIN_DispData',...
'CallBack','ImaGIN_DispData;',...
... ... @@ -291,7 +276,6 @@ uicontrol(Fmenu,'String','Data',...
uicontrol(Fmenu,'String','Time Frequency',...
'Position',[145 240 110 030].*WS,...
'FontSize',FS(10),...
'ToolTipString','Display time frequency analysis',...
'UserData','ImaGIN_DispTF',...
'CallBack','ImaGIN_DispTF',...
... ... @@ -300,7 +284,6 @@ uicontrol(Fmenu,'String','Time Frequency',...
uicontrol(Fmenu,'String','Brain overlay',...
'Position',[145 205 110 030].*WS,...
'ToolTipString', '3D EEG intracerebral data overlaid on a brain',...
'FontSize',FS(10),...
'UserData','ImaGIN_Disp3D;',...
'CallBack','ImaGIN_Disp3D;',...
'Visible','on',...
... ... @@ -308,7 +291,6 @@ uicontrol(Fmenu,'String','Brain overlay',...
uicontrol(Fmenu,'String','Causality',...
'Position',[265 240 110 030].*WS,...
'FontSize',FS(10),...
'ToolTipString','Display causality analysis',...
'UserData','ImaGIN_DispCausality',...
'CallBack','ImaGIN_DispCausality',...
... ... @@ -316,8 +298,8 @@ uicontrol(Fmenu,'String','Causality',...
uicontrol(Fmenu,'String','Results',...
'Position',[130 160 130 030].*WS,...
'FontSize',FS(9), ...
'ToolTipString','Inference and regional responses etc.',...
'FontSize',FS(10),...
'UserData','spm_results_ui',...
'CallBack','[hReg,xSPM,SPM] = spm_results_ui;',...
'Tag', 'EEG');
... ... @@ -328,17 +310,15 @@ uicontrol(Fmenu,'Style','PopUp',...
'String','Display...|images|M/EEG',...
'Position',[020 088 082 024].*WS,...
'ToolTipString','orthogonal sections and M/EEG display',...
'FontSize',FS(9),...
'CallBack','spm(''PopUpCB'',gcbo)',...
'UserData',{ 'spm_jobman(''serial'','''',''jobs.util.disp'');','spm_eeg_review;'},...
'UserData',{'spm_image;','spm_eeg_review;'},...
'Tag', 'EEG')
uicontrol(Fmenu,'String','Check Reg',...
'Position',[112 088 083 024].*WS,...
'ToolTipString','check image registration',...
'FontSize',FS(9),...
'UserData','jobs.util.checkreg',...
'CallBack','spm_jobman(''serial'','''',''jobs.util.checkreg'');')
'UserData','spm_check_registration',...
'CallBack','spm_check_registration;')
uicontrol(Fmenu,'Style','PopUp',...
'String',Modalities,...
... ... @@ -363,45 +343,33 @@ uicontrol(Fmenu,'Style','PopUp',...
uicontrol(Fmenu,'String','Seizure detect',...
'Position',[020 054 083 024].*WS,...
'ToolTipString','Detect seizure and write a time series in a new channel',...
'FontSize',FS(9),...
'UserData','ImaGIN_SeizureDetect',...
'CallBack','ImaGIN_SeizureDetect;')
uicontrol(Fmenu,'String','Epileptogenicity',...
'Position',[020 020 083 024].*WS,...
'ToolTipString','Compute epileptogenicity on SEEG',...
'FontSize',FS(9),...
'UserData','ImaGIN_Epileptogenicity',...
'CallBack','ImaGIN_Epileptogenicity;')
uicontrol(Fmenu,'String','Stim detect',...
'Position',[112 054 083 024].*WS,...
'ToolTipString','Detect stimulation and write events in a text file',...
'FontSize',FS(9),...
'UserData','ImaGIN_StimDetect',...
'CallBack','ImaGIN_StimDetect;')
uicontrol(Fmenu,'String','Artefact correct',...
'Position',[112 020 083 024].*WS,...
'ToolTipString','Correct stimulation artefacts',...
'FontSize',FS(9),...
'UserData','ImaGIN_ArtefactCorrectionModel',...
'CallBack','ImaGIN_ArtefactCorrectionModel;')
uicontrol(Fmenu,'String','Implantation',...
'Position',[205 020 083 024].*WS,...
'ToolTipString','Prepare montage from postop MRI',...
'FontSize',FS(9),...
'UserData','ImaGIN_MRImplantation',...
'CallBack','ImaGIN_MRImplantation;')
% uicontrol(Fmenu,'String','Atlas connect',...
% 'Position',[205 088 083 024].*WS,...
% 'ToolTipString','Display DES connectivity atlas',...
% 'FontSize',FS(9),...
% 'UserData','ImaGIN_ConnectStim',...
% 'CallBack','ImaGIN_ConnectStim;')
uicontrol(Fmenu,'String','Quit',...
'Position',[298 020 082 024].*WS,...
'ToolTipString','exit SPM',...
... ...
... ... @@ -61,7 +61,7 @@ end
% Channels
for i = 1:length(ChannelMat.Channel)
D.channels(i).bad = (sFileIn.channelflag(i) == -1);
D.channels(i).label = {ChannelMat.Channel(i).Name};
D.channels(i).label = ChannelMat.Channel(i).Name;
D.channels(i).type = ChannelMat.Channel(i).Type;
D.channels(i).X_plot2D = [];
D.channels(i).Y_plot2D = [];
... ...
%# -*- texinfo -*-
%# @deftypefn {Function File} {@var{vi} =} griddata3 (@var{x}, @var{y}, @var{z}, @var{v} @var{xi}, @var{yi}, @var{zi}, @var{method}, @var{options})
%#
%# Generate a regular mesh from irregular data using interpolation.
%# The function is defined by @code{@var{y} = f (@var{x},@var{y},@var{z})}.
%# The interpolation points are all @var{xi}.
%#
%# The interpolation method can be @code{'nearest'} or @code{'linear'}.
%# If method is omitted it defaults to @code{'linear'}.
%# @seealso{griddata, delaunayn}
%# @end deftypefn
%# Author: David Bateman <dbateman@free.fr>
function vi = oc_griddata3 (x, y, z, v, xi, yi, zi, method, varargin)
if (nargin < 7)
print_usage ;
end
if (~all (size (x) == size (y) & size (x) == size(z) & size(x) == size (v)))
error ('griddata3: x, y, z, and v must be vectors of same length');
end
%# meshgrid xi, yi and zi if they are vectors unless they
%# are vectors of the same length
if (isvector (xi) && isvector (yi) && isvector (zi) && (numel (xi) ~= numel (yi) || numel (xi) ~= numel (zi)))
[xi, yi, zi] = meshgrid(xi, yi, zi);
end
if (any (size(xi) ~= size(yi)) || any (size(xi) ~= size(zi)))
error ('griddata3: xi, yi and zi must be vectors or matrices of same size');
end
vi = oc_griddatan([x(:), y(:), z(:)], v(:), [xi(:), yi(:), zi(:)], varargin{:});
vi = reshape(vi, size (xi));
\ No newline at end of file
... ...
%# -*- texinfo -*-
%# @deftypefn {Function File} {@var{yi} =} griddatan (@var{x}, @var{y}, @var{xi}, @var{method}, @var{options})
%#
%# Generate a regular mesh from irregular data using interpolation.
%# The function is defined by @code{@var{y} = f (@var{x})}.
%# The interpolation points are all @var{xi}.
%#
%# The interpolation method can be @code{'nearest'} or @code{'linear'}.
%# If method is omitted it defaults to @code{'linear'}.
%# @seealso{griddata, delaunayn}
%# @end deftypefn
%# Author: David Bateman <dbateman@free.fr>
function yi = oc_griddatan (x, y, xi, method, varargin)
if (nargin == 3)
method = 'linear';
end
if (nargin < 3)
print_usage ;
end
if (ischar (method))
method = lower (method);
end
[m, n] = size (x);
[mi, ni] = size (xi);
if (n ~= ni || size (y, 1) ~= m || size (y, 2) ~= 1)
error ('griddatan: dimensional mismatch');
end
%# triangulate data
%# tri = delaunayn(x, varargin{:});
tri = delaunayn(x);
yi = NaN(mi, 1);
if (strcmp (method, 'nearest'))
%# search index of nearest point
idx = dsearchn (x, tri, xi);
valid = ~isnan (idx);
yi(valid) = y(idx(valid));
elseif (strcmp (method, 'linear'))
%# search for every point the enclosing triangle
[tri_list, bary_list] = tsearchn (x, tri, xi);
%# only keep the points within triangles.
valid = ~isnan (tri_list);
tri_list = tri_list(~isnan (tri_list));
bary_list = bary_list(~isnan (tri_list), :);
nr_t = size(tri_list,1);
%# Use barycentric coordinate of point to calculate yi
yi(valid) = sum (y(tri(tri_list,:)) .* bary_list, 2);
else
error ('griddatan: unknown interpolation method');
end
... ...
... ... @@ -116,7 +116,6 @@ for i1=1:length(ev)
end
end
if estimateLength
Data=D(GoodChannels,:);
d=[zeros(size(Data,1),1) abs(diff(Data,2,2)) zeros(size(Data,1),1)];
... ... @@ -168,19 +167,14 @@ end
mmArt2=cat(3,zeros(size(mmArt,1),size(mmArt,2)),mmArt);
mmArt2=mmArt2(:,:,1:size(mmArt,3));
if D.fsample>=2048
mmArt3=cat(3,zeros(size(mmArt,1),size(mmArt,2)),mmArt2);
mmArt3=mmArt3(:,:,1:size(mmArt,3));
% mmArt5=cat(3,zeros(size(mmArt,1),size(mmArt,2)),mmArt4);
% mmArt5=mmArt5(:,:,1:size(mmArt,3));
mmArt=cat(1,mmArt,mmArt2,mmArt3);
else
mmArt=cat(1,mmArt,mmArt2);
end
for c = SelectedChannels
sig = [];
ind1 = zeros(1,length(ev));
... ...
... ... @@ -54,11 +54,6 @@ if iscell(D)
DD=D;clear D
switch Method
case 'Mean'
% data=0;
% for i1=1:length(DD)
% data=data+double(DD{i1}(:,:,:));
% end
% data=data./length(DD);
data=zeros([size(DD{1}) length(DD)]);
for i1=1:length(DD)
D =DD{i1};
... ... @@ -93,7 +88,7 @@ if iscell(D)
Name=spm_input('Name of new file', '+1', 's');
end
D=DD{1};
% D=rmfield(D,'data');
if isempty(Name)%Assume namefiles are numbered, have the same events
for i1=1:length(D.fnamedat)
if ~strcmp(DD{1}.fnamedat(i1),DD{2}.fnamedat(i1))
... ... @@ -258,7 +253,7 @@ else
end
[D.Frequency_window, Ypos] = spm_input(str, Ypos, 'r', [], 2);
inds=find(D.tf.frequencies>=D.Frequency_window(1) & D.tf.frequencies<=D.Frequency_window(2))
inds = find(D.tf.frequencies>=D.Frequency_window(1) & D.tf.frequencies<=D.Frequency_window(2));
if ~isempty(inds) break, end
str = 'No data in range';
end
... ... @@ -266,11 +261,7 @@ else
data=squeeze(mean(D(:,inds,:,:),2));
D=clone(D,['F' num2str(D.Frequency_window(1)) '_' num2str(D.Frequency_window(2)) '_' D.fnamedat], [size(D,1) size(D,3) 1]);
D(:,:)=data;
% D(:,3)=[];
D=rmfield(D,'Nfrequencies');
% probl if isfield(D.tf,'time')
% D=time(D,D.tf.time);
% end
D=rmfield(D,'tf');
save(D);
... ... @@ -299,11 +290,6 @@ else
end
end
data=squeeze(mean(D(:,:,:,:),4));
% Events.time=Events(1).time;
% value=Events(i1).value;
% D.events=rmfield(Events,'value');
% Events(1).value=value;
% Event.type='1';
D=clone(D,['m_' D.fnamedat], [D.nchannels D.Nfrequencies D.nsamples 1]);
D=events(D,1,Events);
D(:,:,:)=data;
... ... @@ -313,3 +299,6 @@ else
error('No time frequency data');
end
end
... ...
function D = ImaGIN_BadChannel(S)
% Extract badchannels indices
% -=============================================================================
% This function is part of the ImaGIN software:
... ... @@ -17,7 +16,7 @@ function D = ImaGIN_BadChannel(S)
%
% Authors: Olivier David
% Extract badchannels indices
FileIn = S.dataset; % cropped seeg file .dat/.mat
badDir = S.DirFileOut; % Dir with badchannels
trainDir = S.trainBase;
... ... @@ -36,9 +35,11 @@ S2.FileName = FileIn;
T = ImaGIN_FeatureSEEG(S2); % function returns a table T of features
%--------- uncomment to retrain the classifier ------------------
Tbase = readtable(strcat(trainDir, '/trainBaseFeatures.csv')); % load training base
trainingData = Tbase(:,2:9);
[trainedClassifier, ~] = ImaGIN_trainClassifier(trainingData); % train the model
%------------------------------------------------------------------
%load(strcat(trainDir, '/ImaGIN_trainedClassifier.mat')) % path??? load the trained classifier
yfit = trainedClassifier.predictFcn(T(:,2:8)); % predict new dataset
bd = strcmp(yfit,'Bad');
... ...
function ImaGIN_ConnectStim(S)
% -=============================================================================
% This function is part of the ImaGIN software:
% https://f-tract.eu/
%
% This software is distributed under the terms of the GNU General Public License
% as published by the Free Software Foundation. Further details on the GPLv3
% license can be found at http://www.gnu.org/copyleft/gpl.html.
%
% FOR RESEARCH PURPOSES ONLY. THE SOFTWARE IS PROVIDED "AS IS," AND THE AUTHORS
% DO NOT ASSUME ANY LIABILITY OR RESPONSIBILITY FOR ITS USE IN ANY CONTEXT.
%
% Copyright (c) 2000-2017 Inserm U1216
% =============================================================================-
%
% Authors: Olivier David
% global defaults
spm('defaults','EEG')
global st
FS1 = spm('FontSize', 14);
% try
% Prefixe=S.Prefixe;
% catch
% Prefixe=spm_input('DES feature ', 1,'ERP|Gamma');
% switch Prefixe
% case 'ERP'
% Prefixe='SPM_';
% case 'Gamma'
% Prefixe='SPMg_';
% end
% end
try
PrefixeLat=S.PrefixeLat;
PrefixePro=S.PrefixePro;
catch
PrefixeLat='Latency_';
PrefixePro='Probability_';
end
try
PatientList=S.PatientList;
catch
PatientList=spm_select(inf,'dir');
S.PatientList=PatientList;
end
Root=fileparts(fileparts(deblank(PatientList(1,:))));
cd(Root)
F = spm_figure('Create','Graphics','Graphics','on');
spm_figure('ColorMap','gray-jet');
draw_anat
WS = spm('WinScale');
uicontrol(F,'Style','Frame','Position',[377 110 180 95].*WS);
uicontrol(F,'Style','Text', 'Position',[382 188 170 016].*WS,'String','Crosshair Position');
uicontrol(F,'Style','Text', 'Position',[382 160 35 025].*WS,'String','mm:');
uicontrol(F,'Style','Text', 'Position',[382 140 35 025].*WS,'String','vx:');
uicontrol(F,'Style','Text', 'Position',[382 118 75 025].*WS,'String','Img Intens.:');
st.mp = uicontrol(F,'Style','edit', 'Position',[418 160 135 025].*WS,'String','','Callback','spm_image(''setposmm'')','ToolTipString','move crosshairs to mm coordinates');
st.vp = uicontrol(F,'Style','edit', 'Position',[418 140 135 025].*WS,'String','','Callback','spm_image(''setposvx'')','ToolTipString','move crosshairs to voxel coordinates');
st.in = uicontrol(F,'Style','Text', 'Position',[428 118 85 025].*WS,'String','');
% st.Callback = 'spm_image(''shopos'');';
h.title=uicontrol(F,'Style','Text', 'Position',[0 720 605 30].*WS,'String','','FontSize',FS1,'BackgroundColor','w');
% Display button
%--------------------------
h.displaybutton=uicontrol(F,'Style','togglebutton','Position',[377 210 82 22].*WS,'String','Build atlas','Callback',@DisplayAtlas,'ToolTipString','Construct DES atlas for current crosshair position');
% Clear button
%--------------------------
h.clearbutton=uicontrol(F,'Style','togglebutton','Position',[463 210 72 22].*WS,'String','Clear atlas','Callback',@ClearAtlas,'ToolTipString','Clear MRI');
% Display N button
%--------------------------
h.Nbutton=uicontrol(F,'Style','togglebutton','Position',[539 210 18 22].*WS,'String','N','Callback',@DisplayNumberStim,'ToolTipString','Display stimulation sites of selected data basis.');
% Latency button
%--------------------------
uicontrol(F,'Style','Frame','Position',[400 400 135 30].*WS);
uicontrol(F,'Style','text','String','Map','HorizontalAlignment','left', ...
'Position',[404 408 90 19].*WS);
txt_box = cell(6,1);
txt_box{1}='Probability';
txt_box{2}='Latency 0.95';
txt_box{3}='Latency 0.96';
txt_box{4}='Latency 0.97';
txt_box{5}='Latency 0.98';
txt_box{6}='Latency 0.99';
h.latencybutton = uicontrol(F,'Style','popup','String',txt_box, ...
'Position',[456 408 80 19].*WS, ...
'Callback',@ChooseLatency,'ToolTipString','Select to display probability maps or median latency maps. Latency estimates depends on the selected proability threshold.');
% Flip button
%--------------------------
uicontrol(F,'Style','Frame','Position',[400 360 135 30].*WS);
uicontrol(F,'Style','text','String','Sum L/R','HorizontalAlignment','left', ...
'Position',[404 368 90 19].*WS);
txt_box = cell(2,1);
txt_box{1}='No';
txt_box{2}='Yes';
h.flipbutton = uicontrol(F,'Style','popup','String',txt_box, ...
'Position',[456 368 80 19].*WS, ...
'Callback',@ChooseFlip,'ToolTipString','Sum both hemispheres to increase number of stimulations around cross-hair.');
% ROI button
%--------------------------
uicontrol(F,'Style','Frame','Position',[400 320 135 30].*WS);
uicontrol(F,'Style','text','String','Radius','HorizontalAlignment','left', ...
'Position',[404 328 90 19].*WS);
txt_box = cell(6,1);
txt_box{1}='5';
txt_box{2}='10';
txt_box{3}='15';
txt_box{4}='20';
txt_box{5}='25';
txt_box{6}='30';
h.ROIbutton = uicontrol(F,'Style','popup','String',txt_box, ...
'Position',[456 328 80 19].*WS, 'Value', 3, ...
'Callback',@ChooseRadius,'ToolTipString','Select radius in mm of ROI sphere around crosshair to count stimulations.');
% Minimal number of stimulations button
%--------------------------
uicontrol(F,'Style','Frame','Position',[400 280 135 30].*WS);
uicontrol(F,'Style','text','String','min(N)','HorizontalAlignment','left', ...
'Position',[404 288 90 19].*WS);
txt_box = cell(10,1);
txt_box{1}='1';
txt_box{2}='2';
txt_box{3}='3';
txt_box{4}='4';
txt_box{5}='5';
txt_box{6}='6';
txt_box{7}='7';
txt_box{8}='8';
txt_box{9}='9';
txt_box{10}='10';
h.Nminbutton = uicontrol(F,'Style','popup','String',txt_box, ...
'Position',[456 288 80 19].*WS, 'Value',5,...
'Callback',@ChooseNmin,'ToolTipString','Select minimal number of recordings for voxels of the atlas.');
% Probability threshold
%--------------------------
uicontrol(F,'Style','Frame','Position',[400 240 135 30].*WS);
uicontrol(F,'Style','text','String','P value','HorizontalAlignment','left', ...
'Position',[404 248 90 19].*WS);
txt_box = cell(11,1);
txt_box{1}='0';
txt_box{2}='0.1';
txt_box{3}='0.2';
txt_box{4}='0.3';
txt_box{5}='0.4';
txt_box{6}='0.5';
txt_box{7}='0.6';
txt_box{8}='0.7';
txt_box{9}='0.8';
txt_box{10}='0.9';
txt_box{11}='1';
h.pvaluebutton = uicontrol(F,'Style','popup','String',txt_box, ...
'Position',[456 248 80 19].*WS, 'Value',1,...
'Callback',@ChoosePvalue,'ToolTipString','Select probability threshold for display.');
% Display button
%--------------------------
h.comparebutton=uicontrol(F,'Style','togglebutton','Position',[377 80 180 19].*WS,'String','Compare to group','Callback',@CompareAtlas,'ToolTipString','Construct patient''s departure from DES atlas');
try
h.S=S;
end
XYZ=[];
for i1=1:size(PatientList,1)
directories=dir(deblank(PatientList(i1,:)));
for i2=3:length(directories)
tmp=max(findstr(directories(i2).name,'_'));
if directories(i2).isdir && strcmp(directories(i2).name(1:length(PrefixeLat)),PrefixeLat)
XYZ(end+1,:)=str2num(directories(i2).name(tmp+1:end));
end
end
end
%Initialisation of maps
cd(Root)
n=3;
bb = [[-78 -112 -50];[78 76 85]];
P=[bb(1,1),bb(1,2),bb(1,3),0,0,0,n,n,n];
n1=length(bb(1,1):n:bb(2,1));
n2=length(bb(1,2):n:bb(2,2));
n3=length(bb(1,3):n:bb(2,3));
V = fullfile(spm('dir'), 'canonical', 'avg152T1.nii');
V=spm_vol(V);
V.mat=spm_matrix(P);
V.dim=[n1 n2 n3];
V.dt=[16 0]; %float 32
V.fname = 'NumberStim.img';
NImage=zeros(n1,n2,n3);
V=spm_write_vol(V,NImage);
[R,C,P] = ndgrid(1:V(1).dim(1),1:V(1).dim(2),1:V(1).dim(3));
RCP = [R(:)';C(:)';P(:)'];
clear R C P
RCP(4,:) = 1;
XYZ1 = V(1).mat(1:3,:)*RCP;
for i1=1:size(XYZ,1)
D=sqrt(sum((XYZ(i1,:)'*ones(1,size(XYZ1,2))-XYZ1).^2));
Sel=find(D<=5);
NImage(Sel)=NImage(Sel)+1;
end
V=spm_vol(V);
V=spm_write_vol(V,NImage);
h.PrefixeLat=PrefixeLat;
h.PrefixePro=PrefixePro;
h.XYZ=XYZ;
h.Root=Root;
h.PatientList=PatientList;
h.st=st;
h.LatencyValues=0.95:0.01:0.99;
guidata(F, h);
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function draw_anat
% This function plots anatomical MRI
global st
spm_orthviews('Reset');
st.callback = 'spm_image(''shopos'');';
P = fullfile(spm('dir'),'canonical','avg152T1.nii');
spms = spm_vol(P);
spm_orthviews('Image',spms);
% spm_orthviews('Image',spms,[0.05 0.05 0.9 0.45]);
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function ChoosePvalue(hObject, events)
global st
F = spm_figure('GetWin','Graphics');
h = guidata(F);
W=h.W;
DataBin2=h.DataBin2;
xSPM=h.xSPM;
Latency=h.Latency;
z=get(h.pvaluebutton);
Zmax=str2num(z.String{z.Value});
h.Zmax=Zmax;
%Display image
i=find(DataBin2>=Zmax);
xSPM.Z=W(i)';
[i,j,k]=ind2sub(size(W),i);
xSPM.XYZ=[i j k]';
xSPM.XYZmm=xSPM.M(1:3,:)*[xSPM.XYZ; ones(1,size(xSPM.XYZ,2))];
CurrentTarget=st.centre;
spm_orthviews('Reset');
draw_anat;
spm_orthviews('addblobs',1,xSPM.XYZ,xSPM.Z,xSPM.M);
spm_orthviews('Redraw');
spm_orthviews('Reposition',CurrentTarget)
st.mp=h.st.mp;
st.vp=h.st.vp;
st.in=h.st.in;
h.xSPM=xSPM;
guidata(F, h);
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function ChooseNmin(hObject, events)
global st
F = spm_figure('GetWin','Graphics');
h = guidata(F);
z=get(h.Nminbutton);
Nmin=str2num(z.String{z.Value});
h.Nmin=Nmin;
SelectionMRI=h.SelectionMRI;
Symmetry=h.Symmetry;
Latency=h.Latency;
Dmax=h.Dmax;
Zmax=h.Zmax;
DataBin=h.DataBin;
DataLat=h.DataLat;
N=h.N;
NLat=h.NLat;
xSPM=h.xSPM;
LatencyValues=h.LatencyValues;
N=h.N;
Dmax=h.Dmax;
Symmetry=h.Symmetry;
DataBin2=h.DataBin;
Root=h.Root;
SelectionMRI=h.SelectionMRI;
n1=h.n1;
n2=h.n2;
n3=h.n3;
%Cut off in voxels with too few recordings
DataBin2=DataBin;
DataBin2(find(N<Nmin))=NaN;
%Show target
DataBin2(SelectionMRI)=1;
DataLat2=DataLat;
for i1=1:length(DataLat2)
DataLat2{i1}(find(NLat{i1}<Nmin))=NaN;
DataLat2{i1}(SelectionMRI)=0;
end
%save images
if ~Symmetry
V.fname = ['Probability_Distance' num2str(Dmax) '.img'];
else
V.fname = ['Probability_Distance' num2str(Dmax) '_Sym.img'];
end
V=spm_vol(V.fname);
spm_write_vol(V,DataBin2);
%smooth image
clear matlabbatch
matlabbatch{1}.spm.spatial.smooth.data = {[V.fname ',1']};
matlabbatch{1}.spm.spatial.smooth.fwhm = [3 3 3];
matlabbatch{1}.spm.spatial.smooth.dtype = 0;
matlabbatch{1}.spm.spatial.smooth.im = 1;
matlabbatch{1}.spm.spatial.smooth.prefix = 's';
spm('defaults', 'EEG');
spm_jobman('run', matlabbatch);
if ~Symmetry
V.fname = ['sProbability_Distance' num2str(Dmax) '.img'];
else
V.fname = ['sProbability_Distance' num2str(Dmax) '_Sym.img'];
end
V=spm_vol(V.fname);
DataBin2=spm_read_vols(V);
for i1=1:length(LatencyValues)
if ~Symmetry
V.fname = ['Latency_' num2str(1000*LatencyValues(i1)) '_Distance' num2str(Dmax) '.img'];
else
V.fname = ['Latency_' num2str(1000*LatencyValues(i1)) '_Distance' num2str(Dmax) '_Sym.img'];
end
V=spm_vol(V);
V=spm_write_vol(V,DataLat2{i1});
%smooth image
clear matlabbatch
matlabbatch{1}.spm.spatial.smooth.data = {[V.fname ',1']};
matlabbatch{1}.spm.spatial.smooth.fwhm = [3 3 3];
matlabbatch{1}.spm.spatial.smooth.dtype = 0;
matlabbatch{1}.spm.spatial.smooth.im = 1;
matlabbatch{1}.spm.spatial.smooth.prefix = 's';
spm('defaults', 'EEG');
spm_jobman('run', matlabbatch);
if ~Symmetry
V.fname = ['sLatency_' num2str(1000*LatencyValues(i1)) '_Distance' num2str(Dmax) '.img'];
else
V.fname = ['sLatency_' num2str(1000*LatencyValues(i1)) '_Distance' num2str(Dmax) '_Sym.img'];
end
V=spm_vol(V.fname);
DataLat2{i1}=spm_read_vols(V);
end
%Display image
switch Latency(1:3)
case 'Lat'
tmp=find(LatencyValues==str2double(Latency(end-3:end)));
I2=DataLat2{tmp};
Zmax=-1;
case 'Pro'
I2=DataBin2;
end
W=I2;
xSPM.M = V.mat;
i=find(~isnan(W));
xSPM.Z=W(i)';
[i,j,k]=ind2sub(size(W),i);
xSPM.XYZ=[i j k]';
xSPM.XYZmm=xSPM.M(1:3,:)*[xSPM.XYZ; ones(1,size(xSPM.XYZ,2))];
CurrentTarget=st.centre;
spm_orthviews('Reset');
draw_anat;
spm_orthviews('addblobs',1,xSPM.XYZ,xSPM.Z,xSPM.M);
spm_orthviews('Redraw');
spm_orthviews('Reposition',CurrentTarget)
st.mp=h.st.mp;
st.vp=h.st.vp;
st.in=h.st.in;
h.xSPM=xSPM;
h.W=W;
h.DataBin2=DataBin2;
h.DataLat2=DataLat2;
h.N=N;
h.NLat=NLat;
guidata(F, h);
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function ChooseLatency(hObject, events)
global st
F = spm_figure('GetWin','Graphics');
h = guidata(F);
PrefixeLat=h.PrefixeLat;
PrefixePro=h.PrefixePro;
z=get(h.latencybutton);
Latency=z.String{z.Value};
switch Latency
case 'Latency 0.95'
Prefixe=[PrefixeLat '950_'];
case 'Latency 0.96'
Prefixe=[PrefixeLat '960_'];
case 'Latency 0.97'
Prefixe=[PrefixeLat '970_'];
case 'Latency 0.98'
Prefixe=[PrefixeLat '980_'];
case 'Latency 0.99'
Prefixe=[PrefixeLat '990_'];
case 'Probability'
Prefixe=PrefixePro;
end
h.Latency=Latency;
Root=h.Root;
PatientList=h.PatientList;
DataBase=h.DataBase;
Selection=h.Selection;
Target=h.Target;
Nmin=h.Nmin;
Symmetry=h.Symmetry;
SelectionMRI=h.SelectionMRI;
Zmax=h.Zmax;
Dmax=h.Dmax;
xSPM=h.xSPM;
n1=h.n1;
n2=h.n2;
n3=h.n3;
LatencyValues=h.LatencyValues;
%Display image
switch Latency(1:3)
case 'Lat'
tmp=find(LatencyValues==str2double(Latency(end-3:end)));
I2=h.DataLat2{tmp};
Zmax=-1;
case 'Pro'
I2=h.DataBin2;
end
W=I2;
i=find(W>Zmax);
xSPM.Z=W(i)';
[i,j,k]=ind2sub(size(W),i);
xSPM.XYZ=[i j k]';
xSPM.XYZmm=xSPM.M(1:3,:)*[xSPM.XYZ; ones(1,size(xSPM.XYZ,2))];
CurrentTarget=st.centre;
spm_orthviews('Reset');
draw_anat;
spm_orthviews('addblobs',1,xSPM.XYZ,xSPM.Z,xSPM.M);
spm_orthviews('Redraw');
spm_orthviews('Reposition',CurrentTarget)
st.mp=h.st.mp;
st.vp=h.st.vp;
st.in=h.st.in;
switch Latency(1:3)
case 'Lat'
tmp=find(LatencyValues==str2double(Latency(end-3:end)));
set(h.title,'String',['Median latency (p=' num2str(LatencyValues(tmp)) ') at ' sprintf('%d %d %d',round(Target))]);
case 'Pro'
set(h.title,'String',['Probability at ' sprintf('%d %d %d',round(Target))]);
end
set(h.displaybutton,'Value',0);
h.xSPM=xSPM;
h.W=W;
guidata(F, h);
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function ChooseFlip(hObject, events)
F = spm_figure('GetWin','Graphics');
h = guidata(F);
z=get(h.flipbutton);
Symmetry=z.String{z.Value};
switch Symmetry
case 'Yes'
Symmetry=1;
case 'No'
Symmetry=0;
end
h.Symmetry=Symmetry;
guidata(F, h);
ChooseRadius
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function ChooseRadius(hObject, events)
global st
F = spm_figure('GetWin','Graphics');
h = guidata(F);
z=get(h.ROIbutton);
Dmax=str2num(z.String{z.Value});
h.Dmax=Dmax;
Root=h.Root;
Target=h.Target;
DataBase=h.DataBase;
Nmin=h.Nmin;
Symmetry=h.Symmetry;
SelectionMRI=h.SelectionMRI;
Latency=h.Latency;
Zmax=h.Zmax;
xSPM=h.xSPM;
n1=h.n1;
n2=h.n2;
n3=h.n3;
ProbabilityThreshold=h.ProbabilityThreshold;
LatencyValues=h.LatencyValues;
D=zeros(1,size(DataBase,2));
for i1=1:size(DataBase,2)
tmp=DataBase(1,i1).xyz;
if Symmetry && sign(Target(1))~=sign(DataBase(1,i1).xyz(1))
tmp(1)=-tmp(1);
end
D(i1)=sqrt(sum((Target-tmp).^2));
end
Selection=find(D<=Dmax);
%Initialisation of maps
cd(Root)
n=3;
bb = [[-78 -112 -50];[78 76 85]];
P=[bb(1,1),bb(1,2),bb(1,3),0,0,0,n,n,n];
n1=length(bb(1,1):n:bb(2,1));
n2=length(bb(1,2):n:bb(2,2));