Skip to content

[WIP] GLM pipeline: surface and template based

Thomas Vincent edited this page May 16, 2019 · 10 revisions

Overview

Inputs

Assumptions

Conventions

The naming of subjects and condition folders is controlled by the function. To clearly separate the outputs of this function from other user-specific data, the suffix tag (__nspst_V1) is used. It is advised not to modify these folders. That way, one knows that the tagged data have been generated automatically by the pipeline function. They can be safely removed and regenerated by running the script again.

Examples

Sample data

The data set consists of one original subject undergoing a tapping task with an optimal montage over the motor cortex. This single subject has been duplicated 9 times to produce 10 dummy subjects coregistered with the Colin27 template. All dummy subjects have the same optode coordinates. Some noise was added in the 9 duplicated subjects to inject some variability.

Here is the montage and signal plots for the initial subject:

sample data

Minimal example script

This script provides a minimal working example of the pipeline on the set of 10 dummy subjects. It starts by importing raw data files in brainstorm. It performs some default preprocessings up to cortical projection on the Colin27 template. Then a GLM with precoloring is run for all nodes of the surface to produce subject-level contrast maps. These maps finally enter a group-level GLM producing mixed effects contrast maps.

Refer to the comments in the script for details about every steps.

In what follows, the outline of the main steps is presented with output illustrations:

1. Importation

sFiles = nst_ppl_surface_template_V1('import', options, nirs_fns, subject_names);

This instruction imports all given nirs data files (nirs_fns) into brainstorm. The returned object sFiles is a cell array of strings gathering all imported brainstorm files. These files can then be customized before processings. See for instance the next step on event reading.

Note that an empty event group called "movement_artefacts" is created by the function. It can be filled by the user while manually tagging movement artefacts. It will be used afterwards during preprocessings to perform movement correction.

Here is the imported anatomy data. All subjects have the default anatomy: the Colin27 template.

import anat

Here is the imported functional data. For every subject, the raw data is located in a folder called "origin".

import func

2. Event reading

The stimulation events are encoded in various ways across experiments. They can be bundled in the nirs files or stored in external files. So it is left to the user to load the events, just after importation.

In the current example, events are read from the 1st auxiliary channel, renamed as "motor". The events duration is then injected while converting to extended events. Here is the code:

% Read stimulation events from AUX channel
for ifile=1:length(sFiles)
 evt_data = load(file_fullpath(sFiles{ifile}), 'Events');
 if ~any(strcmp({evt_data.Events.label}, 'motor')) % Insure that events were not already loaded
     bst_process('CallProcess', 'process_evt_read', sFiles{ifile}, [], ...
                 'stimchan',  'NIRS_AUX', ...
                 'trackmode', 3, ...  % Value: detect the changes of channel value
                 'zero',      0);
     % Rename event AUX1 -> motor
     bst_process('CallProcess', 'process_evt_rename', sFiles{ifile}, [], ...
                 'src',  'AUX1', 'dest', 'motor');
     % Convert to extended event-> add duration of 30 sec to all motor events
     bst_process('CallProcess', 'process_evt_extended', sFiles{ifile}, [], ...
                 'eventname',  'motor', 'timewindow', [0, 30]);
 end
end

Here are the loaded events: the motor ones, and the empty movement_artefacts group for later manual tagging:

import func

3. Preprocessings and GLM

The only mandatory parameters for the processing part of the pipeline are:

  • the events to include in the design matrix of the GLM
  • the contrasts.

Here the motor events are specified along with the motor contrast:

options.GLM_1st_level.stimulation_events = {'motor'};
options.GLM_1st_level.contrasts(1).label = 'motor';
options.GLM_1st_level.contrasts(1).vector = '[1 0]'; % a vector of weights, as a string 

Finally, all processings are run with:

nst_ppl_surface_template_V1('analyse', options, subject_names); % Run the full pipeline

Here is the commented illustration of the resulting brainstorm protocol after execution:

result DB

The number at the beginning of each comment indicates the processing order.

The group-level maps (HbO | con_t-+ motor and HbR | con_t-+ motor) thresholded at 0.05 with Bonferroni correction are:

result maps