日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪(fǎng)問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

VTK修炼之道47:图形基本操作进阶_法向量计算

發(fā)布時(shí)間:2025/3/15 编程问答 35 豆豆
生活随笔 收集整理的這篇文章主要介紹了 VTK修炼之道47:图形基本操作进阶_法向量计算 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

1.點(diǎn)法向量和單元法向量

三維平面的法向量是指垂直于該平面的三維向量。曲面在某點(diǎn)P處的法向量為垂直于該點(diǎn)切平面的向量。對(duì)于一個(gè)網(wǎng)格模型,其每一個(gè)點(diǎn)和單元都可以計(jì)算一個(gè)法向量,在三維計(jì)算機(jī)圖形學(xué)中法向量一個(gè)重要應(yīng)用是光照和陰影計(jì)算。對(duì)于網(wǎng)格模型,模型是有一定數(shù)量的面片(單元)來(lái)逼近的,面片越多,則模型越精細(xì);反之,則越粗糙。在計(jì)算網(wǎng)格模型的法向量時(shí),單元法向量計(jì)算比較簡(jiǎn)單,可以通過(guò)組成每個(gè)單元的任意兩條邊的叉乘向量并歸一化來(lái)表示。而,對(duì)于點(diǎn)的法向量,則是由所有使用該點(diǎn)的單元法向量的平均值來(lái)表示。 VTK中計(jì)算法向量的Filter是vtkPolyDataNormals()。該類(lèi)針對(duì)單元為 三角形或者多邊形類(lèi)型的vtkPolyData數(shù)據(jù)進(jìn)行計(jì)算。由于法向量分為點(diǎn)法向量和單元法向量,可以通過(guò)函數(shù)SetComputeCellNormals()和SetComputePointNormals()來(lái)設(shè)置需要計(jì)算的法向量類(lèi)型。 默認(rèn)情況下計(jì)算點(diǎn)法向量,關(guān)閉單元法向量計(jì)算 示例演示了一個(gè)vtkPolyData模型的點(diǎn)法向量和單位法向量的計(jì)算: #include <vtkAutoInit.h> VTK_MODULE_INIT(vtkRenderingOpenGL); VTK_MODULE_INIT(vtkInteractionStyle);#include <vtkSmartPointer.h> #include <vtkPolyDataReader.h> #include <vtkPolyDataNormals.h> //計(jì)算法向量 #include <vtkMaskPoints.h> #include <vtkArrowSource.h> #include <vtkGlyph3D.h> #include <vtkPointData.h> #include <vtkProperty.h> // #include <vtkPolyDataMapper.h> #include <vtkActor.h> #include <vtkRenderer.h> #include <vtkRenderWindow.h> #include <vtkRenderWindowInteractor.h>int main() {vtkSmartPointer<vtkPolyDataReader> plyReader =vtkSmartPointer<vtkPolyDataReader>::New();plyReader->SetFileName("fran_cut.vtk");plyReader->Update();vtkSmartPointer<vtkPolyDataNormals> normFilter =vtkSmartPointer<vtkPolyDataNormals>::New();normFilter->SetInputData(plyReader->GetOutput());normFilter->SetComputePointNormals(1);//開(kāi)啟點(diǎn)法向量計(jì)算normFilter->SetComputeCellNormals(0); //關(guān)閉單元法向量計(jì)算normFilter->SetAutoOrientNormals(1);normFilter->SetSplitting(0);normFilter->Update();vtkSmartPointer<vtkMaskPoints> mask =vtkSmartPointer<vtkMaskPoints>::New();mask->SetInputData(normFilter->GetOutput());mask->SetMaximumNumberOfPoints(300);mask->RandomModeOn();mask->Update();vtkSmartPointer<vtkArrowSource> arrow =vtkSmartPointer<vtkArrowSource>::New();arrow->Update(); //一定要更新 否則數(shù)據(jù)沒(méi)有添加進(jìn)來(lái),程序會(huì)報(bào)錯(cuò)vtkSmartPointer<vtkGlyph3D> glyph =vtkSmartPointer<vtkGlyph3D>::New();glyph->SetInputData(mask->GetOutput());glyph->SetSourceData(arrow->GetOutput());//每一點(diǎn)用箭頭代替glyph->SetVectorModeToUseNormal();//設(shè)置向量顯示模式和法向量一致glyph->SetScaleFactor(0.01); //設(shè)置伸縮比例glyph->Update();vtkSmartPointer<vtkPolyDataMapper> mapper =vtkSmartPointer<vtkPolyDataMapper>::New();mapper->SetInputData(plyReader->GetOutput());vtkSmartPointer<vtkPolyDataMapper> normMapper =vtkSmartPointer<vtkPolyDataMapper>::New();normMapper->SetInputData(normFilter->GetOutput());vtkSmartPointer<vtkPolyDataMapper> glyphMapper =vtkSmartPointer<vtkPolyDataMapper>::New();glyphMapper->SetInputData(glyph->GetOutput());vtkSmartPointer<vtkActor> actor =vtkSmartPointer<vtkActor>::New();actor->SetMapper(mapper);vtkSmartPointer<vtkActor> normActor =vtkSmartPointer<vtkActor>::New();normActor->SetMapper(normMapper);vtkSmartPointer<vtkActor> glyphActor =vtkSmartPointer<vtkActor>::New();glyphActor->SetMapper(glyphMapper);glyphActor->GetProperty()->SetColor(1, 0, 0);double origView[4] = { 0, 0, 0.33, 1 };double normView[4] = { 0.33, 0, 0.66, 1 };double glyphView[4] = { 0.66, 0, 1, 1 };vtkSmartPointer<vtkRenderer> origRender =vtkSmartPointer<vtkRenderer>::New();origRender->SetViewport(origView);origRender->AddActor(actor);origRender->SetBackground(1, 0, 0);vtkSmartPointer<vtkRenderer> normRender =vtkSmartPointer<vtkRenderer>::New();normRender->SetViewport(normView);normRender->AddActor(normActor);normRender->SetBackground(0, 1, 0);vtkSmartPointer<vtkRenderer> glyphRender =vtkSmartPointer<vtkRenderer>::New();glyphRender->SetViewport(glyphView);glyphRender->AddActor(glyphActor);glyphRender->AddActor(normActor);glyphRender->SetBackground(0, 0, 1);vtkSmartPointer<vtkRenderWindow> rw =vtkSmartPointer<vtkRenderWindow>::New();rw->AddRenderer(origRender);rw->AddRenderer(normRender);rw->AddRenderer(glyphRender);rw->SetWindowName("Calculating Point Norm & Cell Norm");rw->SetSize(960, 320);rw->Render();vtkSmartPointer<vtkRenderWindowInteractor> rwi =vtkSmartPointer<vtkRenderWindowInteractor>::New();rwi->SetRenderWindow(rw);rwi->Initialize();rwi->Start();return 0; }輸出結(jié)果如下圖所示:
在計(jì)算法向量時(shí)需要注意一個(gè)問(wèn)題,即法向量的方向。因?yàn)閷?duì)于同一個(gè)平面來(lái)講,可以有兩個(gè)方向完全相反的法向量。一般是根據(jù)單元的點(diǎn)的順序確定,采用右手定則來(lái)定義一個(gè)平面的法向量方向。因此計(jì)算平面方向量的時(shí)候,法向量的方向與單元的點(diǎn)的順序密切相關(guān)。必須保持單元的點(diǎn)順序一致,才會(huì)得到合理的法向量。當(dāng)然,函數(shù)SetConsistency()可以設(shè)置自動(dòng)調(diào)整模型的單元法向量。SetAutoOrientNormals()可以設(shè)置自動(dòng)調(diào)整法線(xiàn)的方向。

2.關(guān)于類(lèi)vtkGlyph3D

詳細(xì)描述:為每個(gè)輸入點(diǎn)拷貝相應(yīng)方向和伸縮比例的輪廓幾何體
vtkGlyph3d是一個(gè)過(guò)濾器,當(dāng)拷貝幾何體到每個(gè)輸入點(diǎn)時(shí),它起到濾波作用.glyph從過(guò)濾輸入源中以多邊形數(shù)據(jù)形式定義,glyph根據(jù)輸入的矢量和法向量來(lái)確定方向,根據(jù)伸縮數(shù)據(jù)和矢量大小來(lái)確定伸縮比例.當(dāng)glyph較多時(shí),可能通過(guò)對(duì)象源與其相應(yīng)的定義信息來(lái)創(chuàng)建glyph表.glyph表可以通過(guò)伸縮值或矢量大小來(lái)索引相應(yīng)的gpyph對(duì)象.
要使用vtkGlyph3D對(duì)象,我們首先需要提供一個(gè)輸入集和一個(gè)對(duì)象源來(lái)定義ghyph.然后決定是否對(duì)ghyph進(jìn)行伸縮,以及怎樣對(duì)其進(jìn)行伸縮,接下來(lái)決定是否對(duì)glyph設(shè)置方向,以及如何根據(jù)矢量及法向量來(lái)設(shè)置它,最終決定我們是用glyph表還是僅僅是單一的ghyph.如果使用了glyph表,我們還需要考慮相應(yīng)的索引值.

vtkGlyph3D 實(shí)際上是一種符號(hào)化的算法工具,可以使用一個(gè)源(如球體)為輸入數(shù)據(jù)集的每一個(gè)點(diǎn)生成一個(gè)符號(hào),并且可以設(shè)置符號(hào)的方向以及縮放比例,簡(jiǎn)單點(diǎn)說(shuō)就是對(duì)于你想關(guān)注的數(shù)據(jù)點(diǎn)添加符號(hào)標(biāo)注,符號(hào)的樣式由自己指定。比如你有一個(gè)曲面數(shù)據(jù),希望將曲面數(shù)據(jù)的每個(gè)點(diǎn)都用錐體標(biāo)注出來(lái)并且錐體的方向表示該點(diǎn)的法向量方向,這個(gè)時(shí)候就可以使用vtkGlyph3D。

3.本例的注意事項(xiàng)與經(jīng)驗(yàn)談

注意算法執(zhí)行之后,要注意及時(shí)更新,Update()一下!!!

4.參看資料

1.《C++ primer》
2.《The VTK User’s Guide – 11thEdition》
3. ?張曉東, 羅火靈. VTK圖形圖像開(kāi)發(fā)進(jìn)階[M]. 機(jī)械工業(yè)出版社, 2015.

總結(jié)

以上是生活随笔為你收集整理的VTK修炼之道47:图形基本操作进阶_法向量计算的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。