seg.htb 11.8 KB
Newer Older
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
%% SCRIPT DESCRIPTION
% this is a template segmentation script for ERP task data
%
%% From Config          key_strswap         Description
%-----------------------------------------------------------------------------------------------------------------------------
%    in_path =           [in_path]           Relative path to input data files assuming cd = work_path
%    seg_type =          [seg_type]          Type of segmentation (task OR rest)
%    seg_staging =       [seg_staging]       Name of .m script file containing staging of subject demographics info
%	 montage_info =      [montage_info]      Transformations matrix to fit channel locations on a standard surface 
%                                            (e.g. [-.14,-22,-48,-.07,0,-1.57,1080,1260,1240])                                           
%	 ref_loc_file =      [ref_loc_file]      Name of file containing the reference locations (including the relative path)
%    nfids =             [nfids]             Number of fiducials in the ref_loc_file (e.g. 3)
%    nose_dir =          [nose_dir]          Nose direction of montage to apply after interpolation
%    subj_inds =         [subj_inds]         Indices of characters within the filename that represent subject number (optional) (e.g. [6:8])
%    sess_inds =         [sess_inds]         Indices of characters within the filename that represent session number (optional) (e.g. [15:16])
%    conditions =        [conditions]        Cell array of marker names to use for segmentation (conditions can be grouped with nested cell arrays)
%                                            (e.g. {'onset1',{'onset2','onset3'},'offset1',{'offset2,'offset3'}})
%    cond_names =        [cond_names]        Cell array of names of each condition grouping (should be the same size as the number of condition groupings)
%    rest_off =          [rest_off]          Cell array of offset markers used to determine the end of a resting period (e.g. 'EndT')
%    sel_event =         [sel_event]         Select only trials with this/these event(s) in them (optional) (e.g. {'good_trial'})
%    sel_lat =           [sel_lat]           Latency range (in time points) in which to find [sel_event] in each epoch
%                                            (this may also be a cell array of latency ranges for each condition group if each one uses a different range)
%                                            (e.g. -250<=750 OR {''-250<=750'',''-1000<=0''} NOTE: use double quotes in cell array to avoid syntax error)
%    sel_invert =        [sel_invert]        Invert event selection such that only epochs which don't include [sel_event] are used (e.g. on or off)
%    low_bound_hz =      [low_bound_hz]      Lower bound of the filter pass-band
%    high_bound_hz =     [high_bound_hz]     Upper bound of the filter pass-band
%    reref =             [reref]             Perform average rereferencing after purging and interpolating (e.g. yes or no)
%    resample =          [resample]          Adjust the sample rate (optional) (e.g. 500)
%    rest_recur =        [rest_recur]        Recurrence of resting epochs (e.g. 0.5)
%    win_size =          [win_size]          Size and limits of each epoch ( e.g. [-1 1] OR {[-1 1],[-0.5 1.5]} )
%                                            (this may also be a cell array of window sizes for each condition group if each one uses a different size)
%    hanning =           [hanning]           Boolean for whether a hanning window should be applied to resting data (e.g. true (1) or false (0))
%    rm_base =           [rm_base]           baseline correction (in ms) to be applied (e.g. [-200 0])
%    out_path =          [out_path]          Relative path to output data files assuming cd = work_path

%% keep a log file of entire batch (may comment this out)
%diary 'derivatives/lossless/diary/seg.log'

logging_log('NOTICE', 'Starting seg script');

[path name ext] = fileparts('[batch_dfn]');
if ~strcmp(ext,'.set')
    logging_log('ERROR', sprintf('Wrong file format: %s should be .set',ext));
    exit(1);
end
logging_log('INFO', 'Loading set file: [batch_dfn]...');
EEG = pop_loadset('filename','[batch_dfn]','filepath','[batch_dfp]');
EEG = eeg_checkset( EEG );

%% add STUDY variables
if [[subj_inds]];
    EEG.subject = EEG.filename([subj_inds]);
else;
    EEG.subject = EEG.filename([5:8]);
end;

if [[sess_inds]];
    EEG.session = EEG.filename([sess_inds]);
else;
    EEG.session = EEG.filename([15:16]);
end;

%% execute the seg staging script if specified
% this should include code for parsing demographics info from a csv/tsv 
% file into EEG.group, and any other code to prepare events in a file  
if exist('[seg_staging]');
    [ssp,ssn,sse]=fileparts('[seg_staging]');
    addpath(ssp);
    eval(ssn);
end

conditions = [[conditions]];

%% add time marks for resting data if there are onset/offset resting markers
no_data = 0;
if strncmp('[seg_type]','rest',4) & iscell(conditions);
    cond_names = [cond_names];
    rest_off = {[rest_off]};
    no_data = zeros(1,length(cond_names));
    if ~isempty(rest_off); rest_off = rest_off{:}; end;
    for c=1:length(conditions);
        if length(conditions)>length(cond_names);
            cond_tmp = cond_names;
            for i=1:length(conditions)-length(cond_names);
                cond_names = horzcat(cond_names,cond_tmp);
            end;
        end;
        try;
            EEG = pop_marks_event_gap(EEG,{conditions{c},rest_off{c}},[],cond_names{c}, ...
                   [0 1 0],'exact','on','ref_point','both','interval','on');
        catch;
            no_data(c) = 1;
            disp(['SKIPPING ' conditions{c} ' condition for ' EEG.filename ': No ' conditions{c} ' markers.']);
        end;
    end;
end;

cond_names = [cond_names];

if isempty([[conditions]]);
    conditions = {''};
else;
    conditions = [[conditions]];
end;

for c=1:length(conditions);
    if ~iscell(conditions{1,c});
        conditions{1,c}=cellstr(conditions{1,c});
    end;
end;

%% remove flagged channels and time segments
sprintf('%s','Purging flagged channels...\n');
EEG = pop_marks_select_data(EEG,'channel marks',[],'labels',{'manual'},'remove','on');
EEG = pop_marks_select_data(EEG,'time marks',[],'labels',{'manual'},'remove','on');
EEG = pop_marks_select_data(EEG,'component marks',[],'labels',{'manual'},'remove','on');
EEG = eeg_checkset(EEG);
logging_log('INFO', 'TIME TO: PURGE DATA...');

120
if strcmp('[reref]','on');
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
    EEG = pop_reref(EEG,[]);
end;

% for task-based paradigms only
if strncmp('[seg_type]','task',4);
    %% resample the data
    if ([[resample]]);
        if EEG.srate~=[[resample]];
            EEG = pop_resample(EEG,[[resample]]);
        end;
    end;
    %% interpolate
    EEG = warp_locs(EEG,'[ref_loc_file]','transform',[montage_info],'manual','off');
    EEG = interp_mont( EEG,'[ref_loc_file]','nfids',[nfids],'manual','off');
    if ~isempty('[nose_dir]');
        EEG.chaninfo.nosedir = '[nose_dir]';
    end;
    EEG = eeg_checkset(EEG);
end;

%% filter the data
if ([[low_bound_hz]]);
    EEG = pop_eegfiltnew(EEG,[],[[low_bound_hz]],[],1,[],0);
end;
if ([[high_bound_hz]]);
    EEG = pop_eegfiltnew(EEG,[],[[high_bound_hz]],[],0,[],0);
end;

149
if strcmp('[reref]','on');
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
    EEG = pop_reref(EEG,[]);
end;

EEG = eeg_checkset(EEG);


tmpEEG=EEG;

for c=1:length(cond_names);

    if strncmp('[seg_type]','task',4); % task segmentation
        try;
            if iscell([win_size]); % different window sizes for each condition
                win_size = [win_size];
                EEG = pop_epoch( tmpEEG, conditions{1,c},win_size{c}, ...
                                'newname', cond_names{c}, 'epochinfo', 'yes');
                EEG = pop_rmbase(EEG, [rm_base]);
            else;                  % same window size for all conditions
                EEG = pop_epoch( tmpEEG, conditions{1,c},[win_size], ...
                                'newname', cond_names{c}, 'epochinfo', 'yes');
                EEG = pop_rmbase(EEG, [rm_base]);
            end;        
            if ~isempty([[sel_event]]);
                sel_event = {[sel_event]};
                sel_lat = {eval(strrep('[sel_lat]','''''',''''))};
                if iscell(sel_lat{:}); % different latency window to search for each condition
                    sel_lat = sel_lat{:};
                    EEG = pop_selectevent(EEG, 'latency',sel_lat{c},'type',...
                            sel_event{:},'deleteevents','off',...
                            'deleteepochs','on',...
                            'invertepochs','[sel_invert]');
                else;                 % same latency window to search for all conditions
                    EEG = pop_selectevent(EEG, 'latency','[sel_lat]','type',...
                            sel_event{:},'deleteevents','off',...
                            'deleteepochs','on',...
                            'invertepochs','[sel_invert]');
                end;
            end;
        catch;
            disp(['SKIPPING ' cond_names{c} ' condition for ' EEG.filename ': No segments remaining.']);
            continue;
        end;

    elseif strncmp('[seg_type]','rest',4); % rest segmentation

        if no_data(c); continue; end;

        if ~isempty([[rest_off]]);
            if ~isempty(find(tmpEEG.marks.time_info(1,find(strcmp({tmpEEG.marks.time_info.label},cond_names{c}))).flags));
                EEG = pop_marks_select_data(tmpEEG,'time marks',[],'labels',{cond_names{c}},'remove','off');
                EEG = eeg_checkset(EEG);
            else;
                disp(['SKIPPING ' cond_names{c} ' condition for ' EEG.filename ': No good time points remaining.']);
                continue;
            end;
        end;

        EEG = marks_continuous2epochs(EEG,'recurrence',[[rest_recur]],'limits',[win_size],'keepboundary','on','eventtype','rest');

        for i=1:length(EEG.marks.time_info);
            EEG.marks.time_info(i).flags=[];
        end

        % for resting paradigms only
        %% resample the data
        if ([[resample]]);
            if EEG.srate~=[[resample]];
                EEG = pop_resample(EEG,[[resample]]);
            end;
        end;

        %% interpolate
        EEG = warp_locs(EEG,'[ref_loc_file]','transform',[montage_info],'manual','off');
        EEG = interp_mont( EEG,'[ref_loc_file]','nfids',[nfids],'manual','off');
        if ~isempty('[nose_dir]');
            EEG.chaninfo.nosedir = '[nose_dir]';
        end;
        EEG = eeg_checkset(EEG);

        if EEG.trials>1;
            if [[hanning]]; %% apply hanning window
                h=hanning(EEG.pnts);
                hr=repmat(h,1,EEG.trials);

                for i=1:size(EEG.data,1);
                    d=squeeze(EEG.data(i,:,:));
                    EEG.data(i,:,:)=d.*hr;
                end
            end;
            if isempty(EEG.event);
                EEG.event = struct('type','','latency',NaN,'urevent',[],'duration',0,'epoch',0);
            end
        else;
            disp(['SKIPPING ' cond_names{c} ' condition for ' EEG.filename ': single trial remaining.']);
            continue;
        end;
    else;
        disp('ERROR: invalid seg_type: [seg_type]. Must be task OR rest.');
        continue;
    end;

    %% purge unnecessary fields
    for i=1:length(EEG.marks.time_info);
        EEG.marks.time_info(i).flags=[];
    end
    EEG.data_sd_ep=[];
    EEG.c_data_sd_ep=[];
    EEG.data_sd_ch=[];
    EEG.c_data_sd_ch=[];
    EEG.m_neigbr_r_ch=[];
    EEG.c_neigbr_r_ch=[];
    EEG.m_neigbr_r_lat=[];
    EEG.c_neigbr_r_lat=[];
    EEG.amica=[];
    EEG.icaact_sd1_lat=[];
    EEG.c_icaact1_sd_lat=[];
    EEG.icaact_sd2_lat=[];
    EEG.c_icaact_sd2_lat=[];
    EEG.icaact_ta_lat=[];
    EEG.c_icaact_ta_lat=[];
    EEG.icaact_b_lat=[];
    EEG.c_icaact_b_lat=[];
    EEG.icaact = [];
    EEG.icawinv = [];
    EEG.icasphere = [];
    EEG.icaweights = [];
    EEG.icachansind = [];

    if strcmp(EEG.condition,'');
        EEG.condition = cond_names{c};
    end;
    EEG = pop_saveset(EEG, 'filename',['[batch_dfn,_,-1]_' cond_names{c} '_seg.set']);
end;