Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ENH: Agenda for fNIRS processing #7057

Closed
13 of 19 tasks
rob-luke opened this issue Nov 14, 2019 · 51 comments
Closed
13 of 19 tasks

ENH: Agenda for fNIRS processing #7057

rob-luke opened this issue Nov 14, 2019 · 51 comments
Milestone

Comments

@rob-luke
Copy link
Member

rob-luke commented Nov 14, 2019

The current status of NIRS support can be seen in this tutorial.

Here is a rough plan for the development of fNIRS processing in MNE.

Refactor existing code:

  • Use write wavelengths to info['chs'][ii][loc][9] in addition to the channel name
  • Use the info['chs'][ii][loc][9] value rather than channel names in preprocessing

Integrate fNIRS to existing MNE functions:

  • Add support for hbo/hbr to plot_topomap
  • Add support for hbo/hbr to plot_joint

Channel quality measures:

Add overlapping channel support to (these may already work with code changes I made, but don't have tests if they aren't ticked):

Movement correction

Interpolation of bad channels:

File support:

  • Add SNIRF reader MRG: Add SNIRF reader #7972
  • Add SNIRF writer
  • Add BIDS support
  • Add NIRSport1 file reader
  • Add NIRSport2 file reader (low priority as device will soon export in SNIRF format)
  • Add Artinis file reader

Implement HRF GLM style analysis Moved to MNE-NIRS till mature enough to merge in
Source Analysis Moved to MNE-NIRS till mature enough to merge in

@rob-luke
Copy link
Member Author

Currently I am looking at the temporal whitening tutorial as a starting place for the first step of the GLM implementation.

@larsoner
Copy link
Member

larsoner commented Nov 14, 2019

@rob-luke WDYT about implementing TDDR? There is MIT licensed code here that we could adapt.

@larsoner
Copy link
Member

(Unrelatedly, also added a note about refactoring the wavelength to use info['chs'][ii]['loc'] rather than the channel name)

@agramfort
Copy link
Member

agramfort commented Nov 14, 2019 via email

@larsoner
Copy link
Member

Agreed, not sure about prevalence. @rob-luke hopefully can comment.

FWIW the code for TDDR is about 20 active lines so not too painful :)

@rob-luke
Copy link
Member Author

@rob-luke WDYT about implementing TDDR? There is MIT licensed code here that we could adapt.

From that style of processing, TDDR is my preferred approach. I would be happy to implement it after the items listed above.

@rob-luke
Copy link
Member Author

if the code becomes too big I would start by putting it in
dedicated projects unless there is a consensus so that 80% of people will
use this tool anyway

This is handy to know, it will help me think about what to implement in this repo

@rob-luke
Copy link
Member Author

I have put my name next to the items that I have rough code already working for.

@rob-luke
Copy link
Member Author

There is now a python TDDR implementation here.

@agramfort
Copy link
Member

agramfort commented Feb 13, 2020 via email

@rob-luke
Copy link
Member Author

MIT license so we can use it in MNE

Great to hear. Whats the best way to go about adding external code? I assume we don't want to add that repository as a dependency. Do you usually email the author and ask them to add it to MNE, or ask permission for me to add it? Seems like most of the work will be around the data format management which I can do.

@drammock
Copy link
Member

@rob-luke We'll want some changes to docstring, code formatting, etc, so to me it would seem odd to ask the original author to do that work for us. But I think it's polite to let them know that you're going to incorporate their work into MNE-Python, and ask if/how they want to be involved and/or credited.

@rob-luke
Copy link
Member Author

Thanks, I'll get in touch with the author and offer to do the bulk of the boring work and ask how they want to be involved/credited.

@rob-luke
Copy link
Member Author

rob-luke commented Mar 27, 2020

With the 0.20 release coming out soon I thought it would be a good time to say thanks to @larsoner and @agramfort for all the help getting this NIRS integration working. Right now I just completed an analysis ready for publication entirely with MNE. To me it seems all the basic requirements for a NIRS analysis is now present in MNE. Next comes the fun part of developing more advanced analysis/algorithms. Thanks again.

@agramfort
Copy link
Member

agramfort commented Mar 27, 2020 via email

@rob-luke
Copy link
Member Author

don't forget to give us academic credit :)

Absolutely!!

@larsoner
Copy link
Member

Great to hear @rob-luke ! Thanks to you for implementing this stuff, hope to start using it (and contributing more myself) soon :)

@agramfort
Copy link
Member

agramfort commented Apr 15, 2020 via email

@rob-luke
Copy link
Member Author

Thats exactly what I needed @agramfort, somehow I had missed nistats. Thanks

@rob-luke
Copy link
Member Author

rob-luke commented Apr 16, 2020

Ok I got carried away and have made a first pass at the HRF style analysis based on nistats at...

https://mne.tools/mne-nirs/auto_examples/plot_10_hrf.html

And created a meta issue of this meta issue to track my thoughts. I pinged you both as an FYI.

@larsoner
Copy link
Member

Awesome example! I've subscribed to the repo :)

@rob-luke
Copy link
Member Author

Thanks. I will continue the HRF analysis development in MNE-NIRS and once matured we will merge in to MNE.

@kylemath
Copy link
Contributor

Glad I found this great discussion, I have an imagent from ISS and am working on a function to load its phase and intensity data into a MNE format similar to the NIRx.py loading example. We are thinking of moving our code base for fast optical imaging from matlab into python with these tools (currently at github.com/kylemath/mopt3d). Look like you all have thought about many of the major hurdles already, I think I gathered I should work from this new repo: https://github.com/mne-tools/mne-nirs?

@larsoner
Copy link
Member

@kylemath the plan at this point is to support all of the stuff at the top of this issue directly in MNE-Python except what is marked as being for mne-nirs. Mostly that means I/O of fNIRS data is in scope for MNE-Python, but HRF deconvolution is being worked out right now in mne-nirs. Basically mne-nirs is there to allow @rob-luke and other to try things out and figure out APIs, and once they are settled, things should migrate to MNE-Python.

I think I gathered I should work from this new repo: https://github.com/mne-tools/mne-nirs?

I would say you should try implementing your mne.io.read_raw_imagent or mne.io.read_raw_iss here first, probably with guidance from @rob-luke. Once that's it, talk with him about what fits better here or in mne-nirs based on what is standard (enough) practice in the field.

At least that's how I see it! Feel free to clarify @rob-luke @agramfort

@rob-luke
Copy link
Member Author

Hi @kylemath,
I agree with @larsoner, lets get the imagent reader straight in to MNE. I would recommend including at least the following files:

MOpt3d looks great. I think that kind of functionality is more suited to MNE-NIRS than MNE for now. Particularly photon migration is something I would love to get up running (see issue). A quick stalk of your repository reveals that you have extensive experience in this style of analysis. I am trying to sketch out a roadmap over at MNE-NIRS by opening issues, please feel free to create/comment on issues to share your experience of what works or doesn't, or what functionality you think is essential or not.

@kylemath
Copy link
Contributor

kylemath commented Apr 29, 2020

@rob-luke @larsoner - My student and I are working on the function to load BOXY data files from the imagent software, along with digitized sensor location files and lists of location names for our helmets. Screen Shot 2020-04-29 at 4 44 55 PM
This is working quite well at https://github.com/kylemath/pyoptical. We compute the transformation matrix needed to go from our sensor space into the fsaverage space, and add it to the info object to get added to the Raw data objects.

ch_pos, ch_names = ourLoadFunction(datafile)
montage = make_dig_montage(ch_pos, fiducials)
info = create_info(ch_names, srate, 'eeg').set_montage(montage)
mri_fiducials = read_fiducials(fsaverage)
trans = coregister_fiducials(info, fiducials)

We noticed that the nirx function does things a bit different, by precomputing a transformation matrix from fsaverage, applying it to the fNIRS sensor coordinates and outputing those TRANSFORMED VALUES without a transformation matrix. Why does NIRx.py apply the transform ahead of time? Instead of leaving it up to the user?

@larsoner
Copy link
Member

Why does NIRx.py apply the transform ahead of time? Instead of leaving it up to the user?

Channel locations in MNE-Python are supposed to be stored in Neuromag head coordinates, see:

https://mne.tools/dev/auto_tutorials/source-modeling/plot_source_alignment.html
https://mne.tools/dev/overview/implementation.html#the-forward-solution

So the read_raw_nirx transforms them to the head coordinate frame. Since the NIRx are in MNI (apparently?) and fsaverage is in MNI, you can just use fsaverage's standard transformation to get them to (fsaverage) head coordinates.

@larsoner
Copy link
Member

... but see also the evolving discussion here #7691 (comment)

@kylemath
Copy link
Contributor

Ok thanks, I think part of our confusing is that we only have two coordinate frames, and our "head" and "MEG" frames are aligned.

  1. We digitize 300 points on the optical imaging headgear with a subset of those being channel locations (sources or detectors), as well as around the eyes, and fiducials. I am assuming this is our "head" frame.

  2. A subset of these points are also the locations of light sources and detectors, which I assume is like the "MEG" frame, but is already co-registered with our "HEAD" frame

  3. Then we have an average or subject specific MRI parcellation of the surface of the head, "MRI" frame

So I guess this is more analogous to the EEG coregistration in that regard. Is there some discussion of this EEG coregistration case somewhere I can't see, I see this, but not how to get the trans matrix: https://mne.tools/stable/auto_examples/visualization/plot_eeg_on_scalp.html

@rob-luke
Copy link
Member Author

Hi @kylemath,

I will leave these coordinate questions to the others. But it might be easier if you open a pull request as a WIP in this repository for the imagent data reader, that way we can comment directly on the code and iterate faster.

@kylemath
Copy link
Contributor

kylemath commented Apr 30, 2020 via email

@rob-luke
Copy link
Member Author

rob-luke commented May 1, 2020

Great, didn't mean to rush you, just whenever you have time. I found the support from the MNE team very encouraging when I added the NIRX reader.

Opening a PR will also move the detailed conversation there and keep this issue more for higher level agenda discussion.

@kylemath
Copy link
Contributor

kylemath commented May 3, 2020

Moved this discussion to: #7717 @rob-luke

@larsoner
Copy link
Member

@rob-luke this is marked for a 0.21 milestone. Could you look into the remaining plotting issues above in the next couple of weeks so that we can tick a few more boxes for 0.21?

@rob-luke
Copy link
Member Author

Sure I can take a crack at PSD and TFR, but I don't know what projs is and if its relevant to NIRS. The other file type readers are also out of my control, particularly the artinis won't be done by 0.21. Do you plan to create another meta issue after 0.21 for the outstanding issues? I think we could ditch the mega meta style list as everything is running pretty well now and just tackle issues as they arise.

@larsoner
Copy link
Member

larsoner commented Sep 1, 2020

Projs we can tackle at some point if people want to try using it as a means of noise suppression. Agreed we can just open PRs for readers as necessary

@larsoner larsoner closed this as completed Sep 1, 2020
@rob-luke
Copy link
Member Author

rob-luke commented Sep 1, 2020

Its great to have this ticked off. Thanks for the all the help along the road.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

5 participants