【问题标题】:Why is vtkClipPolyData is rendering very slowly in surface rendered output in vtk为什么 vtkClipPolyData 在 vtk 的表面渲染输出中渲染速度非常慢
【发布时间】:2019-03-22 13:37:09
【问题描述】:

我有以下代码来剪裁模型,但是当我更新平面以生成新的剪裁表面时,它非常慢。有没有办法让它更快?还是有另一个 vtk 类可以更快地执行?

vtkSmartPointer<vtkPlane> clipPlane =  vtkSmartPointer<vtkPlane>::New();
clipPlane->SetNormal(1, 1, 0);
clipPlane->SetOrigin(0.0, -10.0, 0.0 );

vtkSmartPointer<vtkClipPolyData> clipper = 
vtkSmartPointer<vtkClipPolyData>::New();
clipper->SetInputData( reader->GetOutput() );
clipper->SetClipFunction( clipPlane );
clipper->Update();

但是我没有找到这个问题的答案。任何帮助都会得到帮助 我发现我的问题与下面给出的链接相同。参考使用下面的链接

http://vtk.1045678.n5.nabble.com/is-vtkClipPolyData-slow-td5727625.html1

【问题讨论】:

  • 嘿,按a“actor”键,就可以进入标准的vtkRenderWindowInteractor进入actor模式(这里解释:vtk.org/doc/nightly/html/classvtkInteractorStyle.html)。试一试:通过映射器在剪裁平面集周围抓取并移动演员。您应该会看到它立即响应。
  • 我正在使用vtkWin32RenderWindowInteractor。您的解决方案在其中有效吗?
  • 确实如此,r 用于重置相机,t 用于轨迹球相机,f 用于飞入多边形位置等等。当演员的变换发生变化(通过鼠标交互)时,剪辑平面不会发生变化。
  • 谢谢。因为我是 vtk 的新手,我会尝试
  • 在可视化工具包弹出窗口中通过鼠标交互;它会在您执行 vtkSmartPointer&lt; vtkRenderWindowInteractor &gt; ia=vtkSmartPointer&lt;vtkRenderWindowInteractor&gt;::New(); ia-&gt;SetRenderWindow( rw );ia-&gt;Initialize(); ia-&gt;Start(); 时打开,希望对您有所帮助:)

标签: c++ visual-studio-2008 vtk


【解决方案1】:

取决于您希望实现的目标:vtkClipPolyData 计算使用提供的vtkImplicitFunction 裁剪的新几何。我猜你可以比当前的更快地编写一个“StrictlyPlaneClipPolyData”过滤器。

但是,如果是渲染,那么您可以(并且应该)让着色器来做。简单如下:

//vtkActor * actor;
actor->GetMapper()->AddClippingPlane( clipPlane );

在交互之后,您可能只应用几何过滤器一次。

* 编辑 *

演示性能的示例代码:

