Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -414,7 +414,7 @@ endfunction ()
set(FMT_REFLECTION_TEST_CODE
"
#include <fmt/enum.h>
enum class [[=fmt::as_identifiers]] color { red };
enum class [[=fmt::as_identifiers()]] color { red };
static_assert(fmt::is_formattable<color>::value, \"\");
int main() {}
")
Expand Down
2 changes: 1 addition & 1 deletion doc/api.md
Original file line number Diff line number Diff line change
Expand Up @@ -566,7 +566,7 @@ enumerator matching the formatted value:

#include <fmt/enum.h>

enum class [[=fmt::as_identifiers]] color { red, green, blue };
enum class [[=fmt::as_identifiers()]] color { red, green, blue };

fmt::print("{}", color::green);
// Output: green
Expand Down
9 changes: 3 additions & 6 deletions include/fmt/enum.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,21 +32,18 @@ FMT_BEGIN_NAMESPACE

#if FMT_USE_REFLECTION

/// The type of the `fmt::as_identifiers` annotation.
FMT_EXPORT struct as_identifiers_t {};

/**
* An annotation that makes an enum format as identifiers of its enumerators.
*
* **Example**:
*
* enum class [[=fmt::as_identifiers]] color { red, green, blue };
* enum class [[=fmt::as_identifiers()]] color { red, green, blue };
* auto s = fmt::format("{}", color::green); // s == "green"
*
* A value that doesn't match any enumerator is represented as its underlying
* value in decimal before applying string formatting.
*/
FMT_EXPORT inline constexpr auto as_identifiers = as_identifiers_t();
FMT_EXPORT struct as_identifiers {};

namespace detail {

Expand All @@ -56,7 +53,7 @@ consteval auto use_identifiers() -> bool {
if constexpr (!std::is_enum<U>::value) {
return false;
} else {
return !std::meta::annotations_of_with_type(^^U, ^^as_identifiers_t)
return !std::meta::annotations_of_with_type(^^U, ^^as_identifiers)
.empty();
}
}
Expand Down
33 changes: 19 additions & 14 deletions test/enum-test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -21,37 +21,42 @@ TEST(enum_test, no_reflection) {

// clang-format doesn't support annotations yet.
// clang-format off
enum class [[=fmt::as_identifiers]] color { red, green, blue };
enum class [[=fmt::as_identifiers()]] color { red, green, blue };
enum class color_without_annotation { red, green, blue };
enum [[=fmt::as_identifiers]] unscoped_color { unscoped_red, unscoped_green };
enum class [[=fmt::as_identifiers]] level : unsigned char { low = 1, high = 2 };
enum class [[=fmt::as_identifiers]] byte_enum : char { one = 1 };
enum class [[=fmt::as_identifiers]] signed_byte_enum : signed char { minus_one = -1 };
enum class [[=fmt::as_identifiers]] bool_enum : bool { off = false };
enum class [[=fmt::as_identifiers]] alias { one = 1, uno = 1 };
enum class [[=fmt::as_identifiers]] empty_enum {};
enum [[=fmt::as_identifiers()]] unscoped_color { unscoped_red, unscoped_green };
enum class [[=fmt::as_identifiers()]] level : unsigned char {
low = 1,
high = 2
};
enum class [[=fmt::as_identifiers()]] byte_enum : char { one = 1 };
enum class [[=fmt::as_identifiers()]] signed_byte_enum : signed char {
minus_one = -1
};
enum class [[=fmt::as_identifiers()]] bool_enum : bool { off = false };
enum class [[=fmt::as_identifiers()]] alias { one = 1, uno = 1 };
enum class [[=fmt::as_identifiers()]] empty_enum {};

// Dense values: formatted via a lookup table.
enum class [[=fmt::as_identifiers]] dense { d0, d1, d2, d3, d4 };
enum class [[=fmt::as_identifiers()]] dense { d0, d1, d2, d3, d4 };
// 3 holes out of 10: the sparsest case that still uses a lookup table.
enum class [[=fmt::as_identifiers]] holey {
enum class [[=fmt::as_identifiers()]] holey {
h0, h1, h2, h3, h4, h5, h6 = 9
};
// 4 holes out of 11: just too sparse, formatted via a linear search.
enum class [[=fmt::as_identifiers]] sparse {
enum class [[=fmt::as_identifiers()]] sparse {
s0, s1, s2, s3, s4, s5, s6 = 10
};
// Values spanning both signs and the extremes of the underlying type.
enum class [[=fmt::as_identifiers]] signed_enum {
enum class [[=fmt::as_identifiers()]] signed_enum {
minus_two = -2,
minus_one = -1,
one = 1
};
enum class [[=fmt::as_identifiers]] extremes : int {
enum class [[=fmt::as_identifiers()]] extremes : int {
lowest = INT_MIN,
highest = INT_MAX
};
enum class [[=fmt::as_identifiers]] big : unsigned long long {
enum class [[=fmt::as_identifiers()]] big : unsigned long long {
huge = ULLONG_MAX
};
// clang-format on
Expand Down
2 changes: 1 addition & 1 deletion test/module-test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -377,7 +377,7 @@ TEST(module_test, compile_format_string) {
defined(__cpp_lib_define_static)
// clang-format doesn't support annotations yet.
// clang-format off
enum class [[=fmt::as_identifiers]] color { red, green, blue };
enum class [[=fmt::as_identifiers()]] color { red, green, blue };
// clang-format on

TEST(module_test, format_enum) {
Expand Down
Loading