This is a collaborative space. In order to contribute, send an email to maximilien.chaumon@icm-institute.org
On any page, type the letter L on your keyboard to add a "Label" to the page, which will make search easier.

Tutoriel avancé d'analyse de donnees MEG

General Overview

You will find below the detail of an advanced analysis of a MEG experiment with the tools available at CENIR. These commands were used to analyze the AEMOS experiment (See S. Dubal and collaborators for more details).

Pre processing

Mean Head Position Computation

This first step uses dataHandler to compute a mean head position by averaging the initial had position of each run. This mean head position is then displayed using megDraw.

## Compute mean head position by averaging initial head positions in all runs
dataHandler_dev -r -avg run??.fif -hp mean -time 0 -.1 meanhp.fif
## Generate *.hc files for each run
dataHandler_dev -r -hc run??.fif meanhp.fif
## Visualize each initial head position and computed mean position (this step is optional)
megDraw *.hc

:hcfig.png?250|Head positions example

tSSS Computation

We used maxfilter to correct for all the main non biological artifacts arising during the recording. maxfilter is configured here to check for bad channels on the entire dataset thanks to the duration computed with dataHandler. The head position for each run is transformed to the above computed mean head position and the MEG signals are recomputed accordingly. If needed you can add manualy bad channels with -bad option.

foreach run (run*.fif)
       	set log = `echo $run | sed "s/.fif/_sss.log/"`
	set duration=`dataHandler -header $run | grep Duration | cut -d " " -f 2 `
       maxfilter -gui -st $duration -trans meanhp.fif -f $run > $log
       ## In case of bad channels not detected
       ## maxfilter -gui -bad 0121 -st $duration -trans meanhp.fif -f $run > $log
end

Triggers Generation

You have to check the quality of the MaxFilter output before going further in your analysis.
First, we use dataHandler to generate the trigger list and add a new marker named "BAD". This marker will be used to mark artifacts and others part of the signals we do not want to use in the analysis.
Then you will use muse to double check the MaxFilter output.

dataHandler -touchmarker BAD run*trans_sss.fif

muse_dev run01_trans_sss.fif

:badexample.png?500|

We then generate all the markers necessary to the signals analysis. This step depends heavily on your own setup.
The first step is to extract the triggers acquired during the experiment.

foreach run (run??_trans_tsss.fif)
    dataHandler -r -triggers -ch STI101 $run
end

We then convert the acquisition triggers into something more readable (for the to be written triggers equations):

foreach run (run??_trans_tsss.fif)
  ## An alias to dataHandler command to simplify the coming call to dataHandler
  alias dh "dataHandler_dev -r $run"
  ## Rename acquisition markers
  dh -adm "T1=STI101_01"
  dh -adm "T2=STI101_02"
  dh -adm "T3=STI101_03"
  dh -adm "T4=STI101_04"
  dh -adm "T5=STI101_05"
  dh -adm "T6=STI101_06"
  dh -adm "T7=STI101_07"
  dh -adm "T8=STI101_08"
  ## Optionally you can then delete STI101 marker
  dh -delm_m STI101
end

The next step is to generate your markers of interest (to be used to compute Evoked Potential, Time-Frequency map, to perform localization …)

set code = "T5 T6 T7 T8;"
foreach run (run??_trans_tsss.fif)
  ## An alias to dataHandler command to simplify the coming call to dataHandler
  alias dh "dataHandler_dev -r $run"
  # Fix, Stimulus and Task
  dh -adm "Fixation=T1"
  dh -adm "Prime=T2"
  dh -adm "Target=T3"
  dh -adm "Scale= T8"
  dh -adm "Response=T4"

  ## (sub) Tasks (combination of T5, T6, T7 & T8 markers)
  dh -adm "PCongruent=Prime & ($

1)"
dh -adm "PIncongruent=Prime & ($

2)"
  dh -adm "PNoAction=Prime & ($

3)"
dh -adm "PNoPrimeBeginning=Prime & ($

4)"
  dh -adm "PNoPrimeEnd=Prime & ($

5)"
dh -adm "PNoPrime=Prime & (($

4) | ($

5))"

    1. Subject response decoding (combination of T5, T6, T7 & T8 markers)
      dh -adm "R1=Response & ($

      1)"
        dh -adm "R2=Response & ($

      2)"
      dh -adm "R3=Response & ($

      3)"
        dh -adm "R4=Response & ($

      4)"
      dh -adm "R5=Response & ($

      5)"
        dh -adm "R6=Response & ($

      6)"
      dh -adm "R7=Response & ($

      7)"
        dh -adm "R8=Response & ($

      8)"
      dh -adm "R9=Response & ($

      9)"
      end
      

