Assign a specific volume into slice

Hi, I have a short question.

I am browsing multiple MR images at the same time.
After loading multiple images (usually done by drag and drop), I want to assign a specific volume using its IDs (such as ‘vtkMRMLScalarVolumeNode11’) into a particular slice( such as ‘slicer5’ or ‘Red’).

I googled it here and there, but I could not find a good answer, so I am posting it here.

Thank you for your time!

These instructions should help:

https://slicer.readthedocs.io/en/latest/developer_guide/script_repository.html#iterate-over-current-visible-slice-views-and-set-foreground-and-background-images

If you need something finer grained, see the implementation of setSliceViewerLayers here:

1 Like

Thanks, Steve.
I read the instructions and tried it.
But it is about overlaying images, not assigning a specific image node into a specific location of slices, such as a Red or Green panel.
Maybe the setSliceViewerLayers function could do the job that I want to do, and I am trying to read the suggested github page.

Thank you again!

I’m not sure, but it sounds like you want this:

n =  slicer.util.getNode("YourVolumeNode")
for color in ["Red", "Yellow", "Green"]:
  slicer.app.layoutManager().sliceWidget(color).sliceLogic().GetSliceCompositeNode().SetForegroundVolumeID(n.GetID())

From here.

1 Like

Yes, it works!
Thank you @pieper

Here is what I used.

ID = "vtkMRMLScalarVolumeNode1" # node ID for image volume
Panel = "Red" # node name for panel view (slice)
slicer.app.layoutManager().sliceWidget(Panel).sliceLogic().GetSliceCompositeNode().SetBackgroundVolumeID(ID)

Thank you again!

Hi @pieper

I have the following code and I want to show an MRI and US images side by side with their corresponding labels. The code does partially the job but still these two parts are not working:

  • The Yellow panel does not show the axial plane, even though I set it in the custom layout.
  • I want each panel show the segmentation of that image only, not overlapping between the panel.

Thank you for the help.

P.S. You may ask why not manually doing this, well we have around 2000 pairs of US and MRI images, and we need to do this somehow automated using python for a multi-reader study.

      customLayout = """
      <layout type="horizontal" split="true">
        <item>
        <view class="vtkMRMLSliceNode" singletontag="Red">
          <property name="orientation" action="default">Axial</property>
          <property name="viewlabel" action="default">R</property>
          <property name="viewcolor" action="default">#F34A33</property>
        </view>
        </item>
        <item>
        <view class="vtkMRMLSliceNode" singletontag="Yellow">
          <property name="orientation" action="default">Axial</property>
          <property name="viewlabel" action="default">Y</property>
          <property name="viewcolor" action="default">#F34A33</property>
        </view>
        </item>
      </layout>
      """
      # Built-in layout IDs are all below 100, so you can choose any large random number
      # for your custom layout ID.
      customLayoutId=501

      layoutManager = slicer.app.layoutManager()
      layoutManager.layoutLogic().GetLayoutNode().AddLayoutDescription(customLayoutId, customLayout)

      # Switch to the new custom layout
      layoutManager.setLayout(customLayoutId)
      slicer.mrmlScene.Clear(0)
      
      # Input nodes
      # layoutManager.sliceWidget('Red').sliceLogic().GetSliceCompositeNode().SetForegroundVolumeID(volumeNode.GetID())
      # Setvolume node as the foreground volume of the Red slice widget.
      # layoutManager.sliceWidget('Yellow').sliceLogic().GetSliceCompositeNode().SetForegroundVolumeID(trusvloumeNode.GetID()) 
      mriVolumeNode = slicer.util.loadVolume(mri_path)
      trusVolumeNode = slicer.util.loadVolume(trus_path)
      
      mriSegmentationNode = slicer.util.loadSegmentation(mri_seg_path)           
      trusSegmentationNode = slicer.util.loadSegmentation(trus_seg_path)
      
      layoutManager.sliceWidget('Red').sliceLogic().GetSliceCompositeNode().SetBackgroundVolumeID(mriVolumeNode.GetID())
      layoutManager.sliceWidget('Yellow').sliceLogic().GetSliceCompositeNode().SetBackgroundVolumeID(trusVolumeNode.GetID())
      
      layoutManager.sliceWidget('Red')
      displayNode = mriSegmentationNode.GetDisplayNode()
      displayNode.SetOpacity3D(0.4)  # Set overall opacity of the segmentation
      displayNode.SetSegmentOpacity3D('Segment_1', 0.2)  # Set opacity of a single segment
      segment_prostate = mriSegmentationNode.GetSegmentation().GetSegment('Segment_1')
      # Segment color is not just a display property, but it is stored in the segment itself (and stored in the segmentation file)
      displayNode.SetSegmentOverrideColor('Segment_1', 1, 0, 0)  # blue
      displayNode.SetSegmentVisibility2DFill('Segment_1', 0)  # blue

      layoutManager.sliceWidget('Yellow')
      displayNode = trusSegmentationNode.GetDisplayNode()
      displayNode.SetOpacity3D(0.4)  # Set overall opacity of the segmentation
      displayNode.SetSegmentOpacity3D('Segment_1', 0.2)  # Set opacity of a single segment
      segment_prostate = trusSegmentationNode.GetSegmentation().GetSegment('Segment_1')
      # Segment color is not just a display property, but it is stored in the segment itself (and stored in the segmentation file)
      displayNode.SetSegmentOverrideColor('Segment_1', 1, 0, 0)  # blue
      displayNode.SetSegmentVisibility2DFill('Segment_1', 0)  # blue

For Axial display you can do

sliceNode = layoutManager.sliceWidget(“Yellow”).mrmlSliceNode()
sliceNode.SetOrientation(“Axial”)

1 Like