Hi all,
I am a 3D Slicer beginner, so please bear with me…
I have a CT image (in DICOM series format) used for radiation treatment planning. I wish to
read it, apply to it an arbitrary 3D rotation around the isocenter, then resave it as a DICOM series (to read it back into the TPS).
I wish to do it by python scripting (because I’ll have many different rotations to explore, so I want to automate the procedure).
I am learning by doing, because at present I don’t have much time to fully understand the software before starting coding.
By reading what I coud find in the Forum and in the documentation, I understood how to:
-
prepare things:
import argparse, sys, shutil, os, logging
import vtk, qt, ctk, slicer
import DICOMLib
from DICOMLib import DICOMUtils -
parse the command line:
def main(argv):
print(‘STARTING!’)
try:
parser = argparse.ArgumentParser(description=“to be done”)
parser.add_argument("-i", “–input-folder”, dest=“input_folder”, metavar=“PATH”,
default="-", required=True, help=“Folder of input DICOM files (can contain sub-folders)”)
parser.add_argument("-o", “–output-folder”, dest=“output_folder”, metavar=“PATH”,
default=".", help=“Folder to save converted datasets”)
args = parser.parse_args(argv)
if args.input_folder == “-”:
print(‘Please specify input DICOM study folder!’)
if args.output_folder == “.”:
print(‘Current directory is selected as output folder (default). To change it, please specify --output-folder’) -
read the dicom series:
logging.info("Import DICOM data from " + args.input_folder)
DICOMUtils.openTemporaryDatabase()
DICOMUtils.importDicom(args.input_folder)
logging.info(“Load first patient into Slicer”)
patient = slicer.dicomDatabase.patients()[0]
DICOMUtils.loadPatientByUID(patient) -
Save as nnrd, which is not what I need, but it was at least a test that I was correctly reading the image and filling the right Slicer structures…
node_key = ‘vtkMRMLScalarVolumeNode*’
sv_nodes = slicer.util.getNodes(node_key)
logging.info(“Save image volumes nodes to directory %s: %s” % (args.output_folder, ‘,’.join(sv_nodes.keys())))
for imageNode in sv_nodes.values():
# Clean up file name and set path
fileName = imageNode.GetName() + ‘.nrrd’
charsRoRemove = [’!’, ‘?’, ‘:’, ‘;’]
fileName = fileName.translate(None, ‘’.join(charsRoRemove))
fileName = fileName.replace(’ ‘, ‘_’)
filePath = args.output_folder + ‘/’ + fileName
logging.info(’ Saving image ’ + imageNode.GetName() + ‘\n to file <’ + filePath + ‘>’)
# Save to file
success = slicer.util.saveNode(imageNode, filePath)
if not success:
logging.error('Failed to save image volume: ’ + filePath) -
Get out:
except Exception, e:
print e
sys.exit()
return
-
Prepare “main” execution:
if name == “main”:
main(sys.argv[1:])
My questions are:
-
How do I apply the rotation transform?
-
I imagine I can apply a chain of transforms, so I can translate the image so that the isocenter is in the axis origin, then rotate, than translate back: how to do it?
-
How do I save the result as a DICOM series, by using the input DICOM series as a model (as to voxel/slice dimensions, and all the other relevant DICOM fields)?
Any hint, code snippets, link to relevant material, is really welcome.
Thank you very much.
Giorgio
PS sorry, after many tries, I am not succeeding in correctly formatting the code snippets… preformatted text does not give the desired result… indentation has totally gone…