View Issue Details

IDProjectCategoryView StatusLast Update
0004513Slicer4Core: Renderingpublic2018-10-16 22:57
Reporterjcfr Assigned Tosankhesh  
PrioritynormalSeverityminorReproducibilityhave not tried
Status resolvedResolutionfixed 
Product Version 
Target VersionSlicer 4.9.0Fixed in VersionSlicer 4.9.0 
Summary0004513: VTK OpenGL2 Backend: Problem with volume rendering surface gradient computation
Description

From Andras:

See full report (with attached sample renderings and volume data set):
http://vtk.1045678.n5.nabble.com/Volume-rendering-produces-rough-surface-at-clipping-plane-td5745442.html

From Sankhesh:

The main problem is that the volume mapper computes gradients inclusive of voxels in the clipped space.
I was able to override the behavior in custom shader code. Please see the example here: https://github.com/sankhesh/TestVolumeClip

Moving forward, I’d like to integrate this into stock VTK and investigate a better value for the gradient:

Either add API for the user to set the voxel values in clipped space.
Interpolate linearly between the sample point and the clipping plane and use that value as the clipped space value.
Derive the gradient from the clipping plane normal

This would involve some trial and error to figure out the best path forward

Tagsvtk-opengl2

Activities

sankhesh

sankhesh

2018-08-20 23:03

developer   ~0015973

VTK merge request: https://gitlab.kitware.com/vtk/vtk/merge_requests/4601

sankhesh

sankhesh

2018-09-10 07:18

developer   ~0015988

The vtk change has been merged in to vtk master.

sankhesh

sankhesh

2018-09-10 07:20

developer   ~0015989

@lassoan, could you please try vtk master to see if this works for you?

lassoan

lassoan

2018-09-10 07:35

developer   ~0015990

Thank you, I'll test this today.

lassoan

lassoan

2018-09-11 23:45

developer   ~0015992

Last edited: 2018-09-11 23:54

View 2 revisions

Sorry for the delay, I had some problems rebuilding Slicer with latest VTK master, but it works now.

I've tested the volume renderer but unfortunately as soon as I switch to Volume renderer module, all VTK render windows turn to solid gray and stay like that. I could not even test any volume rendering feature. I haven't changed anything else anywhere, just upgraded VTK.

The problem is exactly as described in this bug report: https://issues.slicer.org/view.php?id=4598. It is not clear if there is a solution or workaround that I could apply.

jcfr

jcfr

2018-09-12 01:01

administrator   ~0015993

Last edited: 2018-09-12 01:04

View 2 revisions

It is not clear if there is a solution or workaround that I could apply

A solution has been identified, I am working on updating CTK to address this.

The easiest is to use QVTKOpenGLNativeWidget every where the QVTKOpenGLWidget is used.

If you do this replacement it should now work.

lassoan

lassoan

2018-09-13 10:57

developer   ~0016002

Last edited: 2018-10-14 01:39

View 2 revisions

I've tested this on the latest nightly release. Unfortunately, setting clipping intensity has no effect.

How to test:

  • Load CTChest sample data
  • In Volume Rendering module, enable GPU volume rendering, clip into the volume
  • Run the following commands in the Python console:

<pre>
vpn=slicer.mrmlScene.GetFirstNodeByClass('vtkMRMLVolumePropertyNode')
vp=vpn.GetVolumeProperty()

Set clipping intensity

vp.SetUseClippedVoxelIntensity(1)
vp.SetClippedVoxelIntensity(-5000)

Test that clipping intensity is properly set

print vp.GetUseClippedVoxelIntensity()
print vp.GetClippedVoxelIntensity()

Test that changing volume property has an effect

vp.SetInterpolationTypeToNearest()

Restore original interpolation type

vp.SetInterpolationTypeToLinear()
</pre>

jcfr

jcfr

2018-09-13 11:10

administrator   ~0016004

Last edited: 2018-09-13 12:18

View 4 revisions

Looking at the implementation, it seems you need to set the SetShade(1) and also call SetClipSurfaceShade(1)
See https://gitlab.kitware.com/vtk/vtk/merge_requests/4601/diffs

May be you could try:

vpn=slicer.mrmlScene.GetFirstNodeByName('VolumeProperty')
vp=vpn.GetVolumeProperty()

vp.ShadeOn();
vp.ClipSurfaceShadeOn();

