hx3d  1
2D/3D Simple Game Framework
engine.inl.hpp
1 /*
2  Entity Component System: Base Engine.
3  Copyright (C) 2015 Denis BOURGE
4 
5  This library is free software; you can redistribute it and/or
6  modify it under the terms of the GNU Lesser General Public
7  License as published by the Free Software Foundation; either
8  version 2.1 of the License, or (at your option) any later version.
9 
10  This library is distributed in the hope that it will be useful,
11  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13  Lesser General Public License for more details.
14 
15  You should have received a copy of the GNU Lesser General Public
16  License along with this library; if not, write to the Free Software
17  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301
18  USA
19 */
20 
21 namespace hx3d {
22 namespace ecs {
23 
24 template <class T>
26  if (_components.find(entity->getId()) == _components.end()) {
27  Log.Error("No entity %ld", entity->getId());
28  return nullptr;
29  }
30 
31  std::map<std::type_index, Ptr<Component>>& compMap = _components[entity->getId()];
32  if (compMap.find(typeid(T)) == compMap.end()) {
33  Log.Error("No component of type %s in entity %ld", typeid(T).name(), entity->getId());
34  return nullptr;
35  }
36 
37  const Ptr<Component>& component = compMap[typeid(T)];
38  return std::dynamic_pointer_cast<T>(component);
39 }
40 
41 template <class T>
42 void Engine::addComponent(const Ptr<Entity>& entity, const Ptr<Component>& component) {
43  addInternalComponent<T>(entity->getId(), component);
44 }
45 
46 template <class T, class... Args>
47 void Engine::createComponent(const Ptr<Entity>& entity, Args... args) {
48  addInternalComponent<T>(entity->getId(), Make<T>(args...));
49 }
50 
51 template <class T>
52 void Engine::addInternalComponent(const unsigned int entityId, const Ptr<Component>& component) {
53 
54  const auto& type = typeid(T);
55 
56  if (_components.find(entityId) == _components.end()) {
57  Log.Error("No entity %ld", entityId);
58  return;
59  }
60 
61  std::map<std::type_index, Ptr<Component>>& compMap = _components[entityId];
62 
63  // Already a component from this type
64  if (compMap.find(type) != compMap.end()) {
65  if (_onComponentRemoved.find(type) != _onComponentRemoved.end()) {
66  _onComponentRemoved[type](compMap[type], _entities[entityId]);
67  }
68  }
69 
70  compMap[type] = component;
71  _bits[entityId].set(ComponentBits::get<T>());
72 
73  if (_onComponentAdded.find(type) != _onComponentAdded.end()) {
74  auto& func = _onComponentAdded[type];
75  func(component, _entities[entityId]);
76  }
77 }
78 
79 template <class T>
80 void Engine::addSystem(const Ptr<System>& sys) {
81  const auto& type = typeid(T);
82 
83  _systems[type] = sys;
84  _systems[type]->_engine = this;
85 }
86 
87 template <class T, class... Args>
88 void Engine::createSystem(Args... args) {
89  const auto& type = typeid(T);
90 
91  _systems[type] = Make<T>(args...);
92  _systems[type]->_engine = this;
93 }
94 
95 template <class T>
96 void Engine::registerComponentAdded(std::function<void(const Ptr<Component>&, const Ptr<Entity>&)> callback) {
97  _onComponentAdded[typeid(T)] = callback;
98 }
99 
100 template <class T>
101 void Engine::registerComponentRemoved(std::function<void(const Ptr<Component>&, const Ptr<Entity>&)> callback) {
102  _onComponentRemoved[typeid(T)] = callback;
103 }
104 
105 }
106 }
void createSystem(Args...args)
Create a system into the engine.
Definition: engine.inl.hpp:88
hx3d framework namespace
Definition: audio.hpp:26
void registerComponentAdded(std::function< void(const Ptr< Component > &, const Ptr< Entity > &)> callback)
Register a callback for a certain component type when it&#39;s added.
Definition: engine.inl.hpp:96
void addComponent(const Ptr< Entity > &entity, const Ptr< Component > &component)
Add a component for an entity.
Definition: engine.inl.hpp:42
void Error(const std::string fmt,...)
Write an error message.
Definition: log.cpp:72
static hx3d::LogImpl Log
Current log implementation.
Definition: log.hpp:91
void createComponent(const Ptr< Entity > &entity, Args...args)
Create a component for an entity with variable args.
Definition: engine.inl.hpp:47
void registerComponentRemoved(std::function< void(const Ptr< Component > &, const Ptr< Entity > &)> callback)
Register a callback for a certain component type when it&#39;s removed.
Definition: engine.inl.hpp:101
std::shared_ptr< T > Ptr
Quick-typing shared ptr.
Definition: ptr.hpp:34
Ptr< T > getComponent(const Ptr< Entity > &entity)
Get the component for an entity.
Definition: engine.inl.hpp:25
void addSystem(const Ptr< System > &sys)
Add a system to the engine.
Definition: engine.inl.hpp:80