reactphysics3d/src/engine/Entity.h
2019-03-25 18:47:42 +01:00

145 lines
5.6 KiB
C++

/********************************************************************************
* ReactPhysics3D physics library, http://www.reactphysics3d.com *
* Copyright (c) 2010-2018 Daniel Chappuis *
*********************************************************************************
* *
* This software is provided 'as-is', without any express or implied warranty. *
* In no event will the authors be held liable for any damages arising from the *
* use of this software. *
* *
* Permission is granted to anyone to use this software for any purpose, *
* including commercial applications, and to alter it and redistribute it *
* freely, subject to the following restrictions: *
* *
* 1. The origin of this software must not be misrepresented; you must not claim *
* that you wrote the original software. If you use this software in a *
* product, an acknowledgment in the product documentation would be *
* appreciated but is not required. *
* *
* 2. Altered source versions must be plainly marked as such, and must not be *
* misrepresented as being the original software. *
* *
* 3. This notice may not be removed or altered from any source distribution. *
* *
********************************************************************************/
#ifndef REACTPHYSICS3D_ENTITY_H
#define REACTPHYSICS3D_ENTITY_H
// Libraries
#include "configuration.h"
/// Namespace reactphysics3d
namespace reactphysics3d {
// Structure Entity
/**
* This class is used to identify an entity in the Entity-Component-System.
* Entities are used for bodies in the physics engine. The id of an entity is
* a 32 bits integer that is separated in two parts. The index and the generation
* parts. The idea is that the index part directly gives us the index of the entity
* in a lookup array. However, we want to support deletion of the entities. That's why
* we have the generation part. This number is used to distinguish the entities created
* at the same index in the array. If it is the case, we will increase the generation number
* each time.
*
* We use 24 bits for the index. Therefore, we support 16 millions simultaneous entries.
* We use 8 bits for the generation. Therefore, we support 256 entries created at the same index.
* To prevent reaching the 256 entries too fast, we make sure that we do not reuse the same index
* slot too ofen. To do that, we put recycled indices in a queue and only reuse values from that
* queue when it contains at least MINIMUM_FREE_INDICES values. It means, an id will reappear until
* its index has run 256 laps through the queue. It means that we must create and destroy at least
* 256 * MINIMUM_FREE_INDICES entities until an id can reappear. This seems reasonably safe.
*
* This implementation is based on the following article:
* http://bitsquid.blogspot.com/2014/08/building-data-oriented-entity-system.html
*/
struct Entity {
private:
/// Number of bits reserved for the index
static const uint32 ENTITY_INDEX_BITS;
/// Mask for the index part of the id
static const uint32 ENTITY_INDEX_MASK;
/// Number of bits reserved for the generation number
static const uint32 ENTITY_GENERATION_BITS;
/// Mask for the generation part of the id
static const uint32 ENTITY_GENERATION_MASK;
/// Minimum of free indices in the queue before we reuse one from the queue
static const uint32 MINIMUM_FREE_INDICES;
public:
// -------------------- Attributes -------------------- //
/// Id of the entity
uint32 id;
// -------------------- Methods -------------------- //
/// Constructor
Entity(uint32 index, uint32 generation);
/// Return the lookup index of the entity in a array
uint32 getIndex() const;
/// Return the generation number of the entity
uint32 getGeneration() const;
/// Assignment operator
Entity& operator=(const Entity& entity);
/// Equality operator
bool operator==(const Entity& entity) const;
/// Inequality operator
bool operator!=(const Entity& entity) const;
// -------------------- Friendship -------------------- //
friend class EntityManager;
};
// Return the lookup index of the entity in a array
inline uint32 Entity::getIndex() const {
return id & ENTITY_INDEX_MASK;
}
// Return the generation number of the entity
inline uint32 Entity::getGeneration() const {
return (id >> ENTITY_INDEX_BITS) & ENTITY_GENERATION_MASK;
}
// Equality operator
inline bool Entity::operator==(const Entity& entity) const {
return entity.id == id;
}
// Inequality operator
inline bool Entity::operator!=(const Entity& entity) const {
return entity.id != id;
}
}
// Hash function for a reactphysics3d Entity
namespace std {
template <> struct hash<reactphysics3d::Entity> {
size_t operator()(const reactphysics3d::Entity& entity) const {
return entity.id;
}
};
}
#endif