#pragma once #include #include #include #include namespace floormat { template concept DebugPrintable = requires(Debug& dbg, const T& value) { { dbg << value } -> std::convertible_to; }; } // namespace floormat namespace floormat::detail::corrade_debug { // ***** colon ***** struct Colon { char c; }; Debug& operator<<(Debug& dbg, Colon box); // ***** error string ***** struct ErrorString { int value; }; Debug& operator<<(Debug& dbg, ErrorString box); // ***** quoted ***** template struct Quoted { using type = T; T value; char c; }; Debug::Flags quoted_begin(Debug& dbg, char c); Debug& quoted_end(Debug& dbg, Debug::Flags flags, char c); template Debug& operator<<(Debug& dbg, Quoted box) { Debug::Flags flags = quoted_begin(dbg, box.c); dbg << box.value; return quoted_end(dbg, flags, box.c); } } // namespace floormat::detail::corrade_debug // ***** api ***** // ***** functions ***** namespace floormat { floormat::detail::corrade_debug::Colon colon(char c = ':'); floormat::detail::corrade_debug::ErrorString error_string(int error); floormat::detail::corrade_debug::ErrorString error_string(); template auto quoted(T&& value, char c = '\'') { using U = std::remove_cvref_t; using floormat::detail::corrade_debug::Quoted; if constexpr(std::is_rvalue_reference_v) return Quoted{ .value = Utility::move(value), .c = c }; else return Quoted{ .value = value, .c = c }; } template auto quoted2(T&& value) { return quoted(Utility::forward(value), '"'); } } // namespace floormat