internlm/SWE-Fixer-Train-110K huggingface dataset:
Repository: mne-tools/mne-python

Issue:
DOC improve description of dipole_fit procedure
The [example](https://www.martinos.org/mne/stable/auto_tutorials/source-modeling/plot_dipole_fit.html#) showing how to use `dipole_fit` do not give any information on how the source localization is done.

I guess this is probably planned to land in issue #5944 but is it possible to get some resources (like the original ECD paper) to document the general idea. I might give a try if I find some time.


Discussion:
@tomMoral I'm slowly working through the tutorials but I don't have a lot of experience with dipole fitting anyway so your input would be helpful.  If you open a PR I'll gladly review / help.

FYI #5944 is now sort of stale; the changes are being tackled one tutorial at a time instead of waiting until everything is finished and trying to merge them all in at once.
I think the question is what is a good academic reference for the dipole fitting algorithm.

maybe @mshamalainen can help here?


Resolving patch:
diff --git a/tutorials/source-modeling/plot_dipole_fit.py b/tutorials/source-modeling/plot_dipole_fit.py
--- a/tutorials/source-modeling/plot_dipole_fit.py
+++ b/tutorials/source-modeling/plot_dipole_fit.py
@@ -4,7 +4,7 @@
 Source localization with equivalent current dipole (ECD) fit
 ============================================================
 
-This shows how to fit a dipole using mne-python.
+This shows how to fit a dipole [1]_ using mne-python.
 
 For a comparison of fits between MNE-C and mne-python, see
 `this gist <https://gist.github.com/larsoner/ca55f791200fe1dc3dd2>`__.
@@ -101,3 +101,10 @@
 dip_fixed = mne.fit_dipole(evoked_full, fname_cov, fname_bem, fname_trans,
                            pos=dip.pos[best_idx], ori=dip.ori[best_idx])[0]
 dip_fixed.plot(time_unit='s')
+
+##############################################################################
+# References
+# ----------
+# .. [1] Sarvas, J. (1987). Basic mathematical and electromagnetic concepts of
+#        the biomagnetic inverse problem.
+#        Physics in Medicine & Biology, 32(1), 11.


Test patch:
Repository: mne-tools/mne-python

Issue:
Explained variance of eLORETA
Hi, I've seen that the Explained variance reported in the logger when using eLORETA is very strange:

> Applying inverse operator to "stim"...
    Picked 62 channels from the data
    Computing inverse...
    Eigenleads need to be weighted ...
    Computing residual...
    __Explained -916356207643396166123520.0% variance__
    Combining the current components...

When using dSPM the value makes more sense (1.9%)

I've seen that here:

https://github.com/mne-tools/mne-python/blob/3fafe437413f29b91f36ca2726a4cceb87dfbab7/mne/minimum_norm/inverse.py#L906

>data_est_w.max()
Out[15]: 3070785165274.191
>data_w.max()
Out[16]: 21.2237224470818

Maybe it is related to https://github.com/mne-tools/mne-python/pull/6050?
I wish a could try a solution but it goes beyond my current knowledge about computing inverse solutions.

Cheers,




Discussion:
Yes it's currently wrong. It would help if we just printed "unknown" rather than something nonsensical. Would you be up for making a PR to do that when the method is eLORETA?
Sure, I'll do it. Thanks for the clarification.

Resolving patch:
diff --git a/mne/minimum_norm/inverse.py b/mne/minimum_norm/inverse.py
--- a/mne/minimum_norm/inverse.py
+++ b/mne/minimum_norm/inverse.py
@@ -904,7 +904,12 @@ def apply_inverse(evoked, inverse_operator, lambda2=1. / 9., method="dSPM",
                              Pi[:, np.newaxis] * w_t))
     data_est_w = np.dot(inv['whitener'], np.dot(inv['proj'], data_est))
     var_exp = 1 - ((data_est_w - data_w) ** 2).sum() / (data_w ** 2).sum()
-    logger.info('    Explained %5.1f%% variance' % (100 * var_exp,))
+
+    if method == 'eLORETA':
+        logger.info('    Explained variance unknown')
+    else:
+        logger.info('    Explained %5.1f%% variance' % (100 * var_exp,))
+
     if return_residual:
         residual = evoked.copy()
         residual.data[sel] -= data_est


Test patch:
Repository: mne-tools/mne-python

Issue:
BUG/DOC: SSS origin
Hi,

I was fooling around with `mne.preprocessing.maxwell._sss_basis*`, which take an origin parameter for the vector spherical harmonics.

