Update to 14.0-beta1
This commit is contained in:
+24
-22
@@ -57,7 +57,7 @@ static bool WarnCorruptSprite(const SpriteFile &file, size_t file_pos, int line)
|
||||
* @param container_format Container format of the GRF this sprite is in.
|
||||
* @return True if the sprite was successfully loaded.
|
||||
*/
|
||||
bool DecodeSingleSprite(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, int64 num, byte type, ZoomLevel zoom_lvl, byte colour_fmt, byte container_format)
|
||||
bool DecodeSingleSprite(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, int64_t num, byte type, ZoomLevel zoom_lvl, byte colour_fmt, byte container_format)
|
||||
{
|
||||
/*
|
||||
* Original sprite height was max 255 pixels, with 4x extra zoom => 1020 pixels.
|
||||
@@ -70,11 +70,11 @@ bool DecodeSingleSprite(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t f
|
||||
|
||||
std::unique_ptr<byte[]> dest_orig(new byte[num]);
|
||||
byte *dest = dest_orig.get();
|
||||
const int64 dest_size = num;
|
||||
const int64_t dest_size = num;
|
||||
|
||||
/* Read the file, which has some kind of compression */
|
||||
while (num > 0) {
|
||||
int8 code = file.ReadByte();
|
||||
int8_t code = file.ReadByte();
|
||||
|
||||
if (code >= 0) {
|
||||
/* Plain bytes to read */
|
||||
@@ -101,7 +101,7 @@ bool DecodeSingleSprite(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t f
|
||||
|
||||
if (num != 0) return WarnCorruptSprite(file, file_pos, __LINE__);
|
||||
|
||||
sprite->AllocateData(zoom_lvl, sprite->width * sprite->height);
|
||||
sprite->AllocateData(zoom_lvl, static_cast<size_t>(sprite->width) * sprite->height);
|
||||
|
||||
/* Convert colour depth to pixel size. */
|
||||
int bpp = 0;
|
||||
@@ -164,8 +164,8 @@ bool DecodeSingleSprite(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t f
|
||||
data->a = (colour_fmt & SCC_ALPHA) ? *dest++ : 0xFF;
|
||||
if (colour_fmt & SCC_PAL) {
|
||||
switch (sprite_type) {
|
||||
case ST_NORMAL: data->m = file.NeedsPaletteRemap() ? _palmap_w2d[*dest] : *dest; break;
|
||||
case ST_FONT: data->m = std::min<uint>(*dest, 2u); break;
|
||||
case SpriteType::Normal: data->m = file.NeedsPaletteRemap() ? _palmap_w2d[*dest] : *dest; break;
|
||||
case SpriteType::Font: data->m = std::min<byte>(*dest, 2u); break;
|
||||
default: data->m = *dest; break;
|
||||
}
|
||||
/* Magic blue. */
|
||||
@@ -177,13 +177,14 @@ bool DecodeSingleSprite(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t f
|
||||
} while (!last_item);
|
||||
}
|
||||
} else {
|
||||
if (dest_size < sprite->width * sprite->height * bpp) {
|
||||
int64_t sprite_size = static_cast<int64_t>(sprite->width) * sprite->height * bpp;
|
||||
if (dest_size < sprite_size) {
|
||||
return WarnCorruptSprite(file, file_pos, __LINE__);
|
||||
}
|
||||
|
||||
if (dest_size > sprite->width * sprite->height * bpp) {
|
||||
if (dest_size > sprite_size) {
|
||||
static byte warning_level = 0;
|
||||
Debug(sprite, warning_level, "Ignoring {} unused extra bytes from the sprite from {} at position {}", dest_size - sprite->width * sprite->height * bpp, file.GetSimplifiedFilename(), file_pos);
|
||||
Debug(sprite, warning_level, "Ignoring {} unused extra bytes from the sprite from {} at position {}", dest_size - sprite_size, file.GetSimplifiedFilename(), file_pos);
|
||||
warning_level = 6;
|
||||
}
|
||||
|
||||
@@ -200,8 +201,8 @@ bool DecodeSingleSprite(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t f
|
||||
sprite->data[i].a = (colour_fmt & SCC_ALPHA) ? *pixel++ : 0xFF;
|
||||
if (colour_fmt & SCC_PAL) {
|
||||
switch (sprite_type) {
|
||||
case ST_NORMAL: sprite->data[i].m = file.NeedsPaletteRemap() ? _palmap_w2d[*pixel] : *pixel; break;
|
||||
case ST_FONT: sprite->data[i].m = std::min<uint>(*pixel, 2u); break;
|
||||
case SpriteType::Normal: sprite->data[i].m = file.NeedsPaletteRemap() ? _palmap_w2d[*pixel] : *pixel; break;
|
||||
case SpriteType::Font: sprite->data[i].m = std::min<byte>(*pixel, 2u); break;
|
||||
default: sprite->data[i].m = *pixel; break;
|
||||
}
|
||||
/* Magic blue. */
|
||||
@@ -214,7 +215,7 @@ bool DecodeSingleSprite(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t f
|
||||
return true;
|
||||
}
|
||||
|
||||
uint8 LoadSpriteV1(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, bool load_32bpp)
|
||||
uint8_t LoadSpriteV1(SpriteLoader::SpriteCollection &sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, bool load_32bpp)
|
||||
{
|
||||
/* Check the requested colour depth. */
|
||||
if (load_32bpp) return 0;
|
||||
@@ -229,7 +230,7 @@ uint8 LoadSpriteV1(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_p
|
||||
/* Type 0xFF indicates either a colourmap or some other non-sprite info; we do not handle them here */
|
||||
if (type == 0xFF) return 0;
|
||||
|
||||
ZoomLevel zoom_lvl = (sprite_type != ST_MAPGEN) ? ZOOM_LVL_OUT_4X : ZOOM_LVL_NORMAL;
|
||||
ZoomLevel zoom_lvl = (sprite_type != SpriteType::MapGen) ? ZOOM_LVL_OUT_4X : ZOOM_LVL_NORMAL;
|
||||
|
||||
sprite[zoom_lvl].height = file.ReadByte();
|
||||
sprite[zoom_lvl].width = file.ReadWord();
|
||||
@@ -251,7 +252,7 @@ uint8 LoadSpriteV1(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_p
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint8 LoadSpriteV2(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, bool load_32bpp, byte control_flags)
|
||||
uint8_t LoadSpriteV2(SpriteLoader::SpriteCollection &sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, bool load_32bpp, byte control_flags)
|
||||
{
|
||||
static const ZoomLevel zoom_lvl_map[6] = {ZOOM_LVL_OUT_4X, ZOOM_LVL_NORMAL, ZOOM_LVL_OUT_2X, ZOOM_LVL_OUT_8X, ZOOM_LVL_OUT_16X, ZOOM_LVL_OUT_32X};
|
||||
|
||||
@@ -261,11 +262,11 @@ uint8 LoadSpriteV2(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_p
|
||||
/* Open the right file and go to the correct position */
|
||||
file.SeekTo(file_pos, SEEK_SET);
|
||||
|
||||
uint32 id = file.ReadDword();
|
||||
uint32_t id = file.ReadDword();
|
||||
|
||||
uint8 loaded_sprites = 0;
|
||||
uint8_t loaded_sprites = 0;
|
||||
do {
|
||||
int64 num = file.ReadDword();
|
||||
int64_t num = file.ReadDword();
|
||||
size_t start_pos = file.GetPos();
|
||||
byte type = file.ReadByte();
|
||||
|
||||
@@ -278,14 +279,15 @@ uint8 LoadSpriteV2(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_p
|
||||
bool is_wanted_colour_depth = (colour != 0 && (load_32bpp ? colour != SCC_PAL : colour == SCC_PAL));
|
||||
bool is_wanted_zoom_lvl;
|
||||
|
||||
if (sprite_type != ST_MAPGEN) {
|
||||
if (sprite_type != SpriteType::MapGen) {
|
||||
if (zoom < lengthof(zoom_lvl_map)) {
|
||||
is_wanted_zoom_lvl = true;
|
||||
if (_settings_client.gui.sprite_zoom_min >= ZOOM_LVL_OUT_2X &&
|
||||
ZoomLevel zoom_min = sprite_type == SpriteType::Font ? ZOOM_LVL_NORMAL : _settings_client.gui.sprite_zoom_min;
|
||||
if (zoom_min >= ZOOM_LVL_OUT_2X &&
|
||||
HasBit(control_flags, load_32bpp ? SCCF_ALLOW_ZOOM_MIN_2X_32BPP : SCCF_ALLOW_ZOOM_MIN_2X_PAL) && zoom_lvl_map[zoom] < ZOOM_LVL_OUT_2X) {
|
||||
is_wanted_zoom_lvl = false;
|
||||
}
|
||||
if (_settings_client.gui.sprite_zoom_min >= ZOOM_LVL_OUT_4X &&
|
||||
if (zoom_min >= ZOOM_LVL_OUT_4X &&
|
||||
HasBit(control_flags, load_32bpp ? SCCF_ALLOW_ZOOM_MIN_1X_32BPP : SCCF_ALLOW_ZOOM_MIN_1X_PAL) && zoom_lvl_map[zoom] < ZOOM_LVL_OUT_4X) {
|
||||
is_wanted_zoom_lvl = false;
|
||||
}
|
||||
@@ -297,7 +299,7 @@ uint8 LoadSpriteV2(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_p
|
||||
}
|
||||
|
||||
if (is_wanted_colour_depth && is_wanted_zoom_lvl) {
|
||||
ZoomLevel zoom_lvl = (sprite_type != ST_MAPGEN) ? zoom_lvl_map[zoom] : ZOOM_LVL_NORMAL;
|
||||
ZoomLevel zoom_lvl = (sprite_type != SpriteType::MapGen) ? zoom_lvl_map[zoom] : ZOOM_LVL_NORMAL;
|
||||
|
||||
if (HasBit(loaded_sprites, zoom_lvl)) {
|
||||
/* We already have this zoom level, skip sprite. */
|
||||
@@ -348,7 +350,7 @@ uint8 LoadSpriteV2(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_p
|
||||
return loaded_sprites;
|
||||
}
|
||||
|
||||
uint8 SpriteLoaderGrf::LoadSprite(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, bool load_32bpp, byte control_flags)
|
||||
uint8_t SpriteLoaderGrf::LoadSprite(SpriteLoader::SpriteCollection &sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, bool load_32bpp, byte control_flags)
|
||||
{
|
||||
if (this->container_ver >= 2) {
|
||||
return LoadSpriteV2(sprite, file, file_pos, sprite_type, load_32bpp, control_flags);
|
||||
|
||||
@@ -17,7 +17,7 @@ class SpriteLoaderGrf : public SpriteLoader {
|
||||
byte container_ver;
|
||||
public:
|
||||
SpriteLoaderGrf(byte container_ver) : container_ver(container_ver) {}
|
||||
uint8 LoadSprite(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, bool load_32bpp, byte control_flags);
|
||||
uint8_t LoadSprite(SpriteLoader::SpriteCollection &sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, bool load_32bpp, byte control_flags) override;
|
||||
};
|
||||
|
||||
#endif /* SPRITELOADER_GRF_HPP */
|
||||
|
||||
@@ -32,11 +32,11 @@ class SpriteLoader {
|
||||
public:
|
||||
/** Definition of a common pixel in OpenTTD's realm. */
|
||||
struct CommonPixel {
|
||||
uint8 r; ///< Red-channel
|
||||
uint8 g; ///< Green-channel
|
||||
uint8 b; ///< Blue-channel
|
||||
uint8 a; ///< Alpha-channel
|
||||
uint8 m; ///< Remap-channel
|
||||
uint8_t r; ///< Red-channel
|
||||
uint8_t g; ///< Green-channel
|
||||
uint8_t b; ///< Blue-channel
|
||||
uint8_t a; ///< Alpha-channel
|
||||
uint8_t m; ///< Remap-channel
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -46,10 +46,10 @@ public:
|
||||
* This to prevent thousands of malloc + frees just to load a sprite.
|
||||
*/
|
||||
struct Sprite {
|
||||
uint16 height; ///< Height of the sprite
|
||||
uint16 width; ///< Width of the sprite
|
||||
int16 x_offs; ///< The x-offset of where the sprite will be drawn
|
||||
int16 y_offs; ///< The y-offset of where the sprite will be drawn
|
||||
uint16_t height; ///< Height of the sprite
|
||||
uint16_t width; ///< Width of the sprite
|
||||
int16_t x_offs; ///< The x-offset of where the sprite will be drawn
|
||||
int16_t y_offs; ///< The y-offset of where the sprite will be drawn
|
||||
SpriteType type; ///< The sprite type
|
||||
SpriteColourComponent colours; ///< The colour components of the sprite with useful information.
|
||||
SpriteLoader::CommonPixel *data; ///< The sprite itself
|
||||
@@ -62,9 +62,14 @@ public:
|
||||
void AllocateData(ZoomLevel zoom, size_t size) { this->data = Sprite::buffer[zoom].ZeroAllocate(size); }
|
||||
private:
|
||||
/** Allocated memory to pass sprite data around */
|
||||
static ReusableBuffer<SpriteLoader::CommonPixel> buffer[ZOOM_LVL_COUNT];
|
||||
static ReusableBuffer<SpriteLoader::CommonPixel> buffer[ZOOM_LVL_END];
|
||||
};
|
||||
|
||||
/**
|
||||
* Type defining a collection of sprites, one for each zoom level.
|
||||
*/
|
||||
using SpriteCollection = std::array<Sprite, ZOOM_LVL_END>;
|
||||
|
||||
/**
|
||||
* Load a sprite from the disk and return a sprite struct which is the same for all loaders.
|
||||
* @param[out] sprite The sprites to fill with data.
|
||||
@@ -75,16 +80,16 @@ public:
|
||||
* @param control_flags Control flags, see SpriteCacheCtrlFlags.
|
||||
* @return Bit mask of the zoom levels successfully loaded or 0 if no sprite could be loaded.
|
||||
*/
|
||||
virtual uint8 LoadSprite(SpriteLoader::Sprite *sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, bool load_32bpp, byte control_flags) = 0;
|
||||
virtual uint8_t LoadSprite(SpriteLoader::SpriteCollection &sprite, SpriteFile &file, size_t file_pos, SpriteType sprite_type, bool load_32bpp, byte control_flags) = 0;
|
||||
|
||||
virtual ~SpriteLoader() { }
|
||||
virtual ~SpriteLoader() = default;
|
||||
};
|
||||
|
||||
/** Interface for something that can encode a sprite. */
|
||||
class SpriteEncoder {
|
||||
public:
|
||||
|
||||
virtual ~SpriteEncoder() { }
|
||||
virtual ~SpriteEncoder() = default;
|
||||
|
||||
/**
|
||||
* Can the sprite encoder make use of RGBA sprites?
|
||||
@@ -94,7 +99,7 @@ public:
|
||||
/**
|
||||
* Convert a sprite from the loader to our own format.
|
||||
*/
|
||||
virtual Sprite *Encode(const SpriteLoader::Sprite *sprite, AllocatorProc *allocator) = 0;
|
||||
virtual Sprite *Encode(const SpriteLoader::SpriteCollection &sprite, AllocatorProc *allocator) = 0;
|
||||
|
||||
/**
|
||||
* Get the value which the height and width on a sprite have to be aligned by.
|
||||
|
||||
Reference in New Issue
Block a user