简介:
AABB是最常用的碰撞检测使用的包围盒。听起来好像很神秘的,其实就是一个简单的数据结构。
原理可以一句话概括:
因为可以说所有的2d和3d物体都是由点组成的,所以只要找出这些物体的最大值点和最小值点,那么就可以使用这两个点表示该物体的AABB包围盒了。
检测碰撞的时候我们只需要检测这些物体的AABB(即他们的最大值点和最小值点)是否相交,就可以判断是否碰撞了。
缺点:
不准确,因为AABB不能很准确地包围一个物体,所以难免会在不相交的时候误判为相交,如下图:
但是对于一般应用来说,这点误差可以容忍。
优点:
计算简单,速度很快。也因为这样所以应用很广。
下面看看如何表示一个AABB类:
定义:
#ifndef AABB_H #define AABB_H #include "Vector3.h" class AABB { public: AABB(); AABB(const AABB &aabb); ~AABB(); void add(const Vector3 &v); void clear(); void makeAABB(Vector3 V[], int n); Vector3 min, max, center; }; void aabbPrint(AABB &ab); #endif
类实现:
#include<iostream> #include"AABB.h" AABB::AABB() { } AABB::AABB(const AABB &aabb) { min = aabb.min; max = aabb.max; center = aabb.center; } void AABB::clear() { min.x = min.y = min.z = FLT_MAX; //careful: This is not FLT_MIN, 'cause FLT_MIN is a little larger than 0, //hence not a minus value. max.x = max.y = max.z = -FLT_MAX; } void AABB::add(const Vector3 &v) { if (v.x < min.x) min.x = v.x; if (v.y < min.y) min.y = v.y; if (v.z < min.z) min.z = v.z; if (v.x > max.x) max.x = v.x; if (v.y > max.y) max.y = v.y; if (v.z > max.z) max.z = v.z; } //make AABB out of Vector3 points void AABB::makeAABB(Vector3 V[], int n) { if (!V) return; for (int i = 0; i < n; i++) add(V[i]); center.x = (min.x + max.x) * 0.5f; center.y = (min.y + max.y) * 0.5f; center.z = (min.z + max.z) * 0.5f; } AABB::~AABB() { } void aabbPrint(AABB &ab) { std::cout<<"AABB min is: "; ab.min.printVec3(); std::cout<<"AABB max is: "; ab.max.printVec3(); std::cout<<std::endl; }
测试:
#include<iostream> #include "AABB.h" using namespace std; void test() { AABB aabb; aabbPrint(aabb); Vector3 v1(1.0f, 2.0f, 3.0f); Vector3 v2(3.0f, 2.0f, 1.0f); Vector3 v3(-1.0f, -2.0f, -3.0f); Vector3 v4(-2.0f, 1.0f, 3.0f); Vector3 v5(2.0f, -1.0f, 3.0f); Vector3 v6(2.0f, 2.0f, -2.0f); Vector3 v[] = {v1,v2,v3,v4,v5,v6}; aabb.makeAABB(v, 6); aabbPrint(aabb); } int main() { test(); system("pause"); return 0; }
运行结果:
作者:kenden23 发表于2013-12-9 7:47:17 原文链接
阅读:30 评论:0 查看评论