According to the docstring, the origin is given in millimeters. However moving the origin by `[0, 0, 1]` which should give a very modest effect, I get a drastically different SSS basis. Therefore, I suspect that the origin is actually in meters. Also it seems that the functions simply subtract the origin from `rmags` which seem to be in meters. So, can you confirm that the doc is wrong on this?





Discussion:
Yes we do everything in meters, PR welcome to clarify

Resolving patch:
diff --git a/mne/preprocessing/maxwell.py b/mne/preprocessing/maxwell.py
--- a/mne/preprocessing/maxwell.py
+++ b/mne/preprocessing/maxwell.py
@@ -1146,7 +1146,7 @@ def _sss_basis(exp, all_coils):
         Must contain the following keys:
 
             origin : ndarray, shape (3,)
-                Origin of the multipolar moment space in millimeters
+                Origin of the multipolar moment space in meters
             int_order : int
                 Order of the internal multipolar moment space
             ext_order : int
@@ -1439,7 +1439,7 @@ def _update_sss_info(raw, origin, int_order, ext_order, nchan, coord_frame,
         Data to be filtered
     origin : array-like, shape (3,)
         Origin of internal and external multipolar moment space in head coords
-        and in millimeters
+        (in meters)
     int_order : int
         Order of internal component of spherical expansion
     ext_order : int


Test patch:
Repository: mne-tools/mne-python

Issue:
BUG, VIZ: plot_vector_source_estimates
Bug most likely introduced in #7030 where `plot_vector_source_estimates` raises a `ValueError` when `hemi=both`. To reproduce, you can execute this [gist](https://gist.github.com/rythorpe/c51a5b66b492b67437843283c67050af).

More details in https://github.com/mne-tools/mne-python/pull/7030#issuecomment-555175886


Discussion:

Resolving patch:
diff --git a/mne/viz/_3d.py b/mne/viz/_3d.py
--- a/mne/viz/_3d.py
+++ b/mne/viz/_3d.py
@@ -2308,17 +2308,6 @@ def plot_vector_source_estimates(stc, subject=None, hemi='lh', colormap='hot',
                                scale_factor=scale_factor,
                                min=scale_pts[0], max=scale_pts[2],
                                **ad_kwargs)
-            if scale_factor is None:
-                # Compute the width of the brain
-                width = np.ptp(brain.geo[hemi].coords[:, 1])
-                # Retrieve the current hemi
-                for b in brain._brain_list:
-                    if b['hemi'] == hemi:
-                        found_hemi = b['brain']
-                layer_id = brain.data['layer_id']
-                # Configure the glyphs scale directly
-                glyphs = found_hemi.data[layer_id]['glyphs']
-                glyphs.glyph.glyph.scale_factor = width * 0.1
             # depth peeling patch
             if brain_alpha < 1.0:
                 for ff in brain._figures:
@@ -2327,6 +2316,19 @@ def plot_vector_source_estimates(stc, subject=None, hemi='lh', colormap='hot',
                             f.scene.renderer.use_depth_peeling = True
         brain.scale_data_colormap(fmin=scale_pts[0], fmid=scale_pts[1],
                                   fmax=scale_pts[2], **sd_kwargs)
+    if scale_factor is None:
+        # Compute the width of the brain
+        width = np.mean([np.ptp(brain.geo[hemi].coords[:, 1])
+                         for hemi in hemis])
+        for hemi in hemis:
+            # Retrieve the current hemi
+            for b in brain._brain_list:
+                if b['hemi'] == hemi:
+                    found_hemi = b['brain']
+            # Configure the glyphs scale directly
+            for layer in found_hemi.data.values():
+                glyphs = layer['glyphs']
+                glyphs.glyph.glyph.scale_factor = width * 0.1
 
     if time_viewer:
         TimeViewer(brain)


Test patch:
diff --git a/mne/viz/tests/test_3d.py b/mne/viz/tests/test_3d.py
--- a/mne/viz/tests/test_3d.py
+++ b/mne/viz/tests/test_3d.py
@@ -578,6 +578,7 @@ def test_plot_vec_source_estimates():
     with pytest.raises(ValueError, match='use "pos_lims"'):
         stc.plot('sample', subjects_dir=subjects_dir,
                  clim=dict(pos_lims=[1, 2, 3]))
+    stc.plot('sample', subjects_dir=subjects_dir, hemi='both')
 
 
 @testing.requires_testing_data
Repository: mne-tools/mne-python

Issue:
MRG, MAINT: Reduce memory
@drammock this is one way to take the memory from (master):

![Figure_1](https://user-images.githubusercontent.com/2365790/69453774-a706fb80-0d32-11ea-862f-c3049e534bb3.png)

To (this PR):

![Figure_2](https://user-images.githubusercontent.com/2365790/69453795-b0906380-0d32-11ea-8cd4-61d5d08d5f5e.png)

If you don't like how it changes the narrative, feel free to close this and do it a different way (e.g., by deleting objects or using fewer epochs, or slices of epochs rather than epochs.copy, etc.).


Discussion:

Resolving patch:
diff --git a/tutorials/epochs/plot_10_epochs_overview.py b/tutorials/epochs/plot_10_epochs_overview.py
--- a/tutorials/epochs/plot_10_epochs_overview.py
+++ b/tutorials/epochs/plot_10_epochs_overview.py
@@ -71,12 +71,13 @@
 # The example dataset we've been using thus far doesn't include pre-epoched
 # data, so in this section we'll load the continuous data and create epochs
 # based on the events recorded in the :class:`~mne.io.Raw` object's STIM
-# channels.
+# channels. As we often do in these tutorials, we'll :meth:`~mne.io.Raw.crop`
+# the :class:`~mne.io.Raw` data to save memory:
 
 sample_data_folder = mne.datasets.sample.data_path()
 sample_data_raw_file = os.path.join(sample_data_folder, 'MEG', 'sample',
                                     'sample_audvis_raw.fif')
-raw = mne.io.read_raw_fif(sample_data_raw_file, verbose=False)
+raw = mne.io.read_raw_fif(sample_data_raw_file, verbose=False).crop(tmax=60)
 
 ###############################################################################
 # As we saw in the :ref:`tut-events-vs-annotations` tutorial, we can extract an


Test patch:
Repository: mne-tools/mne-python

Issue:
misleading info message in compute_rank
in reviewing #7085 I noticed the output of running `mne.compute_covariance(epochs, ...)` yields the info message 

> Computing data rank from raw with rank=None

Looks like `mne.compute_covariance` converts `epochs` to a numpy array (let's call it "data"), and then `_compute_covariance_auto(data, ...)` calls `compute_rank(RawArray(data.T, ...), ...)`.  So the message will always say you're computing from "raw" regardless of whether you pass in `Raw` or `Epochs`


Discussion:
Yeah it should probably say "Computing rank from data with rank=None" or so, feel free to put it in some PR

Resolving patch:
diff --git a/mne/rank.py b/mne/rank.py
--- a/mne/rank.py
+++ b/mne/rank.py
@@ -339,8 +339,8 @@ def compute_rank(inst, rank=None, scalings=None, info=None, tol='auto',
                                     for name in inst['names']])
     else:
         info = inst.info
-        inst_type = 'raw' if isinstance(inst, BaseRaw) else 'epochs'
-    logger.info('Computing data rank from %s with rank=%r' % (inst_type, rank))
+        inst_type = 'data'
+    logger.info('Computing rank from %s with rank=%r' % (inst_type, rank))
 
     _validate_type(rank, (str, dict, None), 'rank')
     if isinstance(rank, str):  # string, either 'info' or 'full'


Test patch:
Repository: mne-tools/mne-python

Issue:
vims not the same for all images of evoked.plot_image with group_by and axes dicts and a mask
See:

```
import mne

evoked = mne.read_epochs(mne.datasets.kiloword.data_path() + "/kword_metadata-epo.fif").average()
evoked.data[0, :] *= 10
group_by = mne.channels.make_1020_channel_selections(evoked.info, midline="z12")
fig, axes = plt.subplots(nrows=3)
fig.set_size_inches((8, 10))
axes = {roi: ax for roi, ax in zip(group_by, axes)}

evoked.plot_image(
    axes=axes, group_by=group_by, show_names="all", show=False,
    mask=evoked.data < 0
);
```

If you remove the mask, all images have the same vlims.

@drammock if you have time, otherwise I will try to get to it in a month or so.


Discussion:

Resolving patch:
diff --git a/mne/viz/utils.py b/mne/viz/utils.py
--- a/mne/viz/utils.py
+++ b/mne/viz/utils.py
@@ -2883,6 +2883,7 @@ def _plot_masked_image(ax, data, times, mask=None, yvals=None,
             im = ax.imshow(
                 np.ma.masked_where(~mask, data), cmap=cmap, **im_args)
         else:
+            ax.imshow(data, cmap=cmap, **im_args)  # see #6481
             im = ax.imshow(data, cmap=cmap, **im_args)
 
         if draw_contour and np.unique(mask).size == 2:


Test patch:
Repository: mne-tools/mne-python

Issue:
Error when reading BDF file with multiple annotation channels
As reported on the mailing list, [this file](https://drive.google.com/file/d/1GP5FT84sabMCGBRY4oXikcxGf-kKIoa0/view?usp=sharing) cannot be read and throws the following error:

```
Traceback (most recent call last):
  File "mne-python/mne/io/edf/edf.py", line 314, in _read_segment_file
    data[ii, d_sidx:d_eidx] = ch_data.ravel()[r_sidx:r_eidx]
IndexError: index 20 is out of bounds for axis 0 with size 19
```

It seems like this is because the file contains 15 annotation channels (indices 19-33) and the code can only handle one at the moment.

I'll look into it.


Discussion:

Resolving patch:
diff --git a/mne/io/edf/edf.py b/mne/io/edf/edf.py
--- a/mne/io/edf/edf.py
+++ b/mne/io/edf/edf.py
@@ -284,7 +284,7 @@ def _read_segment_file(data, idx, fi, start, stop, raw_extras, chs, filenames):
                 # This now has size (n_chunks_read, n_samp[ci])
                 ch_data = many_chunk[:, ch_offsets[ci]:ch_offsets[ci + 1]]
 
-                if len(tal_idx) and ci == tal_idx[0]:
+                if len(tal_idx) and ci in tal_idx:
                     tal_data.append(ch_data)
                     continue
 


Test patch:
Repository: mne-tools/mne-python

Issue:
plot_epochs_image fails to create new figure when called a second time
**Issue can be reproduced as follows:**

```import mne
import numpy as np
data = np.random.RandomState(0).randn(5, 2, 1000)
info = mne.create_info(2, 1000., 'eeg')
epochs = mne.EpochsArray(data, info)
epochs.plot_image()
epochs.plot_image() # replaces data in first figure window
```
**issue can be worked around with:**

```
def plot_epochs_image_fixed(epochs, *args, **kwargs):
    from matplotlib.pyplot import figure, subplot2grid
    fig = figure()
    colspan = 9
    rowspan = 2
    shape = (3, 10)
    axes = [
        subplot2grid(shape, (0, 0), colspan=colspan, rowspan=rowspan, fig=fig),
        subplot2grid(shape, (2, 0), colspan=colspan, rowspan=1, fig=fig),
        subplot2grid(shape, (0, 9), colspan=1, rowspan=rowspan, fig=fig)]
    return mne.viz.plot_epochs_image(
        epochs, *args, **kwargs, axes=axes)

plot_epochs_image_fixed(epochs)
plot_epochs_image_fixed(epochs) # new figure window
```
_Thanks to Eric Larson for devising reproduction and workaround_



Discussion:

Resolving patch:
diff --git a/mne/viz/epochs.py b/mne/viz/epochs.py
--- a/mne/viz/epochs.py
+++ b/mne/viz/epochs.py
@@ -394,7 +394,8 @@ def _validate_fig_and_axes(fig, axes, group_by, evoked, colorbar, clear=False):
         rowspan = 2 if evoked else 3
         shape = (3, 10)
         for this_group in group_by:
-            this_fig = figure(this_group)
+            this_fig = figure()
+            this_fig.canvas.set_window_title(this_group)
             kwargs = dict()
             if check_version('matplotlib', '2.2'):
                 kwargs['fig'] = this_fig  # unavailable on earlier mpl


Test patch:
diff --git a/mne/viz/tests/test_epochs.py b/mne/viz/tests/test_epochs.py
--- a/mne/viz/tests/test_epochs.py
+++ b/mne/viz/tests/test_epochs.py
@@ -174,9 +174,14 @@ def test_plot_epochs_image():
     `plt.close('all')` just before the offending test seems to prevent this
     warning, though it's unclear why.
     """
+    plt.close('all')
     epochs = _get_epochs()
     figs = epochs.plot_image()
     assert len(figs) == 2  # one fig per ch_type (test data has mag, grad)
+    assert len(plt.get_fignums()) == 2
+    figs = epochs.plot_image()
+    assert len(figs) == 2
+    assert len(plt.get_fignums()) == 4  # should create new figures
     epochs.plot_image(picks='mag', sigma=0.1)
     epochs.plot_image(picks=[0, 1], combine='mean',
                       ts_args=dict(show_sensors=False))
Repository: mne-tools/mne-python

Issue:
Default brainmask value in mne.bem.make_watershed_bem would incur an error by Freesurfer(dev) mri_watershed
#### Describe the bug
Default brainmask value in `mne.bem.make_watershed_bem` would incur an error by Freesurfer (dev a76846c, latest atm) `mri_watershed`

https://github.com/mne-tools/mne-python/blob/maint/0.19/mne/bem.py#L1036

******************************
Saving /home/foucault/data/derivatives/freesurfer/sub-103/bem/watershed/ws
error: unknown file type for file (/home/foucault/data/derivatives/freesurfer/sub-103/bem/watershed/ws)

If the `brainmask='brainmask.mgz'`or `brainmask='ws.mgz'` is set, there's no error message then.



Discussion:
what is the fix?

>

Replace the default value `brainmask='ws'` with `brainmask='ws.mgz'`?

The document (https://github.com/mne-tools/mne-python/blame/master/doc/_includes/bem_model.rst#L42)
 said `ws` is a folder name, but `ws` here is just a file name. Perhaps, a structure like `bem/watershed/ws.mgz` would be satisfying?
So, also suggest to modify the documentation to replace the word `directory` with `file` so that the sentence becomes the following:
 there will be a file called :file:`bem/watershed/ws.mgz` which contains the brain MRI volume.

The output folder structure after modifacation of the default brainmask value to `ws.mgz` would be like :
```
.
├── brain.surf -> watershed/sub-103_brain_surface
├── inner_skull.surf -> watershed/sub-103_inner_skull_surface
├── outer_skin.surf -> watershed/sub-103_outer_skin_surface
├── outer_skull.surf -> watershed/sub-103_outer_skull_surface
├── sub-103-head.fif
└── watershed
         ├── ws.mgz
         ├── sub-103_brain_surface
         ├── sub-103_inner_skull_surface
         ├── sub-103_outer_skin_surface 
```


I could do a PR for this if it is appropriate.
That sounds reasonable to me
+1

>


Resolving patch:
diff --git a/mne/bem.py b/mne/bem.py
--- a/mne/bem.py
+++ b/mne/bem.py
@@ -1042,7 +1042,7 @@ def _check_origin(origin, info, coord_frame='head', disp=False):
 @verbose
 def make_watershed_bem(subject, subjects_dir=None, overwrite=False,
                        volume='T1', atlas=False, gcaatlas=False, preflood=None,
-                       show=False, copy=False, T1=None, brainmask='ws',
+                       show=False, copy=False, T1=None, brainmask='ws.mgz',
                        verbose=None):
     """Create BEM surfaces using the FreeSurfer watershed algorithm.
 


Test patch:
Repository: mne-tools/mne-python

Issue:
'CNTEventType1' object has no attribute 'Latency'
Hi, 

I am trying to read raw EEG from .cnt files. However, Python3 returns the below error. The dataset I am reading is from UC San Diego https://sccn.ucsd.edu/~arno/fam2data/publicly_available_EEG_data.html. 

The dataset can be easily read by EEGLAB, however, I try to do everythig in Python3. 
If comment the lines shown in the Errors, I still receive the correct result. 

`Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python3.7/site-packages/mne/io/cnt/cnt.py", line 169, in read_raw_cnt
    preload=preload, stim_channel=stim_channel, verbose=verbose)
  File "/usr/local/lib/python3.7/site-packages/mne/io/cnt/cnt.py", line 429, in __init__
    _read_annotations_cnt(input_fname, data_format=data_format))
  File "/usr/local/lib/python3.7/site-packages/mne/io/cnt/cnt.py", line 88, in _read_annotations_cnt
    duration = np.array([e.Latency for e in my_events], dtype=float)
  File "/usr/local/lib/python3.7/site-packages/mne/io/cnt/cnt.py", line 88, in <listcomp>
    duration = np.array([e.Latency for e in my_events], dtype=float)
AttributeError: 'CNTEventType1' object has no attribute 'Latency'`


Discussion:
which specific file did you try to read?

>

> which specific file did you try to read?
> […](#)

They are .cnt files recorded by Neuroscan devices. 
The page you point to contains many files. Can you help us by telling which one we should test first ? It saves time for us. Thanks 

I am sorry. 
Below is the link to my drive for one .cnt file. 
https://drive.google.com/file/d/1BNHjcJUSWLXSpXQ1aeVZ3KS4XzX-CfLS/view?usp=sharing

Resolving patch:
diff --git a/mne/io/cnt/cnt.py b/mne/io/cnt/cnt.py
--- a/mne/io/cnt/cnt.py
+++ b/mne/io/cnt/cnt.py
@@ -83,7 +83,9 @@ def _translating_function(offset, n_channels, event_type,
                                       n_channels=n_channels,
                                       event_type=type(my_events[0]),
                                       data_format=data_format)
-        duration = np.array([e.Latency for e in my_events], dtype=float)
+        duration = np.array([getattr(e, 'Latency', 0.) for e in my_events],
+                            dtype=float)
+
         description = np.array([str(e.StimType) for e in my_events])
         return Annotations(onset=onset / sfreq,
                            duration=duration,


Test patch: