Merge colored images and show them as 1 volume

Hello everyone,
is there a way to merge multiple colored png images into one volume and visualize this than in the 3D space?

I really need this feature since in these images, the colors are really important and I can´t segment pixel by pixel…

I would be very pleased if somebody could give me some advice to this topic!

Thank you for your understandings!

Greetings,
Anna

This should help: https://www.slicer.org/wiki/Documentation/Nightly/FAQ#How_to_load_data_from_a_sequence_of_jpg.2C_tif.2C_or_png_files.3F

Thank you Sir for the fast reply!

Is there a way to retain the colors of the images? When I create a scalar volume it automatically creates a grey 3D volume. I really need the colored volume out of theses images like there are in there

… Is there a solution for my problem?

Thanks in advance!

If you just want to visualize them with their original color, apply spatial transforms, etc. then you don’t need to convert to scalar volume. What would you like to do with the image?

I just showed the view of one image. I would like to visualize the colored image stack in their original color in the 3D space (View 1). Since the pixels of the image stack are colored differently, I can´t segment pixel by pixel. It is also not possible to use the vector to scalar volume, since it is creating a Grey-colored 3D volume, where the original color is lost.

I hope that the issue is now understandable.
Is there a way to solve this?

Thank you very much for all help!

If you have a full-color image then you can show a direct volume rendering of it by turning off “independent component” option in the volume renderer (it makes image components interpreted as RGBA). Type this in the Python console after enabling volume rendering:

getNode('VolumeProperty').GetVolumeProperty().SetIndependentComponents(0)

Note that you need an RGBA image (not just RGB). The fourth (alpha) component controls opacity. If you only have an RGB image then you can create the “alpha” volume using “Vector to scalar volume” module, then append this alpha volume to the original RGB volume by copy-pasting this to the Python console:

colorVolume = getNode('MyColorVolume') # RGB vector volume
alphaVolume = getNode('MyAlphaVolume') # scalar volume created from RGB volume using Vector to scalar volume module

append=vtk.vtkImageAppendComponents()
append.AddInputConnection(colorVolume.GetImageDataConnection())
append.AddInputConnection(alphaVolume.GetImageDataConnection())
append.Update()
colorVolume.SetAndObserveImageData(append.GetOutput())

For segmentation (if you want to create a surface mesh, 3D-printable model, etc), use the scalar volume created by “Vector to scalar volume” module.

@lassoan This has been very useful for me to get a very old segmentation from VG Studio Max into Slicer. At the time, I only exported the colored slices (as oppose to exporting them to labelmaps) and I don’t think I have the original data anymore. Two questions:

  1. Is there a different way to manipulate transfer functions for RGBA images (so that I can have better control).
  2. Is there a way for me to import this color stack as a segmentation?

If you convert RGBA images to scalars then it answers both questions. You can convert each color to an index like this:

rgbVolumeNode = ... # input RGB volume

# Create a labelmap volume for the output
labelVolumeNode = slicer.mrmlScene.AddNewNodeByClass('vtkMRMLLabelMapVolumeNode')
imageData = vtk.vtkImageData()
imageData.SetDimensions(rgbVolumeNode.GetImageData().GetDimensions())
imageData.AllocateScalars(vtk.VTK_UNSIGNED_CHAR, 1)
labelVolumeNode.SetAndObserveImageData(imageData)
ijkToRas = vtk.vtkMatrix4x4()
rgbVolumeNode.GetIJKToRASMatrix(ijkToRas)
labelVolumeNode.SetIJKToRASMatrix(ijkToRas)
labelVolumeNode.CreateDefaultDisplayNodes()

rgb = slicer.util.arrayFromVolume(rgbVolumeNode)
label = slicer.util.arrayFromVolume(labelVolumeNode)
# Set label value (1, 2, ...) for each RGB combination
label[:] = 0
label[(rgb[:,:,:,0]==153) & (rgb[:,:,:,1]==117) & (rgb[:,:,:,2]==67)] = 1
label[(rgb[:,:,:,0]==122) & (rgb[:,:,:,1]==108) & (rgb[:,:,:,2]==11)] = 2
...
slicer.util.arrayFromVolumeModified(labelVolumeNode)
1 Like