diff --git a/doc/api.rst b/doc/api.rst index 5a93b4aa096a..548951902693 100644 --- a/doc/api.rst +++ b/doc/api.rst @@ -120,7 +120,7 @@ custom argument formatter class:: // A custom argument formatter that formats negative integers as unsigned // with the ``x`` format specifier. class CustomArgFormatter : - public fmt::BasicArgFormatter { + public fmt::BasicArgFormatter { public: CustomArgFormatter(fmt::BasicFormatter &f, fmt::FormatSpec &s, const char *fmt) diff --git a/fmt/format.h b/fmt/format.h index b8713978ee1e..58b416be52ef 100644 --- a/fmt/format.h +++ b/fmt/format.h @@ -431,7 +431,9 @@ typedef BasicWriter WWriter; template class ArgFormatter; -template +struct FormatSpec; + +template class BasicPrintfArgFormatter; template +template class ArgFormatterBase : public ArgVisitor { private: BasicWriter &writer_; - FormatSpec &spec_; + Spec &spec_; FMT_DISALLOW_COPY_AND_ASSIGN(ArgFormatterBase); @@ -1938,7 +1943,7 @@ class ArgFormatterBase : public ArgVisitor { protected: BasicWriter &writer() { return writer_; } - FormatSpec &spec() { return spec_; } + Spec &spec() { return spec_; } void write(bool value) { const char *str_value = value ? "true" : "false"; @@ -1952,7 +1957,9 @@ class ArgFormatterBase : public ArgVisitor { } public: - ArgFormatterBase(BasicWriter &w, FormatSpec &s) + typedef Spec SpecType; + + ArgFormatterBase(BasicWriter &w, Spec &s) : writer_(w), spec_(s) {} template @@ -2086,8 +2093,8 @@ class FormatterBase { will be called. \endrst */ -template -class BasicArgFormatter : public internal::ArgFormatterBase { +template +class BasicArgFormatter : public internal::ArgFormatterBase { private: BasicFormatter &formatter_; const Char *format_; @@ -2102,8 +2109,8 @@ class BasicArgFormatter : public internal::ArgFormatterBase { \endrst */ BasicArgFormatter(BasicFormatter &formatter, - FormatSpec &spec, const Char *fmt) - : internal::ArgFormatterBase(formatter.writer(), spec), + Spec &spec, const Char *fmt) + : internal::ArgFormatterBase(formatter.writer(), spec), formatter_(formatter), format_(fmt) {} /** Formats an argument of a custom (user-defined) type. */ @@ -2114,12 +2121,14 @@ class BasicArgFormatter : public internal::ArgFormatterBase { /** The default argument formatter. */ template -class ArgFormatter : public BasicArgFormatter, Char> { +class ArgFormatter : + public BasicArgFormatter, Char, FormatSpec> { public: /** Constructs an argument formatter object. */ ArgFormatter(BasicFormatter &formatter, FormatSpec &spec, const Char *fmt) - : BasicArgFormatter, Char>(formatter, spec, fmt) {} + : BasicArgFormatter, + Char, FormatSpec>(formatter, spec, fmt) {} }; /** This template formats data and writes the output to a writer. */ @@ -2501,16 +2510,16 @@ class BasicWriter { void write_int(T value, Spec spec); // Formats a floating-point number (double or long double). - template - void write_double(T value, const FormatSpec &spec); + template + void write_double(T value, const Spec &spec); // Writes a formatted string. template CharPtr write_str(const StrChar *s, std::size_t size, const AlignSpec &spec); - template + template void write_str(const internal::Arg::StringValue &str, - const FormatSpec &spec); + const Spec &spec); // This following methods are private to disallow writing wide characters // and strings to a char stream. If you want to print a wide string as a @@ -2529,10 +2538,10 @@ class BasicWriter { template void append_float_length(Char *&, T) {} - template + template friend class internal::ArgFormatterBase; - template + template friend class BasicPrintfArgFormatter; protected: @@ -2729,9 +2738,9 @@ typename BasicWriter::CharPtr BasicWriter::write_str( } template -template +template void BasicWriter::write_str( - const internal::Arg::StringValue &s, const FormatSpec &spec) { + const internal::Arg::StringValue &s, const Spec &spec) { // Check if StrChar is convertible to Char. internal::CharTraits::convert(StrChar()); if (spec.type_ && spec.type_ != 's') @@ -2855,7 +2864,7 @@ void BasicWriter::write_int(T value, Spec spec) { UnsignedType n = abs_value; if (spec.flag(HASH_FLAG)) { prefix[prefix_size++] = '0'; - prefix[prefix_size++] = spec.type(); + prefix[prefix_size++] = spec.type_prefix(); } unsigned num_digits = 0; do { @@ -2875,7 +2884,7 @@ void BasicWriter::write_int(T value, Spec spec) { UnsignedType n = abs_value; if (spec.flag(HASH_FLAG)) { prefix[prefix_size++] = '0'; - prefix[prefix_size++] = spec.type(); + prefix[prefix_size++] = spec.type_prefix(); } unsigned num_digits = 0; do { @@ -2923,8 +2932,8 @@ void BasicWriter::write_int(T value, Spec spec) { } template -template -void BasicWriter::write_double(T value, const FormatSpec &spec) { +template +void BasicWriter::write_double(T value, const Spec &spec) { // Check type. char type = spec.type(); bool upper = false; @@ -3661,7 +3670,7 @@ const Char *BasicFormatter::format( const Char *&format_str, const internal::Arg &arg) { using internal::Arg; const Char *s = format_str; - FormatSpec spec; + typename ArgFormatter::SpecType spec; if (*s == ':') { if (arg.type == Arg::CUSTOM) { arg.custom.format(this, arg.custom.value, &s); diff --git a/fmt/printf.h b/fmt/printf.h index 80d224417ace..28f32f8e7779 100644 --- a/fmt/printf.h +++ b/fmt/printf.h @@ -189,15 +189,16 @@ class WidthHandler : public ArgVisitor { superclass will be called. \endrst */ -template -class BasicPrintfArgFormatter : public internal::ArgFormatterBase { +template +class BasicPrintfArgFormatter : + public internal::ArgFormatterBase { private: void write_null_pointer() { this->spec().type_ = 0; this->write("(nil)"); } - typedef internal::ArgFormatterBase Base; + typedef internal::ArgFormatterBase Base; public: /** @@ -207,12 +208,12 @@ class BasicPrintfArgFormatter : public internal::ArgFormatterBase { specifier information for standard argument types. \endrst */ - BasicPrintfArgFormatter(BasicWriter &w, FormatSpec &s) - : internal::ArgFormatterBase(w, s) {} + BasicPrintfArgFormatter(BasicWriter &w, Spec &s) + : internal::ArgFormatterBase(w, s) {} /** Formats an argument of type ``bool``. */ void visit_bool(bool value) { - FormatSpec &fmt_spec = this->spec(); + Spec &fmt_spec = this->spec(); if (fmt_spec.type_ != 's') return this->visit_any_int(value); fmt_spec.type_ = 0; @@ -221,7 +222,7 @@ class BasicPrintfArgFormatter : public internal::ArgFormatterBase { /** Formats a character. */ void visit_char(int value) { - const FormatSpec &fmt_spec = this->spec(); + const Spec &fmt_spec = this->spec(); BasicWriter &w = this->writer(); if (fmt_spec.type_ && fmt_spec.type_ != 'c') w.write_int(value, fmt_spec); @@ -271,12 +272,12 @@ class BasicPrintfArgFormatter : public internal::ArgFormatterBase { /** The default printf argument formatter. */ template -class PrintfArgFormatter - : public BasicPrintfArgFormatter, Char> { +class PrintfArgFormatter : + public BasicPrintfArgFormatter, Char, FormatSpec> { public: /** Constructs an argument formatter object. */ PrintfArgFormatter(BasicWriter &w, FormatSpec &s) - : BasicPrintfArgFormatter, Char>(w, s) {} + : BasicPrintfArgFormatter, Char, FormatSpec>(w, s) {} }; /** This template formats data and writes the output to a writer. */ diff --git a/test/custom-formatter-test.cc b/test/custom-formatter-test.cc index cc9c44854b50..0b573841265b 100644 --- a/test/custom-formatter-test.cc +++ b/test/custom-formatter-test.cc @@ -30,8 +30,8 @@ class CustomArgFormatter // A custom argument formatter that doesn't print `-` for floating-point values // rounded to 0. -class CustomPrintfArgFormatter : - public BasicPrintfArgFormatter { +class CustomPrintfArgFormatter + : public BasicPrintfArgFormatter { public: typedef BasicPrintfArgFormatter Base; diff --git a/test/format-test.cc b/test/format-test.cc index c812b067bd35..6d4a8fcd22b1 100644 --- a/test/format-test.cc +++ b/test/format-test.cc @@ -1660,4 +1660,3 @@ void convert(int); TEST(FormatTest, ConvertCollision) { fmt::format("{}", 42); } -