C ++类中的VTK Visualizer无法渲染场景

时间:2018-07-21 22:21:33

标签: c++ class vtk

我正在尝试将VTK here提供的示例放入C ++类。本示例读取STL文件并在窗口中可视化它。

下面是我的代码,没有任何编译器或运行时错误。正确读取了我的输入STL文件,但是我的代码退出了,而没有产生STL对象的任何可视化图像。

在C ++类中,我通过将阅读器与可视化器分离并将它们放入类中的两个函数中来组织了VTK示例代码。可视器使用映射器,演员和渲染器来可视化STL对象。但是,我无法获得代码以可视化我的STL对象。

我可以使C ++类正常工作的唯一方法是将函数visualize的代码复制到我的readSTL函数中,然后我可以看到带有STL对象的窗口它。

有人可以给我一些提示,如何在类中的单独函数中执行可视化吗?

#include <vtkPolyData.h>
#include <vtkSTLReader.h>
#include <vtkSmartPointer.h>
#include <vtkPolyDataMapper.h>
#include <vtkActor.h>
#include <vtkRenderWindow.h>
#include <vtkRenderer.h>
#include <vtkRenderWindowInteractor.h>


class triangulation
{
public:
    vtkIdType numberOfFaces;
    // Constructor
    triangulation(void);
    triangulation(std::string filename);
    void setFilename(std::string filename);
    std::string getFilename(void);

    // Getters
    vtkSmartPointer<vtkPolyData> getMesh(void);
    vtkSmartPointer<vtkCellArray> getPolys(void);
    vtkSmartPointer<vtkPoints>    getPoints(void);
    vtkSmartPointer<vtkDataArray> getDataArray(void);
    vtkIdType getNumberofFaces(void);

    // Visualizer
    void visualize(void);

    // Reader
    void readSTL(void);

private:
    std::string stlFilename;
    vtkSmartPointer<vtkPolyData> mesh;
    vtkSmartPointer<vtkSTLReader> reader;
    vtkSmartPointer<vtkCellArray> polys;
    vtkSmartPointer<vtkPoints>    points;
    vtkSmartPointer<vtkDataArray> dataArray;
};

triangulation::triangulation()
{
    //
}

triangulation::triangulation(std::string filename)
{
    setFilename(filename);
}


void triangulation::readSTL(void)
{
    vtkSmartPointer<vtkSTLReader> reader = vtkSmartPointer<vtkSTLReader>::New();
    reader->SetFileName(stlFilename.c_str());
    reader->Update();
    mesh = reader->GetOutput();
    polys = mesh->GetPolys();
    points = mesh->GetPoints();
    numberOfFaces = mesh->GetNumberOfCells();
}

void triangulation::setFilename(std::string filename)
{
    stlFilename = filename;
}

std::string triangulation::getFilename(void)
{
    return stlFilename;
}

vtkSmartPointer<vtkPolyData> triangulation::getMesh(void)
{
    return mesh;
}

vtkSmartPointer<vtkCellArray> triangulation::getPolys(void)
{
    return polys;
}

vtkIdType triangulation::getNumberofFaces(void)
{
    return numberOfFaces;
}

vtkSmartPointer<vtkPoints> triangulation::getPoints(void)
{
    return points;
}

vtkSmartPointer<vtkDataArray> triangulation::getDataArray(void)
{
    return dataArray;
}

void triangulation::visualize(void)
{
    // Visualize
    vtkSmartPointer<vtkPolyDataMapper> mapper = vtkSmartPointer<vtkPolyDataMapper>::New();
    mapper->SetInputConnection(reader->GetOutputPort());

    vtkSmartPointer<vtkActor> actor = vtkSmartPointer<vtkActor>::New();
    actor->SetMapper(mapper);

    vtkSmartPointer<vtkRenderer> renderer = vtkSmartPointer<vtkRenderer>::New();
    vtkSmartPointer<vtkRenderWindow> renderWindow = vtkSmartPointer<vtkRenderWindow>::New();
    renderWindow->AddRenderer(renderer);
    vtkSmartPointer<vtkRenderWindowInteractor> renderWindowInteractor = vtkSmartPointer<vtkRenderWindowInteractor>::New();
    renderWindowInteractor->SetRenderWindow(renderWindow);

    renderer->AddActor(actor);
    renderer->SetBackground(.3, .6, .3); // Background color green

    renderWindow->Render();
    renderWindowInteractor->Start();
}



int main(int argc, char *argv[])
{
    if (argc != 2)
    {
        cout << "Required parameters: Filename" << endl;
        return EXIT_FAILURE;
    }

    std::string inputFilename = argv[1];
    cout << inputFilename << endl;
    triangulation *tr = new triangulation(inputFilename);
    tr->readSTL();
    cout << "Number of Faces = " << tr->getNumberofFaces() << endl;

    vtkSmartPointer<vtkPolyData> mesh = tr->getMesh();
    vtkSmartPointer<vtkCellArray> polys = tr->getPolys();
    vtkSmartPointer<vtkPoints>    points = tr->getPoints();
    vtkSmartPointer<vtkDataArray> data = tr->getDataArray();
    //mesh->Print(cout);
    // polys->Print(cout);
    // points->Print(cout);
    // data->Print(cout);
    tr->visualize();


    delete tr;
    return EXIT_SUCCESS;
}

这是我用来测试代码的STL对象:

“ myobject.stl”:

solid STL generated by MeshLab
  facet normal -4.919344e-01  2.986337e-01  8.178133e-01
    outer loop
      vertex  -1.265660e+00  4.756133e+00  1.702858e-01
      vertex  -1.649185e+00  4.810246e+00 -8.017353e-02
      vertex  -1.602208e+00  4.484959e+00  6.686619e-02
    endloop
  endfacet
  facet normal -5.898571e-01  2.603427e-01  7.643889e-01
    outer loop
      vertex  -1.861084e+00  4.821712e+00 -2.475956e-01
      vertex  -1.602208e+00  4.484959e+00  6.686619e-02
      vertex  -1.649185e+00  4.810246e+00 -8.017353e-02
    endloop
  endfacet
  facet normal -6.398674e-01  2.007942e-01  7.417893e-01
    outer loop
      vertex  -1.861084e+00  4.821712e+00 -2.475956e-01
      vertex  -1.845646e+00  4.479523e+00 -1.416520e-01
      vertex  -1.602208e+00  4.484959e+00  6.686619e-02
    endloop
  endfacet
  facet normal -6.901410e-01  1.854371e-01  6.995131e-01
    outer loop
      vertex  -2.043903e+00  4.838252e+00 -4.323493e-01
      vertex  -1.845646e+00  4.479523e+00 -1.416520e-01
      vertex  -1.861084e+00  4.821712e+00 -2.475956e-01
    endloop
  endfacet
endsolid vcg

1 个答案:

答案 0 :(得分:4)

如果您仅替换triangulation::readSTL()中的以下行,您的代码将起作用:

// Problem: local variable 'reader' shadows class member 'reader'.
vtkSmartPointer<vtkSTLReader> reader = vtkSmartPointer<vtkSTLReader>::New();
// Solution: 
reader = vtkSmartPointer<vtkSTLReader>::New();

由于类成员reader仍未初始化,因此在triangulation::visualize()中访问该应用程序时,该应用程序会因段错误而崩溃。

提示:如果因此使用this->或命名前缀(m__)来引用类成员,则可能不会遇到此问题。有关某些说明,请参见此SO post