File library for Bitmap images (*.bmp, *.dib). Currently supports only Windows V3 format with 24-bit-per-pixel color depth.
BMPFile.cpp@3:be3e831a86c1, 2015-04-05 (annotated)
- Committer:
- kayekss
- Date:
- Sun Apr 05 14:19:49 2015 +0000
- Revision:
- 3:be3e831a86c1
- Parent:
- 2:89b273c12b0a
(1) Add constructor switch: fetch/not fetch image data. (2) RGB return value is doubled in 16-bit-per-pixel mode.
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
kayekss | 0:4617bf407fe5 | 1 | // ==================================================== Mar 04 2015, kayeks == |
kayekss | 0:4617bf407fe5 | 2 | // BMPFile.cpp |
kayekss | 0:4617bf407fe5 | 3 | // =========================================================================== |
kayekss | 0:4617bf407fe5 | 4 | // File library for Bitmap images (*.bmp, *.dib). |
kayekss | 0:4617bf407fe5 | 5 | |
kayekss | 0:4617bf407fe5 | 6 | #include "BMPFile.h" |
kayekss | 0:4617bf407fe5 | 7 | |
kayekss | 0:4617bf407fe5 | 8 | const char* BMPFile::StatusString[] = { |
kayekss | 0:4617bf407fe5 | 9 | "Success", |
kayekss | 0:4617bf407fe5 | 10 | "NullFileName", |
kayekss | 0:4617bf407fe5 | 11 | "NoSuchFile", |
kayekss | 0:4617bf407fe5 | 12 | "NotABitmapFile", |
kayekss | 0:4617bf407fe5 | 13 | "UnsupportedFormat", |
kayekss | 0:4617bf407fe5 | 14 | "UnsupportedDepth", |
kayekss | 0:4617bf407fe5 | 15 | "AllocationFailed" |
kayekss | 0:4617bf407fe5 | 16 | }; |
kayekss | 0:4617bf407fe5 | 17 | const char* BMPFile::FormatString[] = { |
kayekss | 1:8cf4beca9695 | 18 | "OS2_V1", |
kayekss | 1:8cf4beca9695 | 19 | "OS2_V2", |
kayekss | 0:4617bf407fe5 | 20 | "Windows_V3", |
kayekss | 0:4617bf407fe5 | 21 | "Windows_V4", |
kayekss | 0:4617bf407fe5 | 22 | "Windows_V5", |
kayekss | 0:4617bf407fe5 | 23 | "Unknown" |
kayekss | 0:4617bf407fe5 | 24 | }; |
kayekss | 0:4617bf407fe5 | 25 | |
kayekss | 3:be3e831a86c1 | 26 | void BMPFile::readFile(FILE* fp, bool fetchData) { |
kayekss | 0:4617bf407fe5 | 27 | uint8_t buf8[2]; |
kayekss | 0:4617bf407fe5 | 28 | uint16_t buf16[2]; |
kayekss | 0:4617bf407fe5 | 29 | uint32_t buf32[3]; |
kayekss | 1:8cf4beca9695 | 30 | |
kayekss | 0:4617bf407fe5 | 31 | if (!fp) { |
kayekss | 0:4617bf407fe5 | 32 | status = NoSuchFile; |
kayekss | 0:4617bf407fe5 | 33 | return; |
kayekss | 0:4617bf407fe5 | 34 | } |
kayekss | 0:4617bf407fe5 | 35 | |
kayekss | 0:4617bf407fe5 | 36 | // (0 +2) Magic number ("BM") |
kayekss | 0:4617bf407fe5 | 37 | fread(buf8, 1, 2, fp); |
kayekss | 0:4617bf407fe5 | 38 | if (buf8[0] != 'B' || buf8[1] != 'M') { |
kayekss | 0:4617bf407fe5 | 39 | status = NotABitmapFile; |
kayekss | 0:4617bf407fe5 | 40 | fclose(fp); |
kayekss | 0:4617bf407fe5 | 41 | return; |
kayekss | 0:4617bf407fe5 | 42 | } |
kayekss | 0:4617bf407fe5 | 43 | |
kayekss | 0:4617bf407fe5 | 44 | // (2 +4) File size |
kayekss | 0:4617bf407fe5 | 45 | // (6 +4) Reserved area |
kayekss | 0:4617bf407fe5 | 46 | // (10 +4) Image data offset (unconfirmed) |
kayekss | 0:4617bf407fe5 | 47 | fread(buf32, 4, 3, fp); |
kayekss | 0:4617bf407fe5 | 48 | fileSize = buf32[0]; |
kayekss | 0:4617bf407fe5 | 49 | |
kayekss | 0:4617bf407fe5 | 50 | // (14 +4) Header size |
kayekss | 0:4617bf407fe5 | 51 | fread(buf32, 4, 1, fp); |
kayekss | 0:4617bf407fe5 | 52 | switch (buf32[0]) { |
kayekss | 1:8cf4beca9695 | 53 | case 12: // OS/2 V1 format |
kayekss | 1:8cf4beca9695 | 54 | format = OS2_V1; |
kayekss | 1:8cf4beca9695 | 55 | break; |
kayekss | 1:8cf4beca9695 | 56 | case 64: // OS/2 V2 format |
kayekss | 1:8cf4beca9695 | 57 | format = OS2_V2; |
kayekss | 1:8cf4beca9695 | 58 | break; |
kayekss | 0:4617bf407fe5 | 59 | case 40: // Windows V3 format |
kayekss | 0:4617bf407fe5 | 60 | format = Windows_V3; |
kayekss | 0:4617bf407fe5 | 61 | break; |
kayekss | 0:4617bf407fe5 | 62 | case 108: // Windows V4 format |
kayekss | 0:4617bf407fe5 | 63 | format = Windows_V4; |
kayekss | 0:4617bf407fe5 | 64 | break; |
kayekss | 0:4617bf407fe5 | 65 | case 124: // Windows V5 format |
kayekss | 0:4617bf407fe5 | 66 | format = Windows_V5; |
kayekss | 0:4617bf407fe5 | 67 | break; |
kayekss | 0:4617bf407fe5 | 68 | default: |
kayekss | 0:4617bf407fe5 | 69 | format = Unknown; |
kayekss | 0:4617bf407fe5 | 70 | } |
kayekss | 0:4617bf407fe5 | 71 | |
kayekss | 0:4617bf407fe5 | 72 | switch (format) { |
kayekss | 1:8cf4beca9695 | 73 | case OS2_V1: |
kayekss | 1:8cf4beca9695 | 74 | // (18 +2) Bitmap width |
kayekss | 1:8cf4beca9695 | 75 | // (20 +2) Bitmap height |
kayekss | 1:8cf4beca9695 | 76 | fread(buf16, 4, 2, fp); |
kayekss | 1:8cf4beca9695 | 77 | width = (uint32_t) buf16[0]; |
kayekss | 1:8cf4beca9695 | 78 | height = (uint32_t) buf16[1]; |
kayekss | 1:8cf4beca9695 | 79 | |
kayekss | 1:8cf4beca9695 | 80 | // (22 +2) Number of planes (unconfirmed) |
kayekss | 1:8cf4beca9695 | 81 | // (24 +2) Color depth |
kayekss | 1:8cf4beca9695 | 82 | fread(buf16, 2, 2, fp); |
kayekss | 1:8cf4beca9695 | 83 | colorDepth = buf16[1]; |
kayekss | 1:8cf4beca9695 | 84 | switch (colorDepth) { |
kayekss | 1:8cf4beca9695 | 85 | case 1: case 4: case 8: |
kayekss | 1:8cf4beca9695 | 86 | paletteSize = paletteElemSize(format) * (1ul << colorDepth); |
kayekss | 1:8cf4beca9695 | 87 | break; |
kayekss | 1:8cf4beca9695 | 88 | case 16: case 24: case 32: // No palette |
kayekss | 1:8cf4beca9695 | 89 | paletteSize = 0; |
kayekss | 1:8cf4beca9695 | 90 | break; |
kayekss | 1:8cf4beca9695 | 91 | default: |
kayekss | 1:8cf4beca9695 | 92 | paletteSize = 0; |
kayekss | 1:8cf4beca9695 | 93 | status = UnsupportedDepth; |
kayekss | 1:8cf4beca9695 | 94 | fclose(fp); |
kayekss | 1:8cf4beca9695 | 95 | return; |
kayekss | 1:8cf4beca9695 | 96 | } |
kayekss | 1:8cf4beca9695 | 97 | break; |
kayekss | 0:4617bf407fe5 | 98 | case Windows_V3: |
kayekss | 0:4617bf407fe5 | 99 | // (18 +4) Bitmap width |
kayekss | 0:4617bf407fe5 | 100 | // (22 +4) Bitmap height |
kayekss | 0:4617bf407fe5 | 101 | fread(buf32, 4, 2, fp); |
kayekss | 0:4617bf407fe5 | 102 | width = buf32[0]; |
kayekss | 0:4617bf407fe5 | 103 | height = buf32[1]; |
kayekss | 0:4617bf407fe5 | 104 | |
kayekss | 0:4617bf407fe5 | 105 | // (26 +2) Number of planes (unconfirmed) |
kayekss | 0:4617bf407fe5 | 106 | // (28 +2) Color depth |
kayekss | 0:4617bf407fe5 | 107 | fread(buf16, 2, 2, fp); |
kayekss | 0:4617bf407fe5 | 108 | colorDepth = buf16[1]; |
kayekss | 1:8cf4beca9695 | 109 | switch (colorDepth) { |
kayekss | 1:8cf4beca9695 | 110 | case 1: case 4: case 8: |
kayekss | 1:8cf4beca9695 | 111 | paletteSize = paletteElemSize(format) * (1ul << colorDepth); |
kayekss | 1:8cf4beca9695 | 112 | break; |
kayekss | 1:8cf4beca9695 | 113 | case 16: case 24: case 32: // No palette |
kayekss | 1:8cf4beca9695 | 114 | paletteSize = 0; |
kayekss | 1:8cf4beca9695 | 115 | break; |
kayekss | 1:8cf4beca9695 | 116 | default: |
kayekss | 1:8cf4beca9695 | 117 | paletteSize = 0; |
kayekss | 0:4617bf407fe5 | 118 | status = UnsupportedDepth; |
kayekss | 0:4617bf407fe5 | 119 | fclose(fp); |
kayekss | 0:4617bf407fe5 | 120 | return; |
kayekss | 0:4617bf407fe5 | 121 | } |
kayekss | 0:4617bf407fe5 | 122 | |
kayekss | 0:4617bf407fe5 | 123 | // (30 +4) Compression method (unconfirmed) |
kayekss | 0:4617bf407fe5 | 124 | // (34 +4) Bitmap data size (unconfirmed) |
kayekss | 0:4617bf407fe5 | 125 | // (38 +4) Horizontal resolution (unused) |
kayekss | 0:4617bf407fe5 | 126 | // (42 +4) Vertical resolution (unconfirmed) |
kayekss | 0:4617bf407fe5 | 127 | // (46 +4) Colors (unconfirmed) |
kayekss | 0:4617bf407fe5 | 128 | // (50 +4) Important colors (unconfirmed) |
kayekss | 0:4617bf407fe5 | 129 | fread(buf32, 4, 3, fp); |
kayekss | 0:4617bf407fe5 | 130 | fread(buf32, 4, 3, fp); |
kayekss | 0:4617bf407fe5 | 131 | break; |
kayekss | 1:8cf4beca9695 | 132 | case OS2_V2: |
kayekss | 0:4617bf407fe5 | 133 | case Windows_V4: |
kayekss | 0:4617bf407fe5 | 134 | case Windows_V5: |
kayekss | 0:4617bf407fe5 | 135 | case Unknown: |
kayekss | 0:4617bf407fe5 | 136 | status = UnsupportedFormat; |
kayekss | 0:4617bf407fe5 | 137 | fclose(fp); |
kayekss | 0:4617bf407fe5 | 138 | return; |
kayekss | 0:4617bf407fe5 | 139 | } |
kayekss | 1:8cf4beca9695 | 140 | |
kayekss | 1:8cf4beca9695 | 141 | // Allocate palette space if needed |
kayekss | 1:8cf4beca9695 | 142 | if (paletteSize) { |
kayekss | 1:8cf4beca9695 | 143 | palette = new uint8_t[paletteSize]; |
kayekss | 1:8cf4beca9695 | 144 | |
kayekss | 1:8cf4beca9695 | 145 | // Read palette data |
kayekss | 1:8cf4beca9695 | 146 | fread(palette, 1, paletteSize, fp); |
kayekss | 1:8cf4beca9695 | 147 | } |
kayekss | 0:4617bf407fe5 | 148 | |
kayekss | 1:8cf4beca9695 | 149 | // Calculate stride / data length |
kayekss | 1:8cf4beca9695 | 150 | if (colorDepth == 1) { |
kayekss | 1:8cf4beca9695 | 151 | stride = ALIGN_BY_4((width + 7) / 8); |
kayekss | 1:8cf4beca9695 | 152 | } else if (colorDepth == 4) { |
kayekss | 1:8cf4beca9695 | 153 | stride = ALIGN_BY_4((width + 1) / 2); |
kayekss | 1:8cf4beca9695 | 154 | } else { |
kayekss | 1:8cf4beca9695 | 155 | // Color depth: 8, 16, 24, 32 |
kayekss | 1:8cf4beca9695 | 156 | stride = ALIGN_BY_4(width * colorDepth / 8); |
kayekss | 1:8cf4beca9695 | 157 | } |
kayekss | 1:8cf4beca9695 | 158 | dataSize = stride * height; |
kayekss | 0:4617bf407fe5 | 159 | |
kayekss | 3:be3e831a86c1 | 160 | // Read image data |
kayekss | 3:be3e831a86c1 | 161 | if (fetchData) { |
kayekss | 3:be3e831a86c1 | 162 | readImageData(fp); |
kayekss | 3:be3e831a86c1 | 163 | } |
kayekss | 3:be3e831a86c1 | 164 | fclose(fp); |
kayekss | 3:be3e831a86c1 | 165 | } |
kayekss | 3:be3e831a86c1 | 166 | |
kayekss | 3:be3e831a86c1 | 167 | BMPFile::BMPFile(const char* filename, bool fetchData) { |
kayekss | 3:be3e831a86c1 | 168 | FILE* fp; |
kayekss | 3:be3e831a86c1 | 169 | |
kayekss | 3:be3e831a86c1 | 170 | status = Success; |
kayekss | 3:be3e831a86c1 | 171 | format = Unknown; |
kayekss | 3:be3e831a86c1 | 172 | fileSize = 0; |
kayekss | 3:be3e831a86c1 | 173 | paletteSize = 0; |
kayekss | 3:be3e831a86c1 | 174 | dataSize = 0; |
kayekss | 3:be3e831a86c1 | 175 | stride = 0; |
kayekss | 3:be3e831a86c1 | 176 | width = 0; |
kayekss | 3:be3e831a86c1 | 177 | height = 0; |
kayekss | 3:be3e831a86c1 | 178 | colorDepth = 0; |
kayekss | 3:be3e831a86c1 | 179 | palette = NULL; |
kayekss | 3:be3e831a86c1 | 180 | data = NULL; |
kayekss | 0:4617bf407fe5 | 181 | |
kayekss | 3:be3e831a86c1 | 182 | // Open file |
kayekss | 3:be3e831a86c1 | 183 | if (!filename) { |
kayekss | 3:be3e831a86c1 | 184 | status = NullFilename; |
kayekss | 3:be3e831a86c1 | 185 | return; |
kayekss | 3:be3e831a86c1 | 186 | } |
kayekss | 3:be3e831a86c1 | 187 | fp = fopen(filename, "rb"); |
kayekss | 0:4617bf407fe5 | 188 | |
kayekss | 3:be3e831a86c1 | 189 | // Read file |
kayekss | 3:be3e831a86c1 | 190 | readFile(fp, fetchData); |
kayekss | 3:be3e831a86c1 | 191 | } |
kayekss | 3:be3e831a86c1 | 192 | |
kayekss | 3:be3e831a86c1 | 193 | BMPFile::BMPFile(FILE* fp, bool fetch) { |
kayekss | 3:be3e831a86c1 | 194 | status = Success; |
kayekss | 3:be3e831a86c1 | 195 | format = Unknown; |
kayekss | 3:be3e831a86c1 | 196 | fileSize = 0; |
kayekss | 3:be3e831a86c1 | 197 | paletteSize = 0; |
kayekss | 3:be3e831a86c1 | 198 | dataSize = 0; |
kayekss | 3:be3e831a86c1 | 199 | stride = 0; |
kayekss | 3:be3e831a86c1 | 200 | width = 0; |
kayekss | 3:be3e831a86c1 | 201 | height = 0; |
kayekss | 3:be3e831a86c1 | 202 | colorDepth = 0; |
kayekss | 3:be3e831a86c1 | 203 | palette = NULL; |
kayekss | 3:be3e831a86c1 | 204 | data = NULL; |
kayekss | 3:be3e831a86c1 | 205 | |
kayekss | 3:be3e831a86c1 | 206 | // Read file |
kayekss | 3:be3e831a86c1 | 207 | readFile(fp, fetch); |
kayekss | 0:4617bf407fe5 | 208 | } |
kayekss | 0:4617bf407fe5 | 209 | |
kayekss | 0:4617bf407fe5 | 210 | BMPFile::~BMPFile() { |
kayekss | 1:8cf4beca9695 | 211 | if (palette) { |
kayekss | 1:8cf4beca9695 | 212 | delete[] palette; |
kayekss | 1:8cf4beca9695 | 213 | } |
kayekss | 0:4617bf407fe5 | 214 | if (data) { |
kayekss | 0:4617bf407fe5 | 215 | delete[] data; |
kayekss | 0:4617bf407fe5 | 216 | } |
kayekss | 0:4617bf407fe5 | 217 | } |
kayekss | 1:8cf4beca9695 | 218 | |
kayekss | 3:be3e831a86c1 | 219 | void BMPFile::readImageData(FILE* fp) { |
kayekss | 3:be3e831a86c1 | 220 | // Allocate data space |
kayekss | 3:be3e831a86c1 | 221 | data = new uint8_t[dataSize]; |
kayekss | 3:be3e831a86c1 | 222 | |
kayekss | 3:be3e831a86c1 | 223 | // Read bitmap data |
kayekss | 3:be3e831a86c1 | 224 | fread(data, 1, dataSize, fp); |
kayekss | 3:be3e831a86c1 | 225 | } |
kayekss | 3:be3e831a86c1 | 226 | |
kayekss | 1:8cf4beca9695 | 227 | uint32_t BMPFile::paletteElemSize(BMPFile::Format format) { |
kayekss | 1:8cf4beca9695 | 228 | switch (format) { |
kayekss | 1:8cf4beca9695 | 229 | case OS2_V1: case OS2_V2: |
kayekss | 1:8cf4beca9695 | 230 | // BGR888 |
kayekss | 1:8cf4beca9695 | 231 | return 3; |
kayekss | 1:8cf4beca9695 | 232 | case Windows_V3: case Windows_V4: case Windows_V5: |
kayekss | 1:8cf4beca9695 | 233 | // BGRX8888 |
kayekss | 1:8cf4beca9695 | 234 | return 4; |
kayekss | 1:8cf4beca9695 | 235 | default: |
kayekss | 1:8cf4beca9695 | 236 | return 0; |
kayekss | 1:8cf4beca9695 | 237 | } |
kayekss | 1:8cf4beca9695 | 238 | } |
kayekss | 1:8cf4beca9695 | 239 | |
kayekss | 1:8cf4beca9695 | 240 | int32_t BMPFile::paletteRed(uint8_t index) { |
kayekss | 1:8cf4beca9695 | 241 | if (!palette) { |
kayekss | 1:8cf4beca9695 | 242 | return -1; |
kayekss | 1:8cf4beca9695 | 243 | } |
kayekss | 1:8cf4beca9695 | 244 | switch (colorDepth) { |
kayekss | 1:8cf4beca9695 | 245 | case 1: case 4: case 8: |
kayekss | 1:8cf4beca9695 | 246 | if (index >= 1ul << colorDepth) { |
kayekss | 1:8cf4beca9695 | 247 | return -1; |
kayekss | 1:8cf4beca9695 | 248 | } else { |
kayekss | 1:8cf4beca9695 | 249 | return palette[paletteElemSize(format) * index + 2]; |
kayekss | 1:8cf4beca9695 | 250 | } |
kayekss | 1:8cf4beca9695 | 251 | default: |
kayekss | 1:8cf4beca9695 | 252 | return -1; |
kayekss | 1:8cf4beca9695 | 253 | } |
kayekss | 1:8cf4beca9695 | 254 | } |
kayekss | 1:8cf4beca9695 | 255 | |
kayekss | 1:8cf4beca9695 | 256 | int32_t BMPFile::paletteGreen(uint8_t index) { |
kayekss | 1:8cf4beca9695 | 257 | if (!palette) { |
kayekss | 1:8cf4beca9695 | 258 | return -1; |
kayekss | 1:8cf4beca9695 | 259 | } |
kayekss | 1:8cf4beca9695 | 260 | switch (colorDepth) { |
kayekss | 1:8cf4beca9695 | 261 | case 1: case 4: case 8: |
kayekss | 1:8cf4beca9695 | 262 | if (index >= 1ul << colorDepth) { |
kayekss | 1:8cf4beca9695 | 263 | return -1; |
kayekss | 1:8cf4beca9695 | 264 | } else { |
kayekss | 1:8cf4beca9695 | 265 | return palette[paletteElemSize(format) * index + 1]; |
kayekss | 1:8cf4beca9695 | 266 | } |
kayekss | 1:8cf4beca9695 | 267 | default: |
kayekss | 1:8cf4beca9695 | 268 | return -1; |
kayekss | 1:8cf4beca9695 | 269 | } |
kayekss | 1:8cf4beca9695 | 270 | } |
kayekss | 1:8cf4beca9695 | 271 | |
kayekss | 1:8cf4beca9695 | 272 | int32_t BMPFile::paletteBlue(uint8_t index) { |
kayekss | 1:8cf4beca9695 | 273 | if (!palette) { |
kayekss | 1:8cf4beca9695 | 274 | return -1; |
kayekss | 1:8cf4beca9695 | 275 | } |
kayekss | 1:8cf4beca9695 | 276 | switch (colorDepth) { |
kayekss | 1:8cf4beca9695 | 277 | case 1: case 4: case 8: |
kayekss | 1:8cf4beca9695 | 278 | if (index >= 1ul << colorDepth) { |
kayekss | 1:8cf4beca9695 | 279 | return -1; |
kayekss | 1:8cf4beca9695 | 280 | } else { |
kayekss | 1:8cf4beca9695 | 281 | return palette[paletteElemSize(format) * index]; |
kayekss | 1:8cf4beca9695 | 282 | } |
kayekss | 1:8cf4beca9695 | 283 | default: |
kayekss | 1:8cf4beca9695 | 284 | return -1; |
kayekss | 1:8cf4beca9695 | 285 | } |
kayekss | 1:8cf4beca9695 | 286 | } |
kayekss | 1:8cf4beca9695 | 287 | |
kayekss | 1:8cf4beca9695 | 288 | int32_t BMPFile::red(uint32_t x, uint32_t y) { |
kayekss | 1:8cf4beca9695 | 289 | if (x >= width || y >= height) { |
kayekss | 1:8cf4beca9695 | 290 | return -1; |
kayekss | 1:8cf4beca9695 | 291 | } |
kayekss | 1:8cf4beca9695 | 292 | if (!data) { |
kayekss | 1:8cf4beca9695 | 293 | return -1; |
kayekss | 1:8cf4beca9695 | 294 | } |
kayekss | 1:8cf4beca9695 | 295 | switch (colorDepth) { |
kayekss | 1:8cf4beca9695 | 296 | case 1: // Indexed from palette |
kayekss | 1:8cf4beca9695 | 297 | return paletteRed((data[stride * y + x / 8] >> 7 - x % 8) & 0x01); |
kayekss | 1:8cf4beca9695 | 298 | case 4: // Indexed from palette |
kayekss | 1:8cf4beca9695 | 299 | return paletteRed((data[stride * y + x / 2] >> 4 * (1 - x % 2)) & 0x0f); |
kayekss | 1:8cf4beca9695 | 300 | case 8: // Indexed from palette |
kayekss | 1:8cf4beca9695 | 301 | return paletteRed(data[stride * y + x]); |
kayekss | 1:8cf4beca9695 | 302 | case 16: // BGR565 (bbbbbggg:gggrrrrr) |
kayekss | 3:be3e831a86c1 | 303 | return (data[stride * y + 2 * x + 1] & 0x1f) * 2; |
kayekss | 1:8cf4beca9695 | 304 | case 24: // BGR888 |
kayekss | 2:89b273c12b0a | 305 | return data[stride * y + 3 * x + 2]; |
kayekss | 1:8cf4beca9695 | 306 | case 32: // BGRX8888 |
kayekss | 2:89b273c12b0a | 307 | return data[stride * y + 4 * x + 2]; |
kayekss | 1:8cf4beca9695 | 308 | default: |
kayekss | 1:8cf4beca9695 | 309 | return -1; |
kayekss | 1:8cf4beca9695 | 310 | } |
kayekss | 1:8cf4beca9695 | 311 | } |
kayekss | 1:8cf4beca9695 | 312 | |
kayekss | 1:8cf4beca9695 | 313 | int32_t BMPFile::green(uint32_t x, uint32_t y) { |
kayekss | 1:8cf4beca9695 | 314 | if (x >= width || y >= height) { |
kayekss | 1:8cf4beca9695 | 315 | return -1; |
kayekss | 1:8cf4beca9695 | 316 | } |
kayekss | 1:8cf4beca9695 | 317 | if (!data) { |
kayekss | 1:8cf4beca9695 | 318 | return -1; |
kayekss | 1:8cf4beca9695 | 319 | } |
kayekss | 1:8cf4beca9695 | 320 | switch (colorDepth) { |
kayekss | 1:8cf4beca9695 | 321 | case 1: // Indexed from palette |
kayekss | 1:8cf4beca9695 | 322 | return paletteGreen((data[stride * y + x / 8] >> 7 - x % 8) & 0x01); |
kayekss | 1:8cf4beca9695 | 323 | case 4: // Indexed from palette |
kayekss | 1:8cf4beca9695 | 324 | return paletteGreen((data[stride * y + x / 2] >> 4 * (1 - x % 2)) & 0x0f); |
kayekss | 1:8cf4beca9695 | 325 | case 8: // Indexed from palette |
kayekss | 1:8cf4beca9695 | 326 | return paletteGreen(data[stride * y + x]); |
kayekss | 1:8cf4beca9695 | 327 | case 16: // BGR565 (bbbbbggg:gggrrrrr) |
kayekss | 3:be3e831a86c1 | 328 | return ((data[stride * y + 2 * x] & 0x07) << 3 |
kayekss | 3:be3e831a86c1 | 329 | | data[stride * y + 2 * x + 1] >> 5) * 2; |
kayekss | 1:8cf4beca9695 | 330 | case 24: // BGR888 |
kayekss | 1:8cf4beca9695 | 331 | return data[stride * y + 3 * x + 1]; |
kayekss | 1:8cf4beca9695 | 332 | case 32: // BGRX8888 |
kayekss | 1:8cf4beca9695 | 333 | return data[stride * y + 4 * x + 1]; |
kayekss | 1:8cf4beca9695 | 334 | default: |
kayekss | 1:8cf4beca9695 | 335 | return -1; |
kayekss | 1:8cf4beca9695 | 336 | } |
kayekss | 1:8cf4beca9695 | 337 | } |
kayekss | 1:8cf4beca9695 | 338 | |
kayekss | 1:8cf4beca9695 | 339 | int32_t BMPFile::blue(uint32_t x, uint32_t y) { |
kayekss | 1:8cf4beca9695 | 340 | if (x >= width || y >= height) { |
kayekss | 1:8cf4beca9695 | 341 | return -1; |
kayekss | 1:8cf4beca9695 | 342 | } |
kayekss | 1:8cf4beca9695 | 343 | if (!data) { |
kayekss | 1:8cf4beca9695 | 344 | return -1; |
kayekss | 1:8cf4beca9695 | 345 | } |
kayekss | 1:8cf4beca9695 | 346 | switch (colorDepth) { |
kayekss | 1:8cf4beca9695 | 347 | case 1: // Indexed from palette |
kayekss | 1:8cf4beca9695 | 348 | return paletteBlue((data[stride * y + x / 8] >> 7 - x % 8) & 0x01); |
kayekss | 1:8cf4beca9695 | 349 | case 4: // Indexed from palette |
kayekss | 1:8cf4beca9695 | 350 | return paletteBlue((data[stride * y + x / 2] >> 4 * (1 - x % 2)) & 0x0f); |
kayekss | 1:8cf4beca9695 | 351 | case 8: // Indexed from palette |
kayekss | 1:8cf4beca9695 | 352 | return paletteBlue(data[stride * y + x]); |
kayekss | 1:8cf4beca9695 | 353 | case 16: // RGB565 (bbbbbggg:gggrrrrr) |
kayekss | 3:be3e831a86c1 | 354 | return (data[stride * y + 2 * x] >> 3) * 2; |
kayekss | 1:8cf4beca9695 | 355 | case 24: // BGR888 |
kayekss | 1:8cf4beca9695 | 356 | return data[stride * y + 3 * x]; |
kayekss | 1:8cf4beca9695 | 357 | case 32: // BGRX8888 |
kayekss | 1:8cf4beca9695 | 358 | return data[stride * y + 4 * x]; |
kayekss | 1:8cf4beca9695 | 359 | default: |
kayekss | 1:8cf4beca9695 | 360 | return -1; |
kayekss | 1:8cf4beca9695 | 361 | } |
kayekss | 1:8cf4beca9695 | 362 | } |