-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
introduce bitmask support and std::format specialization
- Loading branch information
Showing
16 changed files
with
1,985 additions
and
738 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,15 @@ | ||
{ | ||
"files.associations": { | ||
"cmath": "cpp", | ||
"string_view": "cpp" | ||
} | ||
"files.associations": { | ||
"cmath": "cpp", | ||
"string_view": "cpp", | ||
"sstream": "cpp", | ||
"optional": "cpp", | ||
"memory": "cpp", | ||
"random": "cpp", | ||
"array": "cpp", | ||
"fstream": "cpp", | ||
"tuple": "cpp", | ||
"type_traits": "cpp", | ||
"system_error": "cpp" | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,20 +1,74 @@ | ||
cmake_minimum_required(VERSION 3.14) | ||
project(enum_name_example VERSION 0.1 LANGUAGES CXX) | ||
|
||
set(CMAKE_CXX_STANDARD 17) | ||
project( | ||
enum_name | ||
VERSION 1.0 | ||
LANGUAGES CXX) | ||
|
||
include(FetchContent) | ||
# Define the library | ||
add_library(enum_name INTERFACE) | ||
|
||
FetchContent_Declare( | ||
DocTest | ||
GIT_REPOSITORY "https://github.com/onqtam/doctest" | ||
GIT_TAG "v2.4.11" | ||
) | ||
# Specify the include directories for the library | ||
target_include_directories( | ||
enum_name INTERFACE $<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/include> | ||
$<INSTALL_INTERFACE:include>) | ||
|
||
# Set the C++ standard | ||
target_compile_features(enum_name INTERFACE cxx_std_11) | ||
|
||
# Install the library | ||
install( | ||
TARGETS enum_name | ||
EXPORT enum_nameTargets | ||
INCLUDES | ||
DESTINATION include) | ||
|
||
install( | ||
EXPORT enum_nameTargets | ||
FILE enum_nameTargets.cmake | ||
NAMESPACE enum_name:: | ||
DESTINATION lib/cmake/enum_name) | ||
|
||
install(DIRECTORY include/ DESTINATION include) | ||
|
||
# Create the package configuration files | ||
include(CMakePackageConfigHelpers) | ||
|
||
write_basic_package_version_file( | ||
"${CMAKE_CURRENT_BINARY_DIR}/enum_nameConfigVersion.cmake" | ||
VERSION ${PROJECT_VERSION} | ||
COMPATIBILITY AnyNewerVersion) | ||
|
||
FetchContent_MakeAvailable(DocTest) | ||
configure_package_config_file( | ||
${CMAKE_CURRENT_LIST_DIR}/cmake/enum_nameConfig.cmake.in | ||
"${CMAKE_CURRENT_BINARY_DIR}/enum_nameConfig.cmake" | ||
INSTALL_DESTINATION lib/cmake/enum_name) | ||
|
||
add_executable(${PROJECT_NAME} example/main.cpp) | ||
target_include_directories(${PROJECT_NAME} PUBLIC ${CMAKE_SOURCE_DIR}/include) | ||
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/enum_nameConfig.cmake" | ||
"${CMAKE_CURRENT_BINARY_DIR}/enum_nameConfigVersion.cmake" | ||
DESTINATION lib/cmake/enum_name) | ||
|
||
export( | ||
EXPORT enum_nameTargets | ||
FILE "${CMAKE_CURRENT_BINARY_DIR}/enum_nameTargets.cmake" | ||
NAMESPACE enum_name::) | ||
|
||
# Enable testing | ||
enable_testing() | ||
add_subdirectory(test) | ||
|
||
# FetchContent to get the Doctest testing framework | ||
include(FetchContent) | ||
FetchContent_Declare( | ||
doctest | ||
GIT_REPOSITORY https://github.com/doctest/doctest.git | ||
GIT_TAG v2.4.11) | ||
FetchContent_MakeAvailable(doctest) | ||
|
||
# Add test executable | ||
add_executable(test_enum_name tests/test_enum_name.cpp) | ||
|
||
# Link the test executable with the library and Doctest | ||
target_link_libraries(test_enum_name PRIVATE enum_name doctest::doctest) | ||
|
||
# Add tests | ||
add_test(NAME test_enum_name COMMAND test_enum_name) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
@PACKAGE_INIT@ | ||
|
||
include("${CMAKE_CURRENT_LIST_DIR}/enum_nameTargets.cmake") |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,33 +1,80 @@ | ||
#include <iostream> | ||
#include "enum_name.hpp" | ||
#include <iostream> | ||
|
||
enum class rgb_color { | ||
red = 1 << 0, | ||
green = 1 << 1, | ||
blue = 1 << 2, | ||
unknown = -1 | ||
}; | ||
|
||
auto constexpr operator|(rgb_color lhs, rgb_color rhs) -> rgb_color { | ||
return static_cast<rgb_color>(mgutility::enum_to_underlying(lhs) | | ||
mgutility::enum_to_underlying(rhs)); | ||
} | ||
|
||
enum class rgb_color { red, green, blue, unknown = -1}; | ||
auto constexpr operator&(rgb_color lhs, rgb_color rhs) -> rgb_color { | ||
return static_cast<rgb_color>(mgutility::enum_to_underlying(lhs) & | ||
mgutility::enum_to_underlying(rhs)); | ||
} | ||
|
||
// you can specialize enum ranges with specialize struct per enum types (option 1) | ||
namespace mgutility{ | ||
template<> | ||
struct enum_range<rgb_color> | ||
{ | ||
static constexpr auto min = -1; | ||
static constexpr auto max = 3; | ||
}; | ||
// specialize rgb_color::unknown to make output "UNKNOWN" instead of "unknown" | ||
template <> | ||
constexpr auto | ||
mgutility::detail::enum_type::name<rgb_color, rgb_color::unknown>() noexcept | ||
-> mgutility::string_view { | ||
return "UNKNOWN"; | ||
} | ||
|
||
// you can specialize enum ranges with overload per enum types (option 1) | ||
template <> struct mgutility::enum_range<rgb_color> { | ||
static constexpr auto min = -1; | ||
static constexpr auto max = 5; | ||
}; | ||
|
||
// you can specialize enum ranges with overload per enum types (option 2) | ||
auto enum_name = [](rgb_color c){ return mgutility::enum_name<-1, 3>(c); }; | ||
|
||
|
||
int main() | ||
{ | ||
auto x = rgb_color::blue; | ||
auto y = mgutility::to_enum<rgb_color>("green"); | ||
|
||
// default signature: enum_name<min_value = -128, max_value = 128, Enum typename>(Enum&&) | ||
// Changing max_value to not too much greater than enum's max value, it will compiles faster | ||
std::cout << mgutility::enum_name(x) << '\n'; // will print "blue" to output | ||
|
||
// calling specialized enum ranges function for rgb_color type | ||
// will print "green" to output, if y can't convert to rgb_color prints "unknown" | ||
std::cout << enum_name(y.value_or(rgb_color::unknown)) << '\n'; | ||
auto enum_name = [](rgb_color c) { return mgutility::enum_name<-1, 5>(c); }; | ||
|
||
#if defined(__cpp_lib_print) | ||
#include <print> | ||
#include <ranges> | ||
#endif | ||
|
||
int main() { | ||
auto x = rgb_color::blue; | ||
auto y = mgutility::to_enum<rgb_color>("green|red"); | ||
|
||
#if defined(__cpp_lib_print) | ||
|
||
// enum_for_each<T> can usable with views and range algorithms | ||
auto colors = mgutility::enum_for_each<rgb_color>() | | ||
std::ranges::views::filter([](auto &&pair) { | ||
return !pair.second.empty() && pair.second != "UNKNOWN"; | ||
}); | ||
|
||
std::ranges::for_each(colors, [](auto &&color) { | ||
std::println("{} \t: {}", color.second, | ||
mgutility::enum_to_underlying(color.first)); | ||
}); | ||
|
||
#else | ||
|
||
for (auto &&e : mgutility::enum_for_each<rgb_color>()) { | ||
if (!e.second.empty() && e.second != "UNKNOWN") { | ||
std::cout << e.second << " \t: " << mgutility::enum_to_underlying(e.first) | ||
<< '\n'; | ||
} | ||
// std::pair<Enum, string_view> {enum_type, name_of_enum} | ||
} | ||
#endif | ||
|
||
// default signature: enum_name<min_value = -128, max_value = 128, Enum | ||
// typename>(Enum&&) Changing max_value to not too much greater than enum's | ||
// max value, it will compiles faster | ||
std::cout << x << '\n'; // will print "blue" to output | ||
|
||
// calling specialized enum ranges function for rgb_color type | ||
// will print "green" to output, if y can't convert to rgb_color prints | ||
// "UNKNOWN" | ||
std::cout << enum_name(y.value_or(rgb_color::unknown)) << '\n'; | ||
} |
Oops, something went wrong.