{"id":13732264,"url":"https://github.com/lohedges/aabbcc","last_synced_at":"2026-02-04T04:46:23.155Z","repository":{"id":37285974,"uuid":"66778170","full_name":"lohedges/aabbcc","owner":"lohedges","description":"Dynamic AABB trees in C++ with support for periodic systems.","archived":false,"fork":false,"pushed_at":"2021-01-02T14:10:09.000Z","size":116,"stargazers_count":313,"open_issues_count":1,"forks_count":60,"subscribers_count":15,"default_branch":"master","last_synced_at":"2024-08-04T02:10:57.933Z","etag":null,"topics":["aabb","aabb-trees","axis-aligned-bounding-box","collision-detection","spatial-decomposition","spatial-partitioning"],"latest_commit_sha":null,"homepage":"","language":"C++","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"other","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/lohedges.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2016-08-28T16:18:00.000Z","updated_at":"2024-08-01T09:17:09.000Z","dependencies_parsed_at":"2022-09-02T13:11:31.177Z","dependency_job_id":null,"html_url":"https://github.com/lohedges/aabbcc","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lohedges%2Faabbcc","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lohedges%2Faabbcc/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lohedges%2Faabbcc/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lohedges%2Faabbcc/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/lohedges","download_url":"https://codeload.github.com/lohedges/aabbcc/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":224708015,"owners_count":17356467,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["aabb","aabb-trees","axis-aligned-bounding-box","collision-detection","spatial-decomposition","spatial-partitioning"],"created_at":"2024-08-03T02:01:50.958Z","updated_at":"2026-02-04T04:46:23.102Z","avatar_url":"https://github.com/lohedges.png","language":"C++","readme":"# AABB.cc\n\nCopyright \u0026copy; 2016-2018 [Lester Hedges](http://lesterhedges.net)\n\n[![Build Status](https://travis-ci.org/lohedges/aabbcc.svg?branch=master)](https://travis-ci.org/lohedges/aabbcc)\n\nReleased under the [Zlib](http://zlib.net/zlib_license.html) license.\n\n## About\nA C++ implementation of a dynamic bounding volume hierarchy\n([BVH](https://en.wikipedia.org/wiki/Bounding_volume_hierarchy)) using\naxis-aligned bounding boxes ([AABBs](https://en.wikipedia.org/wiki/Minimum_bounding_box)).\nThe data structure provides an efficient way of detecting potential overlap\nbetween objects of arbitrary shape and size and is commonly used in\ncomputer game engines for collision detection and ray tracing.\n\nBecause of their speed and flexibility, AABB trees are also well suited\nto overlap detection in physics applications, such as molecular simulation.\nThey are particularly helpful for systems where there is a large size disparity\nbetween particle species, or whenever the particle density is extremely\ninhomogeneous. In such situations, traditional neighbour finding tools, such\nas [cell lists](https://en.wikipedia.org/wiki/Cell_lists), can become extremely\ninefficient (both in terms of memory footprint, and search speed). A good\noverview of the pros and cons of various neighbour finding algorithms\ncan be found [here](http://hoomd-blue.readthedocs.io/en/stable/nlist.html).\n(Note that this only discusses the cost of _querying_ different data\nstructures, not the additional overhead of building them, or maintaining\nthem as objects move around.)\n\nIn statistical physics, a common means of approximating a bulk (infinite)\nsystem is through the use of [periodic boundary conditions](https://en.wikipedia.org/wiki/Periodic_boundary_conditions).\nHere, particles that are on opposite sides of the unit box can interact through\nits periodic image. This library supports periodic and non-periodic systems\nin an arbitrary number of dimensions (\u003e= 2). Support is also provided for simulation\nboxes that are partially periodic, i.e. periodic along specific axes. At present,\nonly orthorhombic simulation boxes are supported.\n\nThe code in this library was adapted from parts of the [Box2D](http://www.box2d.org)\nphysics engine.\n\n## Installation\nA `Makefile` is included for building and installing the AABB library.\n\nTo compile and install the library, documentation, python wrapper, and demos:\n\n```bash\nmake build\nmake install\n```\n\nBy default, the library installs to `/usr/local`. Therefore, you may need admin\nprivileges for the final `make install` step above. An alternative is to change\nthe install location:\n\n```bash\nmake PREFIX=MY_INSTALL_DIR install\n```\nIf you would rather use a header-only version of the library in your application,\nsimply run:\n\n```bash\nmake header-only\n```\n\nThe resulting library header, `header-only/AABB.hpp`, can be directly included\nin your source code without the need for compiling and linking.\n\nFurther details on using the Makefile can be found by running make without\na target, i.e.\n\n```bash\nmake\n```\n\n## Compiling and linking\nTo use the library with a C/C++ code first include the library header file\nin the code.\n\n```cpp\n#include \u003caabb/AABB.h\u003e\n```\n\nThen to compile, we can use something like the following:\n\n```bash\ng++ example.cc -laabb\n```\n\nThis assumes that we have used the default install location `/usr/local`. If\nwe specify an install location, we would use a command more like the following:\n\n```bash\ng++ example.cc -I/my/path/include -L/my/path/lib -laabb\n```\n\n## Python wrapper\nA python wrapper can be built using:\n\n```bash\nmake python\n```\n\nYou will require [python2.7](https://www.python.org/download/releases/2.7)\n(and the development files if your package manager separates them) and\n[SWIG](http://www.swig.org). To use the module you will need the python file\n`aabb.py` and the shared object `_aabb.so` from the `python` directory.\nIf you wish to use a different version of python, simply override the\n`PYTHON` make variable on the command line, e.g.\n\n```bash\nmake PYTHON=3.5 python\n```\n\n(Note that you'll also need to update the shebang at the top of\n[hard_disc.py](python/hard_disc.py) to reflect your changes in order for the\npython demo to work.)\n\n## Example\nLet's consider a two-component system of hard discs in two dimensions, where\none species is much larger than the other. Making use of AABB trees, we can\nefficiently search for potential overlaps between discs by decomposing the\nsystem into its two constituent species and constructing a tree for each one.\nTo test overlaps for any given disc, we simply query the two trees\nindependently in order to find candidates. This decomposition ensures that\neach AABB tree has a well defined length scale, making it simple to construct\nand quick to query.\n\nThe image below shows the example hard disc system (left) and the AABB tree\nstructures for each species (middle and right). Each leaf node in a tree is\nthe AABB of an individual disc. Moving up the tree, AABBs are grouped together\ninto larger bounding volumes in a recursive fashion, leading to a single AABB\nenclosing all of the discs at the root. The box outline in the left-hand image\nshows the periodic boundary of the system.\n\n![AABBs for a binary hard disc system.](https://raw.githubusercontent.com/lohedges/assets/master/aabbcc/images/aabb.png)\n\nTo query overlaps between discs we start at the root node and traverse the\ntree. At each node we test whether the current AABB overlaps the AABB of the\nchosen disc. If so, we add the two children of the node to the stack of nodes\nto test. Whenever we reach a leaf node with which an overlap is found we record\na potential overlap with that disc (we know that the AABBs of the discs overlap,\nbut we need still need to check that discs themselves actually overlap). The\nanimation below shows an example of such a query. The disc of interest is\nhighlighted in green and the boundary of the periodic simulation box is shown\nin orange. At each stage of the search the AABB of the current node in the tree\nis shown in white. Leaf nodes that overlap with the trial disc are highlighted\ngreen. Note that the green leaf node on the right-hand edge of the simulation\nbox overlaps through the periodic boundary.\n\n\u003csection\u003e\n\t\u003cimg width=\"880\" src=\"https://raw.githubusercontent.com/lohedges/assets/master/aabbcc/animations/aabb.gif\" alt=\"Querying an AABB tree for overlaps.\"\u003e\n\u003c/section\u003e\n\nYou may be wondering why the AABBs shown in the previous animation are not\nthe minimum enclosing bounding box for each disc. This is a trick that is\nused to avoid frequent updates of the AABB tree during dynamics (movement\nof the discs). Whenever an AABB changes position we need to delete it from\nthe tree then reinsert the new one (at the updated position). This can be a\ncostly operation. By \"fattening\" the AABBs a small amount it is possible to\nmake many displacements of the objects before an update is triggered, i.e.\nwhen one of the discs moves outside of its fattened AABB. During dynamics it\nis also possible for the tree to become unbalanced, leading to increasingly\ninefficient queries. Here trees are balanced using a surface area heuristic\nand active balancing is handled via tree rotations. The animation below shows\nan example of a hard disc simulation. Dynamic AABB trees were used to maintain\na configuration of non-overlapping discs throughout the trajectory.\n\n\u003csection\u003e\n\t\u003cimg width=\"880\" src=\"https://raw.githubusercontent.com/lohedges/assets/master/aabbcc/animations/dynamics.gif\" alt=\"Dynamics using AABB trees for overlap tests.\"\u003e\n\u003c/section\u003e\n\nThe code used to create the above animation can be found at\n`demos/hard_disc.cc`. When the library is built, you can run the demo\nand use [VMD](http://www.ks.uiuc.edu/Research/vmd/) to view the trajectory\nas follows:\n\n```bash\n./demos/hard_disc\nvmd trajectory.xyz -e demos/vmd.tcl\n```\n\nA python version of the demo can be found at `python/hard_disc.py`. This\nprovides an example of how to use the python wrapper module.\n\n## Usage\nThere are several steps that go into building and using an AABB tree. Below\nare some examples showing how to use the various objects within the library.\n\n### AABB\nThis should be the minimum enclosing axis-aligned bounding box for an object\nin your simulation box. There is no need to fatten the AABB; this will be done\nwhen an object is inserted into the AABB tree. For example, to create an AABB\nfor a two-dimensional disc we could do the following:\n\n```cpp\n// Particle radius.\ndouble radius = 1.0;\n\n// Set the particle position.\nstd::vector\u003cdouble\u003e position({10, 10});\n\n// Compute lower and upper AABB bounds.\nstd::vector\u003cdouble\u003e lowerBound({position[0] - radius, position[1] - radius});\nstd::vector\u003cdouble\u003e upperBound({position[0] + radius, position[1] + radius});\n\n// Create the AABB.\naabb::AABB aabb(lowerBound, upperBound);\n```\n\n(While we refer to _particles_ in this example, in practice a particle could\nbe any object, e.g. a sprite in a computer game.)\n\n### Tree\n#### Initialising a tree\nTo instantiate dynamic AABB trees for a periodic two-component system in\ntwo dimensions:\n\n```cpp\n// Fattening factor.\ndouble fatten = 0.1;\n\n// Periodicity of the simulation box.\nstd::vector\u003cbool\u003e periodicity({true, true});\n\n// Size of the simulation box.\nstd::vector\u003cdouble\u003e boxSize({100, 100});\n\n// Number of small discs.\nunsigned int nSmall = 100;\n\n// Number of large discs.\nunsigned int nLarge = 10;\n\n// Create the AABB trees.\naabb::Tree treeSmall(2, fatten, periodicity, boxSize, nSmall);\naabb::Tree treeLarge(2, fatten, periodicity, boxSize, nLarge);\n```\n\nMany of the arguments to the constructor of `Tree` are optional, see the\n[Doxygen](http://www.doxygen.nl) documentation for details.\n\nNote that both the periodicity and box size can be changed on-the-fly, e.g.\nfor changing the box volume during a constant pressure simulation. See the\n`setPeriodicity` and `setBoxSize` methods for details.\n\n#### Inserting a particle\nTo insert a particle (object) into the tree:\n\n```cpp\n// Particle radius.\ndouble radius = 1.0;\n\n// Particle index (key).\nunsigned int index = 1;\n\n// Set the particle position.\nstd::vector\u003cdouble\u003e position({10.0, 10.0});\n\n// Compute lower and upper AABB bounds.\nstd::vector\u003cdouble\u003e lowerBound({position[0] - radius, position[1] - radius});\nstd::vector\u003cdouble\u003e upperBound({position[0] + radius, position[1] + radius});\n\n// Insert particle into the tree.\ntree.insertParticle(index, position, lowerBound, upperBound);\n```\n\nHere `index` is a key that is used to create a map between particles and nodes\nin the AABB tree. The key should be unique to the particle and can take any value\nbetween 0 and `std::numeric_limits\u003cunsigned int\u003e::max() - 1`.\n\nFor spherical objects, the insertion can be simplified to:\n\n```cpp\ntree.insertParticle(index, position, radius);\n```\n\n#### Removing a particle\nIf you are performing simulations using the [grand canonical ensemble](https://en.wikipedia.org/wiki/Grand_canonical_ensemble)\nyou may wish to remove particles from the tree. To do so:\n\n```cpp\ntree.removeParticle(index);\n```\n\nwhere `index` is the key for the particle to be removed. (You'll need to\nkeep track of the keys).\n\n#### Querying the tree\nYou can query the tree for overlaps with a specific particle, or for overlaps\nwith an arbitrary AABB object. The `query` method returns a vector containing\nthe indices of the AABBs that overlap. You'll then need to test the objects\nenclosed by these AABBs for actual overlap with the particle of interest.\n(using your own overlap code).\n\nFor a particle already in the tree:\n\n```cpp\n// Query AABB overlaps for particle with key 10.\nstd::vector\u003cunsigned int\u003e particles = tree.query(10);\n```\n\nFor an arbitrary AABB:\n\n```cpp\n// Set the AABB bounds.\nstd::vector\u003cdouble\u003e lowerBound({5, 5}};\nstd::vector\u003cdouble\u003e upperBound({10, 10}};\n\n// Create the AABB.\naabb::AABB aabb(lowerBound, upperBound);\n\n// Query the tree for overlap with the AABB.\nstd::vector\u003cunsigned int\u003e particles = tree.query(aabb);\n```\n\n## Tests\nThe AABB tree is self-testing if the library is compiled in development mode, i.e.\n\n```bash\nmake devel\n```\n\n## Disclaimer\nPlease be aware that this a working repository so the code should be used at\nyour own risk.\n\nIt would be great to hear from you if this library was of use in your research.\n\nEmail bugs, comments, and suggestions to lester.hedges+aabbcc@gmail.com.\n","funding_links":[],"categories":["GameProgramming"],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flohedges%2Faabbcc","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Flohedges%2Faabbcc","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flohedges%2Faabbcc/lists"}