注:此文知识学习笔记,仅
记录完整
程序和实现结果,具体原理参见:
https://blog.csdn.net/www_doling_net/article/details/8541534
https://blog.csdn.net/shenziheng1/article/category/6114053/4
3、
灰度图像映射成伪彩色图像(查表法 vtkLookUpTable)
图像彩色映射的原理是首先生成一个颜色查找表,然后根据图像的一个标量值向颜色查找表中查找对应的颜色,并用新颜色值替代原来的像素值。VTK中
vtkImageMapToColors
负责图像彩色映射,
vtkLookUpTable
负责生成颜色查找表。
#include <vtkSmartPointer.h>
#include <vtkJPEGReader.h>
#include <vtkLookupTable.h> //生成颜色查找表
#include <vtkImageMapToColors.h> //实现图像彩色映射
#include <vtkImageActor.h>
#include <vtkRenderer.h>
#include <vtkRenderWindow.h>
#include <vtkRenderWindowInteractor.h>
#include <vtkInteractorStyleImage.h>
int main()
{
vtkSmartPointer<vtkJPEGReader> reader = vtkSmartPointer<vtkJPEGReader>::New();
reader->SetFileName("data\\lena-gray.jpg");
//建立颜色映射查找表
vtkSmartPointer<vtkLookupTable> colorTable = vtkSmartPointer<vtkLookupTable>::New();
colorTable->SetRange(0.0, 255.0);
colorTable->SetHueRange(0.1, 0.5); //色调(H)范围
colorTable->SetValueRange(0.6, 1.0); //明度(V)范围
colorTable->Build(); //生成颜色查找表
//建立颜色映射
vtkSmartPointer<vtkImageMapToColors> colorMap = vtkSmartPointer<vtkImageMapToColors>::New();
colorMap->SetInputConnection(reader->GetOutputPort());
colorMap->SetLookupTable(colorTable); //用来设置相应的颜色查找表
colorMap->Update();
//建立演员
vtkSmartPointer<vtkImageActor> origActor = vtkSmartPointer<vtkImageActor>::New();
origActor->SetInputData(reader->GetOutput());
vtkSmartPointer<vtkImageActor> colorActor = vtkSmartPointer<vtkImageActor>::New();
colorActor->SetInputData(colorMap->GetOutput());
//化妆
double origView[4] = { 0.0, 0.0, 0.5, 1.0 };
double colorView[4] = { 0.5, 0.0, 1.0, 1.0 };
vtkSmartPointer<vtkRenderer> origRender = vtkSmartPointer<vtkRenderer>::New();
origRender->SetViewport(origView);
origRender->AddActor(origActor);
origRender->ResetCamera();
origRender->SetBackground(0.0, 0.0, 0.0);
vtkSmartPointer<vtkRenderer> colorRender = vtkSmartPointer<vtkRenderer>::New();
colorRender->SetViewport(colorView);
colorRender->AddActor(colorActor);
colorRender->ResetCamera();
colorRender->SetBackground(0.0, 0.0, 0.0);
//舞台
vtkSmartPointer<vtkRenderWindow> renderwindow = vtkSmartPointer<vtkRenderWindow>::New();
renderwindow->AddRenderer(origRender);
renderwindow->AddRenderer(colorRender);
renderwindow->SetSize(640, 320);
renderwindow->SetWindowName("GrayToColor");
//设置交互
vtkSmartPointer<vtkRenderWindowInteractor> rwi = vtkSmartPointer<vtkRenderWindowInteractor>::New();
vtkSmartPointer<vtkInteractorStyleImage> style = vtkSmartPointer<vtkInteractorStyleImage>::New();
rwi->SetInteractorStyle(style);
rwi->SetRenderWindow(renderwindow);
rwi->Initialize();
rwi->Start();
return 0;
}
首先读取了一个灰度图像,然后生成
vtkLookUpTable
颜色查找表。构造颜色查找表有两种方法,一种是直接添加颜色,另一种是设置HSV颜色空间变化范围(hue, saturation, value),然后自动生成颜色表。这里采用的是第二种方法,
SetRange
设置要映射的标量数据的范围;
SetHueRange
设置HSV颜色空间的Hue值范围,最大范围为[0,1];
SetValueRange
设置HSV颜色空间的Value范围,最大范围为[0, 1];设置完后,调用Build()来生成颜色查找表。接下来定义
vtkImageMapToColors
对象,
SetLookupTable
()设置相应的颜色查找表,执行Update()后,其输出为一副彩色图像。执行结果如下:
4、颜色合成(三张灰度图合成彩色图)
#include <vtkSmartPointer.h>
#include <vtkImageCanvasSource2D.h>
#include <vtkImageAppendComponents.h> //vtk中提供vtkImageAppendComponents类来合成彩色图像,其输入需要提供三个灰度图像
#include <vtkImageActor.h>
#include <vtkRenderer.h>
#include <vtkRenderWindow.h>
#include <vtkRenderWindowInteractor.h>
#include <vtkInteractorStyleImage.h>
int main()
{
//vtkImageCanvasSource2D定义三个二值图像,每个图像中绘制了一个白色区域
vtkSmartPointer<vtkImageCanvasSource2D> red = vtkSmartPointer<vtkImageCanvasSource2D>::New(); //红色画布
red->SetScalarTypeToUnsignedChar(); //数据类型转换
red->SetNumberOfScalarComponents(1);
red->SetExtent(0, 100, 0, 100, 0, 0);
red->SetDrawColor(0, 0, 0, 0);
red->FillBox(0, 100, 0, 100);
red->SetDrawColor(255, 0, 0, 0);
red->FillBox(20, 40, 20, 40);
red->Update();
vtkSmartPointer<vtkImageCanvasSource2D> green = vtkSmartPointer<vtkImageCanvasSource2D>::New();
green->SetScalarTypeToUnsignedChar();
green->SetNumberOfScalarComponents(1);
green->SetExtent(0, 100, 0, 100, 0, 0);
green->SetDrawColor(0, 0, 0, 0);
green->FillBox(0, 100, 0, 100);
green->SetDrawColor(255, 0, 0, 0);
green->FillBox(30, 50, 30, 50);
green->Update();
vtkSmartPointer<vtkImageCanvasSource2D> blue = vtkSmartPointer<vtkImageCanvasSource2D>::New();
blue->SetScalarTypeToUnsignedChar();
blue->SetNumberOfScalarComponents(1);
blue->SetExtent(0, 100, 0, 100, 0, 0);
blue->SetDrawColor(0, 0, 0, 0);
blue->FillBox(0, 100, 0, 100);
blue->SetDrawColor(255, 0, 0, 0);
blue->FillBox(40, 60, 40, 60);
blue->Update();
//vtkImageAppendComponents对象的输入来合成图像
vtkSmartPointer<vtkImageAppendComponents> appendFilter = vtkSmartPointer<vtkImageAppendComponents>::New();
appendFilter->SetInputConnection(0, red->GetOutputPort());
appendFilter->AddInputConnection(0, green->GetOutputPort());
appendFilter->AddInputConnection(0, blue->GetOutputPort());
appendFilter->Update();
vtkSmartPointer<vtkImageActor> redActor = vtkSmartPointer<vtkImageActor>::New();
redActor->SetInputData(red->GetOutput());
vtkSmartPointer<vtkImageActor> greenActor = vtkSmartPointer<vtkImageActor>::New();
greenActor->SetInputData(green->GetOutput());
vtkSmartPointer<vtkImageActor> blueActor = vtkSmartPointer<vtkImageActor>::New();
blueActor->SetInputData(blue->GetOutput());
vtkSmartPointer<vtkImageActor> combinedActor = vtkSmartPointer<vtkImageActor>::New();
combinedActor->SetInputData(appendFilter->GetOutput()); //合成对象结果作为组合演员展示在显示窗口
// Define viewport ranges
// (xmin, ymin, xmax, ymax)
double redViewport[4] = { 0.0, 0.0, 0.25, 1.0 }; // 定义可视区域
double greenViewport[4] = { 0.25, 0.0, 0.5, 1.0 };
double blueViewport[4] = { 0.5, 0.0, 0.75, 1.0 };
double combinedViewport[4] = { 0.75, 0.0, 1.0, 1.0 };
// Setup renderers
vtkSmartPointer<vtkRenderer> redRenderer = vtkSmartPointer<vtkRenderer>::New();
redRenderer->SetViewport(redViewport);
redRenderer->AddActor(redActor);
redRenderer->ResetCamera();
redRenderer->SetBackground(1.0, 1.0, 1.0);
vtkSmartPointer<vtkRenderer> greenRenderer = vtkSmartPointer<vtkRenderer>::New();
greenRenderer->SetViewport(greenViewport);
greenRenderer->AddActor(greenActor);
greenRenderer->ResetCamera();
greenRenderer->SetBackground(1.0, 1.0, 1.0);
vtkSmartPointer<vtkRenderer> blueRenderer = vtkSmartPointer<vtkRenderer>::New();
blueRenderer->SetViewport(blueViewport);
blueRenderer->AddActor(blueActor);
blueRenderer->ResetCamera();
blueRenderer->SetBackground(1.0, 1.0, 1.0);
vtkSmartPointer<vtkRenderer> combinedRenderer = vtkSmartPointer<vtkRenderer>::New();
combinedRenderer->SetViewport(combinedViewport);
combinedRenderer->AddActor(combinedActor);
combinedRenderer->ResetCamera();
combinedRenderer->SetBackground(1.0, 1.0, 1.0);
vtkSmartPointer<vtkRenderWindow> renderWindow = vtkSmartPointer<vtkRenderWindow>::New();
renderWindow->AddRenderer(redRenderer);
renderWindow->AddRenderer(greenRenderer);
renderWindow->AddRenderer(blueRenderer);
renderWindow->AddRenderer(combinedRenderer);
renderWindow->SetSize(1200, 300);
renderWindow->Render();
renderWindow->SetWindowName("ImageAppendComponentsExample");
vtkSmartPointer<vtkRenderWindowInteractor> renderWindowInteractor = vtkSmartPointer<vtkRenderWindowInteractor>::New();
vtkSmartPointer<vtkInteractorStyleImage> style = vtkSmartPointer<vtkInteractorStyleImage>::New();
renderWindowInteractor->SetInteractorStyle(style);
renderWindowInteractor->SetRenderWindow(renderWindow);
renderWindowInteractor->Initialize();
renderWindowInteractor->Start();
return 0;
}
上面代码中利用vtkImageCanvasSource2D定义了3个二值图像,每个图像中绘制了一个白色矩形,并且三个矩形有部分重叠,然后定义vtkImageAppendComponents对象,并将三个图像设置为vtkImageAppendComponents对象的输入来合成图像。合成的效果为三个图像中对应的三个像素点像素值合成为输出图像的RGB像素值,如三个图像中第100个像素的像素值分别为,255,0和0,那么该点在输出图像中的像素值为(255, 0, 0),显示为红色。本例的执行效果如下:
参考资料:
1.《The Visualization Toolkit – AnObject-Oriented Approach To 3D Graphics (4th Edition)》
2. 张晓东, 罗火灵. VTK图形图像开发进阶[M]. 机械工业出版社, 2015.
所用软件:vtk7.0+visual studio 2013