@@ -290,3 +290,220 @@ def _list_outputs(self):
290
290
outputs = self ._outputs ().get ()
291
291
outputs ['output_image' ] = os .path .abspath (self ._gen_filename ('output_image' ))
292
292
return outputs
293
+
294
+ class antsCorticalThicknessInputSpec (ANTSCommandInputSpec ):
295
+ dimension = traits .Enum (3 , 2 , argstr = '-d %d' , usedefault = True ,
296
+ desc = 'image dimension (2 or 3)' )
297
+ anatomical_image = File (exists = True ,
298
+ argstr = '-a %s' ,
299
+ desc = 'Structural *intensity* image, typically T1.'
300
+ 'If more than one anatomical image is specified,'
301
+ 'subsequently specified images are used during the'
302
+ 'segmentation process. However, only the first'
303
+ 'image is used in the registration of priors.'
304
+ 'Our suggestion would be to specify the T1'
305
+ 'as the first image.' ,
306
+ mandatory = True )
307
+ brain_template = File (exists = True ,
308
+ argstr = '-e %s' ,
309
+ desc = 'Anatomical *intensity* template (possibly created using a'
310
+ 'population data set with buildtemplateparallel.sh in ANTs).'
311
+ 'This template is *not* skull-stripped.' )
312
+ brain_probability_mask = File (exists = True ,
313
+ argstr = '-m %s' , desc = 'brain probability mask in template space' ,
314
+ mandatory = True , copyfile = False )
315
+ segmentation_priors = InputMultiPath (File (exists = True ),
316
+ argstr = '-p %s' )
317
+ out_prefix = traits .Str ('antsCT_' , argstr = '-o %s' , usedefault = True ,
318
+ desc = ('Prefix that is prepended to all output'
319
+ ' files (default = antsCT_)' ))
320
+ image_suffix = traits .Str ('nii.gz' , desc = ('any of standard ITK formats,'
321
+ ' nii.gz is default' ), mandatory = False , argstr = '-s %s' ,
322
+ usedefault = True )
323
+ t1_registration_template = File (exists = True ,
324
+ desc = ('Anatomical *intensity* template'
325
+ '(assumed to be skull-stripped). A common'
326
+ 'case would be where this would be the same'
327
+ 'template as specified in the -e option which'
328
+ 'is not skull stripped.' ),
329
+ mandatory = True , argstr = '-t %s' )
330
+ extraction_registration_mask = File (exists = True , argstr = '-f %s' ,
331
+ mandatory = False , desc = 'Mask (defined in the template'
332
+ 'space) used during registration for brain extraction.' )
333
+ keep_temporary_files = traits .Int (argstrr = '-k %d' ,
334
+ desc = 'Keep brain extraction/segmentation'
335
+ 'warps, etc (default = 0).' , mandatory = False )
336
+ max_iterations = traits .Int (argstr = '-i %d' ,
337
+ desc = 'ANTS registration max iterations'
338
+ '(default = 100x100x70x20)' , mandatory = False )
339
+ prior_segmentation_weight = traits .Float (mandatory = False , argstr = '-w %f' ,
340
+ desc = 'Atropos spatial prior *probability* weight for'
341
+ 'the segmentation' )
342
+ segmentation_iterations = traits .Int (argstr = '-n %d' , mandatory = False ,
343
+ desc = 'N4 -> Atropos -> N4 iterations during segmentation'
344
+ '(default = 3)' )
345
+ posterior_formulation = traits .Str (argstr = '-b %s' , mandatory = False ,
346
+ desc = ('Atropos posterior formulation and whether or not'
347
+ 'to use mixture model proportions.'
348
+ '''e.g 'Socrates[1]' (default) or 'Aristotle[1]'.'''
349
+ 'Choose the latter if you'
350
+ 'want use the distance priors (see also the -l option'
351
+ 'for label propagation control).' ))
352
+ use_floatingpoint_precision = traits .Enum (0 , 1 , argstr = '-j %d' ,
353
+ mandatory = False ,
354
+ desc = 'Use floating point precision in registrations (default = 0)' )
355
+ use_random_seeding = traits .Enum (0 , 1 , argstr = '-u %d' , mandatory = False ,
356
+ desc = 'Use random number generated from system clock in Atropos'
357
+ '(default = 1)' )
358
+ b_spline_smoothing = traits .Bool (argst = '-v' , mandatory = False ,
359
+ desc = 'Use B-spline SyN for registrations and B-spline'
360
+ 'exponential mapping in DiReCT.' )
361
+ cortical_label_image = File (exists = True , mandatory = False ,
362
+ desc = 'Cortical ROI labels to use as a prior for ATITH.' )
363
+ label_propagation = traits .Str (argstr = '-l %s' , mandatory = False ,
364
+ desc = 'Incorporate a distance prior one the posterior formulation. Should be'
365
+ '''of the form 'label[lambda,boundaryProbability]' where label'''
366
+ 'is a value of 1,2,3,... denoting label ID. The label'
367
+ 'probability for anything outside the current label'
368
+ ' = boundaryProbability * exp( -lambda * distanceFromBoundary )'
369
+ 'Intuitively, smaller lambda values will increase the spatial capture'
370
+ 'range of the distance prior. To apply to all label values, simply omit'
371
+ 'specifying the label, i.e. -l [lambda,boundaryProbability].' )
372
+ quick_registration = traits .Bool (argstr = '-q 1' , mandatory = False ,
373
+ desc = 'If = 1, use antsRegistrationSyNQuick.sh as the basis for registration'
374
+ 'during brain extraction, brain segmentation, and'
375
+ '(optional) normalization to a template.'
376
+ 'Otherwise use antsRegistrationSyN.sh (default = 0).' )
377
+ debug = traits .Bool (argstr = '-z 1' , mandatory = False ,
378
+ desc = 'If > 0, runs a faster version of the script.'
379
+ 'Only for testing. Implies -u 0.'
380
+ 'Requires single thread computation for complete reproducibility.' )
381
+
382
+ class antsCorticalThicknessoutputSpec (TraitedSpec ):
383
+ BrainExtractionMask = File (exists = True ,
384
+ desc = 'brain extraction mask' )
385
+ BrainSegmentation = File (exists = True ,
386
+ desc = 'brain segmentaion image' )
387
+ BrainSegmentationN4 = File (exists = True ,
388
+ desc = 'N4 corrected image' )
389
+ BrainSegmentationPosteriorsCSF = File (exists = True ,
390
+ desc = 'CSF posterior probability image' )
391
+ BrainSegmentationPosteriorsGM = File (exists = True ,
392
+ desc = 'GM posterior probability image' )
393
+ BrainSegmentationPosteriorsWM = File (exists = True ,
394
+ desc = 'WM posterior probability image' )
395
+ BrainSegmentationPosteriorsDGM = File (exists = True ,
396
+ desc = 'DGM posterior probability image' )
397
+ CorticalThickness = File (exists = True ,
398
+ desc = 'cortical thickness file' )
399
+ TemplateToSubject1GenericAffine = File (exists = True ,
400
+ desc = 'Template to subject affine' )
401
+ TemplateToSubject0Warp = File (exists = True ,
402
+ desc = 'Template to subject warp' )
403
+ SubjectToTemplate1Warp = File (exists = True ,
404
+ desc = 'Template to subject inverse warp' )
405
+ SubjectToTemplate0GenericAffine = File (exists = True ,
406
+ desc = 'Template to subject inverse affine' )
407
+ TemplateToSubjectLogJacobian = File (exists = True ,
408
+ desc = 'Template to subject log jacobian' )
409
+
410
+ class antsCorticalThickness (ANTSCommand ):
411
+ """
412
+ Examples
413
+ --------
414
+ >>> from nipype.interfaces.ants.segmentation import antsCorticalThickness
415
+ >>> corticalthickness = anstCorticalThickness()
416
+ >>> corticalthickness.inputs.dimension = 3
417
+ >>> corticalthickness.inputs.anatomical_image ='T1.nii.gz'
418
+ >>> corticalthickness.inputs.brain_template = 'study_template.nii.gz'
419
+ >>> corticalthickness.inputs.brain_probability_mask ='ProbabilityMaskOfStudyTemplate.nii.gz'
420
+ >>> corticalthickness.inputs.segmentation_priors =['CSF.nii.gz','WM.nii.gz','GM.nii.gz','DEEP_GM.nii.gz']
421
+ >>> corticalthickness.inputs.t1_registration_template = 'brain_study_template.nii.gz'
422
+ >>> corticalthickness.cmdline
423
+ 'antsCorticalThickness.sh -d 3 -a T1.nii.gz -m ProbabilityMaskOfStudyTemplate.nii.gz -e study_template.nii.gz -o antsCT_ -p BrainSegmentationPrior%0d.nii.gz -t brain_study_template.nii.gz'
424
+ """
425
+
426
+ input_spec = antsCorticalThicknessInputSpec
427
+ output_spec = antsCorticalThicknessoutputSpec
428
+ _cmd = 'antsCorticalThickness.sh'
429
+ def _format_arg (self , opt , spec , val ):
430
+ if opt == 'anatomical_image' :
431
+ retval = '-a %s' % (val )
432
+ return retval
433
+ if opt == 'brain_template' :
434
+ retval = '-e %s' % (val )
435
+ return retval
436
+ if opt == 'brain_probability_mask' :
437
+ retval = '-m %s' % (val )
438
+ return retval
439
+ if opt == 'out_prefix' :
440
+ retval = '-o %s' % (val )
441
+ return retval
442
+ if opt == 't1_registration_template' :
443
+ retval = '-t %s' % (val )
444
+ return retval
445
+ if opt == 'segmentation_priors' :
446
+ _ , _ , ext = split_filename (self .inputs .segmentation_priors [0 ])
447
+ retval = "-p priors/BrainSegmentationPrior%02d"
448
+ retval += ext
449
+ return retval
450
+ return super (ANTSCommand , self )._format_arg (opt , spec , val )
451
+ def _run_interface (self , runtime ):
452
+ priors_directory = os .path .join (os .getcwd (), "priors" )
453
+ if not os .path .exists (priors_directory ):
454
+ os .makedirs (priors_directory )
455
+ _ , _ , ext = split_filename (self .inputs .segmentation_priors [0 ])
456
+ for i , f in enumerate (self .inputs .segmentation_priors ):
457
+ target = os .path .join (priors_directory ,
458
+ 'BrainSegmentationPrior%02d' % (i + 1 ) + ext )
459
+ if not (os .path .exists (target ) and os .path .realpath (target ) == os .path .abspath (f )):
460
+ copyfile (os .path .abspath (f ), os .path .join (priors_directory ,
461
+ 'BrainSegmentationPrior%02d' % (i + 1 ) + ext ))
462
+ runtime = super (antsCorticalThickness , self )._run_interface (runtime )
463
+ return runtime
464
+
465
+ def _list_outputs (self ):
466
+ outputs = self ._outputs ().get ()
467
+ outputs ['BrainExtractionMask' ] = os .path .join (os .getcwd (),
468
+ self .inputs .out_prefix +
469
+ 'BrainExtractionMask.' +
470
+ self .inputs .image_suffix )
471
+ outputs ['BrainSegmentation' ] = os .path .join (os .getcwd (),
472
+ self .inputs .out_prefix +
473
+ 'BrainSegmentation.' +
474
+ self .inputs .image_suffix )
475
+ outputs ['BrainSegmentationN4' ] = os .path .join (os .getcwd (),
476
+ self .inputs .out_prefix +
477
+ 'BrainSegmentation0N4.' +
478
+ self .inputs .image_suffix )
479
+ outputs ['BrainSegmentationPosteriorsCSF' ] = os .path .join (os .getcwd (),
480
+ self .inputs .out_prefix +
481
+ 'BrainSegmentationPosteriors01.' +
482
+ self .inputs .image_suffix )
483
+ outputs ['BrainSegmentationPosteriorsGM' ] = os .path .join (os .getcwd (),
484
+ 'BrainSegmentationPosteriors02.' +
485
+ self .inputs .image_suffix )
486
+ outputs ['BrainSegmentationPosteriorsWM' ] = os .path .join (os .getcwd (),
487
+ 'BrainSegmentationPosteriors03.' +
488
+ self .inputs .image_suffix )
489
+ outputs ['BrainSegmentationPosteriorsDGM' ] = os .path .join (os .getcwd (),
490
+ 'BrainSegmentationPosteriors04.' +
491
+ self .inputs .image_suffix )
492
+ outputs ['CorticalThickness' ] = os .path .join (os .getcwd (),
493
+ self .inputs .out_prefix + 'CorticalThickness.' +
494
+ self .inputs .image_suffix )
495
+ outputs ['TemplateToSubject1GenericAffine' ] = os .path .join (
496
+ os .getcwd (),
497
+ 'TemplateToSubject1GenericAffine.mat' )
498
+ outputs ['TemplateToSubject0Warp' ] = os .path .join (os .getcwd (),
499
+ self .inputs .out_prefix + 'TemplateToSubject0Warp.' +
500
+ self .inputs .image_suffix )
501
+ outputs ['SubjectToTemplate1Warp' ] = os .path .join (os .getcwd (),
502
+ self .inputs .out_prefix + 'SubjectToTemplate1Warp' +
503
+ self .inputs .image_suffix )
504
+ outputs ['SubjectToTemplate0GenericAffine' ] = os .path .join (os .getcwd (),
505
+ self .inputs .out_prefix + 'SubjectToTemplate0GenericAffine.mat' )
506
+ outputs ['TemplateToSubjectLogJacobian' ] = os .path .join (os .getcwd (),
507
+ self .inputs .out_prefix + 'subjectToTemplateLogJacobian.' +
508
+ self .inputs .image_suffix )
509
+ return outputs
0 commit comments