在 C ++ 中实现组件模式,我遇到了与includes相关的问题。
我有一个Entity
类,其中包含以下组件:Renderer
,Physics
和Collider
。它们继承自Component
,它具有单个虚拟方法Component->update(elapsedTime)
以及对其所属的Entity
的引用。
每次更新Entity
时,其组件也会更新。当组件改变Entity
的状态时,我认为让他们引用他们所属的Entity
是一个好主意(我可以通过Entity
作为Component->update()
调用中的参数,但对于性能我不喜欢这样做。
现在,我必须在Renderer
中添加Physics
,Collider
和Entity
,并在Entity
中添加Component
。幸运的是,Entity
调用上述方法,但Component
只存储对Entity
的引用,因此我应该正常包含Renderer
,Physics
和{{1}来自Collider
,并从Entity
转发声明Entity
。在这样做之后,我发现了一个我无法解决或知道如何调查的问题。所以我尝试了另一种方式,其他问题也出现了。
Component
的{{1}},Renderer
和Physics
,以及来自Collider
的转发声明Entity
:包含Entity
的类会抱怨说Component
含糊不清。这是因为(我认为)该类加载Entity
,然后加载其前向声明Entity
的{{1}}。如何在不让其他课程抱怨这种歧义的情况下转发声明Entity
?
Component
,并从Entity
转发声明Entity
,Entity
和Component
:在我的Renderer
方法中,Physics
通过说 Collider
来打破{。}}。
如何在不改变课堂结构或行为的情况下解决这个问题?
以下是文件,使用第一个示例(包括来自Entity
的组件和转发声明Entity->update()
:
this->collision->update()
pointer to incomplete class is not allowed
Entity
Component
Entity.h
#ifndef ENTITY_H
#define ENTITY_H
#include "Collision.h"
#include "Physics.h"
#include "Renderer.h"
#include "TextureRenderer.h"
using namespace Components;
namespace Entities
{
class Entity
{
public:
Entity();
Collision* getCollision();
virtual void update(float elapsedTime);
protected:
Collision* collision;
Physics* physics;
Renderer* renderer;
};
}
#endif
Entity.cpp
#include "Entity.h"
namespace Entities
{
Entity::Entity()
{
}
Collision* Entity::getCollision()
{
return this->collision;
}
void Entity::update(float elapsedTime)
{
collision->update(elapsedTime);
physics->update(elapsedTime);
renderer->update(elapsedTime);
}
}
Component.h
#ifndef COMPONENT_H
#define COMPONENT_H
namespace Components
{
class Component
{
public:
Component(Entity* entity);
virtual void update(float elapsedTime) = 0;
protected:
Entity* entity;
private:
friend class Entity;
};
}
#endif
Component.cpp
#include "Component.h"
#include "Entity.h"
namespace Components
{
Component::Component(Entity* entity)
{
this->entity = entity;
}
}
Collision.h
#ifndef COLLISION_H
#define COLLISION_H
#include "Component.h"
namespace Components
{
class Collision : public Component
{
public:
void collide(Entity* entity);
protected:
virtual bool collidesWith(Entity* entity) = 0;
};
}
#endif
Collision.cpp
#include "Collision.h"
namespace Components
{
void Collision::collide(Entity* entity)
{
if (this->collidesWith(entity))
{
...
}
}
}
并且Renderer.h
几乎是空的,我现在不想添加它。
非常感谢
我已经解决了很多包含问题的方法。出于性能原因,我的代码进行了大量的双重引用,每对类都访问彼此的方法。 C ++讨厌这个,并且定义哪个类应该向前声明另一个是屁股的痛苦。