source: trunk/src/gdi32/blit.cpp@ 5690

Last change on this file since 5690 was 5690, checked in by sandervl, 24 years ago

StretchDIBits now supports negative heightblit.cpp

File size: 22.4 KB
Line 
1/* $Id: blit.cpp,v 1.27 2001-05-11 17:09:45 sandervl Exp $ */
2
3/*
4 * GDI32 blit code
5 *
6 * Copyright 1998 Sander van Leeuwen (sandervl@xs4all.nl)
7 * Copyright 1998 Patrick Haller
8 *
9 * Project Odin Software License can be found in LICENSE.TXT
10 *
11 */
12#include <os2win.h>
13#include <stdlib.h>
14#include <stdarg.h>
15#include <string.h>
16#include <cpuhlp.h>
17#include "misc.h"
18#include "dibsect.h"
19#include "rgbcvt.h"
20
21#define DBG_LOCALLOG DBG_blit
22#include "dbglocal.h"
23
24static ULONG QueryPaletteSize(BITMAPINFOHEADER *pBHdr);
25static ULONG CalcBitmapSize(ULONG cBits, LONG cx, LONG cy);
26
27//******************************************************************************
28//******************************************************************************
29BOOL WIN32API StretchBlt(HDC hdcDest, int nXOriginDest, int nYOriginDest,
30 int nWidthDest, int nHeightDest,
31 HDC hdcSrc, int nXOriginSrc, int nYOriginSrc,
32 int nWidthSrc, int nHeightSrc, DWORD dwRop)
33{
34 BOOL rc;
35
36 dprintf(("GDI32: StretchBlt Dest: %x (%d, %d) size (%d, %d) ROP %x",
37 hdcDest, nXOriginDest, nYOriginDest, nWidthDest, nHeightDest, dwRop));
38 dprintf(("GDI32: StretchBlt Src : %x (%d, %d) size (%d, %d)\n",
39 hdcSrc, nXOriginSrc, nYOriginSrc, nWidthSrc, nHeightSrc));
40 SetLastError(ERROR_SUCCESS);
41 if(DIBSection::getSection() != NULL)
42 {
43 DIBSection *dsect = DIBSection::findHDC(hdcSrc);
44 if(dsect)
45 {
46 rc = dsect->BitBlt( hdcDest,
47 nXOriginDest, nYOriginDest, nWidthDest, nHeightDest,
48 nXOriginSrc, nYOriginSrc, nWidthSrc, nHeightSrc,
49 dwRop);
50 return rc;
51 }
52 }
53 return O32_StretchBlt(hdcDest, nXOriginDest, nYOriginDest, nWidthDest, nHeightDest, hdcSrc, nXOriginSrc, nYOriginSrc, nWidthSrc, nHeightSrc, dwRop);
54}
55//******************************************************************************
56//******************************************************************************
57BOOL WIN32API BitBlt(HDC hdcDest,
58 int nXDest,
59 int nYDest,
60 int nWidth,
61 int nHeight,
62 HDC hdcSrc,
63 int nXSrc,
64 int nYSrc,
65 DWORD dwRop)
66{
67 BOOL rc;
68
69 SetLastError(ERROR_SUCCESS);
70 if(DIBSection::getSection() != NULL)
71 {
72 DIBSection *dsect = DIBSection::findHDC(hdcSrc);
73 if(dsect)
74 {
75 return dsect->BitBlt(hdcDest,
76 nXDest,
77 nYDest,
78 nWidth,
79 nHeight,
80 nXSrc,
81 nYSrc,
82 nWidth,
83 nHeight,
84 dwRop);
85 }
86 }
87 dprintf(("GDI32: BitBlt to hdc %X from hdc %x (%d,%d) to (%d,%d), (%d,%d) rop %X\n",
88 hdcDest, hdcSrc, nXSrc, nYSrc, nXDest, nYDest, nWidth, nHeight, dwRop));
89 return O32_BitBlt(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc, dwRop);
90}
91//******************************************************************************
92//******************************************************************************
93static INT SetDIBitsToDevice_(HDC hdc, INT xDest, INT yDest, DWORD cx,
94 DWORD cy, INT xSrc, INT ySrc,
95 UINT startscan, UINT lines, LPCVOID bits,
96 const BITMAPINFO *info, UINT coloruse)
97{
98 INT result, imgsize, palsize, height, width;
99 char *ptr;
100 ULONG compression = 0, bmpsize;
101 WORD *newbits = NULL;
102 DWORD bitfields[3];
103
104 dprintf(("GDI32: SetDIBitsToDevice hdc:%X xDest:%d yDest:%d, cx:%d, cy:%d, xSrc:%d, ySrc:%d, startscan:%d, lines:%d \nGDI32: bits 0x%X, info 0x%X, coloruse %d",
105 hdc, xDest, yDest, cx, cy, xSrc, ySrc, startscan, lines, (LPVOID) bits, (PBITMAPINFO)info, coloruse));
106
107 SetLastError(ERROR_SUCCESS);
108 if(info == NULL) {
109 goto invalid_parameter;
110 }
111 height = info->bmiHeader.biHeight;
112 width = info->bmiHeader.biWidth;
113
114 if (height < 0) height = -height;
115 if (!lines || (startscan >= height)) {
116 goto invalid_parameter;
117 }
118 if (startscan + lines > height) lines = height - startscan;
119
120 if (ySrc < startscan) ySrc = startscan;
121 else if (ySrc >= startscan + lines) goto invalid_parameter;
122
123 if (xSrc >= width) goto invalid_parameter;
124
125 if (ySrc + cy >= startscan + lines) cy = startscan + lines - ySrc;
126
127 if (xSrc + cx >= width) cx = width - xSrc;
128
129 if (!cx || !cy) goto invalid_parameter;
130
131 //SvL: RP7's bitmap size is not correct; fix it here or else
132 // the blit is messed up in Open32
133 imgsize = CalcBitmapSize(info->bmiHeader.biBitCount,
134 info->bmiHeader.biWidth, info->bmiHeader.biHeight);
135 bmpsize = info->bmiHeader.biSizeImage;
136 if(info->bmiHeader.biCompression == 0 && info->bmiHeader.biSizeImage &&
137 info->bmiHeader.biSizeImage < imgsize)
138 {
139 ((BITMAPINFO *)info)->bmiHeader.biSizeImage = imgsize;
140 }
141
142 switch(info->bmiHeader.biBitCount) {
143 case 15:
144 case 16:
145 bitfields[0] = (info->bmiHeader.biCompression == BI_BITFIELDS) ? *(DWORD *)info->bmiColors : 0x7c00;
146 bitfields[1] = (info->bmiHeader.biCompression == BI_BITFIELDS) ? *((DWORD *)info->bmiColors + 1) : 0x03e0;
147 bitfields[2] = (info->bmiHeader.biCompression == BI_BITFIELDS) ? *((DWORD *)info->bmiColors + 2) : 0x001f;
148 break;
149 case 32:
150 bitfields[0] = (info->bmiHeader.biCompression == BI_BITFIELDS) ? *(DWORD *)info->bmiColors : 0xff0000;
151 bitfields[1] = (info->bmiHeader.biCompression == BI_BITFIELDS) ? *((DWORD *)info->bmiColors + 1) : 0xff00;
152 bitfields[2] = (info->bmiHeader.biCompression == BI_BITFIELDS) ? *((DWORD *)info->bmiColors + 2) : 0xff;
153 break;
154 default:
155 bitfields[0] = 0;
156 bitfields[1] = 0;
157 bitfields[2] = 0;
158 break;
159 }
160 if(bitfields[1] == 0x3E0)
161 {//RGB 555?
162 dprintf(("RGB 555->565 conversion required %x %x %x", bitfields[0], bitfields[1], bitfields[2]));
163
164 newbits = (WORD *)malloc(imgsize);
165 if(CPUFeatures & CPUID_MMX) {
166 RGB555to565MMX(newbits, (WORD *)bits, imgsize/sizeof(WORD));
167 }
168 else RGB555to565(newbits, (WORD *)bits, imgsize/sizeof(WORD));
169 bits = newbits;
170 }
171
172 //SvL: Ignore BI_BITFIELDS type (SetDIBitsToDevice fails otherwise)
173 if(info->bmiHeader.biCompression == BI_BITFIELDS) {
174 ((BITMAPINFO *)info)->bmiHeader.biCompression = 0;
175 compression = BI_BITFIELDS;
176
177 }
178 if(startscan != 0 || lines != info->bmiHeader.biHeight) {
179 dprintf(("WARNING: SetDIBitsToDevice startscan != 0 || lines != info->bmiHeader.biHeight"));
180 }
181
182 result = O32_StretchDIBits(hdc, xDest, yDest, cx, cy, xSrc, ySrc,
183 cx, cy, (void *)bits,
184 (PBITMAPINFO)info, coloruse, SRCCOPY);
185
186 //Open32 always returns height of bitmap (regardless of how many scanlines were copied)
187 if(result != info->bmiHeader.biHeight) {
188 dprintf(("SetDIBitsToDevice failed with rc %x", result));
189 }
190 else
191 {
192 result = info->bmiHeader.biHeight;
193
194 DIBSection *destdib = DIBSection::findHDC(hdc);
195 if(destdib) {
196 if(cx == info->bmiHeader.biWidth && cy == info->bmiHeader.biHeight &&
197 destdib->GetBitCount() == info->bmiHeader.biBitCount &&
198 destdib->GetBitCount() == 8)
199 {
200 destdib->sync(xDest, yDest, cx, cy, (PVOID)bits);
201 }
202 else destdib->sync(hdc, yDest, cy);
203 }
204 }
205 dprintf(("GDI32: SetDIBitsToDevice hdc:%X xDest:%d yDest:%d, cx:%d, cy:%d, xSrc:%d, ySrc:%d, startscan:%d, lines:%d \nGDI32: bits 0x%X, info 0x%X, coloruse %d returned %d",
206 hdc, xDest, yDest, cx, cy, xSrc, ySrc, startscan, lines, (LPVOID) bits, (PBITMAPINFO)info, coloruse, result));
207 dprintf(("GDI32: SetDIBitsToDevice %d %d %d %d %x %d", info->bmiHeader.biWidth, info->bmiHeader.biHeight, info->bmiHeader.biPlanes, info->bmiHeader.biBitCount, info->bmiHeader.biCompression, info->bmiHeader.biSizeImage));
208
209 if(compression == BI_BITFIELDS) {
210 ((BITMAPINFO *)info)->bmiHeader.biCompression = BI_BITFIELDS;
211 }
212 if(newbits) free(newbits);
213 ((BITMAPINFO *)info)->bmiHeader.biSizeImage = bmpsize;
214 return result;
215
216invalid_parameter:
217 SetLastError(ERROR_INVALID_PARAMETER);
218 return 0;
219}
220//******************************************************************************
221//******************************************************************************
222INT WIN32API SetDIBitsToDevice(HDC hdc, INT xDest, INT yDest, DWORD cx,
223 DWORD cy, INT xSrc, INT ySrc,
224 UINT startscan, UINT lines, LPCVOID bits,
225 const BITMAPINFO *info, UINT coloruse)
226{
227 if(info->bmiHeader.biHeight < 0 && info->bmiHeader.biBitCount != 8 && info->bmiHeader.biCompression == 0) {
228 // upside down
229 INT rc = 0;
230 BITMAPINFO newInfo;
231 newInfo.bmiHeader = info->bmiHeader;
232 long lLineByte = ((newInfo.bmiHeader.biWidth * (info->bmiHeader.biBitCount == 15 ? 16 : info->bmiHeader.biBitCount) + 31) / 32) * 4;
233 long lHeight = -newInfo.bmiHeader.biHeight;
234 newInfo.bmiHeader.biHeight = -info->bmiHeader.biHeight;
235
236 char *newBits = (char *)malloc( lLineByte * lHeight );
237 if(newBits) {
238 unsigned char *pbSrc = (unsigned char *)bits + lLineByte * (lHeight - 1);
239 unsigned char *pbDst = (unsigned char *)newBits;
240 for(int y = 0; y < lHeight; y++) {
241 memcpy( pbDst, pbSrc, lLineByte );
242 pbDst += lLineByte;
243 pbSrc -= lLineByte;
244 }
245 rc = SetDIBitsToDevice_( hdc, xDest, yDest, cx, cy, xSrc, ySrc, startscan, lines, (void *)newBits, &newInfo, DIB_RGB_COLORS );
246 free( newBits );
247 }
248 return rc;
249 }
250 else
251 if(info->bmiHeader.biBitCount == 8 && info->bmiHeader.biCompression == 0 && !(GetDeviceCaps( hdc, RASTERCAPS ) & RC_PALETTE)) {
252 INT rc = 0;
253 // convert 8bit to 24bit
254
255 BITMAPINFO newInfo;
256 newInfo.bmiHeader = info->bmiHeader;
257 newInfo.bmiHeader.biBitCount = 24;
258 long lLineByte24 = ((newInfo.bmiHeader.biWidth * 24 + 31) / 32) * 4;
259 long lLineByte8 = ((newInfo.bmiHeader.biWidth * 8 + 31) / 32) * 4;
260 long lHeight = newInfo.bmiHeader.biHeight;
261 if(lHeight < 0) lHeight = -lHeight;
262
263 char *newBits = (char *)malloc( lLineByte24 * lHeight );
264 if(newBits) {
265 //
266 // Get Palette Entries
267 //
268 PALETTEENTRY aEntries[256];
269 LOGPALETTE *pLog = (LOGPALETTE *)malloc( sizeof(LOGPALETTE) + sizeof(PALETTEENTRY) * 256 );
270 pLog->palVersion = 0x300;
271 pLog->palNumEntries = 256;
272
273 HPALETTE hPaletteDummy = CreatePalette( pLog );
274 free( pLog );
275 HPALETTE hPalette = SelectPalette( hdc, hPaletteDummy, FALSE );
276 GetPaletteEntries( hPalette, 0, 255, aEntries );
277 SelectPalette( hdc, hPalette, FALSE );
278 DeleteObject( hPaletteDummy );
279
280 //
281 // convert 8bit to 24bit
282 //
283 if(newInfo.bmiHeader.biHeight > 0) {
284 unsigned char *pbSrc = (unsigned char *)bits;
285 unsigned char *pbDst = (unsigned char *)newBits;
286 for(int y = 0; y < lHeight; y++) {
287 for(int x = 0; x < newInfo.bmiHeader.biWidth; x++) {
288 PALETTEENTRY src = aEntries[pbSrc[x]];
289 pbDst[x * 3 + 0] = src.peBlue;
290 pbDst[x * 3 + 1] = src.peGreen;
291 pbDst[x * 3 + 2] = src.peRed;
292 }
293 pbDst += lLineByte24;
294 pbSrc += lLineByte8;
295 }
296 } else {
297 // upside down
298 newInfo.bmiHeader.biHeight = -info->bmiHeader.biHeight;
299 unsigned char *pbSrc = (unsigned char *)bits + lLineByte8 * (lHeight - 1);
300 unsigned char *pbDst = (unsigned char *)newBits;
301 for(int y = 0; y < lHeight; y++) {
302 for(int x = 0; x < newInfo.bmiHeader.biWidth; x++) {
303 PALETTEENTRY src = aEntries[pbSrc[x]];
304 pbDst[x * 3 + 0] = src.peBlue;
305 pbDst[x * 3 + 1] = src.peGreen;
306 pbDst[x * 3 + 2] = src.peRed;
307 }
308 pbDst += lLineByte24;
309 pbSrc -= lLineByte8;
310 }
311 }
312 rc = SetDIBitsToDevice_( hdc, xDest, yDest, cx, cy, xSrc, ySrc, startscan, lines, (void *)newBits, &newInfo, DIB_RGB_COLORS );
313 free( newBits );
314 }
315 return rc;
316 } else {
317 return SetDIBitsToDevice_( hdc, xDest, yDest, cx, cy, xSrc, ySrc, startscan, lines, bits, info, coloruse );
318 }
319}
320//******************************************************************************
321//******************************************************************************
322BOOL WIN32API PatBlt(HDC hdc,int nXLeft,int nYLeft,int nWidth,int nHeight,DWORD dwRop)
323{
324 BOOL rc;
325
326 //CB: Open32 bug: negative width/height not supported!
327 if (nWidth < 0)
328 {
329 nXLeft += nWidth+1;
330 nWidth = -nWidth;
331 }
332 if (nHeight < 0)
333 {
334 nYLeft += nHeight+1;
335 nHeight = -nHeight;
336 }
337 rc = O32_PatBlt(hdc,nXLeft,nYLeft,nWidth,nHeight,dwRop);
338 if(rc) {
339 DIBSection *destdib = DIBSection::findHDC(hdc);
340 if(destdib) {
341 destdib->sync(hdc, nYLeft, nHeight);
342 }
343 }
344
345 dprintf(("GDI32: PatBlt hdc %x (%d,%d) (%d,%d) returned %d\n",hdc, nXLeft,nYLeft,nWidth,nHeight,rc));
346 return(rc);
347}
348//******************************************************************************
349//******************************************************************************
350BOOL WIN32API MaskBlt( HDC arg1, int arg2, int arg3, int arg4, int arg5, HDC arg6, int arg7, int arg8, HBITMAP arg9, int arg10, int arg11, DWORD arg12)
351{
352 dprintf(("GDI32: MaskBlt"));
353 return O32_MaskBlt(arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8, arg9, arg10, arg11, arg12);
354}
355//******************************************************************************
356//******************************************************************************
357BOOL WIN32API PlgBlt(HDC hdcDest, CONST POINT *lpPoint, HDC hdcSrc, int nXSrc,
358 int nYSrc, int nWidth, int nHeight, HBITMAP hbmMask,
359 int xMast, int yMask)
360{
361 dprintf(("GDI32: PlgBlt, not implemented\n"));
362 return(FALSE);
363}
364//******************************************************************************
365//******************************************************************************
366static INT StretchDIBits_(HDC hdc, INT xDst, INT yDst, INT widthDst,
367 INT heightDst, INT xSrc, INT ySrc, INT widthSrc,
368 INT heightSrc, const void *bits,
369 const BITMAPINFO *info, UINT wUsage, DWORD dwRop )
370{
371 INT rc;
372
373 dprintf(("GDI32: StretchDIBits %x to (%d,%d) (%d,%d) from (%d,%d) (%d,%d), %x %x %x %x", hdc, xDst, yDst, widthDst, heightDst, xSrc, ySrc, widthSrc, heightSrc, bits, info, wUsage, dwRop));
374
375 if(info->bmiHeader.biBitCount == 1) {
376 dprintf(("WARNING: StretchDIBits does NOT work correctly for 1 bpp bitmaps!!"));
377 }
378
379 if(wUsage == DIB_PAL_COLORS && info->bmiHeader.biSize == sizeof(BITMAPINFOHEADER))
380 {
381 // workaround for open32 bug.
382 // If syscolors > 256 and wUsage == DIB_PAL_COLORS.
383
384 int i;
385 USHORT *pColorIndex = (USHORT *)info->bmiColors;
386 RGBQUAD *pColors = (RGBQUAD *) alloca(info->bmiHeader.biClrUsed *
387 sizeof(RGBQUAD));
388 BITMAPINFO *infoLoc = (BITMAPINFO *) alloca(sizeof(BITMAPINFO) +
389 info->bmiHeader.biClrUsed * sizeof(RGBQUAD));
390
391 memcpy(infoLoc, info, sizeof(BITMAPINFO));
392
393 if(GetDIBColorTable(hdc, 0, info->bmiHeader.biClrUsed, pColors) == 0) {
394 dprintf(("ERROR: StretchDIBits: GetDIBColorTable failed!!"));
395 return FALSE;
396 }
397 for(i=0;i<info->bmiHeader.biClrUsed;i++, pColorIndex++)
398 {
399 infoLoc->bmiColors[i] = pColors[*pColorIndex];
400 }
401
402 rc = O32_StretchDIBits(hdc, xDst, yDst, widthDst, heightDst, xSrc, ySrc,
403 widthSrc, heightSrc, (void *)bits,
404 (PBITMAPINFO)infoLoc, DIB_RGB_COLORS, dwRop);
405
406 //Open32 always returns height of bitmap (regardless of how many scanlines were copied)
407 if(rc != heightSrc && rc != infoLoc->bmiHeader.biHeight) {
408 dprintf(("StretchDIBits failed with rc %x", rc));
409 }
410 else {
411 rc = heightSrc;
412
413 DIBSection *destdib = DIBSection::findHDC(hdc);
414 if(destdib) {
415 if(widthDst == widthSrc && heightDst == heightSrc &&
416 destdib->GetBitCount() == infoLoc->bmiHeader.biBitCount &&
417 destdib->GetBitCount() == 8)
418 {
419 destdib->sync(xDst, yDst, widthDst, heightDst, (PVOID)bits);
420 }
421 else destdib->sync(hdc, yDst, heightDst);
422 }
423 }
424
425 return rc;
426 }
427 rc = O32_StretchDIBits(hdc, xDst, yDst, widthDst, heightDst, xSrc, ySrc,
428 widthSrc, heightSrc, (void *)bits,
429 (PBITMAPINFO)info, wUsage, dwRop);
430 //Open32 always returns height of bitmap (regardless of how many scanlines were copied)
431 if(rc != heightSrc && rc != info->bmiHeader.biHeight) {
432 dprintf(("StretchDIBits failed with rc %x", rc));
433 }
434 else
435 {
436 rc = heightSrc;
437
438 DIBSection *destdib = DIBSection::findHDC(hdc);
439 if(destdib) {
440 if(widthDst == widthSrc && heightDst == heightSrc &&
441 destdib->GetBitCount() == info->bmiHeader.biBitCount &&
442 destdib->GetBitCount() == 8)
443 {
444 destdib->sync(xDst, yDst, widthDst, heightDst, (PVOID)bits);
445 }
446 else destdib->sync(hdc, yDst, heightDst);
447 }
448 }
449
450 return rc;
451}
452//******************************************************************************
453//******************************************************************************
454INT WIN32API StretchDIBits(HDC hdc, INT xDst, INT yDst, INT widthDst,
455 INT heightDst, INT xSrc, INT ySrc, INT widthSrc,
456 INT heightSrc, const void *bits,
457 const BITMAPINFO *info, UINT wUsage, DWORD dwRop )
458{
459
460 if(info->bmiHeader.biHeight < 0) {
461 // upside down
462 INT rc = 0;
463 BITMAPINFO newInfo;
464 newInfo.bmiHeader = info->bmiHeader;
465 long lLineByte = ((newInfo.bmiHeader.biWidth * (info->bmiHeader.biBitCount == 15 ? 16 : info->bmiHeader.biBitCount) + 31) / 32) * 4;
466 long lHeight = -newInfo.bmiHeader.biHeight;
467 newInfo.bmiHeader.biHeight = -newInfo.bmiHeader.biHeight;
468
469 char *newBits = (char *)malloc( lLineByte * lHeight );
470 if(newBits) {
471 unsigned char *pbSrc = (unsigned char *)bits + lLineByte * (lHeight - 1);
472 unsigned char *pbDst = (unsigned char *)newBits;
473 for(int y = 0; y < lHeight; y++) {
474 memcpy( pbDst, pbSrc, lLineByte );
475 pbDst += lLineByte;
476 pbSrc -= lLineByte;
477 }
478 rc = StretchDIBits_(hdc, xDst, yDst, widthDst, heightDst, xSrc, ySrc, widthSrc, heightSrc, newBits, info, wUsage, dwRop);
479 free( newBits );
480 }
481 return rc;
482 } else {
483 return StretchDIBits_(hdc, xDst, yDst, widthDst, heightDst, xSrc, ySrc, widthSrc, heightSrc, bits, info, wUsage, dwRop);
484 }
485}
486//******************************************************************************
487//******************************************************************************
488int WIN32API SetStretchBltMode( HDC arg1, int arg2)
489{
490 dprintf(("GDI32: SetStretchBltMode 0x%08X, 0x%08X\n",arg1, arg2));
491
492 if(DIBSection::getSection() != NULL)
493 {
494 DIBSection *dsect = DIBSection::findHDC(arg1);
495 if(dsect)
496 {
497 dprintf((" - DC is DIBSection\n"));
498 }
499 }
500 return O32_SetStretchBltMode(arg1, arg2);
501}
502//******************************************************************************
503//******************************************************************************
504int WIN32API GetStretchBltMode( HDC arg1)
505{
506 dprintf(("GDI32: GetStretchBltMode"));
507 return O32_GetStretchBltMode(arg1);
508}
509//******************************************************************************
510//******************************************************************************
511static ULONG QueryPaletteSize(BITMAPINFOHEADER *pBHdr)
512{
513 ULONG cbPalette;
514
515 switch (pBHdr->biBitCount)
516 {
517 case 1:
518 case 4:
519 case 8:
520 cbPalette = (1 << pBHdr->biBitCount) * sizeof(RGBQUAD);
521 break;
522
523 case 16:
524 case 24:
525 case 32:
526 cbPalette = 0;
527 break;
528
529 default:
530 dprintf(("QueryPaletteSize: error pBHdr->biBitCount = %d", pBHdr->biBitCount));
531 cbPalette = -1;
532 }
533
534 return cbPalette;
535}
536//******************************************************************************
537//******************************************************************************
538static ULONG CalcBitmapSize(ULONG cBits, LONG cx, LONG cy)
539{
540 ULONG alignment;
541 ULONG factor;
542 BOOL flag = TRUE; //true: '*' false: '/'
543
544 cy = cy < 0 ? -cy : cy;
545
546 switch(cBits)
547 {
548 case 1:
549 factor = 8;
550 flag = FALSE;
551 break;
552
553 case 4:
554 factor = 2;
555 flag = FALSE;
556 break;
557
558 case 8:
559 factor = 1;
560 break;
561
562 case 16:
563 factor = 2;
564 break;
565
566 case 24:
567 factor = 3;
568 break;
569
570 case 32:
571 return cx*cy;
572
573 default:
574 return 0;
575 }
576
577 if (flag)
578 alignment = (cx = (cx*factor)) % 4;
579 else
580 alignment = (cx = ((cx+factor-1)/factor)) % 4;
581
582 if (alignment != 0)
583 cx += 4 - alignment;
584
585 return cx*cy;
586}
587//******************************************************************************
588//******************************************************************************
Note: See TracBrowser for help on using the repository browser.