diff --git a/Porytiles-0.x/lib/include/porytiles/cli_options.h b/Porytiles-0.x/lib/include/porytiles/cli_options.h index 3bb1e218..acd31eed 100644 --- a/Porytiles-0.x/lib/include/porytiles/cli_options.h +++ b/Porytiles-0.x/lib/include/porytiles/cli_options.h @@ -490,6 +490,11 @@ const std::string WNO_MISSING_ASSIGN_CONFIG = W_GENERAL + "no-" + WARN_MISSING_A constexpr int WMISSING_ASSIGN_CONFIG_VAL = 50100; constexpr int WNO_MISSING_ASSIGN_CONFIG_VAL = 60100; +const std::string WKEY_FRAME_MISSING_COLORS = W_GENERAL + WARN_KEY_FRAME_MISSING_COLORS; +const std::string WNO_KEY_FRAME_MISSING_COLORS = W_GENERAL + "no-" + WARN_KEY_FRAME_MISSING_COLORS; +constexpr int WKEY_FRAME_MISSING_COLORS_VAL = 50110; +constexpr int WNO_KEY_FRAME_MISSING_COLORS_VAL = 60110; + // Decompilation warnings const std::string WTILE_INDEX_OUT_OF_RANGE = W_GENERAL + WARN_TILE_INDEX_OUT_OF_RANGE; const std::string WNO_TILE_INDEX_OUT_OF_RANGE = W_GENERAL + "no-" + WARN_TILE_INDEX_OUT_OF_RANGE; diff --git a/Porytiles-0.x/lib/include/porytiles/errors_warnings.h b/Porytiles-0.x/lib/include/porytiles/errors_warnings.h index 68b5cd32..345cc607 100644 --- a/Porytiles-0.x/lib/include/porytiles/errors_warnings.h +++ b/Porytiles-0.x/lib/include/porytiles/errors_warnings.h @@ -3,6 +3,7 @@ #include #include +#include #include "types.h" @@ -18,6 +19,7 @@ struct ErrorsAndWarnings { * counts instead of just a generalized count. */ std::size_t errCount; + std::size_t keyFrameMissingColorsErrCount; std::size_t warnCount; bool printErrors; @@ -32,22 +34,27 @@ struct ErrorsAndWarnings { WarningMode assignCacheOverride; WarningMode invalidAssignCache; WarningMode missingAssignCache; + WarningMode keyFrameMissingColors; // Decompilation warnings WarningMode tileIndexOutOfRange; WarningMode paletteIndexOutOfRange; ErrorsAndWarnings() - : errCount{0}, warnCount{0}, printErrors{true}, colorPrecisionLoss{WarningMode::OFF}, + : errCount{0}, keyFrameMissingColorsErrCount{0}, warnCount{0}, printErrors{true}, colorPrecisionLoss{WarningMode::OFF}, keyFrameNoMatchingTile{WarningMode::OFF}, usedTrueColorMode{WarningMode::OFF}, attributeFormatMismatch{WarningMode::OFF}, missingAttributesCsv{WarningMode::OFF}, unusedAttribute{WarningMode::OFF}, transparencyCollapse{WarningMode::OFF}, assignCacheOverride{WarningMode::OFF}, invalidAssignCache{WarningMode::OFF}, - missingAssignCache{WarningMode::OFF}, tileIndexOutOfRange{WarningMode::OFF}, - paletteIndexOutOfRange{WarningMode::OFF} + missingAssignCache{WarningMode::OFF}, keyFrameMissingColors(WarningMode::OFF), + tileIndexOutOfRange{WarningMode::OFF}, paletteIndexOutOfRange{WarningMode::OFF} { } + [[nodiscard]] std::size_t errTotal() const { + return errCount + keyFrameMissingColorsErrCount; + } + void setAllWarnings(WarningMode setting) { // Compilation warnings @@ -61,6 +68,7 @@ struct ErrorsAndWarnings { assignCacheOverride = setting; invalidAssignCache = setting; missingAssignCache = setting; + keyFrameMissingColors = setting; // Decompilation warnings tileIndexOutOfRange = setting; @@ -100,6 +108,9 @@ struct ErrorsAndWarnings { if (missingAssignCache == WarningMode::WARN) { missingAssignCache = WarningMode::ERR; } + if (keyFrameMissingColors == WarningMode::WARN) { + keyFrameMissingColors = WarningMode::ERR; + } // Decompilation warnings if (tileIndexOutOfRange == WarningMode::WARN) { @@ -122,6 +133,7 @@ extern const char *const WARN_TRANSPARENCY_COLLAPSE; extern const char *const WARN_ASSIGN_CACHE_OVERRIDE; extern const char *const WARN_INVALID_ASSIGN_CACHE; extern const char *const WARN_MISSING_ASSIGN_CACHE; +extern const char *const WARN_KEY_FRAME_MISSING_COLORS; // Decompilation warnings extern const char *const WARN_TILE_INDEX_OUT_OF_RANGE; @@ -286,6 +298,9 @@ void warn_invalidAssignCache(ErrorsAndWarnings &err, const CompilerConfig &confi void warn_missingAssignCache(ErrorsAndWarnings &err, const CompilerConfig &config, std::string path); +void warn_keyFrameMissingColors(ErrorsAndWarnings &err, const CompilerSourcePaths &srcs, const CompilerMode &mode, + std::size_t tileIndex, const std::unordered_set &missingColors, const std::string &animName); + /* * Decompilation warnings (due to possible mistakes in user input), decompilation can continue */ diff --git a/Porytiles-0.x/lib/include/porytiles/types.h b/Porytiles-0.x/lib/include/porytiles/types.h index aa401e0d..e880a54a 100644 --- a/Porytiles-0.x/lib/include/porytiles/types.h +++ b/Porytiles-0.x/lib/include/porytiles/types.h @@ -87,39 +87,53 @@ template <> struct std::hash { }; namespace porytiles { -/** - * RGBA32 format. 1 byte per color and 1 byte for alpha channel. - */ -struct RGBA32 { - std::uint8_t red; - std::uint8_t green; - std::uint8_t blue; - std::uint8_t alpha; - - [[nodiscard]] std::string jasc() const - { - return std::to_string(red) + " " + std::to_string(green) + " " + std::to_string(blue); - } + constexpr std::uint8_t ALPHA_TRANSPARENT = 0; + constexpr std::uint8_t ALPHA_OPAQUE = 255; - auto operator<=>(const RGBA32 &rgba) const = default; + /** + * RGBA32 format. 1 byte per color and 1 byte for alpha channel. + */ + struct RGBA32 { + std::uint8_t red; + std::uint8_t green; + std::uint8_t blue; + std::uint8_t alpha; + + [[nodiscard]] std::string jasc() const + { + return std::to_string(red) + " " + std::to_string(green) + " " + std::to_string(blue); + } - friend std::ostream &operator<<(std::ostream &os, const RGBA32 &rgba); + auto operator<=>(const RGBA32 &rgba) const = default; + + friend std::ostream &operator<<(std::ostream &os, const RGBA32 &rgba); + }; + + extern const RGBA32 RGBA_BLACK; + extern const RGBA32 RGBA_RED; + extern const RGBA32 RGBA_GREEN; + extern const RGBA32 RGBA_BLUE; + extern const RGBA32 RGBA_YELLOW; + extern const RGBA32 RGBA_MAGENTA; + extern const RGBA32 RGBA_CYAN; + extern const RGBA32 RGBA_WHITE; + extern const RGBA32 RGBA_GREY; + extern const RGBA32 RGBA_PURPLE; + extern const RGBA32 RGBA_LIME; +} + +// TODO : better hash function +template <> struct std::hash { + std::size_t operator()(const porytiles::RGBA32 &rgba) const noexcept { + std::size_t h1 = std::hash{}(rgba.red); + std::size_t h2 = std::hash{}(rgba.green); + std::size_t h3 = std::hash{}(rgba.blue); + std::size_t h4 = std::hash{}(rgba.alpha); + return h1 ^ (h2 << 8) ^ (h3 << 16) ^ (h4 << 24); + } }; -constexpr std::uint8_t ALPHA_TRANSPARENT = 0; -constexpr std::uint8_t ALPHA_OPAQUE = 255; - -extern const RGBA32 RGBA_BLACK; -extern const RGBA32 RGBA_RED; -extern const RGBA32 RGBA_GREEN; -extern const RGBA32 RGBA_BLUE; -extern const RGBA32 RGBA_YELLOW; -extern const RGBA32 RGBA_MAGENTA; -extern const RGBA32 RGBA_CYAN; -extern const RGBA32 RGBA_WHITE; -extern const RGBA32 RGBA_GREY; -extern const RGBA32 RGBA_PURPLE; -extern const RGBA32 RGBA_LIME; +namespace porytiles { BGR15 rgbaToBgr(const RGBA32 &rgba) noexcept; diff --git a/Porytiles-0.x/lib/src/cli_parser.cpp b/Porytiles-0.x/lib/src/cli_parser.cpp index f989f898..1b26444b 100644 --- a/Porytiles-0.x/lib/src/cli_parser.cpp +++ b/Porytiles-0.x/lib/src/cli_parser.cpp @@ -529,6 +529,8 @@ std::unordered_map> supportedSubcomm {WNO_INVALID_ASSIGN_CONFIG_CACHE, {Subcommand::COMPILE_PRIMARY, Subcommand::COMPILE_SECONDARY}}, {WMISSING_ASSIGN_CONFIG, {Subcommand::COMPILE_PRIMARY, Subcommand::COMPILE_SECONDARY}}, {WNO_MISSING_ASSIGN_CONFIG, {Subcommand::COMPILE_PRIMARY, Subcommand::COMPILE_SECONDARY}}, + {WKEY_FRAME_MISSING_COLORS, {Subcommand::COMPILE_PRIMARY, Subcommand::COMPILE_SECONDARY}}, + {WNO_KEY_FRAME_MISSING_COLORS, {Subcommand::COMPILE_PRIMARY, Subcommand::COMPILE_SECONDARY}}, // Decompilation warnings {WTILE_INDEX_OUT_OF_RANGE, {Subcommand::DECOMPILE_PRIMARY, Subcommand::DECOMPILE_SECONDARY}}, {WNO_TILE_INDEX_OUT_OF_RANGE, {Subcommand::DECOMPILE_PRIMARY, Subcommand::DECOMPILE_SECONDARY}}, @@ -815,6 +817,9 @@ static void parseSubcommandOptions(PorytilesContext &ctx, int argc, char *const {WMISSING_ASSIGN_CONFIG.c_str(), no_argument, nullptr, WMISSING_ASSIGN_CONFIG_VAL}, {WNO_MISSING_ASSIGN_CONFIG.c_str(), no_argument, nullptr, WNO_MISSING_ASSIGN_CONFIG_VAL}, + {WKEY_FRAME_MISSING_COLORS.c_str(), no_argument, nullptr, WKEY_FRAME_MISSING_COLORS_VAL}, + {WNO_KEY_FRAME_MISSING_COLORS.c_str(), no_argument, nullptr, WNO_KEY_FRAME_MISSING_COLORS_VAL}, + // Decompilation warnings {WTILE_INDEX_OUT_OF_RANGE.c_str(), no_argument, nullptr, WTILE_INDEX_OUT_OF_RANGE_VAL}, {WNO_TILE_INDEX_OUT_OF_RANGE.c_str(), no_argument, nullptr, WNO_TILE_INDEX_OUT_OF_RANGE_VAL}, @@ -869,6 +874,11 @@ static void parseSubcommandOptions(PorytilesContext &ctx, int argc, char *const std::optional warnMissingAssignCache{}; std::optional errMissingAssignCache{}; + // Default this warning to on, since it can lead to issues + // https://github.com/grunt-lucas/porytiles/issues/60 + std::optional warnKeyFrameMissingColors{true}; + std::optional errKeyFrameMissingColors{}; + // Decompilation warnings std::optional warnTileIndexOutOfRange{}; std::optional errTileIndexOutOfRange{}; @@ -1147,6 +1157,9 @@ static void parseSubcommandOptions(PorytilesContext &ctx, int argc, char *const else if (strcmp(optarg, WARN_MISSING_ASSIGN_CACHE) == 0) { errMissingAssignCache = true; } + else if (strcmp(optarg, WARN_KEY_FRAME_MISSING_COLORS) == 0) { + errKeyFrameMissingColors = true; + } // Decompilation warnings else if (strcmp(optarg, WARN_TILE_INDEX_OUT_OF_RANGE) == 0) { errTileIndexOutOfRange = true; @@ -1194,6 +1207,9 @@ static void parseSubcommandOptions(PorytilesContext &ctx, int argc, char *const else if (strcmp(optarg, WARN_MISSING_ASSIGN_CACHE) == 0) { errMissingAssignCache = false; } + else if (strcmp(optarg, WARN_KEY_FRAME_MISSING_COLORS) == 0) { + errKeyFrameMissingColors = false; + } // Decompilation warnings else if (strcmp(optarg, WARN_TILE_INDEX_OUT_OF_RANGE) == 0) { errTileIndexOutOfRange = false; @@ -1289,6 +1305,14 @@ static void parseSubcommandOptions(PorytilesContext &ctx, int argc, char *const validateSubcommandContext(ctx, WNO_MISSING_ASSIGN_CONFIG); warnMissingAssignCache = false; break; + case WKEY_FRAME_MISSING_COLORS_VAL: + validateSubcommandContext(ctx, WKEY_FRAME_MISSING_COLORS); + warnKeyFrameMissingColors = true; + break; + case WNO_KEY_FRAME_MISSING_COLORS_VAL: + validateSubcommandContext(ctx, WNO_KEY_FRAME_MISSING_COLORS); + warnKeyFrameMissingColors = false; + break; // Decompilation warnings case WTILE_INDEX_OUT_OF_RANGE_VAL: validateSubcommandContext(ctx, WTILE_INDEX_OUT_OF_RANGE); @@ -1430,6 +1454,9 @@ static void parseSubcommandOptions(PorytilesContext &ctx, int argc, char *const if (warnMissingAssignCache.has_value()) { ctx.err.missingAssignCache = warnMissingAssignCache.value() ? WarningMode::WARN : WarningMode::OFF; } + if (warnKeyFrameMissingColors.has_value()) { + ctx.err.keyFrameMissingColors = warnKeyFrameMissingColors.value() ? WarningMode::WARN : WarningMode::OFF; + } // Decompilation warnings if (warnTileIndexOutOfRange.has_value()) { ctx.err.tileIndexOutOfRange = warnTileIndexOutOfRange.value() ? WarningMode::WARN : WarningMode::OFF; @@ -1562,6 +1589,17 @@ static void parseSubcommandOptions(PorytilesContext &ctx, int argc, char *const ctx.err.missingAssignCache = WarningMode::OFF; } } + if (errKeyFrameMissingColors.has_value()) { + if (errKeyFrameMissingColors.value()) { + ctx.err.keyFrameMissingColors = WarningMode::ERR; + } + else if ((warnKeyFrameMissingColors.has_value() && warnKeyFrameMissingColors.value()) || enableAllWarnings) { + ctx.err.keyFrameMissingColors = WarningMode::WARN; + } + else { + ctx.err.keyFrameMissingColors = WarningMode::OFF; + } + } // Decompilation warnings if (errTileIndexOutOfRange.has_value()) { if (errTileIndexOutOfRange.value()) { diff --git a/Porytiles-0.x/lib/src/compiler.cpp b/Porytiles-0.x/lib/src/compiler.cpp index b6b54e74..3191f563 100644 --- a/Porytiles-0.x/lib/src/compiler.cpp +++ b/Porytiles-0.x/lib/src/compiler.cpp @@ -1125,6 +1125,7 @@ TEST_CASE("normalizeDecompTiles should correctly normalize all tiles in the deco TEST_CASE("normalizeDecompTiles should correctly normalize multi-frame animated tiles") { porytiles::PorytilesContext ctx{}; + ctx.err.printErrors = false; REQUIRE(std::filesystem::exists(std::filesystem::path{"Resources/Tests/2x2_pattern_2.png"})); png::image tilesPng{"Resources/Tests/2x2_pattern_2.png"}; @@ -1243,6 +1244,7 @@ TEST_CASE("normalizeDecompTiles should correctly normalize multi-frame animated TEST_CASE("buildColorIndexMaps should build a map of all unique colors in the decomp tileset") { porytiles::PorytilesContext ctx{}; + ctx.err.printErrors = false; REQUIRE(std::filesystem::exists(std::filesystem::path{"Resources/Tests/2x2_pattern_2.png"})); png::image png1{"Resources/Tests/2x2_pattern_2.png"}; @@ -1299,6 +1301,7 @@ TEST_CASE("toColorSet should return the correct bitset based on the supplied pal TEST_CASE("matchNormalizedWithColorSets should return the expected data structures") { porytiles::PorytilesContext ctx{}; + ctx.err.printErrors = false; REQUIRE(std::filesystem::exists(std::filesystem::path{"Resources/Tests/2x2_pattern_2.png"})); png::image png1{"Resources/Tests/2x2_pattern_2.png"}; @@ -1911,6 +1914,7 @@ TEST_CASE("compile function should fill out secondary CompiledTileset struct wit TEST_CASE("compile function should correctly compile primary set with animated tiles") { porytiles::PorytilesContext ctx{}; + ctx.err.printErrors = false; ctx.fieldmapConfig.numPalettesInPrimary = 3; ctx.fieldmapConfig.numPalettesTotal = 6; ctx.compilerConfig.primaryAssignAlgorithm = porytiles::AssignAlgorithm::DFS; @@ -2124,6 +2128,7 @@ TEST_CASE("compile function should correctly compile primary set with animated t TEST_CASE("compile function should correctly compile secondary set with animated tiles") { porytiles::PorytilesContext ctx{}; + ctx.err.printErrors = false; ctx.fieldmapConfig.numPalettesInPrimary = 3; ctx.fieldmapConfig.numPalettesTotal = 6; ctx.compilerConfig.primaryAssignAlgorithm = porytiles::AssignAlgorithm::DFS; diff --git a/Porytiles-0.x/lib/src/errors_warnings.cpp b/Porytiles-0.x/lib/src/errors_warnings.cpp index 1f95092c..6454368f 100644 --- a/Porytiles-0.x/lib/src/errors_warnings.cpp +++ b/Porytiles-0.x/lib/src/errors_warnings.cpp @@ -31,6 +31,7 @@ const char *const WARN_TRANSPARENCY_COLLAPSE = "transparency-collapse"; const char *const WARN_ASSIGN_CACHE_OVERRIDE = "assign-cache-override"; const char *const WARN_INVALID_ASSIGN_CACHE = "invalid-assign-cache"; const char *const WARN_MISSING_ASSIGN_CACHE = "missing-assign-cache"; +const char *const WARN_KEY_FRAME_MISSING_COLORS = "key-frame-missing-colors"; // Decompilation warnings const char *const WARN_TILE_INDEX_OUT_OF_RANGE = "tile-index-out-of-range"; @@ -737,6 +738,35 @@ void warn_missingAssignCache(ErrorsAndWarnings &err, const CompilerConfig &confi } } +void warn_keyFrameMissingColors(ErrorsAndWarnings &err, const CompilerSourcePaths &srcs, const CompilerMode &mode, + std::size_t tileIndex, const std::unordered_set &missingColors, const std::string &animName) { + if (err.keyFrameMissingColors == WarningMode::ERR) { + err.keyFrameMissingColorsErrCount++; + if (err.printErrors) { + pt_err( + "animation `{}' key frame tile `{}' missing essential colors [{}]", fmt::styled(animName, fmt::emphasis::bold), fmt::styled(tileIndex, fmt::emphasis::bold), + fmt::styled(fmt::format("-Werror={}", WARN_KEY_FRAME_MISSING_COLORS), fmt::emphasis::bold | fmt::fg(fmt::terminal_color::red))); + } + } + else if (err.keyFrameMissingColors == WarningMode::WARN) { + err.warnCount++; + if (err.printErrors) { + pt_warn( + "animation `{}' key frame tile `{}' missing essential colors [{}]", fmt::styled(animName, fmt::emphasis::bold), fmt::styled(tileIndex, fmt::emphasis::bold), + fmt::styled(fmt::format("-W{}", WARN_KEY_FRAME_MISSING_COLORS), fmt::emphasis::bold | fmt::fg(fmt::terminal_color::magenta))); + } + } + if (err.printErrors) { + pt_note("the following colors were missing from the key frame:"); + for (const auto &color: missingColors) { + pt_println(stderr, " {}", fmt::styled(color.jasc(), fmt::emphasis::bold)); + } + pt_println(stderr, "If left uncorrected, this may lead to the issue described here:"); + pt_println(stderr, " https://github.com/grunt-lucas/porytiles/issues/60"); + pt_println(stderr, ""); + } +} + void warn_tileIndexOutOfRange(ErrorsAndWarnings &err, DecompilerMode mode, std::size_t tileIndex, std::size_t tilesheetSize, const RGBATile &tile) { @@ -801,7 +831,7 @@ void die_errorCount(const ErrorsAndWarnings &err, std::string srcPath, std::stri { if (err.printErrors) { std::string errorStr; - if (err.errCount == 1) { + if (err.errTotal() == 1) { errorStr = "error"; } else { @@ -819,7 +849,7 @@ void die_errorCount(const ErrorsAndWarnings &err, std::string srcPath, std::stri std::to_string(err.errCount), errorStr); } else { - pt_println(stderr, "{} {} generated.", std::to_string(err.errCount), errorStr); + pt_println(stderr, "{} {} generated.", std::to_string(err.errTotal()), errorStr); } pt_println(stderr, "terminating compilation of {}", fmt::styled(srcPath, fmt::emphasis::bold)); } diff --git a/Porytiles-0.x/lib/src/importer.cpp b/Porytiles-0.x/lib/src/importer.cpp index e2b30d7c..08052de4 100644 --- a/Porytiles-0.x/lib/src/importer.cpp +++ b/Porytiles-0.x/lib/src/importer.cpp @@ -376,6 +376,56 @@ DecompiledTileset importLayeredTilesFromPngs(PorytilesContext &ctx, CompilerMode return decompiledTiles; } +static void validateAnimFormat(PorytilesContext &ctx, const DecompiledAnimation &anim, CompilerMode compilerMode) { + if (anim.frames.size() < 2) { + internalerror("importer::validateAnimFormat bad anim format, found frames.size() < 2"); + } + std::vector> keyFrameColors{}; + std::vector> regularFrameColors{}; + std::vector> keyFrameMissingColors{}; + + for (const auto &tile : anim.keyFrame().tiles) { + std::unordered_set tileColors{}; + for (const auto &color : tile.pixels) { + tileColors.insert(color); + } + keyFrameColors.push_back(tileColors); + } + + for (int i = 0; i < keyFrameColors.size(); i++) { + regularFrameColors.emplace_back(); + keyFrameMissingColors.emplace_back(); + } + + for (int i = 1; i < anim.size(); i++) { + const auto &frame = anim.frames.at(i); + int tileIndex = 0; + for (const auto &tile : frame.tiles) { + for (const auto &color : tile.pixels) { + regularFrameColors.at(tileIndex).insert(color); + } + tileIndex++; + } + } + + for (int i = 0; i < keyFrameColors.size(); i++) { + const auto &keyFrameColorsSet = keyFrameColors.at(i); + const auto ®ularFrameColorsSet = regularFrameColors.at(i); + auto &keyFrameMissingColorsSet = keyFrameMissingColors.at(i); + for (const auto &color : regularFrameColorsSet) { + if (!keyFrameColorsSet.contains(color)) { + keyFrameMissingColorsSet.insert(color); + } + } + } + + for (int i = 0; i < keyFrameMissingColors.size(); i++) { + if (!keyFrameMissingColors.at(i).empty()) { + warn_keyFrameMissingColors(ctx.err, ctx.compilerSrcPaths, compilerMode, i, keyFrameMissingColors.at(i), anim.animName); + } + } +} + void importAnimTiles(PorytilesContext &ctx, CompilerMode compilerMode, const std::vector>> &rawAnims, DecompiledTileset &tiles) { @@ -443,9 +493,14 @@ void importAnimTiles(PorytilesContext &ctx, CompilerMode compilerMode, } anim.frames.push_back(animFrame); } + validateAnimFormat(ctx, anim, compilerMode); anims.push_back(anim); } + if (ctx.err.keyFrameMissingColorsErrCount > 0) { + die_errorCount(ctx.err, ctx.compilerSrcPaths.modeBasedSrcPath(compilerMode), + "some key frame subtiles were missing essential colors"); + } tiles.anims = anims; } @@ -1336,6 +1391,7 @@ TEST_CASE("importLayeredTilesFromPngs should read the RGBA PNGs into a Decompile TEST_CASE("importAnimTiles should read each animation and correctly populate the DecompiledTileset anims field") { porytiles::PorytilesContext ctx{}; + ctx.err.printErrors = false; REQUIRE(std::filesystem::exists(std::filesystem::path{"Resources/Tests/anim_flower_white"})); REQUIRE(std::filesystem::exists(std::filesystem::path{"Resources/Tests/anim_flower_yellow"})); diff --git a/Porytiles-0.x/lib/src/types.cpp b/Porytiles-0.x/lib/src/types.cpp index 58f4d4b5..ba6baf2b 100644 --- a/Porytiles-0.x/lib/src/types.cpp +++ b/Porytiles-0.x/lib/src/types.cpp @@ -1,7 +1,9 @@ #include "types.h" #include +#include #include +#include #include "errors_warnings.h" @@ -682,7 +684,6 @@ std::string decompilerModeString(DecompilerMode mode) // unreachable, here for compiler throw std::runtime_error("types::decompilerModeString reached unreachable code path"); } - } // namespace porytiles // -------------------- diff --git a/Resources/Examples/simple_primary_1_badanim/anim/flower_white/00.png b/Resources/Examples/simple_primary_1_badanim/anim/flower_white/00.png new file mode 100644 index 00000000..290d8f47 Binary files /dev/null and b/Resources/Examples/simple_primary_1_badanim/anim/flower_white/00.png differ diff --git a/Resources/Examples/simple_primary_1_badanim/anim/flower_white/01.png b/Resources/Examples/simple_primary_1_badanim/anim/flower_white/01.png new file mode 100644 index 00000000..979a0ad7 Binary files /dev/null and b/Resources/Examples/simple_primary_1_badanim/anim/flower_white/01.png differ diff --git a/Resources/Examples/simple_primary_1_badanim/anim/flower_white/02.png b/Resources/Examples/simple_primary_1_badanim/anim/flower_white/02.png new file mode 100644 index 00000000..5efcad54 Binary files /dev/null and b/Resources/Examples/simple_primary_1_badanim/anim/flower_white/02.png differ diff --git a/Resources/Examples/simple_primary_1_badanim/anim/flower_white/key.png b/Resources/Examples/simple_primary_1_badanim/anim/flower_white/key.png new file mode 100644 index 00000000..0b6446b5 Binary files /dev/null and b/Resources/Examples/simple_primary_1_badanim/anim/flower_white/key.png differ diff --git a/Resources/Examples/simple_primary_1_badanim/anim/water/00.png b/Resources/Examples/simple_primary_1_badanim/anim/water/00.png new file mode 100644 index 00000000..63cce504 Binary files /dev/null and b/Resources/Examples/simple_primary_1_badanim/anim/water/00.png differ diff --git a/Resources/Examples/simple_primary_1_badanim/anim/water/01.png b/Resources/Examples/simple_primary_1_badanim/anim/water/01.png new file mode 100644 index 00000000..736f11af Binary files /dev/null and b/Resources/Examples/simple_primary_1_badanim/anim/water/01.png differ diff --git a/Resources/Examples/simple_primary_1_badanim/anim/water/key.png b/Resources/Examples/simple_primary_1_badanim/anim/water/key.png new file mode 100644 index 00000000..63cce504 Binary files /dev/null and b/Resources/Examples/simple_primary_1_badanim/anim/water/key.png differ diff --git a/Resources/Examples/simple_primary_1_badanim/assign.cache b/Resources/Examples/simple_primary_1_badanim/assign.cache new file mode 100644 index 00000000..089a3fb0 --- /dev/null +++ b/Resources/Examples/simple_primary_1_badanim/assign.cache @@ -0,0 +1,3 @@ +assign-algorithm=dfs +explore-cutoff=1000000 +best-branches=2 diff --git a/Resources/Examples/simple_primary_1_badanim/attributes.csv b/Resources/Examples/simple_primary_1_badanim/attributes.csv new file mode 100644 index 00000000..f386f28c --- /dev/null +++ b/Resources/Examples/simple_primary_1_badanim/attributes.csv @@ -0,0 +1,8 @@ +id,behavior +1,MB_TALL_GRASS +2,MB_TALL_GRASS +3,MB_TALL_GRASS +4,MB_TALL_GRASS +5,MB_TALL_GRASS +6,MB_TALL_GRASS +63,MB_PUDDLE diff --git a/Resources/Examples/simple_primary_1_badanim/bottom.png b/Resources/Examples/simple_primary_1_badanim/bottom.png new file mode 100644 index 00000000..ab5bbc2d Binary files /dev/null and b/Resources/Examples/simple_primary_1_badanim/bottom.png differ diff --git a/Resources/Examples/simple_primary_1_badanim/middle.png b/Resources/Examples/simple_primary_1_badanim/middle.png new file mode 100644 index 00000000..aeb6561d Binary files /dev/null and b/Resources/Examples/simple_primary_1_badanim/middle.png differ diff --git a/Resources/Examples/simple_primary_1_badanim/top.png b/Resources/Examples/simple_primary_1_badanim/top.png new file mode 100644 index 00000000..4339f93c Binary files /dev/null and b/Resources/Examples/simple_primary_1_badanim/top.png differ