Adapted ECS for building instances
This commit is contained in:
@@ -1,3 +1,5 @@
|
|||||||
|
#undef NDEBUG
|
||||||
|
#include <cassert>
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <core/os/memory.h>
|
#include <core/os/memory.h>
|
||||||
#include <core/io/json.h>
|
#include <core/io/json.h>
|
||||||
@@ -19,7 +21,12 @@ struct scene_data {
|
|||||||
Ref<PackedScene> packed_scene;
|
Ref<PackedScene> packed_scene;
|
||||||
String path;
|
String path;
|
||||||
Ref<ResourceInteractiveLoader> loader;
|
Ref<ResourceInteractiveLoader> loader;
|
||||||
std::vector<String> buildings;
|
// std::vector<String> buildings;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct CBuildingInstance {
|
||||||
|
String key;
|
||||||
|
Node *node;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct CSceneData {
|
struct CSceneData {
|
||||||
@@ -426,11 +433,28 @@ void BuildingsData::remove_scene_item(const String &key, const String &bkey)
|
|||||||
assert(e.is_valid());
|
assert(e.is_valid());
|
||||||
CSceneData *d = e.get_mut<CSceneData>();
|
CSceneData *d = e.get_mut<CSceneData>();
|
||||||
assert(d);
|
assert(d);
|
||||||
|
#if 0
|
||||||
std::vector<String>::iterator b = d->sd.buildings.begin();
|
std::vector<String>::iterator b = d->sd.buildings.begin();
|
||||||
std::vector<String>::iterator h = d->sd.buildings.end();
|
std::vector<String>::iterator h = d->sd.buildings.end();
|
||||||
// if (item_nodes.has(item))
|
// if (item_nodes.has(item))
|
||||||
// item_nodes[item]->queue_delete();
|
// item_nodes[item]->queue_delete();
|
||||||
d->sd.buildings.erase(std::remove(b, h, bkey), d->sd.buildings.end());
|
d->sd.buildings.erase(std::remove(b, h, bkey), d->sd.buildings.end());
|
||||||
|
#endif
|
||||||
|
flecs::query_builder<const CBuildingInstance> qb =
|
||||||
|
ecs.query_builder<const CBuildingInstance>().with(
|
||||||
|
flecs::ChildOf, e);
|
||||||
|
flecs::query<const CBuildingInstance> q = qb.build();
|
||||||
|
uint64_t key_hash = bkey.hash64();
|
||||||
|
flecs::entity em = q.find([key_hash](const CBuildingInstance &bi) {
|
||||||
|
return bi.key.hash64() == key_hash;
|
||||||
|
});
|
||||||
|
if (em.is_valid()) {
|
||||||
|
CBuildingInstance *bi = em.get_mut<CBuildingInstance>();
|
||||||
|
if (bi->node)
|
||||||
|
bi->node->queue_delete();
|
||||||
|
bi->node = nullptr;
|
||||||
|
em.destruct();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void BuildingsData::add_scene_item(const String &key, const String &bkey)
|
void BuildingsData::add_scene_item(const String &key, const String &bkey)
|
||||||
@@ -439,9 +463,19 @@ void BuildingsData::add_scene_item(const String &key, const String &bkey)
|
|||||||
assert(e.is_valid());
|
assert(e.is_valid());
|
||||||
CSceneData *d = e.get_mut<CSceneData>();
|
CSceneData *d = e.get_mut<CSceneData>();
|
||||||
assert(d);
|
assert(d);
|
||||||
|
#if 0
|
||||||
if (std::find(d->sd.buildings.begin(), d->sd.buildings.end(), bkey) ==
|
if (std::find(d->sd.buildings.begin(), d->sd.buildings.end(), bkey) ==
|
||||||
d->sd.buildings.end())
|
d->sd.buildings.end())
|
||||||
d->sd.buildings.push_back(bkey);
|
d->sd.buildings.push_back(bkey);
|
||||||
|
#endif
|
||||||
|
String ename = "bi:" + bkey;
|
||||||
|
flecs::entity ce = e.lookup(ename.ascii().ptr());
|
||||||
|
if (ce.is_valid())
|
||||||
|
ce.destruct();
|
||||||
|
ce = ecs.entity(ename.ascii().ptr());
|
||||||
|
ce.child_of(e);
|
||||||
|
ce.set<CBuildingInstance>({ bkey, nullptr });
|
||||||
|
print_line("child name: " + String(ce.name()));
|
||||||
}
|
}
|
||||||
|
|
||||||
void BuildingsData::create_scene_data(const String &key, const String &bkey)
|
void BuildingsData::create_scene_data(const String &key, const String &bkey)
|
||||||
@@ -454,11 +488,21 @@ void BuildingsData::create_scene_data(const String &key, const String &bkey)
|
|||||||
sd.path = path;
|
sd.path = path;
|
||||||
sd.loader = ResourceLoader::load_interactive(
|
sd.loader = ResourceLoader::load_interactive(
|
||||||
path, "PackedScene", true);
|
path, "PackedScene", true);
|
||||||
|
#if 0
|
||||||
if (std::find(sd.buildings.begin(), sd.buildings.end(), bkey) ==
|
if (std::find(sd.buildings.begin(), sd.buildings.end(), bkey) ==
|
||||||
sd.buildings.end())
|
sd.buildings.end())
|
||||||
sd.buildings.push_back(bkey);
|
sd.buildings.push_back(bkey);
|
||||||
|
#endif
|
||||||
e.set<CSceneData>({ sd });
|
e.set<CSceneData>({ sd });
|
||||||
assert(e.get_mut<CSceneData>());
|
assert(e.get_mut<CSceneData>());
|
||||||
|
String ename = "bi:" + bkey;
|
||||||
|
flecs::entity ce = e.lookup(ename.ascii().ptr());
|
||||||
|
if (ce.is_valid())
|
||||||
|
ce.destruct();
|
||||||
|
ce = ecs.entity(ename.ascii().ptr());
|
||||||
|
ce.child_of(e);
|
||||||
|
ce.set<CBuildingInstance>({ bkey, nullptr });
|
||||||
|
print_line("child name: " + String(ce.name()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -485,46 +529,183 @@ int BuildingsData::scene_get_item_count(const String &key) const
|
|||||||
assert(e.is_valid());
|
assert(e.is_valid());
|
||||||
const CSceneData *d = e.get<CSceneData>();
|
const CSceneData *d = e.get<CSceneData>();
|
||||||
assert(d);
|
assert(d);
|
||||||
return d->sd.buildings.size();
|
// return d->sd.buildings.size();
|
||||||
|
flecs::query_builder<const CBuildingInstance> qb =
|
||||||
|
ecs.query_builder<const CBuildingInstance>().with(
|
||||||
|
flecs::ChildOf, e);
|
||||||
|
flecs::query<const CBuildingInstance> q = qb.build();
|
||||||
|
int result;
|
||||||
|
q.run([&result](flecs::iter &it) {
|
||||||
|
it.next();
|
||||||
|
result = it.count();
|
||||||
|
it.fini();
|
||||||
|
});
|
||||||
|
// assert(result == d->sd.buildings.size());
|
||||||
|
print_line("scene_get_item_count: " + itos(result));
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
List<String> BuildingsData::scene_get_items(const String &key) const
|
||||||
String BuildingsData::scene_get_item(const String &key, int index) const
|
|
||||||
{
|
{
|
||||||
|
List<String> ret;
|
||||||
|
int i;
|
||||||
flecs::entity e = ecs.lookup(key.ascii().ptr());
|
flecs::entity e = ecs.lookup(key.ascii().ptr());
|
||||||
if (!e.is_valid())
|
if (!e.is_valid())
|
||||||
return "";
|
return List<String>();
|
||||||
if (!e.get<CSceneData>())
|
if (!e.get<CSceneData>())
|
||||||
return "";
|
return List<String>();
|
||||||
assert(e.is_valid());
|
assert(e.is_valid());
|
||||||
const CSceneData *d = e.get<CSceneData>();
|
const CSceneData *d = e.get<CSceneData>();
|
||||||
assert(d);
|
assert(d);
|
||||||
return d->sd.buildings[index];
|
flecs::query_builder<const CBuildingInstance> qb =
|
||||||
|
ecs.query_builder<const CBuildingInstance>().with(
|
||||||
|
flecs::ChildOf, e);
|
||||||
|
flecs::query<const CBuildingInstance> q = qb.build();
|
||||||
|
q.each([&ret](flecs::entity me, const CBuildingInstance &ib) {
|
||||||
|
ret.push_back(ib.key);
|
||||||
|
});
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
void BuildingsData::set_scene_item_node(const String &key, const String &bkey,
|
||||||
|
Node *node)
|
||||||
|
{
|
||||||
|
flecs::entity e = ecs.lookup(key.ascii().ptr());
|
||||||
|
assert(e.is_valid());
|
||||||
|
CSceneData *d = e.get_mut<CSceneData>();
|
||||||
|
assert(d);
|
||||||
|
#if 0
|
||||||
|
if (std::find(d->sd.buildings.begin(), d->sd.buildings.end(), bkey) ==
|
||||||
|
d->sd.buildings.end())
|
||||||
|
d->sd.buildings.push_back(bkey);
|
||||||
|
#endif
|
||||||
|
String ename = "bi:" + bkey;
|
||||||
|
flecs::entity ce = e.lookup(ename.ascii().ptr());
|
||||||
|
assert(ce.is_valid());
|
||||||
|
CBuildingInstance *bi = ce.get_mut<CBuildingInstance>();
|
||||||
|
assert(bi);
|
||||||
|
assert(bi->key == bkey);
|
||||||
|
bi->node = node;
|
||||||
|
}
|
||||||
|
bool BuildingsData::has_scene_item(const String &key, const String &bkey) const
|
||||||
|
{
|
||||||
|
flecs::entity e = ecs.lookup(key.ascii().ptr());
|
||||||
|
assert(e.is_valid());
|
||||||
|
CSceneData *d = e.get_mut<CSceneData>();
|
||||||
|
assert(d);
|
||||||
|
String ename = "bi:" + bkey;
|
||||||
|
flecs::entity ce = e.lookup(ename.ascii().ptr());
|
||||||
|
return ce.is_valid();
|
||||||
|
}
|
||||||
|
Node *BuildingsData::get_scene_item_node(const String &key,
|
||||||
|
const String &bkey) const
|
||||||
|
{
|
||||||
|
flecs::entity e = ecs.lookup(key.ascii().ptr());
|
||||||
|
assert(e.is_valid());
|
||||||
|
CSceneData *d = e.get_mut<CSceneData>();
|
||||||
|
assert(d);
|
||||||
|
String ename = "bi:" + bkey;
|
||||||
|
flecs::entity ce = e.lookup(ename.ascii().ptr());
|
||||||
|
assert(ce.is_valid());
|
||||||
|
CBuildingInstance *bi = ce.get_mut<CBuildingInstance>();
|
||||||
|
assert(bi);
|
||||||
|
assert(bi->key == bkey);
|
||||||
|
return bi->node;
|
||||||
}
|
}
|
||||||
|
|
||||||
void BuildingsData::item_nodes_delete_node(const String &key)
|
void BuildingsData::item_nodes_delete_node(const String &key)
|
||||||
{
|
{
|
||||||
|
#if 0
|
||||||
if (item_nodes.has(key)) {
|
if (item_nodes.has(key)) {
|
||||||
item_nodes[key]->queue_delete();
|
item_nodes[key]->queue_delete();
|
||||||
item_nodes.erase(key);
|
item_nodes.erase(key);
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
flecs::query_builder<const CBuildingInstance> qb =
|
||||||
|
ecs.query_builder<const CBuildingInstance>();
|
||||||
|
flecs::query<const CBuildingInstance> q = qb.build();
|
||||||
|
uint64_t key_hash = key.hash64();
|
||||||
|
flecs::entity e = q.find(
|
||||||
|
[key_hash](flecs::entity me, const CBuildingInstance &ib) {
|
||||||
|
return ib.key.hash64() == key_hash;
|
||||||
|
});
|
||||||
|
assert(e.is_valid());
|
||||||
|
CBuildingInstance *ib = e.get_mut<CBuildingInstance>();
|
||||||
|
if (ib->node)
|
||||||
|
ib->node->queue_delete();
|
||||||
|
ib->node = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if 0
|
||||||
bool BuildingsData::item_nodes_exists(const String &key) const
|
bool BuildingsData::item_nodes_exists(const String &key) const
|
||||||
{
|
{
|
||||||
|
#if 0
|
||||||
|
bool result = false;
|
||||||
return item_nodes.has(key);
|
return item_nodes.has(key);
|
||||||
|
flecs::query_builder<const CBuildingInstance> qb =
|
||||||
|
ecs.query_builder<const CBuildingInstance>();
|
||||||
|
flecs::query<const CBuildingInstance> q = qb.build();
|
||||||
|
uint64_t key_hash = key.hash64();
|
||||||
|
q.run([key_hash, &result](flecs::iter &it) {
|
||||||
|
while (it.next()) {
|
||||||
|
auto em = it.field<flecs::entity>(0);
|
||||||
|
auto ib = it.field<const CBuildingInstance>(1);
|
||||||
|
if (ib->key.hash64() == key_hash) {
|
||||||
|
result = true;
|
||||||
|
it.fini();
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return result;
|
||||||
|
#endif
|
||||||
|
String ename = "bi:" + key;
|
||||||
|
flecs::entity ce = ecs.lookup(ename.ascii().ptr());
|
||||||
|
bool result = ce.is_valid();
|
||||||
|
if (!result)
|
||||||
|
return result;
|
||||||
|
const CBuildingInstance *bi = ce.get<CBuildingInstance>();
|
||||||
|
if (!bi)
|
||||||
|
return false;
|
||||||
|
if (bi->node)
|
||||||
|
return true;
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
void BuildingsData::item_nodes_set_node(const String &key, Node *node)
|
void BuildingsData::item_nodes_set_node(const String &key, Node *node)
|
||||||
{
|
{
|
||||||
item_nodes[key] = node;
|
item_nodes[key] = node;
|
||||||
|
String ename = "bi:" + key;
|
||||||
|
print_line(ename);
|
||||||
|
flecs::entity ce = ecs.lookup(ename.ascii().ptr());
|
||||||
|
assert(ce.is_valid());
|
||||||
|
CBuildingInstance *bi = ce.get_mut<CBuildingInstance>();
|
||||||
|
assert(bi);
|
||||||
|
bi->node = node;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
void BuildingsData::item_nodes_item_removed(const String &key)
|
void BuildingsData::item_nodes_item_removed(const String &key)
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
|
#if 0
|
||||||
if (item_nodes[key])
|
if (item_nodes[key])
|
||||||
item_nodes[key]->queue_delete();
|
item_nodes[key]->queue_delete();
|
||||||
item_nodes.erase(key);
|
item_nodes.erase(key);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
flecs::query_builder<const CBuildingInstance> qb =
|
||||||
|
ecs.query_builder<const CBuildingInstance>();
|
||||||
|
flecs::query<const CBuildingInstance> q = qb.build();
|
||||||
|
Node *ret;
|
||||||
|
uint64_t key_hash = key.hash64();
|
||||||
|
flecs::entity e = q.find([key_hash](const CBuildingInstance &bi) {
|
||||||
|
return bi.key.hash64() == key_hash;
|
||||||
|
});
|
||||||
|
assert(e.is_valid());
|
||||||
|
CBuildingInstance *bi = e.get_mut<CBuildingInstance>();
|
||||||
|
assert(bi);
|
||||||
|
if (bi->node) {
|
||||||
|
bi->node->queue_delete();
|
||||||
|
}
|
||||||
|
bi->node = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
String BuildingsData::item_nodes_get_key(int item) const
|
String BuildingsData::item_nodes_get_key(int item) const
|
||||||
@@ -532,11 +713,34 @@ String BuildingsData::item_nodes_get_key(int item) const
|
|||||||
return buildings[item].key;
|
return buildings[item].key;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if 0
|
||||||
Node *BuildingsData::item_nodes_get_node(const String &key) const
|
Node *BuildingsData::item_nodes_get_node(const String &key) const
|
||||||
{
|
{
|
||||||
if (!item_nodes_exists(key))
|
if (!item_nodes_exists(key))
|
||||||
return nullptr;
|
return nullptr;
|
||||||
return item_nodes[key];
|
// return item_nodes[key];
|
||||||
|
String ename = "bi:" + key;
|
||||||
|
flecs::entity ce = ecs.lookup(ename.ascii().ptr());
|
||||||
|
assert(ce.is_valid());
|
||||||
|
CBuildingInstance *bi = ce.get_mut<CBuildingInstance>();
|
||||||
|
assert(bi);
|
||||||
|
return bi->node;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
Node *BuildingsData::item_nodes_get_node(const String &key) const
|
||||||
|
{
|
||||||
|
flecs::query_builder<const CBuildingInstance> qb =
|
||||||
|
ecs.query_builder<const CBuildingInstance>();
|
||||||
|
flecs::query<const CBuildingInstance> q = qb.build();
|
||||||
|
Node *ret;
|
||||||
|
uint64_t key_hash = key.hash64();
|
||||||
|
flecs::entity e = q.find([key_hash](const CBuildingInstance &bi) {
|
||||||
|
return bi.key.hash64() == key_hash;
|
||||||
|
});
|
||||||
|
if (e.is_valid())
|
||||||
|
return e.get<CBuildingInstance>()->node;
|
||||||
|
else
|
||||||
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
Error BuildingsData::scene_loader_poll(const String &key)
|
Error BuildingsData::scene_loader_poll(const String &key)
|
||||||
|
|||||||
@@ -33,12 +33,17 @@ public:
|
|||||||
void create_scene_data(const String &key, const String &bkey);
|
void create_scene_data(const String &key, const String &bkey);
|
||||||
Ref<PackedScene> scene_get_packed_scene(const String &key) const;
|
Ref<PackedScene> scene_get_packed_scene(const String &key) const;
|
||||||
int scene_get_item_count(const String &key) const;
|
int scene_get_item_count(const String &key) const;
|
||||||
String scene_get_item(const String &key, int index) const;
|
// String scene_get_item(const String &key, int index) const;
|
||||||
|
List<String> scene_get_items(const String &key) const;
|
||||||
|
void set_scene_item_node(const String &key, const String &bkey,
|
||||||
|
Node *node);
|
||||||
|
bool has_scene_item(const String &key, const String &bkey) const;
|
||||||
|
Node *get_scene_item_node(const String &key, const String &bkey) const;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
void item_nodes_delete_node(const String &key);
|
void item_nodes_delete_node(const String &key);
|
||||||
bool item_nodes_exists(const String &key) const;
|
// bool item_nodes_exists(const String &key) const;
|
||||||
void item_nodes_set_node(const String &key, Node *node);
|
// void item_nodes_set_node(const String &key, Node *node);
|
||||||
void item_nodes_item_removed(const String &key);
|
void item_nodes_item_removed(const String &key);
|
||||||
Node *item_nodes_get_node(const String &key) const;
|
Node *item_nodes_get_node(const String &key) const;
|
||||||
String item_nodes_get_key(int item) const;
|
String item_nodes_get_key(int item) const;
|
||||||
@@ -55,7 +60,7 @@ public:
|
|||||||
/* Data for each building in a world */
|
/* Data for each building in a world */
|
||||||
private:
|
private:
|
||||||
std::vector<struct building> buildings;
|
std::vector<struct building> buildings;
|
||||||
HashMap<String, Node *> item_nodes;
|
// HashMap<String, Node *> item_nodes;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
int get_building_count() const;
|
int get_building_count() const;
|
||||||
|
|||||||
@@ -181,7 +181,6 @@ void StreamWorld::request_item(int type, int item)
|
|||||||
print_line("Removing " + itos(item));
|
print_line("Removing " + itos(item));
|
||||||
if (data()->has_scene(id)) {
|
if (data()->has_scene(id)) {
|
||||||
data()->remove_scene_item(id, bkey);
|
data()->remove_scene_item(id, bkey);
|
||||||
data()->item_nodes_delete_node(bkey);
|
|
||||||
}
|
}
|
||||||
} break;
|
} break;
|
||||||
}
|
}
|
||||||
@@ -189,7 +188,6 @@ void StreamWorld::request_item(int type, int item)
|
|||||||
|
|
||||||
void StreamWorld::update_items()
|
void StreamWorld::update_items()
|
||||||
{
|
{
|
||||||
int i;
|
|
||||||
List<String> keys;
|
List<String> keys;
|
||||||
data()->get_scene_keys_list(&keys);
|
data()->get_scene_keys_list(&keys);
|
||||||
List<String>::Element *e = keys.front();
|
List<String>::Element *e = keys.front();
|
||||||
@@ -199,19 +197,24 @@ void StreamWorld::update_items()
|
|||||||
e = e->next();
|
e = e->next();
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
for (i = 0; i < (int)data()->scene_get_item_count(key); i++) {
|
const List<String> &items = data()->scene_get_items(key);
|
||||||
const String &bkey = data()->scene_get_item(key, i);
|
const List<String>::Element *be = items.front();
|
||||||
if (data()->item_nodes_exists(bkey))
|
while (be) {
|
||||||
|
const String &bkey = be->get();
|
||||||
|
if (data()->has_scene_item(key, bkey) &&
|
||||||
|
data()->get_scene_item_node(key, bkey)) {
|
||||||
|
be = be->next();
|
||||||
continue;
|
continue;
|
||||||
|
}
|
||||||
Node *psc =
|
Node *psc =
|
||||||
data()->scene_get_packed_scene(key)->instance();
|
data()->scene_get_packed_scene(key)->instance();
|
||||||
Spatial *psp = Object::cast_to<Spatial>(psc);
|
Spatial *psp = Object::cast_to<Spatial>(psc);
|
||||||
data()->item_nodes_set_node(bkey, psc);
|
// data()->item_nodes_set_node(bkey, psc);
|
||||||
current_scene->add_child(psp);
|
data()->set_scene_item_node(key, bkey, psc);
|
||||||
psp->set_global_transform(
|
current_scene->call_deferred("add_child", psp);
|
||||||
data()->get_building(
|
psp->call_deferred("set_global_transform",
|
||||||
data()->scene_get_item(key, i))
|
data()->get_building(bkey).xform);
|
||||||
.xform);
|
be = be->next();
|
||||||
}
|
}
|
||||||
e = e->next();
|
e = e->next();
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user