From 6b5cac3a6fb6d7d7f3976bc7c808b43b01889721 Mon Sep 17 00:00:00 2001 From: Remi Gau Date: Sat, 3 Apr 2021 10:31:02 +0200 Subject: [PATCH 01/10] set up roi based GLMs --- demos/spm_face_rep/FaceRep_getOption.m | 2 ++ demos/spm_face_rep/face_rep_roi_analysis.m | 4 ++- lib/CPP_ROI | 2 +- src/defaults/checkOptions.m | 2 ++ src/setStatsDir.m | 11 +++++++ src/subject_level/getFFXdir.m | 2 +- src/templates/bidsTemplateWorkflow.m | 23 ++++++++++++++ src/workflows/bidsCreateROI.m | 10 ++++--- src/workflows/bidsRoiBasedGLM.m | 35 ++++++++++++++++++++++ 9 files changed, 84 insertions(+), 7 deletions(-) create mode 100644 src/setStatsDir.m create mode 100644 src/templates/bidsTemplateWorkflow.m create mode 100644 src/workflows/bidsRoiBasedGLM.m diff --git a/demos/spm_face_rep/FaceRep_getOption.m b/demos/spm_face_rep/FaceRep_getOption.m index 2db72558..8704c55c 100644 --- a/demos/spm_face_rep/FaceRep_getOption.m +++ b/demos/spm_face_rep/FaceRep_getOption.m @@ -12,6 +12,8 @@ % The directory where the data are located opt.dataDir = fullfile(fileparts(mfilename('fullpath')), 'outputs', 'raw'); + opt.stats.dir = fullfile(opt.dataDir, '..', 'derivatives', 'cpp_spm-stats'); + opt.model.hrfDerivatives = [1 1]; %% DO NOT TOUCH diff --git a/demos/spm_face_rep/face_rep_roi_analysis.m b/demos/spm_face_rep/face_rep_roi_analysis.m index 06657e9e..cbfdd477 100644 --- a/demos/spm_face_rep/face_rep_roi_analysis.m +++ b/demos/spm_face_rep/face_rep_roi_analysis.m @@ -11,4 +11,6 @@ opt.roi.name = {'V1v', 'V1d'}; opt.roi.space = {'MNI', 'individual'}; -bidsCreateROI(opt); +% bidsCreateROI(opt); + +bidsRoiBasedGLM(opt); diff --git a/lib/CPP_ROI b/lib/CPP_ROI index 1acf17d7..a53b52aa 160000 --- a/lib/CPP_ROI +++ b/lib/CPP_ROI @@ -1 +1 @@ -Subproject commit 1acf17d7b2e5e717e717150e23e6fc0eb0a073b6 +Subproject commit a53b52aa5e971c73b1cf75c2e4a745701d2c28a5 diff --git a/src/defaults/checkOptions.m b/src/defaults/checkOptions.m index c185732c..cb96c9da 100644 --- a/src/defaults/checkOptions.m +++ b/src/defaults/checkOptions.m @@ -82,6 +82,8 @@ fieldsToSet.dataDir = ''; fieldsToSet.derivativesDir = ''; + fieldsToSet.dir = struct('raw', '', ... + 'derivatives', ''); fieldsToSet.groups = {''}; fieldsToSet.subjects = {[]}; diff --git a/src/setStatsDir.m b/src/setStatsDir.m new file mode 100644 index 00000000..4d7cc355 --- /dev/null +++ b/src/setStatsDir.m @@ -0,0 +1,11 @@ +% (C) Copyright 2021 CPP BIDS SPM-pipeline developers + +function opt = setStatsDir(opt) + + opt = setDerivativesDir(opt); + + if ~isfield(opt.dir, 'stats') + opt.dir.stats = fullfile(opt.derivativesDir, '..', 'cpp_spm-stats'); + end + +end diff --git a/src/subject_level/getFFXdir.m b/src/subject_level/getFFXdir.m index 1825b7be..0b9525a5 100644 --- a/src/subject_level/getFFXdir.m +++ b/src/subject_level/getFFXdir.m @@ -25,7 +25,7 @@ glmDirName = [glmDirName, '_desc-', convertToValidCamelCase(model.Name)]; end - ffxDir = fullfile(opt.derivativesDir, ... + ffxDir = fullfile(opt.dir.stats, ... ['sub-', subLabel], ... 'stats', ... glmDirName); diff --git a/src/templates/bidsTemplateWorkflow.m b/src/templates/bidsTemplateWorkflow.m new file mode 100644 index 00000000..39721e4c --- /dev/null +++ b/src/templates/bidsTemplateWorkflow.m @@ -0,0 +1,23 @@ +% (C) Copyright 2021 CPP BIDS SPM-pipeline developers + +function bidsTemplateWorkflow(opt) + % + % + + [BIDS, opt] = setUpWorkflow(opt, 'workflow name'); + + for iSub = 1:numel(opt.subjects) + + subLabel = opt.subjects{iSub}; + + printProcessingSubject(iSub, subLabel); + + matlabbatch = []; + + % matlabbatch = setBatchSTC(matlabbatch, BIDS, opt, subLabel); + + saveAndRunWorkflow(matlabbatch, 'workflow name', opt, subLabel); + + end + +end diff --git a/src/workflows/bidsCreateROI.m b/src/workflows/bidsCreateROI.m index 0b8fc0db..1a810196 100644 --- a/src/workflows/bidsCreateROI.m +++ b/src/workflows/bidsCreateROI.m @@ -8,16 +8,18 @@ function bidsCreateROI(opt) [BIDS, opt] = setUpWorkflow(opt, 'create ROI'); - opt.roiDir = [opt.derivativesDir '-roi']; + opt.dir.roi = [opt.derivativesDir '-roi']; spm_mkdir(fullfile(opt.roiDir, 'group')); + opt.jobsDir = fullfile(opt.dir.roi, 'JOBS', opt.taskName); + hemi = {'lh', 'rh'}; for iHemi = 1:numel(hemi) for iROI = 1:numel(opt.roi.name) - extractRoiFromAtlas(fullfile(opt.roiDir, 'group'), ... + extractRoiFromAtlas(fullfile(opt.dir.roi, 'group'), ... opt.roi.atlas, ... opt.roi.name{iROI}, ... hemi{iHemi}); @@ -55,7 +57,7 @@ function bidsCreateROI(opt) saveAndRunWorkflow(matlabbatch, 'inverseNormalize', opt, subLabel); %% move and rename file - spm_mkdir(opt.roiDir, ['sub-' subLabel], 'roi'); + spm_mkdir(opt.dir.roi, ['sub-' subLabel], 'roi'); roiList = spm_select('FPlist', ... fullfile(opt.roiDir, 'group'), ... @@ -78,7 +80,7 @@ function bidsCreateROI(opt) newName = createFilename(nameStructure); movefile(roiImage, ... - fullfile(opt.roiDir, ['sub-' subLabel], 'roi', newName)); + fullfile(opt.dir.roi, ['sub-' subLabel], 'roi', newName)); end end diff --git a/src/workflows/bidsRoiBasedGLM.m b/src/workflows/bidsRoiBasedGLM.m new file mode 100644 index 00000000..fae4005f --- /dev/null +++ b/src/workflows/bidsRoiBasedGLM.m @@ -0,0 +1,35 @@ +% (C) Copyright 2021 CPP BIDS SPM-pipeline developers + +function bidsRoiBasedGLM(opt) + % + % + + funcFWHM = 0; + + [BIDS, opt] = setUpWorkflow(opt, 'roi based glm'); + + opt = setStatsDir(opt); + opt.space = 'individual'; + opt.jobsDir = fullfile(opt.dir.stats, 'JOBS', opt.taskName); + + if isempty(opt.model.file) + opt = createDefaultModel(BIDS, opt); + end + + for iSub = 1:numel(opt.subjects) + + subLabel = opt.subjects{iSub}; + + printProcessingSubject(iSub, subLabel); + + matlabbatch = []; + + matlabbatch = setBatchSubjectLevelGLMSpec(matlabbatch, BIDS, opt, subLabel, funcFWHM); + + batchName = ['specify_roi_based_GLM_task-', opt.taskName]; + + saveAndRunWorkflow(matlabbatch, batchName, opt, subLabel); + + end + +end From 9bf590676a59aeee2c2845478b1f6d368bac0109 Mon Sep 17 00:00:00 2001 From: Remi Gau Date: Sat, 3 Apr 2021 11:19:19 +0200 Subject: [PATCH 02/10] add mars bar roi based GLM estimation --- demos/spm_face_rep/FaceRep_getOption.m | 6 +-- demos/spm_face_rep/face_rep_roi_analysis.m | 2 + src/defaults/checkOptions.m | 3 +- src/setStatsDir.m | 2 + src/subject_level/getFFXdir.m | 4 ++ src/workflows/bidsCreateROI.m | 1 + src/workflows/bidsFFX.m | 2 +- src/workflows/bidsRoiBasedGLM.m | 47 ++++++++++++++++++++++ 8 files changed, 61 insertions(+), 6 deletions(-) diff --git a/demos/spm_face_rep/FaceRep_getOption.m b/demos/spm_face_rep/FaceRep_getOption.m index 8704c55c..414fe675 100644 --- a/demos/spm_face_rep/FaceRep_getOption.m +++ b/demos/spm_face_rep/FaceRep_getOption.m @@ -6,13 +6,11 @@ opt = []; - % task to analyze opt.taskName = 'facerepetition'; - % The directory where the data are located opt.dataDir = fullfile(fileparts(mfilename('fullpath')), 'outputs', 'raw'); - - opt.stats.dir = fullfile(opt.dataDir, '..', 'derivatives', 'cpp_spm-stats'); + opt.dir.roi = fullfile(opt.dataDir, '..', 'derivatives', 'cpp_spm-roi'); + opt.dir.stats = fullfile(opt.dataDir, '..', 'derivatives', 'cpp_spm-stats'); opt.model.hrfDerivatives = [1 1]; diff --git a/demos/spm_face_rep/face_rep_roi_analysis.m b/demos/spm_face_rep/face_rep_roi_analysis.m index cbfdd477..265a75f3 100644 --- a/demos/spm_face_rep/face_rep_roi_analysis.m +++ b/demos/spm_face_rep/face_rep_roi_analysis.m @@ -13,4 +13,6 @@ % bidsCreateROI(opt); +opt.glm.roibased.do = true; + bidsRoiBasedGLM(opt); diff --git a/src/defaults/checkOptions.m b/src/defaults/checkOptions.m index cb96c9da..fcd6b3c1 100644 --- a/src/defaults/checkOptions.m +++ b/src/defaults/checkOptions.m @@ -115,7 +115,8 @@ fieldsToSet.model.hrfDerivatives = [0 0]; fieldsToSet.contrastList = {}; - fieldsToSet.glmQA.do = true; + fieldsToSet.glm.QA.do = true; + fieldsToSet.glm.roibased.do = false; % specify the results to compute fieldsToSet.result.Steps = returnDefaultResultsStructure(); diff --git a/src/setStatsDir.m b/src/setStatsDir.m index 4d7cc355..48aa4072 100644 --- a/src/setStatsDir.m +++ b/src/setStatsDir.m @@ -8,4 +8,6 @@ opt.dir.stats = fullfile(opt.derivativesDir, '..', 'cpp_spm-stats'); end + opt.dir.stats = spm_file(opt.dir.stats, 'cpath'); + end diff --git a/src/subject_level/getFFXdir.m b/src/subject_level/getFFXdir.m index 0b9525a5..cad5cb71 100644 --- a/src/subject_level/getFFXdir.m +++ b/src/subject_level/getFFXdir.m @@ -30,6 +30,10 @@ 'stats', ... glmDirName); + if opt.glm.roibased.do + ffxDir = [ffxDir '_roi']; + end + spm_mkdir(ffxDir); end diff --git a/src/workflows/bidsCreateROI.m b/src/workflows/bidsCreateROI.m index 1a810196..2349c503 100644 --- a/src/workflows/bidsCreateROI.m +++ b/src/workflows/bidsCreateROI.m @@ -81,6 +81,7 @@ function bidsCreateROI(opt) movefile(roiImage, ... fullfile(opt.dir.roi, ['sub-' subLabel], 'roi', newName)); + end end diff --git a/src/workflows/bidsFFX.m b/src/workflows/bidsFFX.m index a56f5f95..a1472ad5 100644 --- a/src/workflows/bidsFFX.m +++ b/src/workflows/bidsFFX.m @@ -76,7 +76,7 @@ function bidsFFX(action, opt, funcFWHM) saveAndRunWorkflow(matlabbatch, batchName, opt, subLabel); - if opt.glmQA.do + if opt.glm.QA.do plot_power_spectra_of_GLM_residuals( ... getFFXdir(subLabel, funcFWHM, opt), ... opt.metadata.RepetitionTime); diff --git a/src/workflows/bidsRoiBasedGLM.m b/src/workflows/bidsRoiBasedGLM.m index fae4005f..0cb8f4bc 100644 --- a/src/workflows/bidsRoiBasedGLM.m +++ b/src/workflows/bidsRoiBasedGLM.m @@ -30,6 +30,53 @@ function bidsRoiBasedGLM(opt) saveAndRunWorkflow(matlabbatch, batchName, opt, subLabel); + SPM = load(fullfile(getFFXdir(subLabel, funcFWHM, opt), ... + 'SPM.mat')); + + roiList = spm_select('FPList', ... + fullfile(opt.dir.roi, ['sub-' subLabel], 'roi'), ... + '^sub-.*_mask.nii$'); + + model = mardo(SPM); + + for iROI = 1:size(roiList, 1) + + roiImage = deblank(roiList(iROI, :)); + + % create ROI object for Marsbar + % and convert to matrix format to avoid delicacies of image format + roiObject = maroi_image(struct( ... + 'vol', spm_vol(roiImage), ... + 'binarize', true, ... + 'func', [])); + roiObject = maroi_matrix(roiObject); + + % Extract data and do MarsBaR estimation + data = get_marsy(roiObject, model, 'mean'); + estimation = estimate(model, data); + + p = bids.internal.parse_filename(spm_file(roiImage, 'filename')); + fields = {'hemi', 'desc', 'label'}; + for iField = 1:numel(fields) + if ~isfield(p, fields{iField}) + p.(fields{iField}) = ''; + end + end + nameStructure = struct( ... + 'sub', subLabel, ... + 'space', 'individual', ... + 'hemi', p.hemi, ... + 'desc', p.desc, ... + 'label', p.label, ... + 'type', 'estimates', ... + 'ext', '.mat'); + newName = createFilename(nameStructure); + + save(fullfile(getFFXdir(subLabel, funcFWHM, opt), newName), ... + 'estimation'); + + end + end end From 2c88cfdc7db23cb885ae1d76183fac2b8e9a5d12 Mon Sep 17 00:00:00 2001 From: Remi Gau Date: Sat, 3 Apr 2021 12:40:54 +0200 Subject: [PATCH 03/10] fit events and compute percent signal change --- src/workflows/bidsRoiBasedGLM.m | 40 ++++++++++++++++++++++++++++++--- 1 file changed, 37 insertions(+), 3 deletions(-) diff --git a/src/workflows/bidsRoiBasedGLM.m b/src/workflows/bidsRoiBasedGLM.m index 0cb8f4bc..bba3e2da 100644 --- a/src/workflows/bidsRoiBasedGLM.m +++ b/src/workflows/bidsRoiBasedGLM.m @@ -30,8 +30,27 @@ function bidsRoiBasedGLM(opt) saveAndRunWorkflow(matlabbatch, batchName, opt, subLabel); - SPM = load(fullfile(getFFXdir(subLabel, funcFWHM, opt), ... - 'SPM.mat')); + load(fullfile(getFFXdir(subLabel, funcFWHM, opt), 'SPM.mat')); + + nbRuns = numel(SPM.Sess); + + conditions = {}; + runs = []; + durations = []; + for iRun = 1:nbRuns + tmp = cat(2, SPM.Sess(iRun).U(:).name); + conditions = cat(2, conditions, tmp); + runs = [runs ones(size(tmp)) * iRun]; + for iCdt = 1:numel(tmp) + durations = [durations mean(SPM.Sess(iRun).U(iCdt).dur)]; + end + end + + names = unique(conditions); + events = []; + for iEvent = 1:numel(conditions) + events(end + 1) = find(strcmp(conditions(iEvent), names)); + end roiList = spm_select('FPList', ... fullfile(opt.dir.roi, ['sub-' subLabel], 'roi'), ... @@ -55,6 +74,20 @@ function bidsRoiBasedGLM(opt) data = get_marsy(roiObject, model, 'mean'); estimation = estimate(model, data); + % -------------------- IMPROVE ------------------------ % + + % currently this only computes this averages over all all events + % we will want to use the bids model to know which event to fit + % based on the contrasts. + + % Fitted time courses + [tc, dt] = event_fitted(estimation, [runs; events], durations); + + % Get percent signal change + psc = event_signal(estimation, [runs; events], durations, 'abs max'); + + % -------------------- IMPROVE ------------------------ % + p = bids.internal.parse_filename(spm_file(roiImage, 'filename')); fields = {'hemi', 'desc', 'label'}; for iField = 1:numel(fields) @@ -64,6 +97,7 @@ function bidsRoiBasedGLM(opt) end nameStructure = struct( ... 'sub', subLabel, ... + 'task', opt.taskName, ... 'space', 'individual', ... 'hemi', p.hemi, ... 'desc', p.desc, ... @@ -73,7 +107,7 @@ function bidsRoiBasedGLM(opt) newName = createFilename(nameStructure); save(fullfile(getFFXdir(subLabel, funcFWHM, opt), newName), ... - 'estimation'); + 'estimation', 'tc', 'dt', 'psc'); end From 382b8b78e376df27f29cad9803f5f92775c5eb32 Mon Sep 17 00:00:00 2001 From: Remi Gau Date: Sat, 3 Apr 2021 12:41:47 +0200 Subject: [PATCH 04/10] refactor MoAE to allow running with octave --- demos/MoAE/MoAE_run.m | 31 ------------------------ demos/MoAE/MoAE_slice_display.m | 16 ------------ demos/MoAE/dowload_MoAE_ds.m | 31 ++++++++++++++++++++++++ demos/MoAE/return_normalized_anat_file.m | 16 ++++++++++++ 4 files changed, 47 insertions(+), 47 deletions(-) create mode 100644 demos/MoAE/dowload_MoAE_ds.m create mode 100644 demos/MoAE/return_normalized_anat_file.m diff --git a/demos/MoAE/MoAE_run.m b/demos/MoAE/MoAE_run.m index ccf8f007..bd5208ce 100644 --- a/demos/MoAE/MoAE_run.m +++ b/demos/MoAE/MoAE_run.m @@ -47,34 +47,3 @@ % bidsFFX('specifyAndEstimate', opt, FWHM); % bidsFFX('contrasts', opt, FWHM); % bidsResults(opt, FWHM); - -%% -function dowload_MoAE_ds(downloadData) - - if downloadData - - % URL of the data set to download - URL = 'http://www.fil.ion.ucl.ac.uk/spm/download/data/MoAEpilot/MoAEpilot.bids.zip'; - - working_directory = fileparts(mfilename('fullpath')); - - % clean previous runs - if exist(fullfile(working_directory, 'inputs'), 'dir') - rmdir(fullfile(working_directory, 'inputs'), 's'); - end - - spm_mkdir(fullfile(working_directory, 'inputs')); - - %% Get data - fprintf('%-10s:', 'Downloading dataset...'); - urlwrite(URL, 'MoAEpilot.zip'); - fprintf(1, ' Done\n\n'); - - fprintf('%-10s:', 'Unzipping dataset...'); - unzip('MoAEpilot.zip'); - movefile('MoAEpilot', fullfile(working_directory, 'inputs', 'raw')); - fprintf(1, ' Done\n\n'); - - end - -end diff --git a/demos/MoAE/MoAE_slice_display.m b/demos/MoAE/MoAE_slice_display.m index eb7cbe0d..bf370a0c 100644 --- a/demos/MoAE/MoAE_slice_display.m +++ b/demos/MoAE/MoAE_slice_display.m @@ -59,19 +59,3 @@ %% Display the layers [settings, p] = sd_display(layers, settings); - -%% Helper function -function [anat_normalized_file, anatRange] = return_normalized_anat_file(opt, subLabel) - - [BIDS, opt] = getData(opt); - [~, anatDataDir] = getAnatFilename(BIDS, subLabel, opt); - anat_normalized_file = spm_select('FPList', ... - anatDataDir, ... - '^wm.*skullstripped.nii$'); - - hdr = spm_vol(anat_normalized_file); - vol = spm_read_vols(hdr); - - anatRange = [min(vol(:)) max(vol(:))]; - -end diff --git a/demos/MoAE/dowload_MoAE_ds.m b/demos/MoAE/dowload_MoAE_ds.m new file mode 100644 index 00000000..f0be3cf9 --- /dev/null +++ b/demos/MoAE/dowload_MoAE_ds.m @@ -0,0 +1,31 @@ +% (C) Copyright 2021 Remi Gau + +function dowload_MoAE_ds(downloadData) + + if downloadData + + % URL of the data set to download + URL = 'http://www.fil.ion.ucl.ac.uk/spm/download/data/MoAEpilot/MoAEpilot.bids.zip'; + + working_directory = fileparts(mfilename('fullpath')); + + % clean previous runs + if exist(fullfile(working_directory, 'inputs'), 'dir') + rmdir(fullfile(working_directory, 'inputs'), 's'); + end + + spm_mkdir(fullfile(working_directory, 'inputs')); + + %% Get data + fprintf('%-10s:', 'Downloading dataset...'); + urlwrite(URL, 'MoAEpilot.zip'); + fprintf(1, ' Done\n\n'); + + fprintf('%-10s:', 'Unzipping dataset...'); + unzip('MoAEpilot.zip'); + movefile('MoAEpilot', fullfile(working_directory, 'inputs', 'raw')); + fprintf(1, ' Done\n\n'); + + end + +end diff --git a/demos/MoAE/return_normalized_anat_file.m b/demos/MoAE/return_normalized_anat_file.m new file mode 100644 index 00000000..b6a3627f --- /dev/null +++ b/demos/MoAE/return_normalized_anat_file.m @@ -0,0 +1,16 @@ +% (C) Copyright 2021 Remi Gau + +function [anat_normalized_file, anatRange] = return_normalized_anat_file(opt, subLabel) + + [BIDS, opt] = getData(opt); + [~, anatDataDir] = getAnatFilename(BIDS, subLabel, opt); + anat_normalized_file = spm_select('FPList', ... + anatDataDir, ... + '^wm.*skullstripped.nii$'); + + hdr = spm_vol(anat_normalized_file); + vol = spm_read_vols(hdr); + + anatRange = [min(vol(:)) max(vol(:))]; + +end From b599754604a57a04fcf4515c21d3c0fb088f4fee Mon Sep 17 00:00:00 2001 From: Remi Gau Date: Sat, 3 Apr 2021 13:49:11 +0200 Subject: [PATCH 05/10] update tests --- .gitignore | 2 +- src/group_level/getRFXdir.m | 2 +- tests/createDummyDataSet.sh | 24 +++++++++++++--------- tests/test_getFFXdir.m | 6 ++---- tests/test_getRFXdir.m | 6 ++---- tests/test_setBatchMeanAnatAndMask.m | 5 ++--- tests/test_setBatchSmoothConImages.m | 16 +++++++-------- tests/test_setBatchSubjectLevelContrasts.m | 3 +-- tests/test_setBatchSubjectLevelResults.m | 5 +---- tests/utils/defaultOptions.m | 5 ++++- tests/utils/setOptions.m | 4 ++++ 11 files changed, 40 insertions(+), 38 deletions(-) diff --git a/.gitignore b/.gitignore index 547a6cb5..d520b176 100644 --- a/.gitignore +++ b/.gitignore @@ -22,7 +22,7 @@ demos/*/cfg/*.json tests/*.png tests/group/* tests/*/*.json -tests/dummyData/derivatives/cpp_spm/sub-*/ +tests/dummyData/derivatives/cpp_spm*/sub-*/ # ignore content of the build folder of the doc docs/build/* diff --git a/src/group_level/getRFXdir.m b/src/group_level/getRFXdir.m index 492ee3e2..7a96acba 100644 --- a/src/group_level/getRFXdir.m +++ b/src/group_level/getRFXdir.m @@ -32,7 +32,7 @@ end rfxDir = fullfile( ... - opt.derivativesDir, ... + opt.dir.stats, ... 'group', ... glmDirName); diff --git a/tests/createDummyDataSet.sh b/tests/createDummyDataSet.sh index 5b7bc3f7..d38a692e 100755 --- a/tests/createDummyDataSet.sh +++ b/tests/createDummyDataSet.sh @@ -4,24 +4,28 @@ # defines where the BIDS data set will be created StartDir=`pwd` # relative to starting directory -StartDir=$StartDir/dummyData/derivatives/cpp_spm +PrerpoDir=$StartDir/dummyData/derivatives/cpp_spm +StatsDir=$StartDir/dummyData/derivatives/cpp_spm-stats + +mkdir $StatsDir SubList='ctrl01 ctrl02 blind01 blind02 01 02' # subject list SesList='01 02' # session list -for Subject in $SubList # loop through subjects +for Subject in $SubList do - mkdir $StartDir/sub-$Subject # create folder for subject + mkdir $PrerpoDir/sub-$Subject + mkdir $StatsDir/sub-$Subject - for Ses in $SesList # loop through sessions + for Ses in $SesList do # create folder for each session and functional and fmap - mkdir $StartDir/sub-$Subject/ses-$Ses + mkdir $PrerpoDir/sub-$Subject/ses-$Ses # FUNC - ThisDir=$StartDir/sub-$Subject/ses-$Ses/func + ThisDir=$PrerpoDir/sub-$Subject/ses-$Ses/func mkdir $ThisDir touch $ThisDir/sub-$Subject\_ses-$Ses\_task-vismotion_run-1_bold.nii @@ -57,7 +61,7 @@ do echo "6\t2\tVisMotUp" >> $ThisDir/sub-$Subject\_ses-$Ses\_task-vismotion_run-2_events.tsv # FMAP - ThisDir=$StartDir/sub-$Subject/ses-$Ses/fmap + ThisDir=$PrerpoDir/sub-$Subject/ses-$Ses/fmap mkdir $ThisDir touch $ThisDir/sub-$Subject\_ses-$Ses\_run-1_phasediff.nii @@ -82,7 +86,7 @@ do done # ANAT - ThisDir=$StartDir/sub-$Subject/ses-01/anat + ThisDir=$PrerpoDir/sub-$Subject/ses-01/anat mkdir $ThisDir touch $ThisDir/sub-$Subject\_ses-01_T1w.nii @@ -93,8 +97,8 @@ do touch $ThisDir/c3sub-$Subject\_ses-01_T1w.nii # STATS - mkdir $StartDir/sub-$Subject/stats - ThisDir=$StartDir/sub-$Subject/stats/task-vismotion_space-MNI_FWHM-6 + mkdir $StatsDir/sub-$Subject/stats + ThisDir=$StatsDir/sub-$Subject/stats/task-vismotion_space-MNI_FWHM-6 mkdir $ThisDir cp dummyData/SPM.mat $ThisDir/SPM.mat diff --git a/tests/test_getFFXdir.m b/tests/test_getFFXdir.m index 61440e96..829db0e1 100644 --- a/tests/test_getFFXdir.m +++ b/tests/test_getFFXdir.m @@ -14,11 +14,10 @@ function test_getFFXdirBasic() subLabel = '01'; opt = setOptions('vislocalizer', subLabel); - opt = setDerivativesDir(opt); opt = checkOptions(opt); expectedOutput = fullfile(fileparts(mfilename('fullpath')), 'dummyData', 'derivatives', ... - 'cpp_spm', 'sub-01', 'stats', ... + 'cpp_spm-stats', 'sub-01', 'stats', ... 'task-vislocalizer_space-MNI_FWHM-0'); ffxDir = getFFXdir(subLabel, funcFWFM, opt); @@ -34,13 +33,12 @@ function test_getFFXdirUserSpecified() opt = setOptions('nback', subLabel); opt.space = 'individual'; - opt = setDerivativesDir(opt); opt = checkOptions(opt); ffxDir = getFFXdir(subLabel, funcFWHM, opt); expectedOutput = fullfile(fileparts(mfilename('fullpath')), 'dummyData', 'derivatives', ... - 'cpp_spm', 'sub-02', 'stats', ... + 'cpp_spm-stats', 'sub-02', 'stats', ... 'task-nback_space-individual_FWHM-6_desc-nbackMVPA'); assertEqual(exist(expectedOutput, 'dir'), 7); diff --git a/tests/test_getRFXdir.m b/tests/test_getRFXdir.m index 9fa507c3..46deb652 100644 --- a/tests/test_getRFXdir.m +++ b/tests/test_getRFXdir.m @@ -15,7 +15,6 @@ function test_getRFXdirBasic() opt = setOptions('vislocalizer'); opt = checkOptions(opt); - opt = setDerivativesDir(opt); rfxDir = getRFXdir(opt, funcFWHM, conFWHM); @@ -23,7 +22,7 @@ function test_getRFXdirBasic() fileparts(mfilename('fullpath')), ... 'dummyData', ... 'derivatives', ... - 'cpp_spm', ... + 'cpp_spm-stats', ... 'group', ... 'task-vislocalizer_space-MNI_FWHM-0_conFWHM-0'); @@ -38,7 +37,6 @@ function test_getFFXdirUserSpecified() opt = setOptions('nback'); opt = checkOptions(opt); - opt = setDerivativesDir(opt); rfxDir = getRFXdir(opt, funcFWHM, conFWHM); @@ -46,7 +44,7 @@ function test_getFFXdirUserSpecified() fileparts(mfilename('fullpath')), ... 'dummyData', ... 'derivatives', ... - 'cpp_spm', ... + 'cpp_spm-stats', ... 'group', ... 'task-nback_space-MNI_FWHM-6_conFWHM-0_desc-nbackMVPA'); diff --git a/tests/test_setBatchMeanAnatAndMask.m b/tests/test_setBatchMeanAnatAndMask.m index 6ff60d18..7eced5d4 100644 --- a/tests/test_setBatchMeanAnatAndMask.m +++ b/tests/test_setBatchMeanAnatAndMask.m @@ -15,7 +15,6 @@ function test_setBatchMeanAnatAndMaskBasic() opt = setOptions('vismotion'); opt.subjects = {'01', '02'}; - opt = setDerivativesDir(opt); opt = checkOptions(opt); matlabbatch = []; @@ -40,11 +39,11 @@ function test_setBatchMeanAnatAndMaskBasic() expectedBatch{1}.spm.util.imcalc = imcalc; % - imcalc.input{1, 1} = fullfile(opt.derivativesDir, 'sub-01', ... + imcalc.input{1, 1} = fullfile(opt.dir.stats, 'sub-01', ... 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... 'mask.nii'); - imcalc.input{2, 1} = fullfile(opt.derivativesDir, ... + imcalc.input{2, 1} = fullfile(opt.dir.stats, ... 'sub-02', ... 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... diff --git a/tests/test_setBatchSmoothConImages.m b/tests/test_setBatchSmoothConImages.m index 1c2dbd29..276d28d2 100644 --- a/tests/test_setBatchSmoothConImages.m +++ b/tests/test_setBatchSmoothConImages.m @@ -24,16 +24,16 @@ function test_setBatchSmoothConImagesBasic() expectedBatch{1}.spm.spatial.smooth.fwhm = [6 6 6]; expectedBatch{1}.spm.spatial.smooth.prefix = 's6'; - expectedBatch{1}.spm.spatial.smooth.data = {fullfile(opt.derivativesDir, 'sub-01', 'stats', ... + expectedBatch{1}.spm.spatial.smooth.data = {fullfile(opt.dir.stats, 'sub-01', 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... 'con_0001.nii'); ... - fullfile(opt.derivativesDir, 'sub-01', 'stats', ... + fullfile(opt.dir.stats, 'sub-01', 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... 'con_0002.nii'); ... - fullfile(opt.derivativesDir, 'sub-01', 'stats', ... + fullfile(opt.dir.stats, 'sub-01', 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... 'con_0003.nii'); ... - fullfile(opt.derivativesDir, 'sub-01', 'stats', ... + fullfile(opt.dir.stats, 'sub-01', 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... 'con_0004.nii')}; expectedBatch{1}.spm.spatial.smooth.dtype = 0; @@ -41,16 +41,16 @@ function test_setBatchSmoothConImagesBasic() expectedBatch{2}.spm.spatial.smooth.fwhm = [6 6 6]; expectedBatch{2}.spm.spatial.smooth.prefix = 's6'; - expectedBatch{2}.spm.spatial.smooth.data = {fullfile(opt.derivativesDir, 'sub-02', 'stats', ... + expectedBatch{2}.spm.spatial.smooth.data = {fullfile(opt.dir.stats, 'sub-02', 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... 'con_0001.nii'); ... - fullfile(opt.derivativesDir, 'sub-02', 'stats', ... + fullfile(opt.dir.stats, 'sub-02', 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... 'con_0002.nii'); ... - fullfile(opt.derivativesDir, 'sub-02', 'stats', ... + fullfile(opt.dir.stats, 'sub-02', 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... 'con_0003.nii'); ... - fullfile(opt.derivativesDir, 'sub-02', 'stats', ... + fullfile(opt.dir.stats, 'sub-02', 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... 'con_0004.nii')}; expectedBatch{2}.spm.spatial.smooth.dtype = 0; diff --git a/tests/test_setBatchSubjectLevelContrasts.m b/tests/test_setBatchSubjectLevelContrasts.m index b7958221..3c18cf59 100644 --- a/tests/test_setBatchSubjectLevelContrasts.m +++ b/tests/test_setBatchSubjectLevelContrasts.m @@ -14,14 +14,13 @@ function test_setBatchSubjectLevelContrastsBasic() funcFWHM = 6; opt = setOptions('vismotion', subLabel); - opt = setDerivativesDir(opt); opt = checkOptions(opt); matlabbatch = []; matlabbatch = setBatchSubjectLevelContrasts(matlabbatch, opt, subLabel, funcFWHM); expectedBatch = []; - expectedBatch{end + 1}.spm.stats.con.spmmat = {fullfile(opt.derivativesDir, ... + expectedBatch{end + 1}.spm.stats.con.spmmat = {fullfile(opt.dir.stats, ... 'sub-01', ... 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... diff --git a/tests/test_setBatchSubjectLevelResults.m b/tests/test_setBatchSubjectLevelResults.m index ce34aae6..a31debfb 100644 --- a/tests/test_setBatchSubjectLevelResults.m +++ b/tests/test_setBatchSubjectLevelResults.m @@ -18,7 +18,6 @@ function test_setBatchSubjectLevelResultsBasic() opt = setOptions('vismotion', subLabel); opt.space = 'MNI'; - opt = setDerivativesDir(opt); opt = checkOptions(opt); opt.result.Steps.Contrasts.Name = 'VisMot'; @@ -28,7 +27,7 @@ function test_setBatchSubjectLevelResultsBasic() expectedBatch = {}; - expectedBatch{end + 1}.spm.stats.results.spmmat = {fullfile(opt.derivativesDir, ... + expectedBatch{end + 1}.spm.stats.results.spmmat = {fullfile(opt.dir.stats, ... 'sub-01', ... 'stats', ... 'task-vismotion_space-MNI_FWHM-6', ... @@ -60,7 +59,6 @@ function test_setBatchSubjectLevelResultsErrorMissingContrastName() opt = setOptions('vismotion', subLabel); opt.space = 'MNI'; - opt = setDerivativesDir(opt); opt = checkOptions(opt); matlabbatch = []; @@ -88,7 +86,6 @@ function test_setBatchSubjectLevelResultsErrorNoMAtchingContrast() opt = setOptions('vismotion', subLabel); opt.space = 'MNI'; - opt = setDerivativesDir(opt); opt = checkOptions(opt); opt.result.Steps.Contrasts.Name = 'NotAContrast'; diff --git a/tests/utils/defaultOptions.m b/tests/utils/defaultOptions.m index 3337b905..bac6f70c 100644 --- a/tests/utils/defaultOptions.m +++ b/tests/utils/defaultOptions.m @@ -7,6 +7,8 @@ expectedOptions.dataDir = ''; expectedOptions.derivativesDir = ''; + expectedOptions.dir = struct('raw', '', ... + 'derivatives', ''); expectedOptions.funcVoxelDims = []; @@ -31,7 +33,8 @@ expectedOptions.contrastList = {}; - expectedOptions.glmQA.do = true; + expectedOptions.glm.QA.do = true; + expectedOptions.glm.roibased.do = false; expectedOptions.model.file = ''; expectedOptions.model.hrfDerivatives = [0 0]; diff --git a/tests/utils/setOptions.m b/tests/utils/setOptions.m index 27a05a8b..de61cd67 100644 --- a/tests/utils/setOptions.m +++ b/tests/utils/setOptions.m @@ -4,6 +4,8 @@ thisDir = fileparts(mfilename('fullpath')); + opt.dir = []; + if strcmp(task, 'MoAE') opt.dataDir = fullfile(thisDir, ... @@ -22,6 +24,8 @@ end + opt = setStatsDir(opt); + if nargin > 1 opt.subjects = {subLabel}; end From 0eef7e131984e9dba8e1bd64e2e00dbfcd8a8787 Mon Sep 17 00:00:00 2001 From: Remi Gau Date: Sat, 3 Apr 2021 13:56:43 +0200 Subject: [PATCH 06/10] fix test --- tests/test_createAndReturnOnsetFile.m | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/test_createAndReturnOnsetFile.m b/tests/test_createAndReturnOnsetFile.m index d23ec58f..44025e74 100644 --- a/tests/test_createAndReturnOnsetFile.m +++ b/tests/test_createAndReturnOnsetFile.m @@ -28,7 +28,7 @@ function test_createAndReturnOnsetFileBasic() onsetFileName = createAndReturnOnsetFile(opt, subLabel, tsvFile, funcFWHM); expectedFileName = fullfile(fileparts(mfilename('fullpath')), ... - 'dummyData', 'derivatives', 'cpp_spm', 'sub-01', 'stats', ... + 'dummyData', 'derivatives', 'cpp_spm-stats', 'sub-01', 'stats', ... 'task-vislocalizer_space-MNI_FWHM-6', ... 'sub-01_ses-01_task-vislocalizer_space-MNI_onsets.mat'); From 0c1ef801e816b82121e37588649a27701a8721b5 Mon Sep 17 00:00:00 2001 From: Remi Gau Date: Sat, 3 Apr 2021 15:44:28 +0200 Subject: [PATCH 07/10] update tests --- src/batches/setBatchEstimateModel.m | 2 +- src/defaults/checkOptions.m | 2 ++ src/workflows/bidsFFX.m | 2 ++ src/workflows/bidsRFX.m | 2 ++ src/workflows/bidsRoiBasedGLM.m | 1 - tests/test_bidsCopyRawFolder.m | 4 ---- tests/test_checkOptions.m | 3 +-- tests/test_createAndReturnOnsetFile.m | 1 - tests/test_createDefaultModel.m | 2 -- tests/test_getAnatFilename.m | 2 -- tests/test_getBoldFilename.m | 2 -- tests/test_getBoldFilenameForFFX.m | 2 -- tests/test_getData.m | 2 -- tests/test_getFFXdir.m | 2 -- tests/test_getMeanFuncFilename.m | 1 - tests/test_getRFXdir.m | 2 -- tests/test_getRealignParamFile.m | 3 --- tests/test_loadAndCheckOptions.m | 12 ++++-------- tests/test_setBatchCoregistrationFuncToAnat.m | 3 --- tests/test_setBatchFactorialDesign.m | 2 -- tests/test_setBatchMeanAnatAndMask.m | 2 -- tests/test_setBatchRealign.m | 1 - tests/test_setBatchSTC.m | 8 -------- tests/test_setBatchSaveCoregistrationMatrix.m | 2 -- tests/test_setBatchSelectAnat.m | 1 - tests/test_setBatchSkullStripping.m | 1 - tests/test_setBatchSmoothConImages.m | 1 - tests/test_setBatchSmoothingFunc.m | 1 - tests/test_setBatchSubjectLevelContrasts.m | 1 - tests/test_setBatchSubjectLevelGLMSpec.m | 2 -- tests/test_setBatchSubjectLevelResults.m | 3 --- tests/test_unit_createDataDictionary.m | 2 -- tests/test_unit_getInfo.m | 3 --- tests/test_unit_getSliceOrder.m | 3 --- tests/test_unit_getSubjectList.m | 8 -------- tests/test_unit_specifyContrasts.m | 2 -- tests/utils/defaultOptions.m | 8 +++++++- tests/utils/setOptions.m | 2 +- 38 files changed, 20 insertions(+), 83 deletions(-) diff --git a/src/batches/setBatchEstimateModel.m b/src/batches/setBatchEstimateModel.m index fc6614b1..719e284e 100644 --- a/src/batches/setBatchEstimateModel.m +++ b/src/batches/setBatchEstimateModel.m @@ -60,7 +60,7 @@ matlabbatch{end}.spm.stats.fmri_est.spmmat = spmMatFile; writeResiduals = true(); - if ~opt.glmQA.do + if ~opt.glm.QA.do writeResiduals = false(); end matlabbatch{end}.spm.stats.fmri_est.write_residuals = writeResiduals; diff --git a/src/defaults/checkOptions.m b/src/defaults/checkOptions.m index fcd6b3c1..e5bb94e1 100644 --- a/src/defaults/checkOptions.m +++ b/src/defaults/checkOptions.m @@ -75,6 +75,8 @@ opt = orderfields(opt); + opt = setStatsDir(opt); + end function fieldsToSet = setDefaultOption() diff --git a/src/workflows/bidsFFX.m b/src/workflows/bidsFFX.m index a1472ad5..47c45ca6 100644 --- a/src/workflows/bidsFFX.m +++ b/src/workflows/bidsFFX.m @@ -30,6 +30,8 @@ function bidsFFX(action, opt, funcFWHM) [BIDS, opt] = setUpWorkflow(opt, 'subject level GLM'); + opt.jobsDir = fullfile(opt.dir.stats, 'JOBS', opt.taskName); + if isempty(opt.model.file) opt = createDefaultModel(BIDS, opt); end diff --git a/src/workflows/bidsRFX.m b/src/workflows/bidsRFX.m index f72fde14..a735c538 100644 --- a/src/workflows/bidsRFX.m +++ b/src/workflows/bidsRFX.m @@ -41,6 +41,8 @@ function bidsRFX(action, opt, funcFWHM, conFWHM) [~, opt] = setUpWorkflow(opt, 'group level GLM'); + opt.jobsDir = fullfile(opt.dir.stats, 'JOBS', opt.taskName); + switch action case 'smoothContrasts' diff --git a/src/workflows/bidsRoiBasedGLM.m b/src/workflows/bidsRoiBasedGLM.m index bba3e2da..72b5d000 100644 --- a/src/workflows/bidsRoiBasedGLM.m +++ b/src/workflows/bidsRoiBasedGLM.m @@ -8,7 +8,6 @@ function bidsRoiBasedGLM(opt) [BIDS, opt] = setUpWorkflow(opt, 'roi based glm'); - opt = setStatsDir(opt); opt.space = 'individual'; opt.jobsDir = fullfile(opt.dir.stats, 'JOBS', opt.taskName); diff --git a/tests/test_bidsCopyRawFolder.m b/tests/test_bidsCopyRawFolder.m index 523c96bb..a86801ad 100644 --- a/tests/test_bidsCopyRawFolder.m +++ b/tests/test_bidsCopyRawFolder.m @@ -12,8 +12,6 @@ function test_bidsCopyRawFolderBasic() opt = setOptions('MoAE'); - opt = checkOptions(opt); - bidsCopyRawFolder(opt, 1); layoutRaw = bids.layout(opt.dataDir); @@ -52,8 +50,6 @@ function test_bidsCopyRawFolder2tasks() opt.taskName = 'vismotion'; - opt = checkOptions(opt); - unZip = false; deleteZippedNii = false; bidsCopyRawFolder(opt, deleteZippedNii, {'func'}, unZip); diff --git a/tests/test_checkOptions.m b/tests/test_checkOptions.m index a8ae7db1..071e62bf 100644 --- a/tests/test_checkOptions.m +++ b/tests/test_checkOptions.m @@ -13,8 +13,7 @@ function test_checkOptionsBasic() opt.taskName = 'testTask'; opt = checkOptions(opt); - expectedOptions = defaultOptions(); - expectedOptions.taskName = 'testTask'; + expectedOptions = defaultOptions('testTask'); assertEqual(opt, expectedOptions); diff --git a/tests/test_createAndReturnOnsetFile.m b/tests/test_createAndReturnOnsetFile.m index 44025e74..d013bc70 100644 --- a/tests/test_createAndReturnOnsetFile.m +++ b/tests/test_createAndReturnOnsetFile.m @@ -16,7 +16,6 @@ function test_createAndReturnOnsetFileBasic() iRun = 1; opt = setOptions('vislocalizer', subLabel); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); diff --git a/tests/test_createDefaultModel.m b/tests/test_createDefaultModel.m index f95e98a3..bf08364d 100644 --- a/tests/test_createDefaultModel.m +++ b/tests/test_createDefaultModel.m @@ -12,8 +12,6 @@ function test_createDefaultModelBasic() opt = setOptions('vislocalizer'); - opt = checkOptions(opt); - [BIDS, opt] = getData(opt); createDefaultModel(BIDS, opt); diff --git a/tests/test_getAnatFilename.m b/tests/test_getAnatFilename.m index 7cebdfd0..05098182 100644 --- a/tests/test_getAnatFilename.m +++ b/tests/test_getAnatFilename.m @@ -20,8 +20,6 @@ function test_getAnatFilenameBasic() opt = setOptions('vislocalizer', subLabel); - opt = checkOptions(opt); - [BIDS, opt] = getData(opt); [anatImage, anatDataDir] = getAnatFilename(BIDS, subLabel, opt); diff --git a/tests/test_getBoldFilename.m b/tests/test_getBoldFilename.m index 9ea0c257..ee3aa79a 100644 --- a/tests/test_getBoldFilename.m +++ b/tests/test_getBoldFilename.m @@ -17,8 +17,6 @@ function test_getBoldFilenameBasic() opt = setOptions('vislocalizer', subLabel); - opt = checkOptions(opt); - [BIDS, opt] = getData(opt); opt.query = struct('acq', ''); diff --git a/tests/test_getBoldFilenameForFFX.m b/tests/test_getBoldFilenameForFFX.m index f677e761..63675f46 100644 --- a/tests/test_getBoldFilenameForFFX.m +++ b/tests/test_getBoldFilenameForFFX.m @@ -17,8 +17,6 @@ function test_getBoldFilenameForFFXBasic() opt = setOptions('vislocalizer', subLabel); - opt = checkOptions(opt); - [BIDS, opt] = getData(opt); [boldFileName, prefix] = getBoldFilenameForFFX(BIDS, opt, subLabel, funcFWHM, iSes, iRun); diff --git a/tests/test_getData.m b/tests/test_getData.m index dfa32545..6cbd66c4 100644 --- a/tests/test_getData.m +++ b/tests/test_getData.m @@ -13,7 +13,6 @@ function test_getDataMetadata() subLabel = '01'; opt = setOptions('vismotion', subLabel); - opt = checkOptions(opt); [~, opt] = getData(opt, [], 'T1w'); @@ -24,7 +23,6 @@ function test_getDataMetadata() function test_getDataErrorTask() opt = setOptions('testTask'); - opt = checkOptions(opt); assertExceptionThrown( ... @()getData(opt), ... diff --git a/tests/test_getFFXdir.m b/tests/test_getFFXdir.m index 829db0e1..1e0c4005 100644 --- a/tests/test_getFFXdir.m +++ b/tests/test_getFFXdir.m @@ -14,7 +14,6 @@ function test_getFFXdirBasic() subLabel = '01'; opt = setOptions('vislocalizer', subLabel); - opt = checkOptions(opt); expectedOutput = fullfile(fileparts(mfilename('fullpath')), 'dummyData', 'derivatives', ... 'cpp_spm-stats', 'sub-01', 'stats', ... @@ -33,7 +32,6 @@ function test_getFFXdirUserSpecified() opt = setOptions('nback', subLabel); opt.space = 'individual'; - opt = checkOptions(opt); ffxDir = getFFXdir(subLabel, funcFWHM, opt); diff --git a/tests/test_getMeanFuncFilename.m b/tests/test_getMeanFuncFilename.m index 623c1ec1..c5bf35ef 100644 --- a/tests/test_getMeanFuncFilename.m +++ b/tests/test_getMeanFuncFilename.m @@ -13,7 +13,6 @@ function test_getMeanFuncFilenameBasic() subLabel = '01'; opt = setOptions('vislocalizer', subLabel); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); diff --git a/tests/test_getRFXdir.m b/tests/test_getRFXdir.m index 46deb652..c59f51a9 100644 --- a/tests/test_getRFXdir.m +++ b/tests/test_getRFXdir.m @@ -14,7 +14,6 @@ function test_getRFXdirBasic() conFWHM = 0; opt = setOptions('vislocalizer'); - opt = checkOptions(opt); rfxDir = getRFXdir(opt, funcFWHM, conFWHM); @@ -36,7 +35,6 @@ function test_getFFXdirUserSpecified() funcFWHM = 6; opt = setOptions('nback'); - opt = checkOptions(opt); rfxDir = getRFXdir(opt, funcFWHM, conFWHM); diff --git a/tests/test_getRealignParamFile.m b/tests/test_getRealignParamFile.m index 9ebce4ea..a71a9070 100644 --- a/tests/test_getRealignParamFile.m +++ b/tests/test_getRealignParamFile.m @@ -15,7 +15,6 @@ function test_getRealignParamFileBasic() run = ''; opt = setOptions('vislocalizer', subLabel); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); @@ -39,7 +38,6 @@ function test_getRealignParamFileNativeSpace() opt = setOptions('vislocalizer', subLabel); opt.space = 'individual'; - opt = checkOptions(opt); [BIDS, opt] = getData(opt); @@ -63,7 +61,6 @@ function test_getRealignParamFileFFX() iRun = 1; opt = setOptions('vislocalizer', subLabel); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); diff --git a/tests/test_loadAndCheckOptions.m b/tests/test_loadAndCheckOptions.m index ba2dc50f..c06e2bb8 100644 --- a/tests/test_loadAndCheckOptions.m +++ b/tests/test_loadAndCheckOptions.m @@ -21,8 +21,7 @@ function test_loadAndCheckOptionsBasic() % makes sure that it is picked up by default opt = loadAndCheckOptions(); - expectedOptions = defaultOptions(); - expectedOptions.taskName = 'vismotion'; + expectedOptions = defaultOptions('vismotion'); assertEqual(opt, expectedOptions); @@ -39,8 +38,7 @@ function test_loadAndCheckOptionsStructure() % makes sure that it is picked up by default opt = loadAndCheckOptions(opt); - expectedOptions = defaultOptions(); - expectedOptions.taskName = 'vismotion'; + expectedOptions = defaultOptions('vismotion'); assertEqual(opt, expectedOptions); @@ -63,8 +61,7 @@ function test_loadAndCheckOptionsFromFile() % makes sure that it is read correctly from opt = loadAndCheckOptions(filename); - expectedOptions = defaultOptions(); - expectedOptions.taskName = 'vismotion'; + expectedOptions = defaultOptions('vismotion'); expectedOptions.space = 'individual'; assertEqual(opt, expectedOptions); @@ -105,8 +102,7 @@ function test_loadAndCheckOptionsFromSeveralFiles() % makes sure that the right json is read opt = loadAndCheckOptions(); - expectedOptions = defaultOptions(); - expectedOptions.taskName = 'vismotion'; + expectedOptions = defaultOptions('vismotion'); expectedOptions.space = 'individual'; expectedOptions.funcVoxelDims = [1 1 1]'; diff --git a/tests/test_setBatchCoregistrationFuncToAnat.m b/tests/test_setBatchCoregistrationFuncToAnat.m index 20c163eb..45589a53 100644 --- a/tests/test_setBatchCoregistrationFuncToAnat.m +++ b/tests/test_setBatchCoregistrationFuncToAnat.m @@ -16,7 +16,6 @@ function test_setBatchCoregistrationFuncToAnatBasic() subLabel = '02'; opt = setOptions('vismotion', subLabel); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); @@ -52,9 +51,7 @@ function test_setBatchCoregistrationFuncToAnatNoUnwarp() subLabel = '02'; opt = setOptions('vismotion', subLabel); - opt = checkOptions(opt); opt.realign.useUnwarp = false; - opt = checkOptions(opt); [BIDS, opt] = getData(opt); diff --git a/tests/test_setBatchFactorialDesign.m b/tests/test_setBatchFactorialDesign.m index 51186390..7be5aff5 100644 --- a/tests/test_setBatchFactorialDesign.m +++ b/tests/test_setBatchFactorialDesign.m @@ -16,8 +16,6 @@ function test_setBatchFactorialDesignBasic() opt = setOptions('vismotion'); opt.subjects = {'01' '02'}; - opt = checkOptions(opt); - matlabbatch = []; matlabbatch = setBatchFactorialDesign(matlabbatch, opt, funcFWHM, conFWHM); diff --git a/tests/test_setBatchMeanAnatAndMask.m b/tests/test_setBatchMeanAnatAndMask.m index 7eced5d4..af30e028 100644 --- a/tests/test_setBatchMeanAnatAndMask.m +++ b/tests/test_setBatchMeanAnatAndMask.m @@ -15,8 +15,6 @@ function test_setBatchMeanAnatAndMaskBasic() opt = setOptions('vismotion'); opt.subjects = {'01', '02'}; - opt = checkOptions(opt); - matlabbatch = []; matlabbatch = setBatchMeanAnatAndMask(matlabbatch, opt, funcFWHM, pwd); diff --git a/tests/test_setBatchRealign.m b/tests/test_setBatchRealign.m index abccf14b..7ead8b76 100644 --- a/tests/test_setBatchRealign.m +++ b/tests/test_setBatchRealign.m @@ -19,7 +19,6 @@ function test_setBatchRealignBasic() subLabel = '01'; opt = setOptions('MoAE', subLabel); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); matlabbatch = []; diff --git a/tests/test_setBatchSTC.m b/tests/test_setBatchSTC.m index 28e9ace6..39435854 100644 --- a/tests/test_setBatchSTC.m +++ b/tests/test_setBatchSTC.m @@ -13,8 +13,6 @@ function test_setBatchSTCEmpty() subLabel = '02'; opt = setOptions('vislocalizer', subLabel); - opt = setDerivativesDir(opt); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); @@ -31,7 +29,6 @@ function test_setBatchSTCForce() subLabel = '02'; opt = setOptions('vislocalizer', subLabel); - opt = setDerivativesDir(opt); % we give it some slice timing value to force slice timing to happen opt.sliceOrder = linspace(0, 1.6, 10); @@ -68,9 +65,7 @@ function test_setBatchSTCBasic() subLabel = '02'; opt = setOptions('vismotion', subLabel); - opt = setDerivativesDir(opt); opt.query = struct('acq', ''); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); @@ -110,14 +105,11 @@ function test_setBatchSTCErrorInvalidInputTime() subLabel = '02'; opt = setOptions('vislocalizer', subLabel); - opt = setDerivativesDir(opt); opt.sliceOrder = linspace(0, 1.6, 10); opt.sliceOrder(end) = []; opt.STC_referenceSlice = 2; % impossible reference value - opt = checkOptions(opt); - [BIDS, opt] = getData(opt); matlabbatch = []; diff --git a/tests/test_setBatchSaveCoregistrationMatrix.m b/tests/test_setBatchSaveCoregistrationMatrix.m index 582c346f..9492e226 100644 --- a/tests/test_setBatchSaveCoregistrationMatrix.m +++ b/tests/test_setBatchSaveCoregistrationMatrix.m @@ -16,9 +16,7 @@ function test_setBatchSaveCoregistrationMatrixBasic() subLabel = '02'; opt = setOptions('vismotion', subLabel); - opt = setDerivativesDir(opt); opt.query = struct('acq', ''); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); diff --git a/tests/test_setBatchSelectAnat.m b/tests/test_setBatchSelectAnat.m index 38023a7c..7edda8c1 100644 --- a/tests/test_setBatchSelectAnat.m +++ b/tests/test_setBatchSelectAnat.m @@ -17,7 +17,6 @@ function test_setBatchSelectAnatBasic() subLabel = '01'; opt = setOptions('MoAE', subLabel); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); diff --git a/tests/test_setBatchSkullStripping.m b/tests/test_setBatchSkullStripping.m index f6f88159..788e0875 100644 --- a/tests/test_setBatchSkullStripping.m +++ b/tests/test_setBatchSkullStripping.m @@ -13,7 +13,6 @@ function test_setBatchSkullStrippingBasic() subLabel = '01'; opt = setOptions('vislocalizer', subLabel); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); diff --git a/tests/test_setBatchSmoothConImages.m b/tests/test_setBatchSmoothConImages.m index 276d28d2..7a3364c9 100644 --- a/tests/test_setBatchSmoothConImages.m +++ b/tests/test_setBatchSmoothConImages.m @@ -15,7 +15,6 @@ function test_setBatchSmoothConImagesBasic() opt = setOptions('vismotion'); opt.subjects = {'01', '02'}; - opt = checkOptions(opt); [~, opt] = getData(opt); diff --git a/tests/test_setBatchSmoothingFunc.m b/tests/test_setBatchSmoothingFunc.m index 66b6f60f..de198f1d 100644 --- a/tests/test_setBatchSmoothingFunc.m +++ b/tests/test_setBatchSmoothingFunc.m @@ -18,7 +18,6 @@ function test_setBatchSmoothingFuncBasic() funcFWHM = 6; opt = setOptions('MoAE', subLabel); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); diff --git a/tests/test_setBatchSubjectLevelContrasts.m b/tests/test_setBatchSubjectLevelContrasts.m index 3c18cf59..7995a8ab 100644 --- a/tests/test_setBatchSubjectLevelContrasts.m +++ b/tests/test_setBatchSubjectLevelContrasts.m @@ -14,7 +14,6 @@ function test_setBatchSubjectLevelContrastsBasic() funcFWHM = 6; opt = setOptions('vismotion', subLabel); - opt = checkOptions(opt); matlabbatch = []; matlabbatch = setBatchSubjectLevelContrasts(matlabbatch, opt, subLabel, funcFWHM); diff --git a/tests/test_setBatchSubjectLevelGLMSpec.m b/tests/test_setBatchSubjectLevelGLMSpec.m index ec2305f0..410a9599 100644 --- a/tests/test_setBatchSubjectLevelGLMSpec.m +++ b/tests/test_setBatchSubjectLevelGLMSpec.m @@ -17,8 +17,6 @@ function test_setBatchSubjectLevelGLMSpecBasic() opt = setOptions('MoAE', subLabel); - opt = checkOptions(opt); - bidsCopyRawFolder(opt, 1); [BIDS, opt] = getData(opt); diff --git a/tests/test_setBatchSubjectLevelResults.m b/tests/test_setBatchSubjectLevelResults.m index a31debfb..b8f4d636 100644 --- a/tests/test_setBatchSubjectLevelResults.m +++ b/tests/test_setBatchSubjectLevelResults.m @@ -18,7 +18,6 @@ function test_setBatchSubjectLevelResultsBasic() opt = setOptions('vismotion', subLabel); opt.space = 'MNI'; - opt = checkOptions(opt); opt.result.Steps.Contrasts.Name = 'VisMot'; @@ -59,7 +58,6 @@ function test_setBatchSubjectLevelResultsErrorMissingContrastName() opt = setOptions('vismotion', subLabel); opt.space = 'MNI'; - opt = checkOptions(opt); matlabbatch = []; assertExceptionThrown( ... @@ -86,7 +84,6 @@ function test_setBatchSubjectLevelResultsErrorNoMAtchingContrast() opt = setOptions('vismotion', subLabel); opt.space = 'MNI'; - opt = checkOptions(opt); opt.result.Steps.Contrasts.Name = 'NotAContrast'; diff --git a/tests/test_unit_createDataDictionary.m b/tests/test_unit_createDataDictionary.m index 64aebba5..ba1aeecf 100644 --- a/tests/test_unit_createDataDictionary.m +++ b/tests/test_unit_createDataDictionary.m @@ -16,8 +16,6 @@ function test_createDataDictionaryBasic() opt = setOptions('vislocalizer', subLabel); - opt = checkOptions(opt); - [BIDS, opt] = getData(opt); opt.query = struct('acq', ''); diff --git a/tests/test_unit_getInfo.m b/tests/test_unit_getInfo.m index 8496f3e3..ec5198ca 100644 --- a/tests/test_unit_getInfo.m +++ b/tests/test_unit_getInfo.m @@ -13,7 +13,6 @@ function test_getInfoBasic() subLabel = 'ctrl01'; opt = setOptions('vismotion', subLabel); - opt = checkOptions(opt); info = 'sessions'; @@ -55,7 +54,6 @@ function test_getInfoQuery() info = 'filename'; opt = setOptions('vismotion', subLabel); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); @@ -100,7 +98,6 @@ function test_getInfoQueryWithSessionRestriction() subLabel = 'ctrl01'; opt = setOptions('vismotion', subLabel); - opt = checkOptions(opt); [BIDS, opt] = getData(opt); diff --git a/tests/test_unit_getSliceOrder.m b/tests/test_unit_getSliceOrder.m index 12f55d2a..379e0ab1 100644 --- a/tests/test_unit_getSliceOrder.m +++ b/tests/test_unit_getSliceOrder.m @@ -11,7 +11,6 @@ function test_getSliceOrderBasic() opt = setOptions('vismotion'); - opt = checkOptions(opt); [~, opt] = getData(opt); BIDS_sliceOrder = getSliceOrder(opt, 0); @@ -40,7 +39,6 @@ function test_getSliceOrderBasic() function test_getSliceOrderEmpty() opt = setOptions('vislocalizer'); - opt = checkOptions(opt); [~, opt] = getData(opt); @@ -55,7 +53,6 @@ function test_getSliceOrderFromOptions() opt = setOptions('vislocalizer'); opt.STC_referenceSlice = 1000; opt.sliceOrder = 0:250:2000; - opt = checkOptions(opt); [~, opt] = getData(opt); BIDS_sliceOrder = getSliceOrder(opt, 0); diff --git a/tests/test_unit_getSubjectList.m b/tests/test_unit_getSubjectList.m index 4d4a6e5b..880c1d89 100644 --- a/tests/test_unit_getSubjectList.m +++ b/tests/test_unit_getSubjectList.m @@ -11,8 +11,6 @@ function test_getSubjectListNone() opt = setOptions('vismotion'); - opt = setDerivativesDir(opt); - opt = checkOptions(opt); BIDS = bids.layout(opt.derivativesDir); @@ -27,8 +25,6 @@ function test_getSubjectListNone() function test_getSubjectListGroup() opt = setOptions('vismotion'); - opt = setDerivativesDir(opt); - opt = checkOptions(opt); BIDS = bids.layout(opt.derivativesDir); @@ -46,8 +42,6 @@ function test_getSubjectListGroup() function test_getSubjectListBasic() opt = setOptions('vismotion'); - opt = setDerivativesDir(opt); - opt = checkOptions(opt); BIDS = bids.layout(opt.derivativesDir); @@ -64,8 +58,6 @@ function test_getSubjectListBasic() function test_getSubjectListErrorSubject() opt = setOptions('vismotion', '03'); - opt = setDerivativesDir(opt); - opt = checkOptions(opt); BIDS = bids.layout(opt.derivativesDir); diff --git a/tests/test_unit_specifyContrasts.m b/tests/test_unit_specifyContrasts.m index 56cae880..373a13c5 100644 --- a/tests/test_unit_specifyContrasts.m +++ b/tests/test_unit_specifyContrasts.m @@ -15,8 +15,6 @@ function test_specifyContrastsBasic() funcFWFM = 6; opt = setOptions('vismotion', subLabel); - opt = checkOptions(opt); - opt = setDerivativesDir(opt); ffxDir = getFFXdir(subLabel, funcFWFM, opt); diff --git a/tests/utils/defaultOptions.m b/tests/utils/defaultOptions.m index bac6f70c..5c7211f8 100644 --- a/tests/utils/defaultOptions.m +++ b/tests/utils/defaultOptions.m @@ -1,6 +1,6 @@ % (C) Copyright 2021 CPP BIDS SPM-pipeline developers -function expectedOptions = defaultOptions() +function expectedOptions = defaultOptions(taskName) expectedOptions.sliceOrder = []; expectedOptions.STC_referenceSlice = []; @@ -45,6 +45,12 @@ expectedOptions.parallelize.nbWorkers = 3; expectedOptions.parallelize.killOnExit = true; + if nargin > 0 + expectedOptions.taskName = taskName; + end + expectedOptions = orderfields(expectedOptions); + expectedOptions = setStatsDir(expectedOptions); + end diff --git a/tests/utils/setOptions.m b/tests/utils/setOptions.m index de61cd67..9e12acb8 100644 --- a/tests/utils/setOptions.m +++ b/tests/utils/setOptions.m @@ -24,7 +24,7 @@ end - opt = setStatsDir(opt); + opt = checkOptions(opt); if nargin > 1 opt.subjects = {subLabel}; From c57312ccf018fd6ca4d49d9691220f2e67efd8ac Mon Sep 17 00:00:00 2001 From: Remi Gau Date: Sat, 3 Apr 2021 15:45:07 +0200 Subject: [PATCH 08/10] update face rep demo --- demos/spm_face_rep/FaceRep_getOption.m | 1 - demos/spm_face_rep/FaceRep_getOptionResults.m | 2 +- demos/spm_face_rep/face_rep_anat.m | 8 +-- demos/spm_face_rep/face_rep_func.m | 23 ++++---- demos/spm_face_rep/face_rep_resolution.m | 23 ++++++-- demos/spm_face_rep/face_rep_roi_analysis.m | 2 + .../models/model-faceRepetition_smdl.json | 58 +------------------ 7 files changed, 39 insertions(+), 78 deletions(-) diff --git a/demos/spm_face_rep/FaceRep_getOption.m b/demos/spm_face_rep/FaceRep_getOption.m index 414fe675..660accd7 100644 --- a/demos/spm_face_rep/FaceRep_getOption.m +++ b/demos/spm_face_rep/FaceRep_getOption.m @@ -10,7 +10,6 @@ opt.dataDir = fullfile(fileparts(mfilename('fullpath')), 'outputs', 'raw'); opt.dir.roi = fullfile(opt.dataDir, '..', 'derivatives', 'cpp_spm-roi'); - opt.dir.stats = fullfile(opt.dataDir, '..', 'derivatives', 'cpp_spm-stats'); opt.model.hrfDerivatives = [1 1]; diff --git a/demos/spm_face_rep/FaceRep_getOptionResults.m b/demos/spm_face_rep/FaceRep_getOptionResults.m index b367b1cd..bd0600eb 100644 --- a/demos/spm_face_rep/FaceRep_getOptionResults.m +++ b/demos/spm_face_rep/FaceRep_getOptionResults.m @@ -9,7 +9,7 @@ 'models', ... 'model-faceRepetition_smdl.json'); - opt.glmQA.do = false; + opt.glm.QA.do = false; % Specify the result to compute opt.result.Steps(1) = returnDefaultResultsStructure(); diff --git a/demos/spm_face_rep/face_rep_anat.m b/demos/spm_face_rep/face_rep_anat.m index 2d93eb73..7cf2461f 100644 --- a/demos/spm_face_rep/face_rep_anat.m +++ b/demos/spm_face_rep/face_rep_anat.m @@ -27,10 +27,10 @@ end %% Run batches -reportBIDS(opt); -bidsCopyRawFolder(opt, 1, 'anat'); +% reportBIDS(opt); +% bidsCopyRawFolder(opt, 1, 'anat'); -bidsSegmentSkullStrip(opt); +% bidsSegmentSkullStrip(opt); % The following do not run on octave for now (because of spmup) -anatomicalQA(opt); +% anatomicalQA(opt); diff --git a/demos/spm_face_rep/face_rep_func.m b/demos/spm_face_rep/face_rep_func.m index 4d37afcc..972da2db 100644 --- a/demos/spm_face_rep/face_rep_func.m +++ b/demos/spm_face_rep/face_rep_func.m @@ -19,7 +19,7 @@ FWHM = 6; -downloadData = true; +downloadData = false; run ../../initCppSpm.m; @@ -34,23 +34,26 @@ end %% Run batches -reportBIDS(opt); -bidsCopyRawFolder(opt, 1); - -bidsSTC(opt); - -bidsSpatialPrepro(opt); +% reportBIDS(opt); +% bidsCopyRawFolder(opt, 1); +% +% bidsSTC(opt); +% +% bidsSpatialPrepro(opt); % The following do not run on octave for now (because of spmup) -anatomicalQA(opt); -bidsResliceTpmToFunc(opt); +% anatomicalQA(opt); +% bidsResliceTpmToFunc(opt); % DEBUG % functionalQA(opt); -bidsSmoothing(FWHM, opt); +% bidsSmoothing(FWHM, opt); % The following crash on Travis CI + +opt.dir.stats = opt.derivativesDir; + bidsFFX('specifyAndEstimate', opt, FWHM); bidsFFX('contrasts', opt, FWHM); diff --git a/demos/spm_face_rep/face_rep_resolution.m b/demos/spm_face_rep/face_rep_resolution.m index 6db1b455..c4ff9dc4 100644 --- a/demos/spm_face_rep/face_rep_resolution.m +++ b/demos/spm_face_rep/face_rep_resolution.m @@ -7,10 +7,11 @@ clear; clc; +close all; FWHM = 6; -downloadData = true; +downloadData = false; run ../../initCppSpm.m; @@ -29,6 +30,8 @@ reportBIDS(opt); +modelFile = opt.model.file; + for iResolution = 1:0.5:3 opt.funcVoxelDims = repmat(iResolution, 1, 3); @@ -39,13 +42,23 @@ 'derivatives', ... ['cpp_spm-res' num2str(iResolution)]), 'cpath'); - bidsCopyRawFolder(opt, 1); + content = spm_jsonread(opt.model.file); + content.Name = [content.Name, ' resolution - ', num2str(iResolution)]; - bidsSTC(opt); + p = bids.internal.parse_filename(modelFile); + p.model = [p.model, ' resolution', num2str(iResolution)]; + newModel = spm_file(opt.model.file, 'filename', createFilename(p)); + opt.model.file = newModel; - bidsSpatialPrepro(opt); + spm_jsonwrite(newModel, content, struct('indent', ' ')); - bidsSmoothing(FWHM, opt); + % bidsCopyRawFolder(opt, 1); + % + % bidsSTC(opt); + % + % bidsSpatialPrepro(opt); + % + % bidsSmoothing(FWHM, opt); bidsFFX('specifyAndEstimate', opt, FWHM); bidsFFX('contrasts', opt, FWHM); diff --git a/demos/spm_face_rep/face_rep_roi_analysis.m b/demos/spm_face_rep/face_rep_roi_analysis.m index 265a75f3..04fdc3df 100644 --- a/demos/spm_face_rep/face_rep_roi_analysis.m +++ b/demos/spm_face_rep/face_rep_roi_analysis.m @@ -11,6 +11,8 @@ opt.roi.name = {'V1v', 'V1d'}; opt.roi.space = {'MNI', 'individual'}; +opt.dir.stats = fullfile(opt.dataDir, '..', 'derivatives', 'cpp_spm-stats'); + % bidsCreateROI(opt); opt.glm.roibased.do = true; diff --git a/demos/spm_face_rep/models/model-faceRepetition_smdl.json b/demos/spm_face_rep/models/model-faceRepetition_smdl.json index 45ddda67..29fd68f1 100644 --- a/demos/spm_face_rep/models/model-faceRepetition_smdl.json +++ b/demos/spm_face_rep/models/model-faceRepetition_smdl.json @@ -1,5 +1,5 @@ { - "Name": "face repetition resampling", + "Name": "resampling", "Description": "model for face repetition to check resampling effects", "Input": { "task": "facerepetition" @@ -69,62 +69,6 @@ "type": "t" } ] - }, - { - "Level": "run", - "Transformations": [ - { - "Name": "Factor", - "Inputs": [ - "trial_type" - ] - }, - { - "Name": "Convolve", - "Model": "spm", - "Inputs": [ - " " - ] - } - ], - "Model": { - "X": [ - "trial_type.F1", - "trial_type.F2", - "trial_type.N1", - "trial_type.N2", - "trans_x", - "trans_y", - "trans_z", - "rot_x", - "rot_y", - "rot_z" - ], - "Options": { - "high_pass_filter_cutoff_secs": 128 - }, - "Software": { - "SPM": { - "whitening": "FAST" - } - }, - "Mask": " " - }, - "AutoContrasts": [ - "trial_type.F1", - "trial_type.F2", - "trial_type.N1", - "trial_type.N2" - ] - }, - { - "Level": "dataset", - "AutoContrasts": [ - "trial_type.F1", - "trial_type.F2", - "trial_type.N1", - "trial_type.N2" - ] } ] } \ No newline at end of file From bce592cdd31ef9b4870f8bd2396b95092a011a5f Mon Sep 17 00:00:00 2001 From: Remi Gau Date: Sat, 3 Apr 2021 16:13:38 +0200 Subject: [PATCH 09/10] reset demos --- demos/MoAE/MoAE_run.m | 26 +++++++++---------- demos/spm_face_rep/FaceRep_getOptionResults.m | 4 --- demos/spm_face_rep/face_rep_anat.m | 10 +++---- demos/spm_face_rep/face_rep_func.m | 22 +++++++--------- demos/spm_face_rep/face_rep_resolution.m | 16 ++++++------ demos/spm_face_rep/face_rep_roi_analysis.m | 2 +- miss_hit.cfg | 2 +- 7 files changed, 38 insertions(+), 44 deletions(-) diff --git a/demos/MoAE/MoAE_run.m b/demos/MoAE/MoAE_run.m index bd5208ce..bee7d73d 100644 --- a/demos/MoAE/MoAE_run.m +++ b/demos/MoAE/MoAE_run.m @@ -13,7 +13,7 @@ % Smoothing to apply FWHM = 6; -downloadData = false; +downloadData = true; run ../../initCppSpm.m; @@ -23,27 +23,27 @@ dowload_MoAE_ds(downloadData); %% Run batches -% reportBIDS(opt); -% bidsCopyRawFolder(opt, 1); +reportBIDS(opt); +bidsCopyRawFolder(opt, 1); % In case you just want to run segmentation and skull stripping -% -% bidsSegmentSkullStrip(opt); -% + +bidsSegmentSkullStrip(opt); + % NOTE: skull stripping is also included in 'bidsSpatialPrepro' -% bidsSTC(opt); +bidsSTC(opt); -% bidsSpatialPrepro(opt); +bidsSpatialPrepro(opt); % The following do not run on octave for now (because of spmup) % anatomicalQA(opt); % bidsResliceTpmToFunc(opt); % functionalQA(opt); -% -% bidsSmoothing(FWHM, opt); + +bidsSmoothing(FWHM, opt); % The following crash on Travis CI -% bidsFFX('specifyAndEstimate', opt, FWHM); -% bidsFFX('contrasts', opt, FWHM); -% bidsResults(opt, FWHM); +bidsFFX('specifyAndEstimate', opt, FWHM); +bidsFFX('contrasts', opt, FWHM); +bidsResults(opt, FWHM); diff --git a/demos/spm_face_rep/FaceRep_getOptionResults.m b/demos/spm_face_rep/FaceRep_getOptionResults.m index bd0600eb..541fc08a 100644 --- a/demos/spm_face_rep/FaceRep_getOptionResults.m +++ b/demos/spm_face_rep/FaceRep_getOptionResults.m @@ -24,17 +24,13 @@ % Specify how you want your output (all the following are on false by default) opt.result.Steps(1).Output.png = true(); - opt.result.Steps(1).Output.csv = true(); - opt.result.Steps(1).Output.thresh_spm = true(); - opt.result.Steps(1).Output.binary = true(); % MONTAGE FIGURE OPTIONS opt.result.Steps(1).Output.montage.do = true(); opt.result.Steps(1).Output.montage.slices = -26:3:6; % in mm - % axial is default 'sagittal', 'coronal' opt.result.Steps(1).Output.montage.orientation = 'axial'; end diff --git a/demos/spm_face_rep/face_rep_anat.m b/demos/spm_face_rep/face_rep_anat.m index 7cf2461f..0df75713 100644 --- a/demos/spm_face_rep/face_rep_anat.m +++ b/demos/spm_face_rep/face_rep_anat.m @@ -9,7 +9,7 @@ clear; clc; -downloadData = false; +downloadData = true; run ../../initCppSpm.m; @@ -27,10 +27,10 @@ end %% Run batches -% reportBIDS(opt); -% bidsCopyRawFolder(opt, 1, 'anat'); +reportBIDS(opt); +bidsCopyRawFolder(opt, 1, 'anat'); -% bidsSegmentSkullStrip(opt); +bidsSegmentSkullStrip(opt); % The following do not run on octave for now (because of spmup) -% anatomicalQA(opt); +anatomicalQA(opt); diff --git a/demos/spm_face_rep/face_rep_func.m b/demos/spm_face_rep/face_rep_func.m index 972da2db..5a104a5b 100644 --- a/demos/spm_face_rep/face_rep_func.m +++ b/demos/spm_face_rep/face_rep_func.m @@ -19,7 +19,7 @@ FWHM = 6; -downloadData = false; +downloadData = true; run ../../initCppSpm.m; @@ -34,26 +34,24 @@ end %% Run batches -% reportBIDS(opt); -% bidsCopyRawFolder(opt, 1); -% -% bidsSTC(opt); -% -% bidsSpatialPrepro(opt); +reportBIDS(opt); +bidsCopyRawFolder(opt, 1); + +bidsSTC(opt); + +bidsSpatialPrepro(opt); % The following do not run on octave for now (because of spmup) -% anatomicalQA(opt); -% bidsResliceTpmToFunc(opt); +anatomicalQA(opt); +bidsResliceTpmToFunc(opt); % DEBUG % functionalQA(opt); -% bidsSmoothing(FWHM, opt); +bidsSmoothing(FWHM, opt); % The following crash on Travis CI - opt.dir.stats = opt.derivativesDir; - bidsFFX('specifyAndEstimate', opt, FWHM); bidsFFX('contrasts', opt, FWHM); diff --git a/demos/spm_face_rep/face_rep_resolution.m b/demos/spm_face_rep/face_rep_resolution.m index c4ff9dc4..3e2ec99e 100644 --- a/demos/spm_face_rep/face_rep_resolution.m +++ b/demos/spm_face_rep/face_rep_resolution.m @@ -11,7 +11,7 @@ FWHM = 6; -downloadData = false; +downloadData = true; run ../../initCppSpm.m; @@ -52,13 +52,13 @@ spm_jsonwrite(newModel, content, struct('indent', ' ')); - % bidsCopyRawFolder(opt, 1); - % - % bidsSTC(opt); - % - % bidsSpatialPrepro(opt); - % - % bidsSmoothing(FWHM, opt); + bidsCopyRawFolder(opt, 1); + + bidsSTC(opt); + + bidsSpatialPrepro(opt); + + bidsSmoothing(FWHM, opt); bidsFFX('specifyAndEstimate', opt, FWHM); bidsFFX('contrasts', opt, FWHM); diff --git a/demos/spm_face_rep/face_rep_roi_analysis.m b/demos/spm_face_rep/face_rep_roi_analysis.m index 04fdc3df..dc8b8af3 100644 --- a/demos/spm_face_rep/face_rep_roi_analysis.m +++ b/demos/spm_face_rep/face_rep_roi_analysis.m @@ -13,7 +13,7 @@ opt.dir.stats = fullfile(opt.dataDir, '..', 'derivatives', 'cpp_spm-stats'); -% bidsCreateROI(opt); +bidsCreateROI(opt); opt.glm.roibased.do = true; diff --git a/miss_hit.cfg b/miss_hit.cfg index 2c6a2b5c..bce4b86c 100644 --- a/miss_hit.cfg +++ b/miss_hit.cfg @@ -1,6 +1,6 @@ # styly guide (https://florianschanda.github.io/miss_hit/style_checker.html) line_length: 100 -regex_function_name: "[a-z]+(_*([a-zA-Z0-9]){1}[A-Za-z]+)*" # almost anything goes in the root folder +regex_function_name: "[a-z]+(_*([a-zA-Z0-9]){1}[A-Za-z]+)*" exclude_dir: "lib" copyright_entity: "JH" copyright_entity: "DSS" From d3f0a1b51e3a93d38454cfda4e6efe19be580fde Mon Sep 17 00:00:00 2001 From: Remi Gau Date: Wed, 7 Apr 2021 18:00:23 +0200 Subject: [PATCH 10/10] add errors in FFX and roi based GLMs to prevent running them with the wrong options AKA child protection --- src/workflows/bidsFFX.m | 8 ++++++++ src/workflows/bidsRoiBasedGLM.m | 8 ++++++++ 2 files changed, 16 insertions(+) diff --git a/src/workflows/bidsFFX.m b/src/workflows/bidsFFX.m index 47c45ca6..5765e289 100644 --- a/src/workflows/bidsFFX.m +++ b/src/workflows/bidsFFX.m @@ -27,6 +27,14 @@ function bidsFFX(action, opt, funcFWHM) % For unsmoothed data ``funcFWHM = 0``, for smoothed data ``funcFWHM = ... mm``. % In this way we can make multiple ffx for different smoothing degrees. % + + if opt.glm.roibased.do + message = sprintf(... + ['The option opt.glm.roibased.do is set to true.\n', ... + ' Change the option to false to use this workflow or\n', ... + ' use the bidsRoiBasedGLM workflow to run roi based GLM.']); + error(message); + end [BIDS, opt] = setUpWorkflow(opt, 'subject level GLM'); diff --git a/src/workflows/bidsRoiBasedGLM.m b/src/workflows/bidsRoiBasedGLM.m index 72b5d000..fdc02688 100644 --- a/src/workflows/bidsRoiBasedGLM.m +++ b/src/workflows/bidsRoiBasedGLM.m @@ -3,6 +3,14 @@ function bidsRoiBasedGLM(opt) % % + + if ~opt.glm.roibased.do + message = sprintf(... + ['The option opt.glm.roibased.do is set to false.\n', ... + ' Change the option to true to use this workflow or\n', ... + ' use the bidsFFX workflow to run whole brain GLM.']); + error(message); + end funcFWHM = 0;