+#include "part.h"
#include "partcache.h"
+using namespace std;
+
namespace Msp {
namespace GLtk {
-CachedPart::CachedPart():
- texture(0),
- mesh(0)
-{ }
+CachedPart::CachedPart(CachedPart &&other):
+ part(other.part),
+ texture(other.texture),
+ mesh(other.mesh)
+{
+ other.mesh = nullptr;
+}
+
+CachedPart &CachedPart::operator=(CachedPart &&other)
+{
+ delete mesh;
+ part = other.part;
+ texture = other.texture;
+ mesh = other.mesh;
+ other.mesh = nullptr;
+ return *this;
+}
CachedPart::~CachedPart()
{
delete mesh;
}
-void CachedPart::clear_mesh()
+
+void PartCache::begin_rebuild()
{
- if(!mesh)
- mesh = new GL::Mesh((GL::TEXCOORD2, GL::COLOR4_UBYTE, GL::VERTEX2));
+ if(rebuilding)
+ throw logic_error("nested rebuild");
+ rebuilding = true;
+
+ next = parts.begin();
+ current = parts.end();
+}
+
+void PartCache::insert_special(const Part &part)
+{
+ if(part.get_name().empty())
+ throw invalid_argument("PartCache::insert_special");
+ if(!rebuilding)
+ throw logic_error("!rebuilding");
+
+ current = find_if(next, parts.end(), [&part](const CachedPart &p){ return p.part==∂ });
+ if(current!=parts.end())
+ parts.erase(next, current);
+
+ if(current==parts.end())
+ current = parts.insert(next, CachedPart());
else
- mesh->clear();
+ *current = CachedPart();
+ current->part = ∂
+
+ next = current;
+ ++next;
+}
+
+GL::Mesh &PartCache::create_mesh(const Part &part, const GL::Texture2D &tex)
+{
+ if(!rebuilding)
+ throw logic_error("!rebuilding");
+
+ if(current!=parts.end() && current->texture==&tex)
+ return *current->mesh;
+
+ for(current=next; current!=parts.end(); ++current)
+ if(current->texture==&tex)
+ {
+ parts.erase(next, current);
+ break;
+ }
+
+ if(current==parts.end())
+ {
+ current = parts.insert(next, CachedPart());
+ current->texture = &tex;
+ current->mesh = new GL::Mesh((GL::TEXCOORD2, GL::COLOR4,GL::UNSIGNED_BYTE, GL::VERTEX2));
+ }
+ else
+ current->mesh->clear();
+ current->part = ∂
+
+ next = current;
+ ++next;
+
+ return *current->mesh;
+}
+
+void PartCache::end_rebuild()
+{
+ rebuilding = false;
+ parts.erase(next, parts.end());
}
} // namespace GLtk