Commit 5bba74303d5585b93b167010b5c83269d1cafa2c

Authored by Santiago Castro
1 parent 829e75d1
Exists in command-line

Add option to import every group of DICOM images

Showing 2 changed files with 57 additions and 12 deletions   Show diff stats
@@ -26,6 +26,8 @@ import sys @@ -26,6 +26,8 @@ import sys
26 import shutil 26 import shutil
27 import traceback 27 import traceback
28 28
  29 +import re
  30 +
29 if sys.platform == 'win32': 31 if sys.platform == 'win32':
30 import _winreg 32 import _winreg
31 else: 33 else:
@@ -270,6 +272,9 @@ def parse_comand_line(): @@ -270,6 +272,9 @@ def parse_comand_line():
270 action="store", 272 action="store",
271 dest="dicom_dir") 273 dest="dicom_dir")
272 274
  275 + parser.add_option("--import-all",
  276 + action="store")
  277 +
273 parser.add_option("-s", "--save", 278 parser.add_option("-s", "--save",
274 help="Save the project after an import.") 279 help="Save the project after an import.")
275 280
@@ -296,7 +301,7 @@ def use_cmd_optargs(options, args): @@ -296,7 +301,7 @@ def use_cmd_optargs(options, args):
296 # If import DICOM argument... 301 # If import DICOM argument...
297 if options.dicom_dir: 302 if options.dicom_dir:
298 import_dir = options.dicom_dir 303 import_dir = options.dicom_dir
299 - Publisher.sendMessage('Import directory', import_dir) 304 + Publisher.sendMessage('Import directory', {'directory': import_dir, 'gui': not options.no_gui})
300 305
301 if options.save: 306 if options.save:
302 Publisher.sendMessage('Save project', os.path.abspath(options.save)) 307 Publisher.sendMessage('Save project', os.path.abspath(options.save))
@@ -305,6 +310,14 @@ def use_cmd_optargs(options, args): @@ -305,6 +310,14 @@ def use_cmd_optargs(options, args):
305 check_for_export(options) 310 check_for_export(options)
306 311
307 return True 312 return True
  313 + elif options.import_all:
  314 + import invesalius.reader.dicom_reader as dcm
  315 + for patient in dcm.GetDicomGroups(options.import_all):
  316 + for group in patient.GetGroups():
  317 + Publisher.sendMessage('Import group', {'group': group, 'gui': not options.no_gui})
  318 + check_for_export(options, suffix=group.title, remove_surfaces=False)
  319 + Publisher.sendMessage('Remove masks', [0])
  320 + return True
308 321
309 # Check if there is a file path somewhere in what the user wrote 322 # Check if there is a file path somewhere in what the user wrote
310 # In case there is, try opening as it was a inv3 323 # In case there is, try opening as it was a inv3
@@ -320,13 +333,29 @@ def use_cmd_optargs(options, args): @@ -320,13 +333,29 @@ def use_cmd_optargs(options, args):
320 return False 333 return False
321 334
322 335
323 -def check_for_export(options): 336 +def sanitize(text):
  337 + text = str(text).strip().replace(' ', '_')
  338 + return re.sub(r'(?u)[^-\w.]', '', text)
  339 +
  340 +
  341 +def check_for_export(options, suffix='', remove_surfaces=False):
  342 + suffix = sanitize(suffix)
  343 +
324 if options.export: 344 if options.export:
325 if not options.threshold: 345 if not options.threshold:
326 print("Need option --threshold when using --export.") 346 print("Need option --threshold when using --export.")
327 exit(1) 347 exit(1)
328 - threshold_range = tuple([int(n) for n in options.threshold.split('-')])  
329 - export(options.export, threshold_range) 348 + threshold_range = tuple([int(n) for n in options.threshold.split(',')])
  349 +
  350 + if suffix:
  351 + if options.export.endswith('.stl'):
  352 + path_ = '{}-{}.stl'.format(options.export[:-4], suffix)
  353 + else:
  354 + path_ = '{}-{}.stl'.format(options.export, suffix)
  355 + else:
  356 + path_ = options.export
  357 +
  358 + export(path_, threshold_range, remove_surface=remove_surfaces)
330 elif options.export_to_all: 359 elif options.export_to_all:
331 # noinspection PyBroadException 360 # noinspection PyBroadException
332 try: 361 try:
@@ -334,15 +363,15 @@ def check_for_export(options): @@ -334,15 +363,15 @@ def check_for_export(options):
334 363
335 for threshold_name, threshold_range in Project().presets.thresh_ct.iteritems(): 364 for threshold_name, threshold_range in Project().presets.thresh_ct.iteritems():
336 if isinstance(threshold_range[0], int): 365 if isinstance(threshold_range[0], int):
337 - path_ = u'{}-{}.stl'.format(options.export_to_all, threshold_name)  
338 - export(path_, threshold_range) 366 + path_ = u'{}-{}-{}.stl'.format(options.export_to_all, suffix, threshold_name)
  367 + export(path_, threshold_range, remove_surface=True)
339 except: 368 except:
340 traceback.print_exc() 369 traceback.print_exc()
341 finally: 370 finally:
342 exit(0) 371 exit(0)
343 372
344 373
345 -def export(path_, threshold_range): 374 +def export(path_, threshold_range, remove_surface=False):
346 import invesalius.constants as const 375 import invesalius.constants as const
347 376
348 Publisher.sendMessage('Set threshold values', threshold_range) 377 Publisher.sendMessage('Set threshold values', threshold_range)
@@ -362,6 +391,8 @@ def export(path_, threshold_range): @@ -362,6 +391,8 @@ def export(path_, threshold_range):
362 } 391 }
363 Publisher.sendMessage('Create surface from index', surface_options) 392 Publisher.sendMessage('Create surface from index', surface_options)
364 Publisher.sendMessage('Export surface to file', (path_, const.FILETYPE_STL)) 393 Publisher.sendMessage('Export surface to file', (path_, const.FILETYPE_STL))
  394 + if remove_surface:
  395 + Publisher.sendMessage('Remove surfaces', [0])
365 396
366 397
367 def print_events(data): 398 def print_events(data):
invesalius/control.py
@@ -61,6 +61,7 @@ class Controller(): @@ -61,6 +61,7 @@ class Controller():
61 61
62 def __bind_events(self): 62 def __bind_events(self):
63 Publisher.subscribe(self.OnImportMedicalImages, 'Import directory') 63 Publisher.subscribe(self.OnImportMedicalImages, 'Import directory')
  64 + Publisher.subscribe(self.OnImportGroup, 'Import group')
64 Publisher.subscribe(self.OnShowDialogImportDirectory, 65 Publisher.subscribe(self.OnShowDialogImportDirectory,
65 'Show import directory dialog') 66 'Show import directory dialog')
66 Publisher.subscribe(self.OnShowDialogImportOtherFiles, 67 Publisher.subscribe(self.OnShowDialogImportOtherFiles,
@@ -440,10 +441,11 @@ class Controller(): @@ -440,10 +441,11 @@ class Controller():
440 #----------- to import by command line --------------------------------------------------- 441 #----------- to import by command line ---------------------------------------------------
441 442
442 def OnImportMedicalImages(self, pubsub_evt): 443 def OnImportMedicalImages(self, pubsub_evt):
443 - directory = pubsub_evt.data  
444 - self.ImportMedicalImages(directory) 444 + directory = pubsub_evt.data['directory']
  445 + gui = pubsub_evt.data['gui']
  446 + self.ImportMedicalImages(directory, gui)
445 447
446 - def ImportMedicalImages(self, directory): 448 + def ImportMedicalImages(self, directory, gui=True):
447 patients_groups = dcm.GetDicomGroups(directory) 449 patients_groups = dcm.GetDicomGroups(directory)
448 name = directory.rpartition('\\')[-1].split('.') 450 name = directory.rpartition('\\')[-1].split('.')
449 print "patients: ", patients_groups 451 print "patients: ", patients_groups
@@ -451,7 +453,7 @@ class Controller(): @@ -451,7 +453,7 @@ class Controller():
451 if len(patients_groups): 453 if len(patients_groups):
452 # OPTION 1: DICOM 454 # OPTION 1: DICOM
453 group = dcm.SelectLargerDicomGroup(patients_groups) 455 group = dcm.SelectLargerDicomGroup(patients_groups)
454 - matrix, matrix_filename, dicom = self.OpenDicomGroup(group, 0, [0, 0], gui=True) 456 + matrix, matrix_filename, dicom = self.OpenDicomGroup(group, 0, [0, 0], gui=gui)
455 self.CreateDicomProject(dicom, matrix, matrix_filename) 457 self.CreateDicomProject(dicom, matrix, matrix_filename)
456 else: 458 else:
457 # OPTION 2: NIfTI, Analyze or PAR/REC 459 # OPTION 2: NIfTI, Analyze or PAR/REC
@@ -474,6 +476,18 @@ class Controller(): @@ -474,6 +476,18 @@ class Controller():
474 self.LoadProject() 476 self.LoadProject()
475 Publisher.sendMessage("Enable state project", True) 477 Publisher.sendMessage("Enable state project", True)
476 478
  479 + def OnImportGroup(self, pubsub_evt):
  480 + group = pubsub_evt.data['group']
  481 + gui = pubsub_evt.data['gui']
  482 + self.ImportGroup(group, gui)
  483 +
  484 + def ImportGroup(self, group, gui=True):
  485 + matrix, matrix_filename, dicom = self.OpenDicomGroup(group, 0, [0, 0], gui=gui)
  486 + self.CreateDicomProject(dicom, matrix, matrix_filename)
  487 +
  488 + self.LoadProject()
  489 + Publisher.sendMessage("Enable state project", True)
  490 +
477 #------------------------------------------------------------------------------------- 491 #-------------------------------------------------------------------------------------
478 492
479 def LoadProject(self): 493 def LoadProject(self):
@@ -788,7 +802,7 @@ class Controller(): @@ -788,7 +802,7 @@ class Controller():
788 n_slices = len(filelist) 802 n_slices = len(filelist)
789 resolution_percentage = utils.calculate_resizing_tofitmemory(int(sx), int(sy), n_slices, bits/8) 803 resolution_percentage = utils.calculate_resizing_tofitmemory(int(sx), int(sy), n_slices, bits/8)
790 804
791 - if resolution_percentage < 1.0: 805 + if resolution_percentage < 1.0 and gui:
792 re_dialog = dialog.ResizeImageDialog() 806 re_dialog = dialog.ResizeImageDialog()
793 re_dialog.SetValue(int(resolution_percentage*100)) 807 re_dialog.SetValue(int(resolution_percentage*100))
794 re_dialog_value = re_dialog.ShowModal() 808 re_dialog_value = re_dialog.ShowModal()