#pragma once #include // Para uint8_t, uint16_t, uint32_t #include // Para vector namespace GIF { // Constantes definidas con constexpr, en lugar de macros constexpr uint8_t EXTENSION_INTRODUCER = 0x21; constexpr uint8_t IMAGE_DESCRIPTOR = 0x2C; constexpr uint8_t TRAILER = 0x3B; constexpr uint8_t GRAPHIC_CONTROL = 0xF9; constexpr uint8_t APPLICATION_EXTENSION = 0xFF; constexpr uint8_t COMMENT_EXTENSION = 0xFE; constexpr uint8_t PLAINTEXT_EXTENSION = 0x01; #pragma pack(push, 1) struct ScreenDescriptor { uint16_t width; uint16_t height; uint8_t fields; uint8_t background_color_index; uint8_t pixel_aspect_ratio; }; struct RGB { uint8_t r, g, b; }; struct ImageDescriptor { uint16_t image_left_position; uint16_t image_top_position; uint16_t image_width; uint16_t image_height; uint8_t fields; }; #pragma pack(pop) struct DictionaryEntry { uint8_t byte; int prev; int len; }; struct Extension { uint8_t extension_code; uint8_t block_size; }; struct GraphicControlExtension { uint8_t fields; uint16_t delay_time; uint8_t transparent_color_index; }; struct ApplicationExtension { uint8_t application_id[8]; uint8_t version[3]; }; struct PlaintextExtension { uint16_t left, top, width, height; uint8_t cell_width, cell_height; uint8_t foreground_color, background_color; }; class Gif { public: // Descompone (uncompress) el bloque comprimido usando LZW. // Este método puede lanzar std::runtime_error en caso de error. static void decompress(int code_length, const uint8_t* input, int input_length, uint8_t* out); // Carga la paleta (global color table) a partir de un buffer, // retornándola en un vector de uint32_t (cada color se compone de R, G, B). static std::vector loadPalette(const uint8_t* buffer); // Carga el stream GIF; devuelve un vector con los datos de imagen sin comprimir y // asigna el ancho y alto mediante referencias. static std::vector loadGif(const uint8_t* buffer, uint16_t& w, uint16_t& h); private: // Lee los sub-bloques de datos y los acumula en un std::vector. static std::vector readSubBlocks(const uint8_t*& buffer); // Procesa el Image Descriptor y retorna el vector de datos sin comprimir. static std::vector processImageDescriptor(const uint8_t*& buffer, const std::vector& gct, int resolution_bits); // Procesa el stream completo del GIF y devuelve los datos sin comprimir. static std::vector processGifStream(const uint8_t* buffer, uint16_t& w, uint16_t& h); }; } // namespace GIF