1 /* SPDX-License-Identifier: BSL-1.0 OR BSD-3-Clause */ 2 3 #ifndef MPT_FORMAT_SIMPLE_HPP 4 #define MPT_FORMAT_SIMPLE_HPP 5 6 7 8 #include "mpt/base/namespace.hpp" 9 #include "mpt/base/pointer.hpp" 10 #include "mpt/format/default_formatter.hpp" 11 #include "mpt/format/simple_floatingpoint.hpp" 12 #include "mpt/format/simple_integer.hpp" 13 #include "mpt/format/simple_spec.hpp" 14 #include "mpt/string/utility.hpp" 15 16 #include <type_traits> 17 18 #include <cstddef> 19 20 21 22 namespace mpt { 23 inline namespace MPT_INLINE_NS { 24 25 26 27 template <typename Tstring> 28 struct format : format_simple_base { 29 30 template <typename T> valmpt::MPT_INLINE_NS::format31 static inline Tstring val(const T & x) { 32 return mpt::default_formatter::format<Tstring>(x); 33 } 34 35 template <typename T> fmtmpt::MPT_INLINE_NS::format36 static inline Tstring fmt(const T & x, const format_simple_spec & f) { 37 return mpt::format_simple<Tstring>(x, f); 38 } 39 40 template <typename T> decmpt::MPT_INLINE_NS::format41 static inline Tstring dec(const T & x) { 42 static_assert(std::numeric_limits<T>::is_integer); 43 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseDec().FillOff()); 44 } 45 template <int width, typename T> dec0mpt::MPT_INLINE_NS::format46 static inline Tstring dec0(const T & x) { 47 static_assert(std::numeric_limits<T>::is_integer); 48 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseDec().FillNul().Width(width)); 49 } 50 51 template <typename T> decmpt::MPT_INLINE_NS::format52 static inline Tstring dec(unsigned int g, char s, const T & x) { 53 static_assert(std::numeric_limits<T>::is_integer); 54 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseDec().FillOff().Group(g).GroupSep(s)); 55 } 56 template <int width, typename T> dec0mpt::MPT_INLINE_NS::format57 static inline Tstring dec0(unsigned int g, char s, const T & x) { 58 static_assert(std::numeric_limits<T>::is_integer); 59 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseDec().FillNul().Width(width).Group(g).GroupSep(s)); 60 } 61 62 template <typename T> hexmpt::MPT_INLINE_NS::format63 static inline Tstring hex(const T & x) { 64 static_assert(std::numeric_limits<T>::is_integer); 65 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseHex().CaseLow().FillOff()); 66 } 67 template <typename T> HEXmpt::MPT_INLINE_NS::format68 static inline Tstring HEX(const T & x) { 69 static_assert(std::numeric_limits<T>::is_integer); 70 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseHex().CaseUpp().FillOff()); 71 } 72 template <int width, typename T> hex0mpt::MPT_INLINE_NS::format73 static inline Tstring hex0(const T & x) { 74 static_assert(std::numeric_limits<T>::is_integer); 75 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseHex().CaseLow().FillNul().Width(width)); 76 } 77 template <int width, typename T> HEX0mpt::MPT_INLINE_NS::format78 static inline Tstring HEX0(const T & x) { 79 static_assert(std::numeric_limits<T>::is_integer); 80 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseHex().CaseUpp().FillNul().Width(width)); 81 } 82 83 template <typename T> hexmpt::MPT_INLINE_NS::format84 static inline Tstring hex(unsigned int g, char s, const T & x) { 85 static_assert(std::numeric_limits<T>::is_integer); 86 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseHex().CaseLow().FillOff().Group(g).GroupSep(s)); 87 } 88 template <typename T> HEXmpt::MPT_INLINE_NS::format89 static inline Tstring HEX(unsigned int g, char s, const T & x) { 90 static_assert(std::numeric_limits<T>::is_integer); 91 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseHex().CaseUpp().FillOff().Group(g).GroupSep(s)); 92 } 93 template <int width, typename T> hex0mpt::MPT_INLINE_NS::format94 static inline Tstring hex0(unsigned int g, char s, const T & x) { 95 static_assert(std::numeric_limits<T>::is_integer); 96 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseHex().CaseLow().FillNul().Width(width).Group(g).GroupSep(s)); 97 } 98 template <int width, typename T> HEX0mpt::MPT_INLINE_NS::format99 static inline Tstring HEX0(unsigned int g, char s, const T & x) { 100 static_assert(std::numeric_limits<T>::is_integer); 101 return mpt::format_simple<Tstring>(x, format_simple_spec().BaseHex().CaseUpp().FillNul().Width(width).Group(g).GroupSep(s)); 102 } 103 104 template <typename T> fltmpt::MPT_INLINE_NS::format105 static inline Tstring flt(const T & x, int precision = -1) { 106 static_assert(std::is_floating_point<T>::value); 107 return mpt::format_simple<Tstring>(x, format_simple_spec().NotaNrm().FillOff().Precision(precision)); 108 } 109 template <typename T> fixmpt::MPT_INLINE_NS::format110 static inline Tstring fix(const T & x, int precision = -1) { 111 static_assert(std::is_floating_point<T>::value); 112 return mpt::format_simple<Tstring>(x, format_simple_spec().NotaFix().FillOff().Precision(precision)); 113 } 114 template <typename T> scimpt::MPT_INLINE_NS::format115 static inline Tstring sci(const T & x, int precision = -1) { 116 static_assert(std::is_floating_point<T>::value); 117 return mpt::format_simple<Tstring>(x, format_simple_spec().NotaSci().FillOff().Precision(precision)); 118 } 119 120 template <typename T> ptrmpt::MPT_INLINE_NS::format121 static inline Tstring ptr(const T & x) { 122 static_assert(std::is_pointer<T>::value || std::is_same<T, std::uintptr_t>::value || std::is_same<T, std::intptr_t>::value, ""); 123 return hex0<mpt::pointer_size * 2>(mpt::pointer_cast<const std::uintptr_t>(x)); 124 } 125 template <typename T> PTRmpt::MPT_INLINE_NS::format126 static inline Tstring PTR(const T & x) { 127 static_assert(std::is_pointer<T>::value || std::is_same<T, std::uintptr_t>::value || std::is_same<T, std::intptr_t>::value, ""); 128 return HEX0<mpt::pointer_size * 2>(mpt::pointer_cast<const std::uintptr_t>(x)); 129 } 130 pad_leftmpt::MPT_INLINE_NS::format131 static inline Tstring pad_left(std::size_t width_, const Tstring & str) { 132 typedef mpt::string_traits<Tstring> traits; 133 typename traits::size_type width = static_cast<typename traits::size_type>(width_); 134 return traits::pad(str, width, 0); 135 } pad_rightmpt::MPT_INLINE_NS::format136 static inline Tstring pad_right(std::size_t width_, const Tstring & str) { 137 typedef mpt::string_traits<Tstring> traits; 138 typename traits::size_type width = static_cast<typename traits::size_type>(width_); 139 return traits::pad(str, 0, width); 140 } leftmpt::MPT_INLINE_NS::format141 static inline Tstring left(std::size_t width_, const Tstring & str) { 142 typedef mpt::string_traits<Tstring> traits; 143 typename traits::size_type width = static_cast<typename traits::size_type>(width_); 144 return (traits::length(str) < width) ? traits::pad(str, 0, width - traits::length(str)) : str; 145 } rightmpt::MPT_INLINE_NS::format146 static inline Tstring right(std::size_t width_, const Tstring & str) { 147 typedef mpt::string_traits<Tstring> traits; 148 typename traits::size_type width = static_cast<typename traits::size_type>(width_); 149 return (traits::length(str) < width) ? traits::pad(str, width - traits::length(str), 0) : str; 150 } centermpt::MPT_INLINE_NS::format151 static inline Tstring center(std::size_t width_, const Tstring & str) { 152 typedef mpt::string_traits<Tstring> traits; 153 typename traits::size_type width = static_cast<typename traits::size_type>(width_); 154 return (traits::length(str) < width) ? traits::pad(str, (width - traits::length(str)) / 2, (width - traits::length(str) + 1) / 2) : str; 155 } 156 157 }; // struct format 158 159 160 161 } // namespace MPT_INLINE_NS 162 } // namespace mpt 163 164 165 166 #endif // MPT_FORMAT_SIMPLE_HPP 167