グラフィックエンジンで作業しています。エンジンはドロワーブルのstd::vector
を持っています。 Drawableは、ModelとDrawableObjectを含むオブジェクトで、2Dまたは3Dモデルからシェーダプログラムとバンチ頂点を保持します。新しいDrawableを追加するとうまくいきます。Drawableを削除しようとすると問題が発生します。最後のDrawableは常に削除され、最後のDrawableはその値が変更されます。std :: eraseを正常に使用したメソッドを離れると間違った要素が削除される
コード
Drawable.h
class Drawable
{
public:
Drawable& operator=(const Drawable& other)
{
Drawable tmp(other);
std::swap(model, other.model);
std::swap(drawableObject, other.drawableObject);
return *this;
}
Drawable(domain::Model& model, DrawableObject& drawableObject) :
model(model),
drawableObject(drawableObject)
{}
domain::Model& model;
DrawableObject& drawableObject;
};
game.cpp
void Game::init_game()
{
human = domain::Model(glm::vec3(0, 0, -3));
moveables.push_back(&human);
room = domain::Model(glm::vec3(0, 0, -10));
props.push_back(&room);
cube = domain::Model(glm::vec3(0, 0, 0));
props.push_back(&cube);
}
void Game::init_graphics_engine()
{
// ... load graphics models
// add drawables
graphicsEngine->add(cube, Drawable::CUBE);
graphicsEngine->add(human, Drawable::HUMAN);
graphicsEngine->add(room, Drawable::ROOM);
graphicsEngine->add(topDownScene->cursor, Drawable::MARKER);
}
graphics_engine/engine.cpp
void Engine::add(domain::Model& model, unsigned int object)
{
auto drawableObject = drawableObjects[object];
// make sure not to add a model that already is represented
auto it = std::find_if(drawables.begin(), drawables.end(), [&model](Drawable& drawable) {return &drawable.model == &model;});
if(drawableObject && it == drawables.end())
drawables.push_back(Drawable(model, *drawableObject));
}
void Engine::remove(domain::Model& model)
{
auto predicate = [&model](Drawable& drawable)
{
return &drawable.model == &model;
};
drawables.erase(std::remove_if(drawables.begin(), drawables.end(), predicate), drawables.end());
}
シーン
これは私がアプリケーションを起動したときにシーンがどのように見えるかです:
このシーンは、小さな「人間のキューブを消去しようとした後、次のようになりますミドル:
コードがある最後のDrawableのを、削除します白いマーカを使用し、部屋のz位置を変更しました。これはほとんどの場合起こります。最後の要素を削除し、2番目の要素を最後に変更しました。 initメソッドの最後に '人間'のキューブを追加すると機能します。オブジェクトを削除する前に
ブレーク
:
オブジェクトを除去した後:
これは正しいです。
removeメソッドを残してレンダリングループで見てみる:
はどういうわけか変更。
コピー代入演算子が右辺を修正するのを待ちますか? 'tmp'とは何ですか? – NPE
@NPE [コピー&スワップイディオム](https://stackoverflow.com/questions/3279543/what-is-the-copy-and-swap-idiom) – LogicStuff
@LogicStuff:これは、私が想像していることですが、あなたがコードをよく読んでも意味がありません。(私が何かを見逃していない限り、もちろん可能性もあります)。 – NPE