bmp.cc
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "bmp.h"
00024 #include "bmp-internal.h"
00025 #include "error.h"
00026 #include "endian.h"
00027
00028 namespace Barry {
00029
00030
00031
00032
00033
00034
00035
00036
00037 BXEXPORT size_t GetTotalBitmapSize(const JLScreenInfo &info)
00038 {
00039 return sizeof(bmp_file_header_t) +
00040 sizeof(bmp_info_header_t) +
00041 (info.width * info.height * 4);
00042
00043 }
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057 BXEXPORT void ScreenshotToBitmap(const JLScreenInfo &info,
00058 const Data &screenshot,
00059 Data &bitmap)
00060 {
00061
00062 size_t width = info.width;
00063 size_t height = info.height;
00064 size_t total_bitmap_size = GetTotalBitmapSize(info);
00065
00066
00067
00068 if( screenshot.GetSize() < (width * height * 2) )
00069 throw Error("Screenshot data size is too small for given width+height");
00070
00071
00072
00073 unsigned char *write = bitmap.GetBuffer(total_bitmap_size);
00074
00075
00076
00077
00078 bmp_file_header_t *fileheader = (bmp_file_header_t*) write;
00079 write += sizeof(bmp_file_header_t);
00080
00081
00082 fileheader->bfType[0] = 'B';
00083 fileheader->bfType[1] = 'M';
00084
00085
00086 fileheader->bfSize = btohl(total_bitmap_size);
00087
00088
00089 fileheader->bfReserved1 = 0;
00090 fileheader->bfReserved2 = 0;
00091
00092
00093 fileheader->bfOffBits = btohl(sizeof(bmp_file_header_t) + sizeof(bmp_info_header_t));
00094
00095
00096
00097
00098
00099 bmp_info_header_t *infoheader = (bmp_info_header_t*) write;
00100 write += sizeof(bmp_info_header_t);
00101
00102
00103 infoheader->biSize = btohl(sizeof(bmp_info_header_t));
00104
00105
00106 infoheader->biWidth = btohl(width);
00107 infoheader->biHeight = btohl(height);
00108
00109
00110 infoheader->biPlanes = btohs(0x01);
00111
00112
00113 infoheader->biBitCount = btohs(0x20);
00114
00115
00116 infoheader->biCompression = 0;
00117
00118
00119 infoheader->biSizeImage = btohl(4 * width * height);
00120
00121
00122 infoheader->biXPelsPerMeter = 0;
00123 infoheader->biYPelsPerMeter = 0;
00124
00125
00126 infoheader->biClrUsed = 0;
00127
00128
00129 infoheader->biClrImportant = 0;
00130
00131
00132
00133 const uint16_t *data = (const uint16_t*) screenshot.GetData();
00134 size_t pixel_count = width * height;
00135
00136
00137
00138 for (size_t j=0; j<height; j++) {
00139 for (size_t i=0; i<width; i++) {
00140
00141 short value = data[(pixel_count - 1) - ((width-1 - i) + (width * j))];
00142
00143
00144
00145
00146
00147
00148
00149 write[3] = 0x00;
00150 write[2] = (((value >> 11) & 0x1F) * 0xFF) / 0x1F;
00151 write[1] = (((value >> 5) & 0x3F) * 0xFF) / 0x3F;
00152 write[0] = ((value & 0x1F) * 0xFF) / 0x1F;
00153
00154 write += 4;
00155 }
00156 }
00157
00158 bitmap.ReleaseBuffer(total_bitmap_size);
00159 }
00160
00161 }
00162