Classe BoundingVolumeTrigger pour vos triggers

1

Intro :

Dans un jeu vidéo on doit utiliser beaucoup de bounding boxes pour déclencher certains événements.

Prérequis :

Si vous ne savez pas ce qu’est une Bounding Box : se référer à l’article traitant les Bounding Boxes.
Si vous ne savez pas ce qu’est un Event : se référer à l’article traitant les Events.

Utilisation :

Par exemple lorsque que le joueur entre dans une nouvelle zone, on a besoin de tester deux bounding boxes : celle du joueur et celle du trigger (déclencheur), pour ensuite faire appel à l’événement (Event) associé.

Voici une classe à copier pour implémenter le mécanisme de triggers dans vos jeux.

Dans le fichier .h :


#ifndef BOUNDING_BOX_TRIGGER_H
#define BOUNDING_BOX_TRIGGER_H

class BoundingVolumeTrigger
{
public:
    BoundingVolumeTrigger(const Ogre::AxisAlignedBox& BV);
    virtual ~BoundingVolumeTrigger();

    // AABB / Sphere principale à tester
    void registerMainCheckedBV(const Ogre::AxisAlignedBox& BV);

    // Les AABB / Sphere sur lequels sont testées les intersections de AABB / Sphere
    void registerBoundingBox(const Ogre::AxisAlignedBox& BV);    

    // Les events à invoquer lors d'une collision
    void registerEvent(Event* pEvent);

    bool checkCollision();

    // Met à jour les vérification de déclenchement (triggering)
    void update();

private:
    Ogre::AxisAlignedBox m_testedAABB;

    std::vector<const Ogre::AxisAlignedBox> m_boundingBoxesToTest;

    std::vector<Event*> m_pCollisionEvents;

    bool m_bTriggerDone;
};

#endif

Dans le fichier .cpp :


BoundingVolumeTrigger::BoundingVolumeTrigger(const Ogre::AxisAlignedBox& BV)
{
    m_bTriggerDone = false;
    m_testedAABB = BV;
}

BoundingVolumeTrigger::~BoundingVolumeTrigger()
{
}

void BoundingVolumeTrigger::registerMainCheckedBV(const Ogre::AxisAlignedBox& BV)
{
    m_testedAABB = BV;
}

void BoundingVolumeTrigger::registerBoundingBox(const Ogre::AxisAlignedBox& BV)
{
    m_boundingBoxesToTest.push_back(BV);
}

void BoundingVolumeTrigger::registerBoundingSphere(const Ogre::Sphere& BV)
{
    m_boundingSpheresToTest.push_back(BV);
}

void BoundingVolumeTrigger::registerEvent(Event* pEvent)
{
    m_pCollisionEvents.push_back(pEvent);
}

void BoundingVolumeTrigger::update()
{
    bool bColision = checkCollision();

    // Invoque tous les events associés à la collision
    if (bColision && !m_bTriggerDone)
    {
        for (unsigned int i = 0; i < m_pCollisionEvents.size(); i++)
        {
            Event* pEvent = m_pCollisionEvents[i];
            
            pEvent->trigger();
        }

        m_bTriggerDone = true;
    }
}

bool BoundingVolumeTrigger::checkCollision()
{
    bool collided = false;

    // AABB à tester
    for (unsigned int i = 0; i < m_boundingBoxesToTest.size(); i++)
    {
        if (m_testedAABB.contains(m_boundingBoxesToTest[i]))
        {
            collided = true;

        }
    }

    return collided;
}

La variable m_bTriggerDone restreint l’invocation du déclencheur à un seul appel par rencontre
de collision.

Résumé : 

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *