Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
25 commits
Select commit Hold shift + click to select a range
e797cdb
add files for visfAtlas
marcobarilari May 13, 2022
a9d603f
update functions to accomodate visfAtlas
marcobarilari May 13, 2022
855a90d
update demo with visfAtlas demo
marcobarilari May 13, 2022
9b939cb
[pre-commit.ci] auto fixes from pre-commit.com hooks
pre-commit-ci[bot] May 13, 2022
0991874
add new atlas to the readme
marcobarilari May 13, 2022
7851f07
convert README to md
marcobarilari May 17, 2022
f53f429
[pre-commit.ci] auto fixes from pre-commit.com hooks
pre-commit-ci[bot] May 17, 2022
887ce23
add tests for atlas visfAtlas
marcobarilari May 17, 2022
36c0227
add error message if hemisphere label is not correct
marcobarilari May 17, 2022
a124301
[pre-commit.ci] auto fixes from pre-commit.com hooks
pre-commit-ci[bot] May 17, 2022
3efae81
Auto stash before merge of "marco_add-visfAtlas" and "marcobarilari/m…
marcobarilari May 17, 2022
5bca4fe
[pre-commit.ci] auto fixes from pre-commit.com hooks
pre-commit-ci[bot] May 17, 2022
794b027
fix bug
marcobarilari May 17, 2022
5f7916d
[pre-commit.ci] auto fixes from pre-commit.com hooks
pre-commit-ci[bot] May 17, 2022
e71caa2
Apply suggestions from code review
marcobarilari May 17, 2022
52b3f9c
change one test to adapt to new bids matlab
Remi-Gau May 17, 2022
47918f6
fix another test that was failing because of a bids matlab update
Remi-Gau May 17, 2022
051519d
add a clean_lib recipe to makefile
Remi-Gau May 17, 2022
12ea04d
[pre-commit.ci] auto fixes from pre-commit.com hooks
pre-commit-ci[bot] May 17, 2022
d3ce3e6
Apply suggestions from code review
marcobarilari May 18, 2022
73a0867
[pre-commit.ci] auto fixes from pre-commit.com hooks
pre-commit-ci[bot] May 18, 2022
ee42b7b
fix failing tests
marcobarilari May 18, 2022
fa80716
[pre-commit.ci] auto fixes from pre-commit.com hooks
pre-commit-ci[bot] May 18, 2022
ca14a77
fix case bug in test
marcobarilari May 18, 2022
3786bb0
make things less case sensitive
Remi-Gau May 18, 2022
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,10 @@
clean:
rm -rf coverage*
rm version.txt

clean_lib:
rm -rf lib/bids-matlab

install_dev:
git clone https://github.com/bids-standard/bids-matlab.git --branch dev --depth 1 lib/bids-matlab

Expand Down
5 changes: 5 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,11 @@ as a submodule, and intitialized when running `initCppSpm`.
Probabilistic Maps of Visual Topography in Human Cortex. Cerebral
cortex (New York, N.Y. : 1991), 25(10), 3911–3931.
https://doi.org/10.1093/cercor/bhu277
- the probabilistic functional atlas of human occipito-temporal visual cortex
- Rosenke, M., van Hoof, R., van den Hurk, J., Grill-Spector, K., & Goebel, R. (2021).
A Probabilistic Functional Atlas of Human Occipito-Temporal Visual Cortex.
Cerebral cortex (New York, N.Y. : 1991), 31(1), 603–619.
https://doi.org/10.1093/cercor/bhaa246

Also includes:

Expand Down
9 changes: 8 additions & 1 deletion atlas/returnAtlasDir.m
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,21 @@

if nargin > 0

switch atlas
switch lower(atlas)

case 'wang'
atlasDir = fullfile(atlasDir, 'visual_topography_probability_atlas');

case 'anatomy_toobox'
atlasDir = fullfile(spm('dir'), 'toolbox', 'Anatomy');

case 'visfatlas'
atlasDir = fullfile(atlasDir, 'visfAtlas');

case 'neuromorphometrics'

otherwise
error('unknown atlas type');
end

end
Expand Down
34 changes: 34 additions & 0 deletions atlas/visfAtlas/LUT.csv
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
label,ROI,func
1,lh_mFus,faces
2,lh_pFus,faces
3,lh_IOG,faces
4,lh_OTS,bodies
5,lh_ITG,bodies
6,lh_MTG,bodies
7,lh_LOS,bodies
8,lh_pOTS,characters
9,lh_IOS,haracters
10,lh_CoS,places
11,lh_hMT,motion
12,lh_v1d,retinotopic
13,lh_v2d,retinotopic
14,lh_v3d,retinotopic
15,lh_v1v,retinotopic
16,lh_v2v,retinotopic
17,lh_v3v,retinotopic
18,rh_mFus,faces
19,rh_pFus,faces
20,rh_IOG,faces
21,rh_OTS,bodies
22,rh_ITG,bodies
23,rh_MTG,bodies
24,rh_LOS,bodies
25,rh_CoS,places
26,rh_TOS,places
27,rh_hMT,motion
28,rh_v1d,retinotopic
29,rh_v2d,retinotopic
30,rh_v3d,retinotopic
31,rh_v1v,retinotopic
32,rh_v2v,retinotopic
33,rh_v3v,retinotopic
16 changes: 16 additions & 0 deletions atlas/visfAtlas/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
visfAtlas in nifti volume format

