mne-tools / mne-python

MNE: Magnetoencephalography (MEG) and Electroencephalography (EEG) in Python
https://mne.tools
BSD 3-Clause "New" or "Revised" License
2.62k stars 1.3k forks source link

`mne.Brain` fails to set renderer when blocking #12607

Closed alexk101 closed 3 days ago

alexk101 commented 2 months ago

Description of the problem

We are attempting to create some visualization for some fnirs data and have found the existing visualizations functions to be insufficient for our needs. We, therefore, have been looking into creating some bespoke functions using the mne.viz.Brain class.

While doing this, we found that when setting the block param in the mne.viz.Brain constructor, subsequent calls to methods of the Brain class fail, specifically show_view.

Steps to reproduce

This snippet runs without issue

import mne

brain = mne.viz.Brain("sample", subjects_dir=subjects_dir)
brain.show_view(azimuth=190, elevation=70, distance=350, focalpoint=(0, 0, 20))

This snippet fails on the call to `show_view`
```python
import mne

brain = mne.viz.Brain("sample", subjects_dir=subjects_dir, block=True)
brain.show_view(azimuth=190, elevation=70, distance=350, focalpoint=(0, 0, 20))

### Link to data

n/a

### Expected results

Method calls to `Brain` objects created with the `block` param should not fail.

### Actual results

Method calls to `Brain` objects created with the `block` param fail. I expect that somewhere in this class that when `block` is set, once the window is closed, the renderer is cleaned up, so subsequent calls find that it is set to none. If we set the `show` param in the `Brain` constructor to False, then we again, don't receive this error.

### Additional information

Platform Linux-6.8.9-arch1-1-x86_64-with-glibc2.39 Python 3.11.8 | packaged by conda-forge | (main, Feb 16 2024, 20:53:32) [GCC 12.3.0] Executable /home/alexk101/.mambaforge/envs/fnirs/bin/python CPU (16 cores) Memory 30.5 GB

Core ├☑ mne 1.8.0.dev33+g1c5b39ff1d9 (devel, latest release is 1.7.0) ├☑ numpy 1.26.4 (OpenBLAS 0.3.26 with 16 threads) ├☑ scipy 1.12.0 └☑ matplotlib 3.8.3 (backend=QtAgg)

Numerical (optional) ├☑ sklearn 1.4.1.post1 ├☑ numba 0.59.0 ├☑ nibabel 5.2.1 ├☑ nilearn 0.10.3 ├☑ pandas 2.0.3 ├☑ h5io 0.2.2 ├☑ h5py 3.10.0 └☐ unavailable dipy, openmeeg, cupy

Visualization (optional) ├☑ pyvista 0.43.5 (OpenGL 4.5.0 NVIDIA 550.78 via NVIDIA GeForce RTX 3070 Ti Laptop GPU/PCIe/SSE2) ├☑ pyvistaqt 0.11.0 ├☑ vtk 9.2.6 ├☑ qtpy 2.4.1 (PyQt5=5.15.8) └☐ unavailable ipympl, pyqtgraph, mne-qt-browser, ipywidgets, trame_client, trame_server, trame_vtk, trame_vuetify

Ecosystem (optional) ├☑ mne-nirs 0.7.0.dev0 └☐ unavailable mne-bids, mne-features, mne-connectivity, mne-icalabel, mne-bids-pipeline, neo, eeglabio, edfio, mffpy, pybv

larsoner commented 2 months ago

Thinking about it, block=True shouldn't really be an argument to mne.viz.Brain at all. I can't imagine there is a wide use case for blocking the plot as soon as the Brain is created. +1 for deprecating the parameter for eventual removal.

Then we'd maybe want a way to block our 3D plots, like and equivalent of plt.show(block=True), but we can add that later if people really need it