{- | Module : Data.Octree.BoundingBox.BoundingBox Copyright : Copyright (c) 2016 Michael Litchard License : BSD3 Maintainer : Michael Litchard Stability : experimental Portability: not portable This module provides a way to use bounding boxes with Octrees. -} module Data.Octree.BoundingBox.BoundingBox ( BBoxConfig (..) , traverseOctreeBB , defBBoxConfig ) where import Data.Maybe (mapMaybe) import Data.BoundingBox.B3 (BBox3) import Data.Octree.Internal (Octree (..), allOctants) import Data.Octree.BoundingBox.Internal -- | BBoxConfig - The functions traverseOctreeBB needs data BBoxConfig x y a = BBoxConfig { -- | A function to recurse down the Octree select :: BBox3 -> x -> Maybe x, -- | A function to pre-condition the leaves procLeaf :: BBox3 -> x -> [LeafValue a] -> y, -- | A function to recurse back up the tree combine :: x -> [y] -> y } -- | defBBoxConfig - default BBoxConfig defBBoxConfig :: BBoxConfig DefInput DefOutput DefNodeValue defBBoxConfig = BBoxConfig { select = filterNodes , procLeaf = points, combine = result } -- | traverseOctreeBB - Generalized Octree traversal function based on BBox3 -- Base case processes leaves traverseOctreeBB :: BBoxConfig x y a -> BBox3 -> Octree a -> x -> y traverseOctreeBB bbc bbx (Leaf leaf_vals) input = procLeaf' bbx input leaf_vals where procLeaf' = procLeaf bbc -- | General framework to traverse an Octree in terms of a BBox3 traverseOctreeBB bbc bbx (Node split' nwu' nwd' neu' ned' swu' swd' seu' sed') x = combine' x res where combine' = combine bbc res = mapMaybe traverseOctreeBB' octList select' = select bbc traverseOctreeBB' (subbox, subtree) = case select' subbox x of Just x' -> Just (traverseOctreeBB bbc subbox subtree x) Nothing -> Nothing octList = zip boxList children boxList = map (newBBox3 bbx split') allOctants children = [swd',sed',nwd',ned',swu',seu',nwu',neu']