Docker container for working with MR Spectroscopy data
Please see https://openmrslab.readthedocs.io for more information
MRS processing tools
Home Page: https://suspect.readthedocs.io/en/latest/
License: MIT License
Docker container for working with MR Spectroscopy data
Please see https://openmrslab.readthedocs.io for more information
For some types of Siemens DICOM file the load_siemens_dicom() function fails to find the tag containing the CSA header and throws a KeyError
It would be nice to be able to access the individual direction vectors of an image volume, normalised, to make it easy to construct an aligned coordinate system for slicing other volumes, for example. It would be even better to be able to also ask for the axial/sagittal/coronal directions (or closest approximations) so that such slices can be constructed easily without reference to the original planes of the image.
Currently singlet fitting will return an FID with the best fit, but this does not incorporate any baseline estimation. As the first few points are not used in the fit as they are assumed to include baseline, this usually means that the fit and the data do not align very well. It would be better if the results included a baseline estimate as well, which could be derived by applying a spline smoothing to the difference between fit and data. Additional parameters should be added to the fit function controlling the smoothness and number of knots on this baseline.
It should be possible to call a create_mask()
function which produces a binary mask showing which voxels of a reference image are inside a spectroscopy voxel. In the default case this would be for all the voxels in the spectroscopy, but it should also be possible to specify a specific voxel or list of voxels to be used instead, so that masks for individual CSI voxels are also possible.
Currently processing data with Tarquin just returns the metabolite concentrations and SDs, but it would also be useful to have the various data plots available for display and saving.
The io functions require that the path names to the files are Mac-style (not Windows style). Let's put in some functionality to automatically detect this and work around it, instead of just barfing when it seeing a Windows-style path : )
There should be a single source of the version number for the library, rather than having to keep multiple places in sync, such as sphinx conf.py and setuptools setup.py
Channel combination is currently done with a rank-1 SVD algorithm. In some cases receiver channels have correlated noise and this should be whitened before the channel combination is performed. In addition, significant improvements in channel weighting estimation can be gained by apodisation of the FID signals to suppress the noise after the signal has died away, and for CSI data by performing some spatial blurring across voxels on the assumption that the sensitivities are spatially smooth compared to the voxel size.
Currently the to_scanner() and from_scanner() functions take three arguments: x, y, z and return an numpy array. It would be convenient if the functions could handle a numpy array as an input for consistency, this would also allow passing in an array of coords to be transformed all at once, for example from meshgrid(). On the other hand, in the case where the user wants to pass in simple known x, y and z values, this requires them to be wrapped in a tuple, being called like to_scanner((x, y, z)), similarly to the numpy.ones() function. This could be addressed by permitting either 1 or 3 *args and interpreting either as an ndarray of shape [...3] or 3 floats.
At the moment, only rda files load a transform to enable them to be co-registered to structural MRI images. It should in theory be possible to read this information out of the twix file as well.
LCModel .control files created by lcmodel.write_all_files don't have quotes around strings from the params dict, which breaks passing them to pylcmodel.
Currently suspect knows how to submit data to the tarquin cli for fitting, and can write data in formats ready for lcmodel to process in the same way, but there is no automated way to perform the processing and read the results back into the Python interpreter.
There are many fitting routines available from within Suspect, the built-in AMARES-style singlet fitting and integration with Tarquin and LCModel. It would be better if these different routines had more of a standardised interface, particularly with regard to returning the fitting result, so that they become more interchangeable.
Add a changelog folder to the docs which will keep track of what changes have been incorporated into each release of the software.
Is there documentation for getting location variables form a TWIX file, I believe it is not in Suspect itself.
The correct echo time must be read when loading twix files.
Add a function which can be passed an MRSData object and a zeroth (and optional first) order phase, and returns a new MRSData object which has had the phase shifts applied. This should also be callable with a method on the original MRSData object, by analogy with methods like np.ndarray.clip()
Conventional wisdom suggests that Python docstrings are easier to read in either NumPy or Google styles, rather than reStructuredText. Given the close relationship of this library with NumPy, it makes sense to choose that style for our docstrings.
Add some algorithms for automatic phase estimation. Good first candidate is mag/real comparison, could also look at Ernst (minimise integral of imaginary component).
It should be possible to do frequency correction by specifying the expected frequency of a peak, finding the nearest peak to that frequency and moving the spectrum to align the peak to the frequency.
right now can the image module be used in some way to correlate MRS data instance with voxel locations? Sorry I am very new to dicom.
The image.create_mask() function should return an ImageBase with a transform instead of a bare ndarray, so that it can be easily saved to nii format etc.
It should be possible to generate a slice object for a specified frequency range from an MRSSpectrum object, which can be used to extract specific regions of a spectrum (or set of spectra).
The spectral_registration() function does not cope with having a limited frequency range set. If frequency limits are given then there is an error message, if a weight vector is given then the weights are not correctly applied and incorrect results are given.
When getting axial/coronal/sagittal vectors from an image volume, they should always be predominantly aligned with the primary quadrant. This would mean that it is always possible to define a coordinate system of known orientation but aligned with the volume.
In numpy 1.12 spline denoising fails because it passes floating point values to _pad and roll instead of integer values.
It should be possible to derive a new ImageBase from an existing ImageBase object by supplying the coordinate system, size and shape.
Because we use a different coordinate convention from nifti files (DICOM standard), we should provide helper functions to load and save nifti files including making the transform in conventions.
The current svd_weighting code assumes that the input data is 2D, channels and ADC, but in some cases we might want to for example calculate the weights on repetitions x channels x ADC, which should be done by permuting the axes into the 2D shape channels x (repetitions x ADC) etc. This means svd_weighting()
should support an optional axis
parameter to define the axis of the provided ndarray which represents the channels.
Currently frequency correction is applied with the transform_fid function in the processing module, but it would be logically better to put this in the MRSData class, by analogy with the existing adjust_phase() function.
Support loading DICOM SOP 1.2.840.10008.5.1.4.1.1.4.2 files
Siemens DICOM files from VB17A (from Magnetom 7T) have a ProtocolSliceNumber parameters in the CSA header which is not handled by the load_siemens_dicom() function, leading to an error in import.
In addition, at this point there is probably no need to produce an error on an unrecognised CSA tag, as all essential tags are already being read in, all others are metadata at best and so if some are missing it shouldn't matter. Instead a warning could be raised which would allow users to report back if they find a new parameter to be missing, without it affecting their use of the software.
Hi,
I'm having some trouble with the anonymize_twix() function. My file is read as the VB format.
Decoding to windows-1252 produces the error:
UnicodeDecodeError: 'charmap' codec can't decode byte 0x8f in position 418277: character maps to <undefined>
Decoding using latin-1 works (as shown in the load_twix_vb() function). However, I can't write the anonymized header to a new file. Using windows-1252, there is again an issue with the 0x8f character.
Several of the methods in suspect.processing.denoising return real results from complex inputs.
At the moment, the twix loading code responsible for generating the data transform reads the field of view data and uses it as the size of a voxel. This works for single voxel data but not for CSI.
SIFT denoising can be used to denoise either real or complex data, but currently always returns the real part of the result. It would be better if it returned a result which matched the type of the original input data (internally the data always becomes complex due to the FT operation).
@josephmje requested that PatientWeight, PatientAge and PatientTelephoneNumber fields from the twix header should also be anonymised by the anonymize_twix()
function.
When transforming coordinates the arrays are squeezed which can remove singlet spatial dimensions, leading to issues in interpreting the coordinate arrays.
In cases where multiple spectroscopy exams are performed on the same subject, it is often necessary to register them to each other. This is usually done by registering co-acquired structural images together to get a transform between the patient position in each case, then that transform must also be applied to the spectroscopy data. Therefore it should be possible to apply a transform to an MRSBase object to update its internal transform to a new space. This will not affect the internal data, but will be relevant for resampling and superimposing on structural images.
At the moment the channel combination averages over the first axis, but should really be the second to last axis (this is always the channel axis on multi-channel data).
In the spectral registration method the initial guess is used as the shift to map the FID onto the target, not the amount the FID has been shifted away, which is what is returned. When used iteratively, this means negating the shifts each time.
Check to see how suspect.fitting.singlet.fit() performs phase adjustments for a given fid. Modify the method to use suspect.MRSData.adjust_phase() so that there is one standard protocol for phase adjustment.
The anonymise_vd function is just a stub right now. The header shouldn't be that different to that for VB and nothing else needs to change, so shouldn't be too hard to implement.
Currently MRSData objects contain FID data and provide various convenience methods and properties, while spectra are bare ndarrays without any additional information. It would be better if the two classes inherited from (let's say) MRSBase giving some core methods, and then provided their own methods on top of those. Calling .spectrum() on an MRSData would return an MRSSpectrum object and calling .fid() on an MRSSpectrum object would return an MRSData object. Then users can work with whichever domain they prefer, without having to go back and forth all the time.
When using the singlet fitting library, the returned fit object is an ndarray which does not benefit from useful methods such as .spectrum() and .frequency_axis(). As the function is called with an MRSData object, it is very simple for the returned value to inherit from the input value.
At the moment, loading dicom images through the image module is very clunky, returning multiple independent components on load and without any useful functions to make it easy to work with. This could be solved by creating an MRBase
class as a superclass of MRSBase
, representing a multi-dimensional array of data with a transform and to/from_scanner()
functions. This could then be used for image data as well.
There should be a helper script (similar to anonymise_twix) that will take a .coord file from lcmodel and convert it to a css file with the different plots as columns, for easy plotting in excel and other tools.
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.