Removing time segments from raw object without epoching

  • MNE version: 0.24.0
  • operating system: macOS 12.0.1

Dear MNE experts,

Due to specific design of my MEG experiment, I would need to separate different experimental conditions and reject some time segments (e.g. inter-trial intervals) from RAW object (without epoching), and obtain updated event arrays or annotations.
I tried to add annotations to the RAW object according to the following tutorial:
https://mne.tools/stable/auto_tutorials/preprocessing/20_rejecting_bad_data.html
As far as I understood, the “Bad Breaks” can be rejected from epoched data but not from a raw object.
of course, I could use raw.get_data() and do all these steps using Numpy. Thought maybe there is an MNE function for this purpose which takes care of events’/annotations’ timing, automatically.

Best,
Keyvan

There currently isn’t a simple way to cut a span out of the middle of a Raw object. It is possible to do it by repeatedly copying and cropping the raw, and then concatenating the resulting shorter raw spans. Some pseudocode:

  • make an empty container list
  • for index in range(len(raw.annotations)):
    • copy the raw
    • get annotation onset and duration
    • if it’s the first annotation, crop the copy from beginning of raw to onset of raw.annotations[index]; otherwise, crop from raw.annotations[index].onset + raw.annotations[index].duration to raw.annotations[index + 1].onset
    • append the cropped raw to a container list
  • concatenate the raws in the container list

the resulting concatenated raw will have new edge annotations at every concatenation point, so that MNE-Python’s filtering operations will know not to treat that part of the data as continuous.

1 Like

Thanks for sharing your points. I ended up with the following function!

def reject_bad_segs(raw):
    """ This function rejects all time spans annotated as 'bad_ITI' and concatenates the rest"""
    raw_segs = []
    for jsegment in range(len(raw.annotations)):
        if raw.annotations.description[jsegment] != 'bad_ITI':  # Append all other than 'bad_ITI'
            raw_segs.append(raw.copy().crop(tmin=raw.annotations.onset[jsegment], tmax=raw.annotations.onset[jsegment+1],
            include_tmax=False))
    return mne.concatenate_raws(raw_segs)