Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revision Previous revision
Next revision
Previous revision
blog:x68_launcher_3 [2020/09/07 11:10] – [bmp.c / bmp.h] johnblog:x68_launcher_3 [2020/09/07 11:51] (current) john
Line 2: Line 2:
  
 ==== bmp.c / bmp.h ==== ==== bmp.c / bmp.h ====
 +
 +   * https://github.com/megatron-uk/x68klauncher/blob/master/src/bmp.c
 +   * https://github.com/megatron-uk/x68klauncher/blob/master/src/bmp.h
  
 The header includes these common files: The header includes these common files:
Line 17: Line 20:
  
 <code "C"> <code "C">
 +#include <stdint.h>
 +
 #define BMP_FILE_SIG_OFFSET 0x0000 // Should always be 'BM' #define BMP_FILE_SIG_OFFSET 0x0000 // Should always be 'BM'
 #define BMP_FILE_SIZE_OFFSET 0x0002 // Size of file, including headers #define BMP_FILE_SIZE_OFFSET 0x0002 // Size of file, including headers
 #define DATA_OFFSET_OFFSET 0x000A // How many bytes from 0x0000 the data section starts #define DATA_OFFSET_OFFSET 0x000A // How many bytes from 0x0000 the data section starts
-#define DIB_HEADER_OFFSET 0x000E // Where the DIB header can be found 
-#define DIB_HEADER_SIZE 4      // DIB header size field is 4 bytes 
 #define WIDTH_OFFSET 0x0012 // Where we can find the x-axis pixel size #define WIDTH_OFFSET 0x0012 // Where we can find the x-axis pixel size
 #define HEIGHT_OFFSET 0x0016 // Where we can find the y-axis pixel size #define HEIGHT_OFFSET 0x0016 // Where we can find the y-axis pixel size
Line 32: Line 35:
 #define INFO_HEADER_SIZE 40 #define INFO_HEADER_SIZE 40
 #define BMP_1BPP 1 #define BMP_1BPP 1
-#define BMP_4BPP 4 
 #define BMP_8BPP 8  #define BMP_8BPP 8
 #define BMP_16BPP 16 #define BMP_16BPP 16
Line 46: Line 48:
 #define BMP_ERR_FONT_WIDTH -7 // We dont support fonts of this width #define BMP_ERR_FONT_WIDTH -7 // We dont support fonts of this width
 #define BMP_ERR_FONT_HEIGHT -8 // We dont support fonts of this height #define BMP_ERR_FONT_HEIGHT -8 // We dont support fonts of this height
 +
 #define BMP_FONT_MAX_WIDTH 8 #define BMP_FONT_MAX_WIDTH 8
 #define BMP_FONT_MAX_HEIGHT 16 #define BMP_FONT_MAX_HEIGHT 16
 #define BMP_FONT_PLANES 4 // Number of colour planes per pixel #define BMP_FONT_PLANES 4 // Number of colour planes per pixel
  
-// ============================ 
-// 
-// A single palette entry of 8bit r, g and b values 
-// 
-// ============================ 
-typedef struct pal_entry { 
- unsigned char r; 
- unsigned char g; 
- unsigned char b; 
- unsigned char new_palette_entry; 
-} pal_entry_t; 
  
 // ============================ // ============================
Line 68: Line 60:
 // ============================ // ============================
 typedef struct bmpdata { typedef struct bmpdata {
- unsigned int width; // X resolution in pixels + unsigned int width; // X resolution in pixels 
- unsigned int height; // Y resolution in pixels + unsigned int height; // Y resolution in pixels 
- char compressed; // If the data is compressed or not (usually RLE) + char compressed;     // If the data is compressed or not (usually RLE) 
- unsigned int dib_size; // size of the DIB header + uint16_t  bpp; // Bits per pixel 
- unsigned char is_indexed; // If the image uses a palette table + uint16_t bytespp; // Bytes per pixel 
- unsigned short colours_offset; + uint32_t offset; // Offset from header to data section, in bytes 
- unsigned int colours; // Count of colours used + unsigned int row_padded; // Size of a row without padding 
- unsigned short bpp; // Bits per pixel + unsigned int row_unpadded; // SIze of a row, padded to a multiple of 4 bytes 
- unsigned short bytespp; // Bytes per pixel + unsigned int size; // Size of the pixel data, in bytes 
- unsigned int offset; // Offset from header to data section, in bytes + unsigned int n_pixels; // Number of pixels 
- unsigned int row_padded; // Size of a row without padding + uint8_t  *pixels; // Pointer to raw pixels - in font mode each byte is a single character 
- unsigned int row_unpadded;         // SIze of a row, padded to a multiple of 4 bytes +__attribute__((__packed__)) __attribute__((aligned (2))) bmpdata_t;
- unsigned int size; // Size of the pixel data, in bytes +
- unsigned int n_pixels; // Number of pixels +
- struct pal_entry palette[256]; // Palette entries for 8bit indexed images +
- unsigned char *pixels; // Pointer to raw pixels - in font mode each byte is a single pixel +
-} bmpdata_t;+
  
 // ============================ // ============================
Line 94: Line 81:
  unsigned int width_bytes;  unsigned int width_bytes;
  unsigned int rows_remaining; // Total number of rows left to be read  unsigned int rows_remaining; // Total number of rows left to be read
- unsigned char *pixels; // Needs to be malloc'ed to the width of a single row of pixels + uint8_t *pixels; // Needs to be malloc'ed to the width of a single row of pixels 
-} bmpstate_t;+__attribute__((__packed__)) __attribute__((aligned (2))) bmpstate_t;
  
 // ============================ // ============================
Line 108: Line 95:
 //============================= //=============================
 typedef struct fontdata { typedef struct fontdata {
- unsigned char width; // Width of each character, in pixels + uint8_t width; // Width of each character, in pixels 
- unsigned char height; // Height of each character, in pixels + uint8_t height; // Height of each character, in pixels 
- unsigned char ascii_start; // ASCII number of symbol 0 + uint8_t ascii_start; // ASCII number of symbol 0 
- unsigned char n_symbols; // Total number of symbols + uint8_t n_symbols; // Total number of symbols 
- unsigned char unknown_symbol; // Which symbol do we map to unknown/missing symbols? + uint8_t unknown_symbol; // Which symbol do we map to unknown/missing symbols? 
- unsigned char symbol[96][16][16]; // Only up to 16px high, 16 px wide fonts + uint8_t symbol[96][BMP_FONT_MAX_HEIGHT][BMP_FONT_PLANES];  
- fontdata_t;+__attribute__((__packed__)) __attribute__((aligned (2))) fontdata_t;
  
 void bmp_Destroy(bmpdata_t *bmpdata); void bmp_Destroy(bmpdata_t *bmpdata);
 void bmp_DestroyFont(fontdata_t *fontdata); void bmp_DestroyFont(fontdata_t *fontdata);
-int bmp_ReadFont(FILE *bmp_image, bmpdata_t *bmpdata, fontdata_t *fontdata, unsigned char header, unsigned char palette, unsigned char data, unsigned char font_width, unsigned char font_height); +int bmp_ReadFont(FILE *bmp_image, bmpdata_t *bmpdata, fontdata_t *fontdata, uint8_t header, uint8_t data, uint8_t font_width, uint8_t font_height); 
-int bmp_ReadImage(FILE *bmp_image, bmpdata_t *bmpdata, unsigned char header, unsigned char palette, unsigned char data);+int bmp_ReadImage(FILE *bmp_image, bmpdata_t *bmpdata, uint8_t header, uint8_t data);
 int bmp_ReadImageHeader(FILE *bmp_image, bmpdata_t *bmpdata); int bmp_ReadImageHeader(FILE *bmp_image, bmpdata_t *bmpdata);
-int bmp_ReadImagePalette(FILE *bmp_image, bmpdata_t *bmpdata); 
 int bmp_ReadImageData(FILE *bmp_image, bmpdata_t *bmpdata); int bmp_ReadImageData(FILE *bmp_image, bmpdata_t *bmpdata);
 +</code>
  
 +The bitmap library has a single function, __bmp_ReadImage()__, that is called in several different ways to parse BMP headers and subsequently read pixel data.
 +
 +The reason the function is called in two passes is to ensure that when the header data is retrieved the image does not exceeded any specific size:
 +
 +   * Open file
 +   * Read BMP header
 +   * Check BMP is correct pixel depth and size
 +   * Read pixel data
 +
 +
 +<code "C">
 +FILE *f;
 +int status;
 +
 +f = fopen("bitmap.bmp", "rb");
 +if (f == NULL){
 +   return -1;
 +}
 +
 +bmp = (bmpdata_t *) malloc(sizeof(bmpdata_t));
 +bmp->pixels = NULL;
 +status = bmp_ReadImageHeader(f, bmp);
 +if (status != 0){
 +   fclose(f);
 +   return -1;
 +}
 +
 +if (bmp->width > 200){
 +  printf("Error, image is more than 200 pixels wide!\n");
 +} else (
 +  printf("Loading pixel data\n");
 +  status = bmp_ReadImageData(f, bmp);
 +)
 +
 +fclose(f);
 </code> </code>
 +
 +----
 +
 +[[blog:x68_launcher_2|<< Back (#2: Filesystem tools, data scraping)]] | [[blog:x68_launcher_4|(#4: Graphics hardware functions) Next >>]]
 +
 +
  • blog/x68_launcher_3.1599473403.txt.gz
  • Last modified: 2020/09/07 11:10
  • by john