【libigl】Libigl_Tutorials -第三章(共6节)

5f4e2a8088c38114adb33309257d8542.jpeg

第 3 章:矩阵和线性代数

Libigl 严重依赖 Eigen 库来实现密集和稀疏线性代数例程。除了几何处理例程之外,libigl 还具有引导 Eigen 的线性代数例程,使其感觉更类似于 Matlab 等高级代数库。

 一、切片Slice

Matlab 中一个非常熟悉且功能强大的例程是数组切片。这允许读取或写入可能不连续的子矩阵。让我们考虑一下 Matlab 代码:

 
 
B = A(R,C);

如果 A 是 m×n�×� 矩阵,并且 R 是 j� 行索引长列表(介于 1 和 m� 是一个 k� 长列索引列表,那么结果 B 将是 j×k�×� 根据 R 和 C 从 A 绘制元素的矩阵。在 libigl 中, slice 函数提供了相同的功能(示例 301):

 
 
VectorXi R,C;
MatrixXd A,B;
...
igl::slice(A,R,C,B);

请注意, A 和 B 也可以是稀疏矩阵。

同样,考虑 Matlab 代码:

 
 
A(R,C) = B;

现在,选择位于左侧,因此 j×k�×� 矩阵 B 被写入由 R 子矩阵中> 和 C 。 libigl 中使用 slice_into 提供了此功能:

igl::slice_into(B,R,C,A);

b64f3fc1965d9b1529d3353342a5df0b.png

示例 Slice 展示了如何使用 igl::slice 更改网格上三角形的颜色。

# include <igl/floor.h>
# include <igl/readOFF.h>
# include <igl/find.h>
# include <igl/opengl/glfw/Viewer.h>
# include <iostream>


// 主函数入口
int main(int argc, char *argv[])
{
  using namespace Eigen; // 使用Eigen命名空间
  using namespace std; // 使用标准库命名空间
  MatrixXd V; // 定义顶点坐标矩阵V
  MatrixXi F; // 定义面索引矩阵F
  igl::readOFF(TUTORIAL_SHARED_PATH "/decimated-knight.off",V,F); // 读取OFF格式的模型文件


  // 100个随机索引,指向F的行
  VectorXi I; 
  // 利用随机数生成索引I
  igl::floor((0.5*(VectorXd::Random(100,1).array()+1.)*F.rows()).eval(),I); 


  // 50个随机索引,指向I的行
  VectorXi J;
  // 利用随机数生成索引J
  igl::floor((0.5*(VectorXd::Random(50,1).array()+1.)*I.rows()).eval(),J);


  VectorXi K = I(J); // 根据索引J取出I中对应的元素,存放到K中
  // 该行代码被注释掉,因为I(J)已经完成了相应的工作,不再需要这个函数


  // 所有面默认为绿色
  MatrixXd C = RowVector3d(0.4,0.8,0.3).replicate(F.rows(),1); // 生成F行数相同的绿色矩阵
  // 红色用于标记K中的每一个索引
  MatrixXd R = RowVector3d(1.0,0.3,0.3).replicate(K.rows(),1); // 生成K行数相同的红色矩阵
  // 将C矩阵中K指定的行替换为红色R
  C(K,Eigen::all) = R;
  // 该行代码被注释掉,因为上一行代码已经完成了相应的工作,不再需要这个函数


  // 随机化颜色数组,其中25%的几率为true
  Eigen::Array<bool,Eigen::Dynamic,1> W = Eigen::VectorXd::Random(F.rows()).array()>0.5;
  // 将1/4的颜色设置为蓝色
  MatrixXd B = RowVector3d(0.3,0.3,1.0).replicate(W.count(),1); // 生成W中true计数相同的蓝色矩阵
  // 将C矩阵中W标记为true的行替换为蓝色B
  C(igl::find(W),Eigen::all) = B;


  // 使用伪彩色绘制网格
  igl::opengl::glfw::Viewer viewer; // 创建一个Viewer实例
  viewer.data().set_mesh(V, F); // 将顶点坐标和面索引传递给viewer
  viewer.data().set_colors(C); // 将颜色矩阵传递给viewer
  viewer.launch(); // 启动viewer窗口
}

以上代码是使用libigl库的示例,通过以下步骤来显示带有伪彩色的3D模型网格:

  1. 读取OFF格式的3D模型文件,并且分别存储顶点坐标到矩阵V和面索引到矩阵F。

  2. 生成100个随机的索引I,指向面矩阵F的行。

  3. 从上述I中再随机取出50个索引J。

  4. K为J在I中对应的元素,即最终确定的面索引集合。

  5. 初始化颜色矩阵C,默认为绿色,然后将K索引指向的对应行设置为红色。

  6. 通过随机选择一半的面,并将这些面的颜色设置为蓝色。

  7. 创建视图窗口,并设置网格与颜色数据,最终启动窗口展示结果。

总之,这段代码演示了如何用libigl库加载一个3D模型,给它应用随机颜色,并在窗口中渲染出来。

b19626d9ea9bfcbb97921c0ac0a511d4.png

Eigen::Array<bool,Eigen::Dynamic,1> W = Eigen::VectorXd::Random(F.rows()).array()>0.5;

7eacb07ef798a543e6298d4b35939260.png

二、 Sort 排序

8f16834c1118f43428ddaad49b8cedc5.png

这段代码的作用是使用libigl的功能来加载和显示一个三维网格模型,并为

网格顶点生成伪彩色。这基于每个顶点对应的质心的排序,具体步骤如下:

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值