include/PxBroadPhase.h

File members: include/PxBroadPhase.h

// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions
// are met:
//  * Redistributions of source code must retain the above copyright
//    notice, this list of conditions and the following disclaimer.
//  * Redistributions in binary form must reproduce the above copyright
//    notice, this list of conditions and the following disclaimer in the
//    documentation and/or other materials provided with the distribution.
//  * Neither the name of NVIDIA CORPORATION nor the names of its
//    contributors may be used to endorse or promote products derived
//    from this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ''AS IS'' AND ANY
// EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
// PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
// OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
//
// Copyright (c) 2008-2023 NVIDIA Corporation. All rights reserved.
// Copyright (c) 2004-2008 AGEIA Technologies, Inc. All rights reserved.
// Copyright (c) 2001-2004 NovodeX AG. All rights reserved.

#ifndef PX_BROAD_PHASE_H
#define PX_BROAD_PHASE_H
#include "PxPhysXConfig.h"
#include "foundation/PxBounds3.h"

#if !PX_DOXYGEN
namespace physx
{
#endif

    class PxBaseTask;
    class PxCudaContextManager;

    struct PxBroadPhaseType
    {
        enum Enum
        {
            eSAP,
            eMBP,
            eABP,
            ePABP,
            eGPU,
            eLAST
        };
    };

    struct PxBroadPhaseRegion
    {
        PxBounds3   mBounds;
        void*       mUserData;
    };

    struct PxBroadPhaseRegionInfo
    {
        PxBroadPhaseRegion  mRegion;
        PxU32               mNbStaticObjects;
        PxU32               mNbDynamicObjects;
        bool                mActive;
        bool                mOverlap;
    };

    struct PxBroadPhaseCaps
    {
        PxU32   mMaxNbRegions;
    };

    class PxBroadPhaseDesc
    {
        public:
        PxBroadPhaseDesc(PxBroadPhaseType::Enum type = PxBroadPhaseType::eLAST) :
            mType                       (type),
            mContextID                  (0),
            mContextManager             (NULL),
            mFoundLostPairsCapacity     (256 * 1024),
            mDiscardStaticVsKinematic   (false),
            mDiscardKinematicVsKinematic(false)
        {}

        PxBroadPhaseType::Enum  mType;
        PxU64                   mContextID;

        PxCudaContextManager*   mContextManager;
        PxU32                   mFoundLostPairsCapacity;

        bool                    mDiscardStaticVsKinematic;
        bool                    mDiscardKinematicVsKinematic;

        PX_INLINE   bool        isValid()   const
        {
            if(PxU32(mType)>=PxBroadPhaseType::eLAST)
                return false;

            if(mType==PxBroadPhaseType::eGPU && !mContextManager)
                return false;

            return true;
        }
    };

    typedef PxU32 PxBpIndex;
    typedef PxU32 PxBpFilterGroup;
    #define PX_INVALID_BP_FILTER_GROUP  0xffffffff

    PX_C_EXPORT PX_PHYSX_CORE_API   PxBpFilterGroup PxGetBroadPhaseStaticFilterGroup();

    PX_C_EXPORT PX_PHYSX_CORE_API   PxBpFilterGroup PxGetBroadPhaseDynamicFilterGroup(PxU32 id);

    PX_C_EXPORT PX_PHYSX_CORE_API   PxBpFilterGroup PxGetBroadPhaseKinematicFilterGroup(PxU32 id);

    class PxBroadPhaseUpdateData
    {
        public:

        PxBroadPhaseUpdateData( const PxBpIndex* created, PxU32 nbCreated,
                                const PxBpIndex* updated, PxU32 nbUpdated,
                                const PxBpIndex* removed, PxU32 nbRemoved,
                                const PxBounds3* bounds, const PxBpFilterGroup* groups, const float* distances,
                                PxU32 capacity) :
            mCreated    (created),  mNbCreated  (nbCreated),
            mUpdated    (updated),  mNbUpdated  (nbUpdated),
            mRemoved    (removed),  mNbRemoved  (nbRemoved),
            mBounds     (bounds),   mGroups     (groups),   mDistances  (distances),
            mCapacity   (capacity)
        {
        }

        PxBroadPhaseUpdateData(const PxBroadPhaseUpdateData& other) :
            mCreated    (other.mCreated),   mNbCreated  (other.mNbCreated),
            mUpdated    (other.mUpdated),   mNbUpdated  (other.mNbUpdated),
            mRemoved    (other.mRemoved),   mNbRemoved  (other.mNbRemoved),
            mBounds     (other.mBounds),    mGroups     (other.mGroups),    mDistances  (other.mDistances),
            mCapacity   (other.mCapacity)
        {
        }

        PxBroadPhaseUpdateData& operator=(const PxBroadPhaseUpdateData& other);

        const PxBpIndex*        mCreated;
        const PxU32             mNbCreated;

        const PxBpIndex*        mUpdated;
        const PxU32             mNbUpdated;

        const PxBpIndex*        mRemoved;
        const PxU32             mNbRemoved;

        const PxBounds3*        mBounds;
        const PxBpFilterGroup*  mGroups;
        const float*            mDistances;
        const PxU32             mCapacity;
    };

    struct PxBroadPhasePair
    {
        PxBpIndex   mID0;
        PxBpIndex   mID1;
    };

    struct PxBroadPhaseResults
    {
        PxBroadPhaseResults() : mNbCreatedPairs(0), mCreatedPairs(NULL), mNbDeletedPairs(0), mDeletedPairs(NULL)    {}

        PxU32                   mNbCreatedPairs;
        const PxBroadPhasePair* mCreatedPairs;

        PxU32                   mNbDeletedPairs;
        const PxBroadPhasePair* mDeletedPairs;
    };

    class PxBroadPhaseRegions
    {
        protected:
                PxBroadPhaseRegions()   {}
        virtual ~PxBroadPhaseRegions()  {}
        public:

        virtual PxU32   getNbRegions()  const   = 0;

        virtual PxU32   getRegions(PxBroadPhaseRegionInfo* userBuffer, PxU32 bufferSize, PxU32 startIndex=0)    const   = 0;

        virtual PxU32   addRegion(const PxBroadPhaseRegion& region, bool populateRegion, const PxBounds3* bounds, const float* distances)   = 0;

        virtual bool    removeRegion(PxU32 handle)  = 0;

        /*
        \brief Return the number of objects that are not in any region.
        */
        virtual PxU32   getNbOutOfBoundsObjects()   const   = 0;

        /*
        \brief Return an array of objects that are not in any region.
        */
        virtual const PxU32*    getOutOfBoundsObjects() const   = 0;
    };

    class PxBroadPhase
    {
        protected:
                PxBroadPhase()  {}
        virtual ~PxBroadPhase() {}
        public:

        /*
        \brief Releases the broadphase.
        */
        virtual void    release()   = 0;

        virtual PxBroadPhaseType::Enum  getType()   const   = 0;

        virtual void    getCaps(PxBroadPhaseCaps& caps) const   = 0;

        virtual PxBroadPhaseRegions*    getRegions()    = 0;

        virtual PxAllocatorCallback*    getAllocator()  = 0;

        virtual PxU64   getContextID()  const   = 0;

        virtual void    setScratchBlock(void* scratchBlock, PxU32 size) = 0;

        virtual void    update(const PxBroadPhaseUpdateData& updateData, PxBaseTask* continuation=NULL) = 0;

        virtual void    fetchResults(PxBroadPhaseResults& results)  = 0;

        PX_FORCE_INLINE void    update(PxBroadPhaseResults& results, const PxBroadPhaseUpdateData& updateData)
        {
            update(updateData);
            fetchResults(results);
        }
    };

    PX_C_EXPORT PX_PHYSX_CORE_API   PxBroadPhase*   PxCreateBroadPhase(const PxBroadPhaseDesc& desc);

    class PxAABBManager
    {
        protected:
                PxAABBManager()     {}
        virtual ~PxAABBManager()    {}
        public:

        /*
        \brief Releases the AABB manager.
        */
        virtual void    release()   = 0;

        virtual PxBroadPhase&   getBroadPhase() = 0;

        virtual const PxBounds3*    getBounds() const   = 0;

        virtual const float*    getDistances()  const   = 0;

        virtual const PxBpFilterGroup*  getGroups() const   = 0;

        virtual PxU32   getCapacity()   const   = 0;

        virtual void    addObject(PxBpIndex index, const PxBounds3& bounds, PxBpFilterGroup group, float distance=0.0f) = 0;

        virtual void    removeObject(PxBpIndex index)   = 0;

        virtual void    updateObject(PxBpIndex index, const PxBounds3* bounds=NULL, const float* distance=NULL) = 0;

        virtual void    update(PxBaseTask* continuation=NULL)   = 0;

        virtual void    fetchResults(PxBroadPhaseResults& results)  = 0;

        PX_FORCE_INLINE void    update(PxBroadPhaseResults& results)
        {
            update();
            fetchResults(results);
        }
    };

    PX_C_EXPORT PX_PHYSX_CORE_API   PxAABBManager*  PxCreateAABBManager(PxBroadPhase& broadphase);

#if !PX_DOXYGEN
} // namespace physx
#endif

#endif