Trouble with rendering VTKImageData in VTKImageViewer2 and VTKLineWidget2

I’m working on a project that involves loading medical image data in VTK (Visualization Toolkit), Qt, cpp and rendering it using VTKImageViewer2. Additionally, I need to draw a line on the displayed image using VTKLineWidget2. I’ve made some progress, but I’m facing an issue where the line I draw using VTKLineWidget2 appears behind the image, making it hard to see.

Here’s a summary of my code:

QVTKOpenGLWidget *m_pvtkWidget = new QVTKOpenGLWidget;
m_pvtkWidget->setStyleSheet("background-color: black");
vtkNew <vtkGenericOpenGLRenderWindow> m_openGlRenWin;

m_pvtkWidget->SetRenderWindow(m_openGlRenWin);
vtkNew<vtkImageViewer2> m_pvtkImageViewer; 
m_pvtkImageViewer->OffScreenRenderingOn();

vtkSmartPointer<vtkDICOMImageReader> reader = vtkSmartPointer<vtkDICOMImageReader>::New();
QString filep= "path to dicom file";
reader->SetFileName(filep.toUtf8().constData());
reader->Update();
vtkSmartPointer<vtkImageData> imageData = reader->GetOutput();
m_pvtkImageViewer->SetInputData(imageData);
m_pvtkImageViewer->SetRenderWindow(m_pvtkWidget->GetRenderWindow());
m_pvtkImageViewer->SetupInteractor(m_pvtkWidget->GetInteractor());
m_pvtkImageViewer->GetRenderer()->ResetCamera();
m_pvtkImageViewer->GetRenderer()->GetActiveCamera()->SetViewUp(0,1,0);
m_pvtkImageViewer->Render();
m_pvtkWidget->GetInteractor()->ReInitialize();

qDebug()<<"showImage";
vtkSmartPointer<vtkLineWidget2> m_objvtkLineWidget2 = vtkSmartPointer<vtkLineWidget2>::New();
double pointPos1[3];
double pointPos2[3];
pointPos1[0]=50;
pointPos1[1]=50;
pointPos1[2]=0;
pointPos2[0]=150;
pointPos2[1]=150;
pointPos2[2]=0;
m_objvtkLineWidget2->CreateDefaultRepresentation();
m_objvtkLineWidget2->GetLineRepresentation()->SetLineColor(255, 0,0);
m_objvtkLineWidget2->GetLineRepresentation()->GetLineProperty()->SetLineWidth(.25);
m_objvtkLineWidget2->GetLineRepresentation()->SetPoint1WorldPosition(pointPos1);
m_objvtkLineWidget2->GetLineRepresentation()->SetPoint2WorldPosition(pointPos2);
m_objvtkLineWidget2->GetRepresentation()->SetHandleSize(0);
m_objvtkLineWidget2->GetEventTranslator()->ClearEvents();
m_objvtkLineWidget2->SetInteractor(m_pvtkWidget->GetRenderWindow()->GetInteractor());
m_objvtkLineWidget2->On();
m_pvtkImageViewer->GetRenderer()->ResetCamera();
m_pvtkImageViewer->Render();
m_pvtkWidget->GetInteractor()->ReInitialize();

The issue is that the line drawn with VTKLineWidget2 appears behind the loaded image, making it difficult to see. I would like the line to appear on top of the image.

Is there a way to control the rendering order in VTKImageViewer2 or another solution to ensure that the line is rendered in front of the image?

Any help or guidance on how to resolve this issue would be greatly appreciated.

Hello,

I suggest you to add two renderers: the main one that you already have and a new one to display foreground actors:

    m_rendererMainScene = vtkSmartPointer<vtkRenderer>::New();

    ...

    m_rendererMainScene->GradientBackgroundOn();
    ...
    m_rendererMainScene->SetLayer( 0 ); //only the renderer of layer 0 has background.

    ...

    m_rendererForeground = vtkSmartPointer<vtkRenderer>::New();
    ...
    m_rendererForeground->SetLayer( 1 ); //layers greater than zero have no background and are rendered last.

    ...

    m_vtkwidget->renderWindow()->AddRenderer(m_rendererMainScene);
    m_vtkwidget->renderWindow()->AddRenderer(m_rendererForeground);

    ...

Then, you assign the widget’s graphical representation (a kind of actor) to the foreground renderer: m_objvtkLineWidget2->GetLineRepresentation()->SetRenderer(m_rendererForeground);.

take care,

PC

Thank you. Its very much helpful that i can set layers of renderers. i have tried with given details. Unfortunately only image is showing. Below, i have given the code. Could you please take a look on it and kindly help me to sort it out.

QVTKOpenGLWidget *m_pvtkWidget = new QVTKOpenGLWidget;
m_pvtkWidget->setStyleSheet("background-color: black");
vtkNew <vtkGenericOpenGLRenderWindow> m_openGlRenWin;

m_pvtkWidget->SetRenderWindow(m_openGlRenWin);


vtkSmartPointer<vtkDICOMImageReader> reader = vtkSmartPointer<vtkDICOMImageReader>::New();
QString filep= "path to dicom file";
reader->SetFileName(filep.toUtf8().constData());
reader->Update();
vtkSmartPointer<vtkImageData> imageData = reader->GetOutput();  

vtkSmartPointer<vtkRenderer> m_rendererMainScene = vtkSmartPointer<vtkRenderer>::New();
    // Configure properties for m_rendererMainScene, if needed

    // Enable gradient background for Layer 0
    m_rendererMainScene->GradientBackgroundOn();
    m_rendererMainScene->SetLayer(0); // Layer 0 has a background

   vtkSmartPointer<vtkRenderer> m_rendererForeground = vtkSmartPointer<vtkRenderer>::New();
 
    m_rendererForeground->SetLayer(1);

     m_pvtkWidget->GetRenderWindow()->AddRenderer(m_rendererMainScene);
     m_pvtkWidget->GetRenderWindow()->AddRenderer(m_rendererForeground);

    vtkNew<vtkImageActor> imageActor;
     imageActor->GetMapper()->SetInputData(imageData );

 
    m_rendererMainScene->AddActor(imageActor);

    // Create a VTKLineWidget2 for m_rendererForeground (Layer 1)
    vtkSmartPointer<vtkLineWidget2> lineWidget = vtkSmartPointer<vtkLineWidget2>::New();
    double pointPos1[3];
    double pointPos2[3];
    pointPos1[0]=50;
    pointPos1[1]=50;
    pointPos1[2]=0;
    pointPos2[0]=150;
    pointPos2[1]=150;
    pointPos2[2]=0;
    lineWidget->CreateDefaultRepresentation();
    lineWidget->GetLineRepresentation()->SetLineColor(255, 0,0);
    lineWidget->GetLineRepresentation()->GetLineProperty()->SetLineWidth(.25);
    lineWidget->GetLineRepresentation()->SetPoint1WorldPosition(pointPos1);
    lineWidget->GetLineRepresentation()->SetPoint2WorldPosition(pointPos2);
    lineWidget->GetRepresentation()->SetHandleSize(0);
    lineWidget->GetEventTranslator()->ClearEvents();
       lineWidget->SetInteractor(m_pvtkWidget->GetRenderWindow()->GetInteractor());
    // Add the line widget to m_rendererForeground (Layer 1)
    m_rendererForeground->AddActor(lineWidget->GetLineRepresentation());
    lineWidget->On();

   m_pvtkWidget->GetRenderWindow()->Render();
    m_pvtkWidget->GetRenderWindow()->GetInteractor()->Start();

once again Thanking you in advcance. awaiting for your reply :slight_smile: