MetaStuff
MetaStuff copied to clipboard
Add EnumMember type to MetaStuff.
Adds CMakeLists.txt for example for easier compilation.
Documentation is being added as we speak, putting code up for review so any changes needed to be made will be made.
EnumMember is implements a toString and fromString to convert Enum types from and to strings instead of by numeric number.
Implementation is rough, as the map is generated per-clas,, any ideas on how to move it to per-enum?Unless theres a use case for to map the same enum as different string values....
This is great. Can we merge it?
I kinda feel bad for not giving it enough attention and forgetting about it. :( @iamPHEN, are you still interested in this? There are some thing that need to be fixed and I'll be willing to merge.
Otherwise I can take your idea and implement it myself with all things I want to see here.
This feature would also be very important for me.
I have more free time now, so I'll give it a closer look in a few days. :)
That's great, thanks!
Still thinking about the best way to handle enum members... they're tricky!
As a temporary workaround, you can use this:
enum class Color
{
Red, Blue
};
class Person {
/* ... */
std::string getFavouriteColorString() const
{
switch (favouriteColor) {
case Color::Red:
return "Red";
case Color::Blue:
return "Blue";
}
}
void setFavouriteColorByString(std::string str)
{
if (str == "Red") {
favouriteColor = Color::Red;
} else if (str == "Blue") {
favouriteColor = Color::Blue;
}
}
};
template <>
inline auto registerMembers<Person>()
{
return members(
/* ... */
member("favouriteColor", &Person::getFavouriteColorString,
&Person::setFavouriteColorByString)
);
}
It's possible to replace std::string with const char* if you want, but that doesn't work with JSON example (deserialization only, serialization works fine), and it's pretty hard to fix it at the moment. :)
Another solution is to change serializer/deserializer to call another function if the member is enum. For example:
template <typename Class,
typename>
json serialize(const Class& obj)
{
json value;
meta::doForAllMembers<Class>(
[&obj, &value](auto& member)
{
auto& valueName = value[member.getName()];
using MemberT = meta::get_member_type<decltype(member)>;
if constexpr (!std::is_enum_v<MemberT>) {
...
} else {
valueName = enumToString(member.get(obj));
}
}
);
return value;
}
And now, we'll have to define enumToString function and an overload for Color like this:
std::string enumToString<Color>(const Color& color)
{
switch (color) {
case Color::Red:
return "Red";
case Color::Blue:
return "Blue";
}
}
And we register Color member like this:
member("favouriteColor", &Person::favouriteColor)