39 const std::string &anim_name,
40 const std::string &frame_name,
41 std::size_t internal_tile_index,
42 std::size_t subtile_row,
43 std::size_t subtile_col)
46 "{} '{}' | frame '{}' | subtile {} | pixel {},{}",
57 const std::string &anim_name,
58 const std::string &frame_name,
59 std::size_t internal_tile_index)
62 "{} '{}' | frame '{}' | subtile {}",
88template <SupportsTransparency PixelType>
97 [[nodiscard]]
const std::string &
name()
const
109 params_ = std::move(
params);
117 return key_frame_.has_value();
130 if (!key_frame_.has_value()) {
131 panic(
"key_frame() called on Animation with no key frame set");
141 [[nodiscard]]
const std::map<std::string, AnimFrame<PixelType>> &
frames()
const
146 [[nodiscard]] std::map<std::string, AnimFrame<PixelType>> &
frames()
153 return frames_ | std::views::values | std::ranges::to<std::vector>();
161 return !frames_.empty();
169 return frames_.size();
174 return frames_.contains(frame_name);
184 if (!frames_.contains(frame_name)) {
185 panic(
"anim '" + name_ +
"' has no such frame '" + frame_name +
"'");
187 return frames_.at(frame_name);
196 frames_.emplace(
name, std::move(frame));
218 requires requires(
const PixelType &p) { p.is_transparent(p); }
225 std::size_t tile_count = 0;
230 tile_count = frames_.begin()->second.tile_count();
233 panic(
"composite_frame() called on Animation with no key frame and no frames");
236 AnimFrame<PixelType> composite{
"composite"};
238 for (std::size_t tile_idx = 0; tile_idx < tile_count; ++tile_idx) {
239 std::set<PixelType> all_colors;
243 auto key_colors =
key_frame().tile_at(tile_idx).unique_nontransparent_colors(extrinsic_transparency);
244 all_colors.merge(key_colors);
248 for (
const auto &[
name, frame] : frames_) {
249 auto colors = frame.tile_at(tile_idx).unique_nontransparent_colors(extrinsic_transparency);
250 all_colors.merge(colors);
254 PixelTile<PixelType> composite_tile{extrinsic_transparency};
255 std::size_t pix_idx = 1;
256 for (
const auto &color : all_colors) {
258 panic(
"pix_idx exceeded tile size in pixels");
260 composite_tile.set(pix_idx++, color);
263 if (composite_tile.unique_nontransparent_colors(extrinsic_transparency).size() >=
palette::max_size) {
264 panic(
"composite tile had >= 16 colors");
267 composite.add_tile(std::move(composite_tile));
276 std::optional<AnimFrame<PixelType>> key_frame_;
277 std::map<std::string, AnimFrame<PixelType>> frames_;
Represents a single frame of an animation, containing tiles and a frame name.
Configuration parameters for a single tileset animation.
A complete tileset animation with name, configuration, and frame data.
const AnimParams & params() const
AnimFrame< PixelType > composite_frame(const PixelType &extrinsic_transparency) const
Returns the "composite" frame for this animation.
Animation(std::string name)
const AnimFrame< PixelType > & frame_for_name(const std::string &frame_name) const
Returns the frame with the specified name.
void params(AnimParams params)
bool has_frames() const
Checks if this animation has any frames.
const std::string & name() const
void key_frame(AnimFrame< PixelType > key_frame)
bool has_key_frame() const
Checks if this animation has a key frame set.
Animation(std::string name, AnimParams params)
const AnimFrame< PixelType > & key_frame() const
Returns the key frame of this animation.
void put_frame(const std::string &name, AnimFrame< PixelType > frame)
Adds a frame to this Animation frame map.
std::map< std::string, AnimFrame< PixelType > > & frames()
bool has_frame(const std::string &frame_name)
std::vector< AnimFrame< PixelType > > frames_values() const
const std::map< std::string, AnimFrame< PixelType > > & frames() const
std::size_t frame_count() const
Returns the number of frames in this animation.
std::string to_pascal_case() const
Outputs all words flattened and joined in PascalCase (each word capitalized, no separators).
Abstract base class for applying text styling with context-aware formatting.
virtual std::string format(const std::string &format_str, const std::vector< FormatParam > ¶ms) const
Formats a string with styled parameters using fmtlib syntax.
std::string managed_callback_name(const std::string &tileset_name)
constexpr std::string porytiles_managed_prefix
constexpr std::string_view porytiles_managed_callback_prefix
constexpr std::string g_tileset_anims_prefix
constexpr std::string s_tileset_anims_prefix
std::string message_header(const TextFormatter &format, const std::string &anim_name, const std::string &frame_name, std::size_t internal_tile_index, std::size_t subtile_row, std::size_t subtile_col)
constexpr std::size_t max_size
constexpr std::size_t size_pix
void panic(const StringViewSourceLoc &s)
Unconditionally terminates the program with a panic message.
DynamicCasedName extract_tileset_cased_name(const std::string &tileset_name)
Extracts the tileset short name and wraps it in a DynamicCasedName.
Utility functions for string manipulation and formatting.