#include "vtkInteractorStyleTrackballCamera.h"
#include "vtkRenderer.h"
#include "vtkRenderWindow.h"
#include "vtkRenderer.h"
#include "vtkClipPolyData.h"
#include "vtkPolyDataMapper.h"
#include "vtkActor.h"
#include <Windows.h>
#include "vtkPlane.h"
#include "vtkTransform.h"
#include "vtkMath.h"
#include "vtkProperty.h"
// performance counter in ms units
double ticks(void)
{
    LARGE_INTEGER lg,f;
    if ( QueryPerformanceCounter( &lg ) && QueryPerformanceFrequency( &f ) )
        return 1000.0 * (double)lg.QuadPart/(double)f.QuadPart;
    else
        return (double)GetTickCount();
}
void ClipSample( void )
{
    vtkPolyData * monkey;
    // monkey is the Blender monkey courtesy of Blender.org 
    // @126 k vertices
    // make sure to transform the monkey into origin 

    // create render window
    vtkSmartPointer< vtkRenderer > ren = vtkSmartPointer< vtkRenderer >::New();
    vtkSmartPointer< vtkRenderWindow > rw = vtkSmartPointer< vtkRenderWindow >::New();
    rw->AddRenderer( ren );
    rw->SetSize( 1024,1024 );
    // create interactor used later
    vtkSmartPointer< vtkRenderWindowInteractor > ia = vtkSmartPointer<vtkRenderWindowInteractor>::New();
    ia->SetRenderWindow( rw );
    ia->SetInteractorStyle(  vtkSmartPointer< vtkInteractorStyleTrackballCamera >::New() );
    ia->Initialize();

    // create clipper
    vtkSmartPointer<vtkPlane> plane = vtkSmartPointer<vtkPlane> ::New();
    plane->SetNormal(0,0,1);
    plane->SetOrigin(0,0,0);

//#define SOFTWARE_CLIPPER

    // create mapper
    vtkSmartPointer< vtkPolyDataMapper > mapper = vtkSmartPointer< vtkPolyDataMapper >::New();
#ifdef SOFTWARE_CLIPPER
    vtkSmartPointer< vtkClipPolyData > clipper = vtkSmartPointer< vtkClipPolyData >::New();
    clipper->SetInputData( monkey );
    clipper->SetClipFunction( plane );
    mapper->SetInputConnection( clipper->GetOutputPort() );
#else
    mapper->SetInputData( monkey );
    mapper->AddClippingPlane( plane );
#endif

    // create actor
    vtkSmartPointer< vtkActor > actor = vtkSmartPointer< vtkActor >::New();
    actor->SetMapper( mapper );
    actor->GetProperty()->SetColor( 0.3, 1.0, 0.7 );

    // color back face to emphasize clipping
    vtkSmartPointer< vtkProperty > backface = vtkSmartPointer< vtkProperty > ::New();
    backface->SetColor(1,0,0);
    actor->SetBackfaceProperty( backface );

    ren->AddActor( actor );
    double delta = 20.0;

    double timeTotal=0.0;
    double count=0.0;
    for ( int i=0;i<10;++i)
    {
        // make rotation axis
        vtkSmartPointer<vtkTransform> trf0=vtkSmartPointer<vtkTransform>::New();
        trf0->RotateZ( vtkMath::Random(-90,90) );
        trf0->RotateX( vtkMath::Random(-90,90) );
        trf0->RotateY( vtkMath::Random(-90,90) );
        const double * axis = trf0->TransformNormal(0,0,1);

        for ( double z=-180; z<180; z+=delta ) 
        {
            double time = ticks();
            // rotate the clipper around its axis
            double normal[3];
            vtkSmartPointer<vtkTransform> trf=vtkSmartPointer<vtkTransform>::New();
            trf->RotateWXYZ( z, axis );
            plane->SetNormal( trf->TransformNormal(0,0,1) );
            ia->Render();
            time = ticks()-time;
            timeTotal+=time;
            count+=1.0;
            Sleep( 30 ); // too fast otherwise
        }
    }
#ifdef SOFTWARE_CLIPPER
    std::cout << "Software clipper: ";
#else
    std::cout << "Hardware clipper: ";
#endif
    std::cout << "time per iteration " << timeTotal/count << " ms" << std::endl;
    ia->Start(); // start interactor finally: use 'C','A' etc. for changing interaction modes
}

硬件和软件剪​​辑器的比较(Windows 10、Intel i5 8th gen、VTK8.1):

Software clipper: time per iteration 76.5701 ms

Hardware clipper: time per iteration 1.63613 ms

【讨论】:

  • 我试过这样vtkSmartPointer&lt;vtkPlane&gt; clipPlane = vtkSmartPointer&lt;vtkPlane&gt;::New(); clipPlane-&gt;SetNormal(1, 1, 0); clipPlane-&gt;SetOrigin(0.0, -10.0, 0.0 ); vtkSmartPointer&lt;vtkClipPolyData&gt; clipper = vtkSmartPointer&lt;vtkClipPolyData&gt;::New(); clipper-&gt;SetInputData( reader-&gt;GetOutput() ); clipper-&gt;SetClipFunction( clipPlane ); clipper-&gt;Update(); mapper-&gt;SetInput(clipper-&gt;GetOutput()); actor-&gt;SetMapper(mapper); actor-&gt;GetMapper()-&gt;AddClippingPlane( clipPlane); renderer-&gt;AddActor(actor);但没有改善
  • @Ria 那样,你做了两次剪辑。只需将reader-&gt;GetOutput() 连接到映射器(请务必调用reader-&gt;Update() 或使用SetInputConnection 替代方法。
  • 喜欢这个? vtkSmartPointer&lt;vtkPlane&gt; clipPlane = vtkSmartPointer&lt;vtkPlane&gt;::New(); clipPlane-&gt;SetNormal(1, 1, 0); clipPlane-&gt;SetOrigin(0.0, -10.0, 0.0 ); mapper-&gt;SetInput(reader-&gt;GetOutput()); reader-&gt;Update(); actor-&gt;SetMapper(mapper); actor-&gt;GetMapper()-&gt;AddClippingPlane( plane1); renderer-&gt;AddActor(aActor); renderWindow-&gt;Render(); interactor-&gt;Initialize();
  • @Ria 是的,就像这样。尽管如此,我猜想vtkClipPolyData 的成本与从磁盘读取文件相比可以忽略不计。如果你重复剪辑,那么它当然很慢。
  • @Ria 好吧,渲染器的初始化和读取也需要一些时间
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多