Environment: VTK8.2.0, ITK5.0.0

Here is a demo project to display DICOM data by ITK and VTK.

CMakeLists.txt

cmake_minimum_required(VERSION 2.8)

project(vtkAndITK)

# Find ITK.
find_package( ITK REQUIRED )
include( ${ITK_USE_FILE} )

# Find VTK.
find_package( VTK REQUIRED )
include( ${VTK_USE_FILE} )

add_executable(${PROJECT_NAME} "main.cpp")

target_link_libraries( ${PROJECT_NAME} ${VTK_LIBRARIES} ${ITK_LIBRARIES} )

main.cpp

#include <iostream>

#include <itkImage.h>
#include <itkGDCMImageIO.h>
#include <itkGDCMSeriesFileNames.h>
#include <itkImageSeriesReader.h>
#include <itkImageToVTKImageFilter.h>
#include <itkPointSet.h>
#include <itkObject.h>

#include <vtkImageActor.h>
#include <vtkSmartPointer.h>
#include <vtkRenderer.h>
#include <vtkRenderWindow.h>
#include <vtkRenderWindowInteractor.h>
#include <vtkInteractorStyleImage.h>
#include <string>
#include <vtkImageMapToWindowLevelColors.h>
#include <vtkInformation.h>
#include <vtkStreamingDemandDrivenPipeline.h>

using namespace std;

using PixelType = signed short;
using ImageType3D = itk::Image<PixelType, 3>;
using ImageType2D = itk::Image<PixelType, 2>;
using ImageIoType = itk::GDCMImageIO;
using NamesGeneratorType = itk::GDCMSeriesFileNames;
using ReaderType3D = itk::ImageSeriesReader<ImageType3D>;
using ConnectorType3D = itk::ImageToVTKImageFilter<ImageType3D>;
using ConnectorType2D = itk::ImageToVTKImageFilter<ImageType2D>;
using MetaDataStringType = itk::MetaDataObject<std::string>;
int main( int argc, char *argv[] )
{
    ReaderType3D::Pointer ImageReader3D = ReaderType3D::New();
    ImageIoType::Pointer dicomIO = ImageIoType::New();
    ImageReader3D->SetImageIO(dicomIO);

    std::string folder = argv[1];
    NamesGeneratorType::Pointer nameGenerator = NamesGeneratorType::New();
    nameGenerator->SetDirectory(folder);

    using FilenamesContainer  = std::vector<std::string>;
    FilenamesContainer fileNames = nameGenerator->GetInputFileNames();
    ImageReader3D->SetFileNames(fileNames);
    try
    {
        ImageReader3D->Update();
    }
    catch (itk::ExceptionObject &ex)
    {
        std::cout << ex << std::endl;
        return -2;
    }

    ConnectorType3D::Pointer ImageConnector3D = ConnectorType3D::New();
    ImageConnector3D->SetInput(ImageReader3D->GetOutput());
    try
    {
        ImageConnector3D->Update();
    }
    catch (itk::ExceptionObject & ex)
    {
        std::cout << ex << std::endl;
        return -3;
    }

    double ColorLevel;
    double ColorWindow;

    const itk::MetaDataDictionary& dictionary = dicomIO->GetMetaDataDictionary();
    auto itr = dictionary.Begin();
    auto end = dictionary.End();
    std::string entryId = "0028|1050";
    auto tagItr = dictionary.Find(entryId);
    if (tagItr != end)
    {
        MetaDataStringType::ConstPointer entryvalue =
            dynamic_cast<const MetaDataStringType*> (tagItr->second.GetPointer());
        if (entryvalue)
        {
            std::string tagvalue = entryvalue->GetMetaDataObjectValue();
            ColorLevel = stod(tagvalue);
        }
    }

    entryId = "0028|1051";
    tagItr = dictionary.Find(entryId);
    if (tagItr != end)
    {
        MetaDataStringType::ConstPointer entryvalue =
            dynamic_cast<const MetaDataStringType*> (tagItr->second.GetPointer());
        if (entryvalue)
        {
            std::string tagvalue = entryvalue->GetMetaDataObjectValue();
            ColorWindow = stod(tagvalue);
        }
    }

    vtkSmartPointer<vtkImageMapToWindowLevelColors> imgToColors = vtkSmartPointer<vtkImageMapToWindowLevelColors>::New();
    imgToColors->SetInputData( ImageConnector3D->GetOutput() );
    imgToColors->SetLevel( ColorLevel );
    imgToColors->SetWindow( ColorWindow );
    imgToColors->Update();

    vtkAlgorithm *alg = imgToColors->GetInputAlgorithm();

    vtkImageData *data = imgToColors->GetOutput();
    vtkInformation* outInfo = alg->GetOutputInformation(0);
    int *w_ext = outInfo->Get(vtkStreamingDemandDrivenPipeline::WHOLE_EXTENT());

    vtkSmartPointer<vtkImageActor> actor = vtkSmartPointer<vtkImageActor>::New();
    actor->SetInputData( data );
    int slice = (w_ext[4] + w_ext[5])/2;
    actor->SetDisplayExtent( w_ext[0], w_ext[1], w_ext[2], w_ext[3], slice, slice );

    // w_ext: 0, 480, 0, 480, 0, 480
    cout << "w_ext: " << w_ext[0] << ", " << w_ext[1] << ", " << w_ext[2] << ", " << w_ext[3]
         << ", " << w_ext[4] << ", " << w_ext[5] << endl;

    vtkSmartPointer<vtkRenderer> ren = vtkSmartPointer<vtkRenderer>::New();
    ren->AddActor( actor );

    vtkSmartPointer<vtkRenderWindow> renWin = vtkSmartPointer<vtkRenderWindow>::New();
    renWin->AddRenderer( ren );

    vtkSmartPointer<vtkRenderWindowInteractor> iren = vtkSmartPointer<vtkRenderWindowInteractor>::New();
    iren->SetRenderWindow( renWin );
    iren->Initialize();

    vtkSmartPointer<vtkInteractorStyleImage> iStyle = vtkSmartPointer<vtkInteractorStyleImage>::New();
    iren->SetInteractorStyle( iStyle );

    ren->AddActor( actor );
    renWin->SetSize( 800, 800 );
    renWin->Render();
    ren->ResetCamera();
    renWin->Render();
    iren->Start();
    return 0;
}

The folder contains a series of dcm files.
Run it.

 ./vtkAndITK.exe "D:\case\tmp"

Convert it to RGBA Image crudely.

vtkSmartPointer<vtkLookupTable> table = vtkSmartPointer<vtkLookupTable>::New();
table->SetNumberOfTableValues(256);
table->SetRange(0, 255);
table->Build();

vtkSmartPointer<vtkImageMapToColors> filter = vtkSmartPointer<vtkImageMapToColors>::New();
filter->SetLookupTable(table);
filter->SetOutputFormat(VTK_RGBA);
filter->SetInputData( ImageConnector3D->GetOutput() );
filter->Update();

actor->SetInputData( filter->GetOutput() );
Categories: ITKVTK

0 0 votes
Article Rating
Subscribe
Notify of
guest

1 Comment
Oldest
Newest Most Voted
Inline Feedbacks
View all comments
trackback

[…] post is based on an old project Use ITK And VTK To Show DICOM Image. We want to add an above layer which drawed translucent red color on the gray […]

XOR Strings
: Input your strings, the tool can encrypt and decrypt them.

X
1
0
Would love your thoughts, please comment.x
()
x