The visfAtlas is based on N19 subjects. In FreeSurfer, it is aligned to the fsaverage brain. In BrainVoyager, it is aligned to a newly generated average brain for BrainVoyager, called the BVaverage. The BVaverage is distributed with this publication. The nifti volume atlas is aligned to the MNI colin27 brain.

Citing:

Please cite the article for use of the functional atlas as well as the BVaverage.

Rosenke, M., van Hoof, R., van den Hurk, J., Goebel, R. (2020). A probabilistic functional parcellation of human occipito-temporal cortex. TBD

To acknowledge using this atlas in your research, you might include a sentence like one of the following:

"We used the functional atlas of visual cortex developed by Rosenke et al. (2020)…”


The maximum probability map can be visualized by opening the visfATlas\_volume.nii.gz file and loading the correct color map (visfAtlas\_FSL.cmap) through the overlay display panel.
Binary file not shown.
12 changes: 9 additions & 3 deletions demos/atlas/create_roi_from_atlas.m
Original file line number Diff line number Diff line change
@@ -1,12 +1,18 @@
% (C) Copyright 2021 CPP ROI developers

opt.roi.atlas = 'wang';
opt.roi.name = {'V1v', 'V1d'};
clear all;
clc;

% options : 'wang', 'neuromorphometrics', 'anatomy_toobox', 'visfAtlas'
opt.roi.atlas = 'visfAtlas';

% to get the list of possible run `getLookUpTable(opt.roi.atlas)`
opt.roi.name = {'pFus', 'mFus', 'CoS'};
opt.roi.dir = fullfile(pwd, 'derivatives', 'cpp_roi', 'group');

spm_mkdir(opt.roi.dir);

hemi = {'L', 'H'};
hemi = {'L', 'R'};

for iHemi = 1:numel(hemi)

Expand Down
23 changes: 20 additions & 3 deletions src/atlas/extractRoiFromAtlas.m
Original file line number Diff line number Diff line change
Expand Up @@ -18,19 +18,25 @@
%
% (C) Copyright 2021 CPP ROI developers

if ~ismember(hemisphere, {'L', 'R'})

error('\n Hemisphere label %s not valid, try "L" or "R"', hemisphere);

end

[atlasFile, lut] = getAtlasAndLut(atlasName);

if strcmp(atlasName, 'wang')
if strcmpi(atlasName, 'wang')

if strcmp(hemisphere, 'L')
if strcmpi(hemisphere, 'L')
atlasFile = atlasFile(1, :);
else
atlasFile = atlasFile(2, :);
end

roiIdx = strcmp(roiName, lut.ROI);

elseif strcmp(atlasName, 'neuromorphometrics')
elseif strcmpi(atlasName, 'neuromorphometrics')

roiName = regexprep(roiName, '(Left )|(Right )', '');

Expand All @@ -43,6 +49,17 @@

roiIdx = strcmp([prefix roiName], lut.ROI);

elseif strcmpi(atlasName, 'visfatlas')

prefix = '';
if strcmp(hemisphere, 'L')
prefix = 'lh_';
elseif strcmp(hemisphere, 'R')
prefix = 'rh_';
end

roiIdx = strcmp([prefix roiName], lut.ROI);

end

% create ROI
Expand Down
6 changes: 5 additions & 1 deletion src/atlas/getAtlasFilename.m
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@

atlasDir = returnAtlasDir(atlasName);

if ~ismember(atlasName, {'wang', 'neuromorphometrics', 'anatomy_toobox'})
if ~ismember(lower(atlasName), {'wang', 'neuromorphometrics', 'anatomy_toobox', 'visfatlas'})
% TODO throw a proper error here
error('unknown atlas type');
end
Expand Down Expand Up @@ -46,6 +46,10 @@

error('not implemented yet');

case 'visfatlas'

atlasFilename = fullfile(atlasDir, 'space-MNI_atlas-visfAtlas_dseg.nii');

end

end
8 changes: 7 additions & 1 deletion src/atlas/getLookUpTable.m
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@

atlasDir = returnAtlasDir(atlasName);

if ~ismember(atlasName, {'wang', 'neuromorphometrics', 'anatomy_toobox'})
if ~ismember(lower(atlasName), {'wang', 'neuromorphometrics', 'anatomy_toobox', 'visfatlas'})
% TODO throw a proper error here
error('unknown atlas type');
end
Expand Down Expand Up @@ -55,6 +55,12 @@
roiLabelLUT = struct('ROI', C(1), ...
'label', C(2));

case 'visfatlas'

unzipAtlas('visfAtlas');

roiLabelLUT = spm_load(fullfile(atlasDir, 'LUT.csv'));

end

end
6 changes: 6 additions & 0 deletions src/atlas/unzipAtlas.m
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,12 @@ function unzipAtlas(atlas)

end

elseif strcmp(atlas, 'visfAtlas')

file = fullfile(atlasDir, 'visfAtlas/space-MNI_atlas-visfAtlas_dseg.nii.gz');

gunzip(file);

end

end
11 changes: 7 additions & 4 deletions tests/test_createRoi.m
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ function test_createRoi_intersection_mask_sphere()

mask = createRoi('intersection', specification, volumeDefiningImage, outputDir, saveImg);

basename = 'rspace-MNI_atlas-neurosynth_label-visualMotionIntersection_desc-p10pt00_mask';
basename = 'space-MNI_atlas-neurosynth_label-visualMotionIntersection_desc-p10pt00_mask';

assertEqual(exist(fullfile(thisDir(), [basename '.nii']), 'file'), 2);
assertEqual(exist(fullfile(thisDir(), [basename '.json']), 'file'), 2);
Expand All @@ -75,7 +75,7 @@ function test_createRoi_intersection_mask_sphere()

mask = createRoi('expand', specification, volumeDefiningImage, outputDir, saveImg);

basename = 'rspace-MNI_atlas-neurosynth_label-visualMotionExpandVox57_desc-p10pt00_mask';
basename = 'space-MNI_atlas-neurosynth_label-visualMotionExpandVox57_desc-p10pt00_mask';

assertEqual(mask.roi.size, 57);

Expand All @@ -95,7 +95,8 @@ function test_createRoi_intersection_mask_sphere()

value = fullfile(thisDir(), '..', 'demos', 'roi', 'inputs');

if exist(fullfile(value, 'TStatistic.nii'), 'file') == 0
if exist(fullfile(value, 'TStatistic.nii'), 'file') == 0 || ...
exist(fullfile(value, 'visual motion_association-test_z_FDR_0.01.nii'), 'file') == 0
gunzip(fullfile(value, '*.gz'));
end

Expand All @@ -106,7 +107,7 @@ function test_createRoi_intersection_mask_sphere()
volumeDefiningImage = fullfile(demoDir(), 'TStatistic.nii');

roiFilename = fullfile(demoDir(), ...
'rspace-MNI_atlas-neurosynth_label-visualMotion_desc-p10pt00_mask.nii');
'space-MNI_atlas-neurosynth_label-visualMotion_desc-p10pt00_mask.nii');

if exist(roiFilename, 'file') == 2

Expand All @@ -117,6 +118,8 @@ function test_createRoi_intersection_mask_sphere()
zMap = renameNeuroSynth(zMap);
zMap = resliceRoiImages(volumeDefiningImage, zMap);

zMap = removePrefix(zMap, 'r');

threshold = 10;
roiFilename = thresholdToMask(zMap, threshold);

Expand Down
7 changes: 1 addition & 6 deletions tests/test_createRoiName.m
Original file line number Diff line number Diff line change
Expand Up @@ -28,14 +28,9 @@ function test_createRoiName_non_sphere()
roiName = createRoiName(mask);
assertEqual(roiName, 'one-entity_mask.nii');

% This will likely break when bids-matlab is updated and the order of entities
% is imposed by the schema
%
% label-foo_one-entity_mask.nii
%
mask.label = 'foo';
roiName = createRoiName(mask);
assertEqual(roiName, 'one-entity_label-foo_mask.nii');
assertEqual(roiName, 'label-foo_one-entity_mask.nii');

end

Expand Down
16 changes: 16 additions & 0 deletions tests/test_extractRoiFromAtlas.m
Original file line number Diff line number Diff line change
Expand Up @@ -40,3 +40,19 @@ function test_extractRoiFromAtlas_neuromorphometrics()
delete(fullfile(pwd, '*.json'));

end

function test_extractRoiFromAtlas_visfAtlas()

roiImage = extractRoiFromAtlas(pwd, 'visfatlas', 'pFus', 'L');

assertEqual(exist(fullfile(pwd, 'hemi-L_space-MNI_atlas-visfatlas_label-pFus_mask.nii'), ...
'file'), ...
2);

vol = spm_read_vols(spm_vol(roiImage));
assertEqual(sum(vol(:) == 1), 655); % check the ROI has the right number of voxel

delete(fullfile(pwd, '*.nii'));
delete(fullfile(pwd, '*.json'));

end
9 changes: 9 additions & 0 deletions tests/test_getLookUpTable.m
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,15 @@ function test_lut_neuromorpho()

end

function test_lut_visfAtlas()

lut = getLookUpTable('visfatlas');

assertEqual(lut.label, [1:33]');
assertEqual(lut.ROI{1}, 'lh_mFus');

end

function cleanUp()

pause(1);
Expand Down
2 changes: 1 addition & 1 deletion tests/test_unit_returnAtlasDir.m
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@

function test_returnAtlasDir_default()

atlasDir = returnAtlasDir('neuromorphometric');
atlasDir = returnAtlasDir('neuromorphometrics');

assertEqual(atlasDir, returnAtlasDir());

Expand Down