You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
113 lines
2.4 KiB
113 lines
2.4 KiB
#pragma once |
|
|
|
#include <cstring> |
|
#include <initializer_list> |
|
|
|
#include <fmt/format.h> |
|
|
|
#include "utils/stdcompat/string_view.hpp" |
|
|
|
namespace devilution { |
|
|
|
class BaseFileNameGenerator { |
|
public: |
|
BaseFileNameGenerator(std::initializer_list<string_view> prefixes, string_view suffix) |
|
: suffix_(suffix) |
|
, prefixEnd_(Append(buf_, prefixes)) |
|
{ |
|
} |
|
|
|
const char *operator()() const |
|
{ |
|
*Append(prefixEnd_, suffix_) = '\0'; |
|
return buf_; |
|
} |
|
|
|
protected: |
|
static char *Append(char *buf, std::initializer_list<string_view> strings) |
|
{ |
|
for (string_view str : strings) |
|
buf = Append(buf, str); |
|
return buf; |
|
} |
|
|
|
static char *Append(char *buf, string_view str) |
|
{ |
|
memcpy(buf, str.data(), str.size()); |
|
return buf + str.size(); |
|
} |
|
|
|
[[nodiscard]] string_view Suffix() const |
|
{ |
|
return suffix_; |
|
} |
|
[[nodiscard]] char *PrefixEnd() const |
|
{ |
|
return prefixEnd_; |
|
} |
|
[[nodiscard]] const char *Buffer() const |
|
{ |
|
return buf_; |
|
} |
|
|
|
private: |
|
string_view suffix_; |
|
char *prefixEnd_; |
|
char buf_[256]; |
|
}; |
|
|
|
/** |
|
* @brief Generates file names from prefixes, a suffix, and an index. |
|
* |
|
* @example FileNameGenerator f({"a/", "b"}, ".txt", 1); |
|
* f() // "a/b.txt" |
|
* f(0) // "a/b1.txt" |
|
* f(1) // "a/b2.txt" |
|
*/ |
|
class FileNameGenerator : public BaseFileNameGenerator { |
|
public: |
|
FileNameGenerator(std::initializer_list<string_view> prefixes, string_view suffix, unsigned min = 1) |
|
: BaseFileNameGenerator(prefixes, suffix) |
|
, min_(min) |
|
{ |
|
} |
|
|
|
using BaseFileNameGenerator::operator(); |
|
|
|
const char *operator()(size_t i) const |
|
{ |
|
*Append(fmt::format_to(PrefixEnd(), "{}", static_cast<unsigned>(min_ + i)), Suffix()) = '\0'; |
|
return Buffer(); |
|
} |
|
|
|
private: |
|
unsigned min_; |
|
}; |
|
|
|
/** |
|
* @brief Generates file names from prefixes, a suffix, a char array and an index into it. |
|
* |
|
* @example FileNameWithCharAffixGenerator f({"a/", "b"}, ".txt", "ABC"); |
|
* f(0) // "a/bA.txt" |
|
* f(1) // "a/bB.txt" |
|
*/ |
|
class FileNameWithCharAffixGenerator : public BaseFileNameGenerator { |
|
public: |
|
FileNameWithCharAffixGenerator(std::initializer_list<string_view> prefixes, string_view suffix, const char *chars) |
|
: BaseFileNameGenerator(prefixes, suffix) |
|
, chars_(chars) |
|
{ |
|
*Append(PrefixEnd() + 1, Suffix()) = '\0'; |
|
} |
|
|
|
const char *operator()(size_t i) const |
|
{ |
|
PrefixEnd()[0] = chars_[i]; |
|
return Buffer(); |
|
} |
|
|
|
private: |
|
const char *chars_; |
|
}; |
|
|
|
} // namespace devilution
|
|
|