If you need an accurate timing with respect to your visual stimulation, you have to put a trigger on the signal coming from the photodiode (the threshold should be adapted, take a look with muse to choose the right one, and check the result of the detection and the corresponding delay in the log file!)

foreach run (run??_trans_tsss.fif)
  ## An alias to dataHandler command to simplify the coming call to dataHandler
  alias dh "dataHandler_dev -r $run"
  #Photodiode crossing including the threshold
  dh -thd LIGHT 1 1 -ch MISC002

  # display the synchronization between stimulus onset and the photodiode
  dh -rt Target LIGHT > PhotoD_Sync_${run}.log
end

If you used the Eyelink to track the eye movement use the following command to synchronize the eyelink recordings and the MEG recordings:

As a first step you to retreive the eyelinks files and to put them in a directory named eyelink. The dataHandler matches triggers channels from eyelink and meg recording to synchronize the files.

foreach run (run01 run02 run03 run04 run05 run06 run07 run08 run09 run10 run11)
  ## An alias to dataHandler command to simplify the coming call to dataHandler
  alias dh "dataHandler_dev -r $run"

  dh -edf eyelink/${run}.asc
end

Blink Detection

You can then run the blink detection using dataHandler. Check the results, if not enough blink is detected decrease maxvar option, if too many blinks are detected lower it and rerun the command. Of course your vertical EOG should be on BIO002 (standard location) and it should be reasonably clean (without artifacts bigger than the blinks amplitudes).

dataHandler -tm BLINK maxvar -5 -ch BIO002 -time -.15 .6 -r run*trans_sss.fif > blinks.log

:blinkdetection.png?500|

QRS detection

Same thing for cardiac artifact, you should have a number of artifacts more or less equivalent to the number of seconds in your recordings (check the cardio.log file! you should find a line similar to this one: ExtractTemplate: corrected correlation: total points = 670 — we had a 10 minutes run so 670 fits well).

dataHandler -r -tm CARDIO auto -.6 -hpf .3 -time 0 .6 -ch BIO003 run*trans_sss.fif > cardio.log

:cardioexample.png?500|

QRS Artifact correction

Once the cardiac artifacts are detected (please check the output of the previous dataHandler command!), run the following call to dataHandler to correct the cardiac artifacts. The output will be stored in cardiocor_run*.fif files.

dataHandler -r -pcavg CARDIO 2 -time -.1 .6 -mag -grad *trans_sss.fif  -new cardiocor_ > corrcardio.log

Adding markers based on eyelink markers and others artifact markers

Here we generate the final markers to be used for averaging and others processing by taking into account markers from the eyelink recordings and manually marked events (muscle activity).

foreach run (run??_trans_tsss.fif)

  alias dh "dataHandler -r $run"
  # defines EYE events as blinks and start of saccades > 5 degrees
  dh -adm "EYE = EL_ESACC_L_5 |EL_SBLINK_L_ |EL_EBLINK_L_ | EL_ESACC_R_5 |EL_SBLINK_R_ |EL_EBLINK_R_ "
  dh -adm "BLINK = EL_SBLINK_L_ |EL_EBLINK_L_ |EL_SBLINK_R_ |EL_EBLINK_R_"

  # select targets without EYE events in given range
  # one way is to define a fixed period "eyefree" around target
  dh -adm "FixPost=Fixation+.4"
  # defines FixOK in coincidence with FixPost
  dh -adm "FixOK=FixPost[Prime]&EYE~"

  # defines TargetOK in coincidence with Target, when immediately following a FixOK
  dh -adm "PaintOK=Target[Scale]&EYE~"
  dh -adm "TargetOK=PaintOK[-3 2.5]&FixOK"
  dh -adm "BlinkTarget=Target[Scale]&BLINK"

  # defines MUSCLE events indicated by bad markers
  dh -adm "MUSCLE = BAD"
  # select trials without MUSCLE events in given range
  dh -adm "MuscleOK=Fixation[Scale]&MUSCLE~"

  # select trials without clean baseline and target periods
  dh -adm "TrialOK=TargetOK[-3 2.5]&MuscleOK" > selectevents_5deg_${run}.log
end

Basic Triggers manipulation & Basic Averaging

You can then start averaging steps to obtain your evoked potentials:

foreach run in (cardiocor_*sss.fif)
   alias dh "dataHandler -r -avg $run "
   foreach cond (PCongruent PIncongruent PNoAction PNoPrimeBeginning PNoPrimeEnd)
	# baseline is taken from FixOK (.3s after Fixation) to Priming.
	dh -sync "TrialOK[-1.1 .5]&${cond}" -rbm FixOK 0 .2 -time -.1 1.1  CC_${cond}_5d.fif > averages.log
   end
end

:evp.png?500|