Use "if constexpr" provided by C++17

This commit is contained in:
Stephen Seo 2018-05-21 19:19:43 +09:00
parent 8f133acbc6
commit f59f78385d
3 changed files with 57 additions and 55 deletions

View file

@ -31,7 +31,7 @@ set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Wextra -Wpedantic")
set(CMAKE_CXX_FLAGS_DEBUG "-O0 -g")
set(CMAKE_CXX_FLAGS_RELEASE "-O3 -D NDEBUG")
target_compile_features(EntityComponentSystem INTERFACE cxx_std_14)
target_compile_features(EntityComponentSystem INTERFACE cxx_std_17)
if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
message(STATUS "Setting build type to 'Debug', none was specified.")
@ -53,7 +53,7 @@ if(GTEST_FOUND)
add_executable(UnitTests ${UnitTests_SOURCES})
target_link_libraries(UnitTests EntityComponentSystem ${GTEST_LIBRARIES})
target_include_directories(UnitTests PUBLIC ${GTEST_INCLUDE_DIR})
target_compile_features(UnitTests PUBLIC cxx_std_14)
target_compile_features(UnitTests PUBLIC cxx_std_17)
enable_testing()
add_test(NAME UnitTests COMMAND UnitTests)

View file

@ -66,7 +66,7 @@ namespace EC
Bitset<ComponentsList, TagsList> bitset;
EC::Meta::forEach<Contents>([&bitset] (auto t) {
if(EC::Meta::Contains<decltype(t), Combined>::value)
if constexpr (EC::Meta::Contains<decltype(t), Combined>::value)
{
bitset[EC::Meta::IndexOf<decltype(t), Combined>::value] =
true;

View file

@ -32,7 +32,6 @@
#include "Meta/Matching.hpp"
#include "Meta/ForEachWithIndex.hpp"
#include "Meta/ForEachDoubleTuple.hpp"
#include "Meta/IndexOf.hpp"
#include "Bitset.hpp"
namespace EC
@ -67,7 +66,7 @@ namespace EC
template <typename... Types>
struct Storage
{
using type = std::tuple<std::vector<Types>..., std::vector<char> >;
using type = std::tuple<std::vector<Types>...>;
};
using ComponentsStorage =
typename EC::Meta::Morph<ComponentsList, Storage<> >::type;
@ -242,15 +241,10 @@ namespace EC
template <typename Component>
Component* getEntityData(const std::size_t& index)
{
constexpr auto componentIndex = EC::Meta::IndexOf<
Component, Components>::value;
if(componentIndex < Components::size)
if constexpr (EC::Meta::Contains<Component, Components>::value)
{
// Cast required due to compiler thinking that an invalid
// Component is needed even though the enclosing if statement
// prevents this from ever happening.
return (Component*) &std::get<componentIndex>(
componentsStorage).at(index);
return &std::get<std::vector<Component> >(componentsStorage)
.at(index);
}
else
{
@ -295,15 +289,10 @@ namespace EC
template <typename Component>
const Component* getEntityData(const std::size_t& index) const
{
constexpr auto componentIndex = EC::Meta::IndexOf<
Component, Components>::value;
if(componentIndex < Components::size)
if constexpr (EC::Meta::Contains<Component, Components>::value)
{
// Cast required due to compiler thinking that an invalid
// Component is needed even though the enclosing if statement
// prevents this from ever happening.
return (Component*) &std::get<componentIndex>(
componentsStorage).at(index);
return &std::get<std::vector<Component> >(componentsStorage)
.at(index);
}
else
{
@ -395,27 +384,25 @@ namespace EC
template <typename Component, typename... Args>
void addComponent(const std::size_t& entityID, Args&&... args)
{
if(!EC::Meta::Contains<Component, Components>::value
|| !isAlive(entityID))
if constexpr (!EC::Meta::Contains<Component, Components>::value)
{
return;
}
else
{
if(!isAlive(entityID))
{
return;
}
Component component(std::forward<Args>(args)...);
Component component(std::forward<Args>(args)...);
std::get<BitsetType>(
entities[entityID]
).template getComponentBit<Component>() = true;
std::get<BitsetType>(
entities[entityID]
).template getComponentBit<Component>() = true;
constexpr auto index =
EC::Meta::IndexOf<Component, Components>::value;
// Cast required due to compiler thinking that vector<char> at
// index = Components::size is being used, even if the previous
// if statement will prevent this from ever happening.
(*((std::vector<Component>*)(&std::get<index>(
componentsStorage
))))[entityID] = std::move(component);
std::get<std::vector<Component> >(componentsStorage)[entityID]
= std::move(component);
}
}
/*!
@ -432,15 +419,20 @@ namespace EC
template <typename Component>
void removeComponent(const std::size_t& entityID)
{
if(!EC::Meta::Contains<Component, Components>::value
|| !isAlive(entityID))
if constexpr (!EC::Meta::Contains<Component, Components>::value)
{
return;
}
std::get<BitsetType>(
entities[entityID]
).template getComponentBit<Component>() = false;
else
{
if(!isAlive(entityID))
{
return;
}
std::get<BitsetType>(
entities[entityID]
).template getComponentBit<Component>() = false;
}
}
/*!
@ -454,15 +446,20 @@ namespace EC
template <typename Tag>
void addTag(const std::size_t& entityID)
{
if(!EC::Meta::Contains<Tag, Tags>::value
|| !isAlive(entityID))
if constexpr (!EC::Meta::Contains<Tag, Tags>::value)
{
return;
}
std::get<BitsetType>(
entities[entityID]
).template getTagBit<Tag>() = true;
else
{
if(!isAlive(entityID))
{
return;
}
std::get<BitsetType>(
entities[entityID]
).template getTagBit<Tag>() = true;
}
}
/*!
@ -478,15 +475,20 @@ namespace EC
template <typename Tag>
void removeTag(const std::size_t& entityID)
{
if(!EC::Meta::Contains<Tag, Tags>::value
|| !isAlive(entityID))
if constexpr (!EC::Meta::Contains<Tag, Tags>::value)
{
return;
}
std::get<BitsetType>(
entities[entityID]
).template getTagBit<Tag>() = false;
else
{
if(!isAlive(entityID))
{
return;
}
std::get<BitsetType>(
entities[entityID]
).template getTagBit<Tag>() = false;
}
}
private: