9#include "format_surface.hpp"
42template <
typename Sink,
typename Format,
typename... Args>
43requires OutputSink<Sink> && CompiledFormat<std::remove_cvref_t<Format>>
44[[nodiscard]]
inline ErrorCode Write(Sink& sink,
const Format& format, Args&&... args)
46 using Built = std::remove_cvref_t<Format>;
47 return Writer::template RunArgumentOrder<Sink, Built, Built::ArgumentOrder()>(
48 sink, format, std::forward<Args>(args)...);
56template <OutputSink Sink,
typename Format,
typename... Args>
57[[nodiscard]]
inline ErrorCode FormatTo(Sink& sink,
const Format& format, Args&&... args)
59 return Write(sink, format, std::forward<Args>(args)...);
67template <Text Source, OutputSink Sink,
typename... Args>
68[[nodiscard]]
inline ErrorCode FormatTo(Sink& sink, Args&&... args)
71 return FormatTo(sink, format, std::forward<Args>(args)...);
79template <Text Source, OutputSink Sink,
typename... Args>
80[[nodiscard]]
inline ErrorCode PrintfTo(Sink& sink, Args&&... args)
83 return FormatTo(sink, format, std::forward<Args>(args)...);
103[[nodiscard]]
inline size_t FormatIntoBuffer(
char* buffer,
size_t capacity,
const auto& format,
108 char* buffer =
nullptr;
109 size_t retain_limit = 0;
110 size_t retained_size = 0;
111 size_t total_size = 0;
113 [[nodiscard]]
ErrorCode Write(std::string_view chunk)
115 total_size += chunk.size();
117 if (buffer ==
nullptr || retained_size >= retain_limit)
119 return ErrorCode::OK;
122 size_t writable = retain_limit - retained_size;
123 size_t copy_size = chunk.size() < writable ? chunk.size() : writable;
126 std::memcpy(buffer + retained_size, chunk.data(), copy_size);
127 retained_size += copy_size;
129 return ErrorCode::OK;
135 .retain_limit = capacity > 0 ? capacity - 1 : 0,
137 auto ec = Write(sink, format, std::forward<
decltype(args)>(args)...);
140 if (capacity > 0 && buffer !=
nullptr)
147 if (capacity > 0 && buffer !=
nullptr)
149 buffer[sink.retained_size] =
'\0';
152 return sink.total_size;
161template <Text Source,
typename... Args>
162[[nodiscard]]
inline size_t FormatIntoBuffer(
char* buffer,
size_t capacity, Args&&... args)
165 return FormatIntoBuffer(buffer, capacity, format, std::forward<Args>(args)...);
174template <Text Source,
typename... Args>
175[[nodiscard]]
inline size_t PrintfIntoBuffer(
char* buffer,
size_t capacity, Args&&... args)
178 return FormatIntoBuffer(buffer, capacity, format, std::forward<Args>(args)...);
191[[nodiscard]]
inline int SNPrintf(
char* buffer,
size_t capacity,
const auto& format,
195 FormatIntoBuffer(buffer, capacity, format, std::forward<
decltype(args)>(args)...);
196 if (total_size >
static_cast<size_t>(std::numeric_limits<int>::max()))
200 return static_cast<int>(total_size);
211template <Text Source,
typename... Args>
212[[nodiscard]]
inline int SNPrintf(
char* buffer,
size_t capacity, Args&&... args)
215 return SNPrintf(buffer, capacity, format, std::forward<Args>(args)...);
static consteval Compiled< Source > Build()
Parses and validates a printf format at compile time.
@ OK
操作成功 | Operation successful