{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "\n\n# Compute cross-talk functions for LCMV beamformers\n\nVisualise cross-talk functions at one vertex for LCMV beamformers computed\nwith different data covariance matrices, which affects their cross-talk\nfunctions.\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "# Author: Olaf Hauk \n#\n# License: BSD-3-Clause\n# Copyright the MNE-Python contributors." ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "import mne\nfrom mne.beamformer import make_lcmv, make_lcmv_resolution_matrix\nfrom mne.datasets import sample\nfrom mne.minimum_norm import get_cross_talk\n\nprint(__doc__)\n\ndata_path = sample.data_path()\nsubjects_dir = data_path / \"subjects\"\nmeg_path = data_path / \"MEG\" / \"sample\"\nfname_fwd = meg_path / \"sample_audvis-meg-eeg-oct-6-fwd.fif\"\nfname_cov = meg_path / \"sample_audvis-cov.fif\"\nfname_evo = meg_path / \"sample_audvis-ave.fif\"\nraw_fname = meg_path / \"sample_audvis_filt-0-40_raw.fif\"\n\n# Read raw data\nraw = mne.io.read_raw_fif(raw_fname)\n\n# only pick good EEG/MEG sensors\nraw.info[\"bads\"] += [\"EEG 053\"] # bads + 1 more\npicks = mne.pick_types(raw.info, meg=True, eeg=True, exclude=\"bads\")\n\n# Find events\nevents = mne.find_events(raw)\n\n# event_id = {'aud/l': 1, 'aud/r': 2, 'vis/l': 3, 'vis/r': 4}\nevent_id = {\"vis/l\": 3, \"vis/r\": 4}\n\ntmin, tmax = -0.2, 0.25 # epoch duration\nepochs = mne.Epochs(\n raw,\n events,\n event_id=event_id,\n tmin=tmin,\n tmax=tmax,\n picks=picks,\n baseline=(-0.2, 0.0),\n preload=True,\n)\ndel raw\n\n# covariance matrix for pre-stimulus interval\ntmin, tmax = -0.2, 0.0\ncov_pre = mne.compute_covariance(epochs, tmin=tmin, tmax=tmax, method=\"empirical\")\n\n# covariance matrix for post-stimulus interval (around main evoked responses)\ntmin, tmax = 0.05, 0.25\ncov_post = mne.compute_covariance(epochs, tmin=tmin, tmax=tmax, method=\"empirical\")\ninfo = epochs.info\ndel epochs\n\n# read forward solution\nforward = mne.read_forward_solution(fname_fwd)\n# use forward operator with fixed source orientations\nmne.convert_forward_solution(forward, surf_ori=True, force_fixed=True, copy=False)\n\n# read noise covariance matrix\nnoise_cov = mne.read_cov(fname_cov)\n\n# regularize noise covariance (we used 'empirical' above)\nnoise_cov = mne.cov.regularize(noise_cov, info, mag=0.1, grad=0.1, eeg=0.1, rank=\"info\")" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Compute LCMV filters with different data covariance matrices\n\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "# compute LCMV beamformer filters for pre-stimulus interval\nfilters_pre = make_lcmv(\n info,\n forward,\n cov_pre,\n reg=0.05,\n noise_cov=noise_cov,\n pick_ori=None,\n rank=None,\n weight_norm=None,\n reduce_rank=False,\n verbose=False,\n)\n\n# compute LCMV beamformer filters for post-stimulus interval\nfilters_post = make_lcmv(\n info,\n forward,\n cov_post,\n reg=0.05,\n noise_cov=noise_cov,\n pick_ori=None,\n rank=None,\n weight_norm=None,\n reduce_rank=False,\n verbose=False,\n)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Compute resolution matrices for the two LCMV beamformers\n\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "# compute cross-talk functions (CTFs) for one target vertex\nsources = [3000]\nverttrue = [forward[\"src\"][0][\"vertno\"][sources[0]]] # pick one vertex\nrm_pre = make_lcmv_resolution_matrix(filters_pre, forward, info)\nstc_pre = get_cross_talk(rm_pre, forward[\"src\"], sources, norm=True)\ndel rm_pre" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "rm_post = make_lcmv_resolution_matrix(filters_post, forward, info)\nstc_post = get_cross_talk(rm_post, forward[\"src\"], sources, norm=True)\ndel rm_post" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Visualize\nPre:\n\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "brain_pre = stc_pre.plot(\n \"sample\",\n \"inflated\",\n \"lh\",\n subjects_dir=subjects_dir,\n figure=1,\n clim=dict(kind=\"value\", lims=(0, 0.2, 0.4)),\n)\n\nbrain_pre.add_text(\n 0.1,\n 0.9,\n \"LCMV beamformer with pre-stimulus\\ndata covariance matrix\",\n \"title\",\n font_size=16,\n)\n\n# mark true source location for CTFs\nbrain_pre.add_foci(\n verttrue, coords_as_verts=True, scale_factor=1.0, hemi=\"lh\", color=\"green\"\n)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Post:\n\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "brain_post = stc_post.plot(\n \"sample\",\n \"inflated\",\n \"lh\",\n subjects_dir=subjects_dir,\n figure=2,\n clim=dict(kind=\"value\", lims=(0, 0.2, 0.4)),\n)\n\nbrain_post.add_text(\n 0.1,\n 0.9,\n \"LCMV beamformer with post-stimulus\\ndata covariance matrix\",\n \"title\",\n font_size=16,\n)\n\nbrain_post.add_foci(\n verttrue, coords_as_verts=True, scale_factor=1.0, hemi=\"lh\", color=\"green\"\n)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The pre-stimulus beamformer's CTF has lower values in parietal regions\nsuppressed alpha activity?) but larger values in occipital regions (less\nsuppression of visual activity?).\n\n" ] } ], "metadata": { "kernelspec": { "display_name": "Python 3", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.12.2" } }, "nbformat": 4, "nbformat_minor": 0 }