# Set clipping intensity
vp.SetUseClippedVoxelIntensity(1)
vp.SetClippedVoxelIntensity(-5000)

# Test that clipping intensity is properly set
print vp.GetUseClippedVoxelIntensity()
print vp.GetClippedVoxelIntensity()

# Test that changing volume property has an effect
vp.SetInterpolationTypeToNearest()
# Restore original interpolation type
vp.SetInterpolationTypeToLinear()
lassoan

lassoan

2018-09-13 12:03

developer   ~0016012

I don't see ClipSurfaceShade property anywhere in VTK master. The merge request that you've referred to superseded by https://gitlab.kitware.com/vtk/vtk/merge_requests/4627.

jcfr

jcfr

2018-09-13 12:19

administrator   ~0016014

you've referred to superseded by https://gitlab.kitware.com/vtk/vtk/merge_requests/4627.

Good point. This is definitively an issue then.

Are you able to run the associated VTK test on your workstation then ?

lassoan

lassoan

2018-09-13 22:58

developer   ~0016016

Last edited: 2018-09-13 23:17

View 2 revisions

I've figured out why it does not work in Slicer:

  1. Clipped voxel intensity is ignored if gradient opacity function is set. Slicer always sets gradient opacity function, but usually all of its values are 1.0, so it has no effect.

Potential solution: If gradient opacity only contains 1.0 values (so it is fully opaque), or disabled (using vp.SetDisableGradientOpacity(1)) then clipped voxel intensity should be used. This could be implemented in UseClippedVoxelIntensity(…) function in vtkVolumeShaderComposer.h.

  1. If depth peeling is enabled and the renderer contains a VTK box widget then there are random striping artifacts (regions alternating between smooth and non-smooth surface) on the rendered volume surface.

In Slicer, cropping region is usually visualized using VTK box widget, so most would run into this issue when clipping a volume.

Box widget has serious rendering issues. This problem might be related to incorrect rendering box widget when depth peeling is enabled (see 0004609).

lassoan

lassoan

2018-09-13 22:59

developer   ~0016017

If gradient opacity is enabled then the feature does not work at all:



lassoan

lassoan

2018-09-13 23:03

developer   ~0016018

Clipping surface is correct if vtkVolumeShaderComposer.h is changed to take into account GetDisableGradientOpacity() and vp.SetDisableGradientOpacity(1) is called (and depth peeling is disabled).

Modified HasGradientOpacity function:

<pre>
bool HasGradientOpacity(vtkOpenGLGPUVolumeRayCastMapper::VolumeInputMap& inputs)
{
for (auto& item : inputs)
{
vtkVolumeProperty* volProp = item.second.Volume->GetProperty();
const bool gradOp = volProp->HasGradientOpacity() && !volProp->GetDisableGradientOpacity();
if (gradOp)
return true;
}
return false;
}
</pre>



lassoan

lassoan

2018-09-13 23:04

developer   ~0016019

If we enable depth peeling then striping artifacts appear:



lassoan

lassoan

2018-09-13 23:19

developer   ~0016020

Box widget can be anywhere in the render view, it causes artifacts appear on the volume surface:



lassoan

lassoan

2018-09-14 10:23

developer   ~0016021

