Marching Cubes初探——Marching Cubes构建体素圆

本文介绍了Marching Cubes算法在构建体素圆中的应用。首先,文章详细阐述了如何将点云数据转换为体数据。接着,讨论了如何找到六面体体素与等值面的交点,以生成等值面。最后,文章讲解了如何用这些交点表示等值面的三角形,以实现体素球的可视化。附带了相关的代码实现。
摘要由CSDN通过智能技术生成

Marching Cubes初探——Marching Cubes构建体素圆

标签(空格分隔): MarchingCubes OpenGL


Marching Cubes根据三维规则数据生成等值面,从而构成三维体数据。
我们的需求是自己生成三维球的点云数据,并通过Marching Cubes可视化体素球。


整个流程可分为三步:

  1. 点云数据向体数据转换
  2. 求六面体体素棱边与等值面的交点,构成等值面
  3. 等值面的三角形表示

笔记

image_1ctsq1q2a1ttphtn7m9h0p89mg.png-114.6kB
image_1ctsq2u5v1ulb1j341dir1eu2cflt.png-179.7kB
image_1ctsq40ta1nqp14ju1qg31jg59471a.png-230kB
image_1ctsq5b041loq1m9prgoo401mtn1n.png-246.1kB
image_1ctsq6e201fcb1nl85m2loc1dbb24.png-171.9kB
image_1ctsq7fgk1vpgi32b2hh5o1oq031.png-156.8kB
image_1ctsq7vdk1r8l1sd1o6l7008l43e.png-194.8kB
image_1ctsq8sqs1a3ssgd12u1cu57ep3r.png-333kB
image_1ctsq9h61t5ndo6q5gam31jkm48.png-227.5kB
image_1ctsqa2vh1c4b1nud1bokdkndbr4l.png-69.4kB
image_1ctsqas1laq21ikhl219an1lgq52.png-204.9kB
image_1ctsqbj8b6di1pvp43t10s81e7o5f.png-242.1kB
image_1ctsqd5ae1j0h1hih157hokb10lk62.png-56.8kB


效果

MC.gif-19332.8kB


代码

PointF.h
#pragma once
#include
#include
#include<GL/glew.h>
#include<GL/freeglut.h>

using namespace std;
#pragma  comment(lib, "glew32.lib")

class PointF{
private :
	float x, y, z;				//三维点坐标
	bool isInsideSphere;		//该点是否在球内的标记

public:
	PointF();
	~PointF();

	PointF(float x, float y, float z);
	float GetX();
	float GetY();
	float GetZ();
	bool GetIsInsideSphere();
	void SetIsInsideSphere(PointF cSphere, float R);

};

PointF.cpp

#include "PointF.h"

PointF::PointF() {
	x = 0.0f;
	y = 0.0f;
	z = 0.0f;
	isInsideSphere = false;
}

PointF::~PointF() {}

PointF::PointF(float x, float y, float z) {
	this->x = x;
	this->y = y;
	this->z = z;
}

float PointF::GetX() {
	return x;
}

float PointF::GetY() {
	return y;
}

float PointF::GetZ() {
	return z;
}

bool PointF::GetIsInsideSphere() {
	return isInsideSphere;
}

void PointF::SetIsInsideSphere(PointF cSphere, float R) {
	float xx = cSphere.GetX() - x;
	float yy = cSphere.GetY() - y;
	float zz = cSphere.GetZ() - z;

	float dis = xx * xx + yy * yy + zz * zz;
	float RR = R * R;
	if (RR > dis)
		isInsideSphere = true;
	else
		isInsideSphere = false;
}

VData.h

    #pragma once
    #include"PointF.h"
    
    class Voxel {
    private :
    	PointF iVertex[8];						//六面体体素的8个顶点
    	int iIndex;								//六面体根据顶点数据生成的EdgeTable和TriTable的下标
    	PointF iIntersectVertex[12];			//六面体12条棱边与等值面的交点
    
    public:
    	Voxel();
    	~Voxel();
    	void SetVertex(PointF p, int index);
    	PointF GetVertex(int index);
    	void CalculateiIndex();
    	void CalculateIntersectVertex();
    
    	void DrawWireCubes();
    	void DrawISOSurface();
    
    };

VData.cpp

#include "VData.h"
#include "PointF.h"

//点与边的关系
int vertexTable[12][15] = {
	{ 0,1 },
	{ 1,2 },
	{ 2,3 },
	{ 3,0 },
	{ 4,5 },
	{ 5,6 },
	{ 6,7 },
	{ 7,4 },
	{ 0,4 },
	{ 1,5 },
	{ 2,6 },
	{ 3,7 } };

//哪些边会与等值面相交
int edgeTable[256] = {
	0x0  , 0x109, 0x203, 0x30a, 0x406, 0x50f, 0x605, 0x70c,
	0x80c, 0x905, 0xa0f, 0xb06, 0xc0a, 0xd03, 0xe09, 0xf00,
	0x190, 0x99 , 0x393, 0x29a, 0x596, 0x49f, 0x795, 0x69c,
	0x99c, 0x895, 0xb9f, 0xa96, 0xd9a, 0xc93, 0xf99, 0xe90,
	0x230, 0x339, 0x33 , 0x13a, 0x636, 0x73f, 0x435, 0x53c,
	0xa3c, 0xb35, 0x83f, 0x936, 0xe3a, 0xf33, 0xc39, 0xd30,
	0x3a0, 0x2a9, 0x1a3, 0xaa , 0x7a6, 0x6af, 0x5a5, 0x4ac,
	0xbac, 0xaa5, 0x9af, 0x8a6, 0xfaa, 0xea3, 0xda9, 0xca0,
	0x460, 0x569, 0x663, 0x76a, 0x66 , 0x16f, 0x265, 0x36c,
	0xc6c, 0xd65, 0xe6f, 0xf66, 0x86a, 0x963, 0xa69, 0xb60,
	0x5f0, 0x4f9, 0x7f3, 0x6fa, 0x1f6, 0xff , 0x3f5, 0x2fc,
	0xdfc, 0xcf5, 0xfff, 0xef6, 0x9fa, 0x8f3, 0xbf9, 0xaf0,
	0x650, 0x759, 0x453, 0x55a, 0x256, 0x35f, 0x55 , 0x15c,
	0xe5c, 0xf55, 0xc5f, 0xd56, 0xa5a, 0xb53, 0x859, 0x950,
	0x7c0, 0x6c9, 0x5c3, 0x4ca, 0x3c6, 0x2cf, 0x1c5, 0xcc ,
	0xfcc, 0xec5, 0xdcf, 0xcc6, 0xbca, 0xac3, 0x9c9, 0x8c0,
	0x8c0, 0x9c9, 0xac3, 0xbca, 0xcc6, 0xdcf, 0xec5, 0xfcc,
	0xcc , 0x1c5, 0x2cf, 0x3c6, 0x4ca, 0x5c3, 0x6c9, 0x7c0,
	0x950, 0x859, 0xb53, 0xa5a, 0xd56, 0xc5f, 0xf55, 0xe5c,
	0x15c, 0x55 , 0x35f, 0x256, 0x55a, 0x453, 0x759, 0x650,
	0xaf0, 0xbf9, 0x8f3, 0x9fa, 0xef6, 0xfff, 0xcf5, 0xdfc,
	0x2fc, 0x3f5, 0xff , 0x1f6, 0x6fa, 0x7f3, 0x4f9, 0x5f0,
	0xb60, 0xa69, 0x963, 0x86a, 0xf66, 0xe6f, 0xd65, 0xc6c,
	0x36c, 0x265, 0x16f, 0x66 , 0x76a, 0x663, 0x569, 0x460,
	0xca0, 0xda9, 0xea3, 0xfaa, 0x8a6, 0x9af, 0xaa5, 0xbac,
	0x4ac, 0x5a5, 0x6af, 0x7a6, 0xaa , 0x1a3, 0x2a9, 0x3a0,
	0xd30, 0xc39, 0xf33, 0xe3a, 0x936, 0x83f, 0xb35, 0xa3c,
	0x53c, 0x435, 0x73f, 0x636, 
  • 7
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值