diff --git a/libs/util/tests/ecs.cpp b/libs/util/tests/ecs.cpp index 396d0a3e..dc558bd1 100644 --- a/libs/util/tests/ecs.cpp +++ b/libs/util/tests/ecs.cpp @@ -74,23 +74,23 @@ namespace } -test_case(util_ecs_species__impl_component) +test_case(util_ecs_species__impl_sparse_component) { using namespace psemek::util::ecs_detail; - species_impl species("species 1", 0, test_component_1{10}); + sparse_species_impl species("species 1", 0, test_component_1{10}); expect_different_ptr(species.get_species_component(), nullptr); expect_equal(species.get_species_component()->species_value_1, 10); expect_equal_ptr(species.get_species_component(), nullptr); - species_impl species_2("species 2", 1, test_component_2{20}); + sparse_species_impl species_2("species 2", 1, test_component_2{20}); expect_equal_ptr(species_2.get_species_component(), nullptr); expect_different_ptr(species_2.get_species_component(), nullptr); expect_equal(species_2.get_species_component()->species_value_2, 20); - species_impl species_12("species 12", 2, test_component_1{100}, test_component_2{200}); + sparse_species_impl species_12("species 12", 2, test_component_1{100}, test_component_2{200}); expect_different_ptr(species_12.get_species_component(), nullptr); expect_equal(species_12.get_species_component()->species_value_1, 100); @@ -98,11 +98,35 @@ test_case(util_ecs_species__impl_component) expect_equal(species_12.get_species_component()->species_value_2, 200); } -test_case(util_ecs_species__impl_entity) +test_case(util_ecs_species__impl_packed_component) { using namespace psemek::util::ecs_detail; - species_impl species("species", 0, test_component_1{10}); + packed_species_impl species("species 1", 0, test_component_1{10}); + + expect_different_ptr(species.get_species_component(), nullptr); + expect_equal(species.get_species_component()->species_value_1, 10); + expect_equal_ptr(species.get_species_component(), nullptr); + + packed_species_impl species_2("species 2", 1, test_component_2{20}); + + expect_equal_ptr(species_2.get_species_component(), nullptr); + expect_different_ptr(species_2.get_species_component(), nullptr); + expect_equal(species_2.get_species_component()->species_value_2, 20); + + packed_species_impl species_12("species 12", 2, test_component_1{100}, test_component_2{200}); + + expect_different_ptr(species_12.get_species_component(), nullptr); + expect_equal(species_12.get_species_component()->species_value_1, 100); + expect_different_ptr(species_12.get_species_component(), nullptr); + expect_equal(species_12.get_species_component()->species_value_2, 200); +} + +test_case(util_ecs_species__impl_sparse_entity) +{ + using namespace psemek::util::ecs_detail; + + sparse_species_impl species("species", 0, test_component_1{10}); expect_equal(species.entity_count(), 0); @@ -133,32 +157,86 @@ test_case(util_ecs_species__impl_entity) expect_equal(cptr_1[i].entity_value_1, i); } -test_case(util_ecs_entity) +test_case(util_ecs_species__impl_packed_entity) +{ + using namespace psemek::util::ecs_detail; + + packed_species_impl species("species", 0, test_component_1{10}); + + expect_equal(species.entity_count(), 0); + + int const N = 10; + + for (std::size_t i = 0; i < N; ++i) + species.add_entity(); + + expect_equal(species.entity_count(), N); + + test_component_1::data * cptr_1 = species.get_entity_component(); + + expect_different(cptr_1, nullptr); + + for (std::size_t i = 0; i < N; ++i) + cptr_1[i].entity_value_1 = i; + + for (std::size_t i = 0; i < N; ++i) + species.add_entity(); + + expect_equal(species.entity_count(), 2 * N); + + cptr_1 = species.get_entity_component(); + + expect_different(cptr_1, nullptr); + + for (std::size_t i = 0; i < N; ++i) + expect_equal(cptr_1[i].entity_value_1, i); +} + +test_case(util_ecs_entity_sparse) { using namespace psemek; util::ecs ecs; - auto species = ecs.register_species("species", test_component_1{10}); + auto species = ecs.register_species("species", util::ecs::policy::sparse, test_component_1{10}); expect_equal(ecs.entity_count(species), 0); auto entity = ecs.add_entity(species); - ecs.get(species, entity).entity_value_1 = 100; + ecs.get(entity).entity_value_1 = 100; - expect_equal(ecs.get(species, entity).entity_value_1, 100); + expect_equal(ecs.get(entity).entity_value_1, 100); - expect_throw(ecs.get(species, entity), std::exception); + expect_throw(ecs.get(entity), std::exception); } -test_case(util_ecs_behavior_1) +test_case(util_ecs_entity_packed) { using namespace psemek; util::ecs ecs; - auto species = ecs.register_species("species", test_component_1{10}); + auto species = ecs.register_species("species", util::ecs::policy::packed, test_component_1{10}); + + expect_equal(ecs.entity_count(species), 0); + + auto entity = ecs.add_entity(species); + + ecs.get(entity).entity_value_1 = 100; + + expect_equal(ecs.get(entity).entity_value_1, 100); + + expect_throw(ecs.get(entity), std::exception); +} + +test_case(util_ecs_behavior_1_sparse) +{ + using namespace psemek; + + util::ecs ecs; + + auto species = ecs.register_species("species", util::ecs::policy::sparse, test_component_1{10}); expect_equal(ecs.entity_count(species), 0); @@ -167,7 +245,7 @@ test_case(util_ecs_behavior_1) for (int i = 0; i < N; ++i) { auto entity = ecs.add_entity(species); - ecs.get(species, entity).entity_value_1 = i; + ecs.get(entity).entity_value_1 = i; } test_behavior_1 behavior_1; @@ -186,27 +264,61 @@ test_case(util_ecs_behavior_1) expect_equal(behavior_12.value_sum_2, 0); } -test_case(util_ecs_behavior_1__2) +test_case(util_ecs_behavior_1_packed) { using namespace psemek; util::ecs ecs; - auto species_1 = ecs.register_species("species 1", test_component_1{10}); - auto species_2 = ecs.register_species("species 2", test_component_2{20}); + auto species = ecs.register_species("species", util::ecs::policy::packed, test_component_1{10}); + + expect_equal(ecs.entity_count(species), 0); + + int N = 100; + + for (int i = 0; i < N; ++i) + { + auto entity = ecs.add_entity(species); + ecs.get(entity).entity_value_1 = i; + } + + test_behavior_1 behavior_1; + + ecs.apply(behavior_1); + + expect_equal(behavior_1.call_count, N); + expect_equal(behavior_1.value_sum, (N * (N - 1)) / 2); + + test_behavior_12 behavior_12; + + ecs.apply(behavior_12); + + expect_equal(behavior_12.call_count, 0); + expect_equal(behavior_12.value_sum_1, 0); + expect_equal(behavior_12.value_sum_2, 0); +} + +test_case(util_ecs_behavior_1__2_sparse) +{ + using namespace psemek; + + util::ecs ecs; + + auto species_1 = ecs.register_species("species 1", util::ecs::policy::sparse, test_component_1{10}); + auto species_2 = ecs.register_species("species 2", util::ecs::policy::sparse, test_component_2{20}); int N = 100; for (int i = 0; i < N; ++i) { auto entity = ecs.add_entity(species_1); - ecs.get(species_1, entity).entity_value_1 = i; + ecs.get(entity).entity_value_1 = i; } for (int i = 0; i < N; ++i) { auto entity = ecs.add_entity(species_2); - ecs.get(species_2, entity).entity_value_2 = -i; + ecs.get(entity).entity_value_2 = -i; } test_behavior_1 behavior; @@ -225,21 +337,60 @@ test_case(util_ecs_behavior_1__2) expect_equal(behavior_12.value_sum_2, 0); } -test_case(util_ecs_behavior_12) +test_case(util_ecs_behavior_1__2_packed) { using namespace psemek; util::ecs ecs; - auto species = ecs.register_species("species", test_component_1{10}, test_component_2{20}); + auto species_1 = ecs.register_species("species 1", util::ecs::policy::packed, test_component_1{10}); + auto species_2 = ecs.register_species("species 2", util::ecs::policy::packed, test_component_2{20}); + + int N = 100; + + for (int i = 0; i < N; ++i) + { + auto entity = ecs.add_entity(species_1); + ecs.get(entity).entity_value_1 = i; + } + + for (int i = 0; i < N; ++i) + { + auto entity = ecs.add_entity(species_2); + ecs.get(entity).entity_value_2 = -i; + } + + test_behavior_1 behavior; + + ecs.apply(behavior); + + expect_equal(behavior.call_count, N); + expect_equal(behavior.value_sum, (N * (N - 1)) / 2); + + test_behavior_12 behavior_12; + + ecs.apply(behavior_12); + + expect_equal(behavior_12.call_count, 0); + expect_equal(behavior_12.value_sum_1, 0); + expect_equal(behavior_12.value_sum_2, 0); +} + +test_case(util_ecs_behavior_12_sparse) +{ + using namespace psemek; + + util::ecs ecs; + + auto species = ecs.register_species("species", util::ecs::policy::sparse, test_component_1{10}, test_component_2{20}); int N = 100; for (int i = 0; i < N; ++i) { auto entity = ecs.add_entity(species); - ecs.get(species, entity).entity_value_1 = i; - ecs.get(species, entity).entity_value_2 = -i; + ecs.get(entity).entity_value_1 = i; + ecs.get(entity).entity_value_2 = -i; } test_behavior_1 behavior; @@ -258,21 +409,80 @@ test_case(util_ecs_behavior_12) expect_equal(behavior_12.value_sum_2, - (N * (N - 1)) / 2); } -test_case(util_ecs_behavior_species) +test_case(util_ecs_behavior_12_packed) { using namespace psemek; util::ecs ecs; - auto species = ecs.register_species("species", test_component_1{10}, test_component_2{20}); + auto species = ecs.register_species("species", util::ecs::policy::packed, test_component_1{10}, test_component_2{20}); int N = 100; for (int i = 0; i < N; ++i) { auto entity = ecs.add_entity(species); - ecs.get(species, entity).entity_value_1 = 0; - ecs.get(species, entity).entity_value_2 = 0; + ecs.get(entity).entity_value_1 = i; + ecs.get(entity).entity_value_2 = -i; + } + + test_behavior_1 behavior; + + ecs.apply(behavior); + + expect_equal(behavior.call_count, N); + expect_equal(behavior.value_sum, (N * (N - 1)) / 2); + + test_behavior_12 behavior_12; + + ecs.apply(behavior_12); + + expect_equal(behavior_12.call_count, N); + expect_equal(behavior_12.value_sum_1, (N * (N - 1)) / 2); + expect_equal(behavior_12.value_sum_2, - (N * (N - 1)) / 2); +} + +test_case(util_ecs_behavior_species_sparse) +{ + using namespace psemek; + + util::ecs ecs; + + auto species = ecs.register_species("species", util::ecs::policy::sparse, test_component_1{10}, test_component_2{20}); + + int N = 100; + + for (int i = 0; i < N; ++i) + { + auto entity = ecs.add_entity(species); + ecs.get(entity).entity_value_1 = 0; + ecs.get(entity).entity_value_2 = 0; + } + + test_behavior_species_12 behavior; + behavior.expected_value_1 = 10; + behavior.expected_value_2 = 20; + + ecs.apply(behavior); + + expect_equal(behavior.call_count, N); +} + +test_case(util_ecs_behavior_species_packed) +{ + using namespace psemek; + + util::ecs ecs; + + auto species = ecs.register_species("species", util::ecs::policy::packed, test_component_1{10}, test_component_2{20}); + + int N = 100; + + for (int i = 0; i < N; ++i) + { + auto entity = ecs.add_entity(species); + ecs.get(entity).entity_value_1 = 0; + ecs.get(entity).entity_value_2 = 0; } test_behavior_species_12 behavior;