Other software will run into the same issue, so at least the limitation should be clearly documented (https://www.vtk.org/doc/nightly/html/classvtkVolumeProperty.html#a614b3114b709495810c438078fe9c4a6). Maybe even logging a warning would be appropriate when clipped voxel intensity is not used despite UseClippedVoxelIntensity is enabled.

sankhesh

sankhesh

2018-09-17 09:40

developer   ~0016022

@lassoan,

Sorry for the delay in responding - I was out last week.

When implementing the clipped voxel intensity mode, I chose to leave gradient magnitude calculations as is considering that the magnitude should be "true" magnitude. In hindsight, it seems it would be better to use the clipped voxel intensity for gradient opacity magnitude calculations as well. I'll make the change.

As for depth peeling, I think it is a separate issue. But I'll take a look at it as well.

lassoan

lassoan

2018-09-17 14:24

developer   ~0016023

Great, thank you!

sankhesh

sankhesh

2018-09-26 17:24

developer   ~0016041

@lassoan, Mind trying out this change:

https://gitlab.kitware.com/sankhesh/vtk/commits/gradient_magnitude_clip

It ensures that the clipped voxel intensity is used for gradient magnitude computations as well.

lassoan

lassoan

2018-10-03 17:25

developer   ~0016066

I tested this and commented at the pull request. It works great except when depth peeling is enabled and there are semi-transparent actors in the scene (anywhere, does not have to be inside or near the volume) - in that case artifacts appear at the clipped surface.

jcfr

jcfr

2018-10-16 06:09

administrator   ~0016143

Here is the following up MR from @allison.vacanti
https://gitlab.kitware.com/vtk/vtk/merge_requests/4780

jcfr

jcfr

2018-10-16 06:10

administrator   ~0016144

Last edited: 2018-10-16 06:10

View 2 revisions

From @lassoan (copied from the MR referenced below): I've spent a few hours testing this and although there were still rendering settings that produced unexpected artifacts (when sampling distances are larger, when cut surface is semi-transparent, or when there are abrupt changes in transfer functions), with some experimentation most of the time I could achieve nice smooth cut surface. I think this is good to go! Thank you very much Allison.

jcfr

jcfr

2018-10-16 22:57

administrator   ~0016161

Fixed in r27498
See http://viewvc.slicer.org/viewvc.cgi/Slicer4?view=revision&amp;revision=27498

Issue History

Date Modified Username Field Change
2018-02-27 16:36 jcfr New Issue
2018-02-27 16:36 jcfr Status new => assigned
2018-02-27 16:36 jcfr Assigned To => sankhesh
2018-03-02 16:05 jcfr Tag Attached: vtk-opengl2
2018-03-03 00:56 jcfr Summary OpenGL2: Problem with volume rendering surface gradient computation => VTK OpenGL2 Backend: Problem with volume rendering surface gradient computation
2018-08-06 09:28 jcfr Category Core: Base Code => Core: Rendering
2018-08-20 23:03 sankhesh Note Added: 0015973
2018-09-10 07:18 sankhesh Note Added: 0015988
2018-09-10 07:20 sankhesh Note Added: 0015989
2018-09-10 07:35 lassoan Note Added: 0015990
2018-09-11 23:45 lassoan Note Added: 0015992
2018-09-11 23:54 lassoan Note Edited: 0015992 View Revisions
2018-09-12 01:01 jcfr Note Added: 0015993
2018-09-12 01:04 jcfr Note Edited: 0015993 View Revisions
2018-09-13 10:57 lassoan Note Added: 0016002
2018-09-13 11:10 jcfr Note Added: 0016004
2018-09-13 12:03 lassoan Note Added: 0016012
2018-09-13 12:18 jcfr Note Edited: 0016004 View Revisions
2018-09-13 12:18 jcfr Note Edited: 0016004 View Revisions
2018-09-13 12:18 jcfr Note Edited: 0016004 View Revisions
2018-09-13 12:19 jcfr Note Added: 0016014
2018-09-13 22:58 lassoan Note Added: 0016016
2018-09-13 22:59 lassoan File Added: clipping-gradient-opacity-enabled.png
2018-09-13 22:59 lassoan Note Added: 0016017
2018-09-13 23:03 lassoan File Added: clipping-gradient-opacity-disabled-depth-peeling-off.png
2018-09-13 23:03 lassoan Note Added: 0016018
2018-09-13 23:04 lassoan File Added: clipping-gradient-opacity-disabled-depth-peeling-on.png
2018-09-13 23:04 lassoan Note Added: 0016019
2018-09-13 23:17 lassoan Note Edited: 0016016 View Revisions
2018-09-13 23:19 lassoan File Added: clipping-depth-peeling-enabled-boxwidget.png
2018-09-13 23:19 lassoan Note Added: 0016020
2018-09-14 10:23 lassoan Note Added: 0016021
2018-09-17 09:40 sankhesh Note Added: 0016022
2018-09-17 14:24 lassoan Note Added: 0016023
2018-09-26 17:24 sankhesh Note Added: 0016041
2018-10-03 17:25 lassoan Note Added: 0016066
2018-10-14 01:39 lassoan Note Edited: 0016002 View Revisions
2018-10-16 06:09 jcfr Note Added: 0016143
2018-10-16 06:10 jcfr Note Added: 0016144
2018-10-16 06:10 jcfr Note Edited: 0016144 View Revisions
2018-10-16 22:57 jcfr Status assigned => resolved
2018-10-16 22:57 jcfr Resolution open => fixed
2018-10-16 22:57 jcfr Fixed in Version => Slicer 4.9.0
2018-10-16 22:57 jcfr Note Added: 0016161