Procedure to detect non-steady state volumes in rsfMRI

Hi AFNI experts,

I am using AFNI_24.2.01 'Macrinus' with a multiband rsfMRI dataset. Prior to preprocessing, is there an AFNI command or set of commands that can be used to determine whether your data has any initial non-steady-state volumes?

Best,
Jenna

Hi, Jenna-

The simplest and quickest way to do this: open up the FMRI time series in the GUI, set it to be the underlay, and look at the graph time series. If all time series have one or a couple big values to start and then smaller ones after, you likely have pre-steady state time series.

More automagically, afni_proc.py will do this as part of its processing, and save the result to a text file. It reports this as part of its warnings. See Fig. 17 here:

For checking a lot of data quickly and systematically for pre-steady state and other charming quirks, we typically recommend running the script ap_run_simple_rest.tcsh, which runs afni_proc.py for a rest-like processing, making most choices for you so you just need to input 1 or more EPIs and that's basically it (you can also include an anatomical, though it isn't necessary). It runs relatively speedily, because it will just do affine registation to a template if you provide an anatomical, rather than slower nonlinear alignment. This will run AP through regression, per usual, so you can get a quick QC generated and see the outputs easily, including the warnings. It's what we recommend running quickly on any downloaded data to systematically+efficiently check it, as well as something you can run on data you acquire to quickly check it without having to worry about processing details.

Finally, you could steal what AP itself creates within the proc script to do its pre-steady state investigation. That chunk of the code looks like this (it's tcsh syntax):

# ========================== auto block: outcount ==========================
# QC: compute outlier fraction for each volume
touch out.pre_ss_warn.txt
foreach run ( $runs )
    3dToutcount -automask -fraction -polort 3 -legendre                     \
                pb00.$subj.r$run.tcat+orig > outcount.r$run.1D

    # censor outlier TRs per run, ignoring the first 0 TRs
    # - censor when more than 0.05 of automask voxels are outliers
    # - step() defines which TRs to remove via censoring
    1deval -a outcount.r$run.1D -expr "1-step(a-0.05)" > rm.out.cen.r$run.1D

    # outliers at TR 0 might suggest pre-steady state TRs
    if ( `1deval -a outcount.r$run.1D"{0}" -expr "step(a-0.4)"` ) then
        echo "** TR #0 outliers: possible pre-steady state TRs in run $run" \
            >> out.pre_ss_warn.txt
    endif
end

# catenate outlier counts into a single time series
cat outcount.r*.1D > outcount_rall.1D

# catenate outlier censor files into a single time series
cat rm.out.cen.r*.1D > outcount_${subj}_censor.1D

... but note that running the simple AP should be even easier and include checks for many more things: scanner saturation, variance lines, high motion, and more.

--pt