source: trunk/src/msvfw32/drawdib.c@ 7502

Last change on this file since 7502 was 7502, checked in by phaller, 24 years ago

Fixed out-of-scope FIXME,TRACE,WARN macros

File size: 12.5 KB
Line 
1/*
2 * Copyright 2000 Bradley Baetz
3 *
4 * Fixme: Some flags are ignored
5 *
6 * Handle palettes
7 */
8
9#include <string.h>
10#include "windef.h"
11#include "winbase.h"
12#include "wingdi.h"
13#include "winuser.h"
14#include "wine/winbase16.h"
15#include "debugtools.h"
16#include "vfw.h"
17#include "vfw16.h"
18#include "windef.h"
19
20DEFAULT_DEBUG_CHANNEL(msvideo);
21
22typedef struct {
23 HDC hdc;
24 INT dxDst;
25 INT dyDst;
26 LPBITMAPINFOHEADER lpbi;
27 INT dxSrc;
28 INT dySrc;
29 HPALETTE hpal; /* Palette to use for the DIB */
30 BOOL begun; /* DrawDibBegin has been called */
31 LPBITMAPINFOHEADER lpbiOut; /* Output format */
32 HIC hic; /* HIC for decompression */
33 HDC hMemDC; /* DC for buffering */
34 HBITMAP hOldDib; /* Original Dib */
35 HBITMAP hDib; /* DibSection */
36 LPVOID lpvbits; /* Buffer for holding decompressed dib */
37} WINE_HDD;
38
39#ifdef __WIN32OS2__
40#include <heapstring.h>
41
42#define GlobalAlloc16 GlobalAlloc
43#define GlobalLock16 GlobalLock
44#define GlobalUnlock16 GlobalUnlock
45#define GlobalFree16 GlobalFree
46
47#undef FIXME
48#undef TRACE
49#ifdef DEBUG
50// PH 2001-11-30
51// this macro definition causes the control leave the scope of a
52// non-curly-braced preceeding if statement. Therefore,
53// if (p!=NULL)
54// TRACE("p->a=%d", p->a)
55// crashes.
56//
57// !!! ENSURE TRACES AND FIXMES WITH PRECEEDING IF STATEMENT
58// !!! ARE PUT INTO CURLY BRACES
59#define TRACE WriteLog("MSVFW32: %s", __FUNCTION__); WriteLog
60#define FIXME WriteLog("FIXME MSVFW32: %s", __FUNCTION__); WriteLog
61#else
62#define TRACE 1 ? (void)0 : (void)((int (*)(char *, ...)) NULL)
63#define FIXME 1 ? (void)0 : (void)((int (*)(char *, ...)) NULL)
64#endif
65
66#endif
67
68/***********************************************************************
69 * DrawDibOpen [MSVFW32.@]
70 */
71HDRAWDIB VFWAPI DrawDibOpen(void) {
72 HDRAWDIB hdd;
73
74 TRACE("(void)\n");
75 hdd = GlobalAlloc16(GHND,sizeof(WINE_HDD));
76 TRACE("=> %d\n",hdd);
77 return hdd;
78}
79
80/***********************************************************************
81 * DrawDibOpen [MSVIDEO.102]
82 */
83HDRAWDIB16 VFWAPI DrawDibOpen16(void) {
84 return (HDRAWDIB16)DrawDibOpen();
85}
86
87/***********************************************************************
88 * DrawDibClose [MSVFW32.@]
89 */
90BOOL VFWAPI DrawDibClose(HDRAWDIB hdd) {
91 WINE_HDD *whdd = GlobalLock16(hdd);
92
93 TRACE("(0x%08lx)\n",(DWORD)hdd);
94
95 if (!whdd)
96 return FALSE;
97
98 if (whdd->begun)
99 DrawDibEnd(hdd);
100
101 GlobalUnlock16(hdd);
102 GlobalFree16(hdd);
103 return TRUE;
104}
105
106/***********************************************************************
107 * DrawDibClose [MSVIDEO.103]
108 */
109BOOL16 VFWAPI DrawDibClose16(HDRAWDIB16 hdd) {
110 return DrawDibClose(hdd);
111}
112
113/***********************************************************************
114 * DrawDibEnd [MSVFW32.@]
115 */
116BOOL VFWAPI DrawDibEnd(HDRAWDIB hdd) {
117 BOOL ret = TRUE;
118 WINE_HDD *whdd = GlobalLock16(hdd);
119
120 TRACE("(0x%08lx)\n",(DWORD)hdd);
121
122 whdd->hpal = 0; /* Do not free this */
123 whdd->hdc = 0;
124 if (whdd->lpbi) {
125 HeapFree(GetProcessHeap(),0,whdd->lpbi);
126 whdd->lpbi = NULL;
127 }
128 if (whdd->lpbiOut) {
129 HeapFree(GetProcessHeap(),0,whdd->lpbiOut);
130 whdd->lpbiOut = NULL;
131 }
132
133 whdd->begun = FALSE;
134
135 /*if (whdd->lpvbits)
136 HeapFree(GetProcessHeap(),0,whdd->lpvbuf);*/
137
138 if (whdd->hMemDC) {
139 SelectObject(whdd->hMemDC,whdd->hOldDib);
140 DeleteDC(whdd->hMemDC);
141 }
142
143 if (whdd->hDib)
144 DeleteObject(whdd->hDib);
145
146 if (whdd->hic) {
147 ICDecompressEnd(whdd->hic);
148 ICClose(whdd->hic);
149 }
150
151 whdd->lpvbits = NULL;
152
153 GlobalUnlock16(hdd);
154 return ret;
155}
156
157/***********************************************************************
158 * DrawDibEnd [MSVIDEO.105]
159 */
160BOOL16 VFWAPI DrawDibEnd16(HDRAWDIB16 hdd) {
161 return DrawDibEnd(hdd);
162}
163
164/***********************************************************************
165 * DrawDibBegin [MSVFW32.@]
166 */
167BOOL VFWAPI DrawDibBegin(HDRAWDIB hdd,
168 HDC hdc,
169 INT dxDst,
170 INT dyDst,
171 LPBITMAPINFOHEADER lpbi,
172 INT dxSrc,
173 INT dySrc,
174 UINT wFlags) {
175 BOOL ret = TRUE;
176 WINE_HDD *whdd;
177
178 TRACE("(%d,0x%lx,%d,%d,%p,%d,%d,0x%08lx)\n",
179 hdd,(DWORD)hdc,dxDst,dyDst,lpbi,dxSrc,dySrc,(DWORD)wFlags
180 );
181 TRACE("lpbi: %ld,%ld/%ld,%d,%d,%ld,%ld,%ld,%ld,%ld,%ld\n",
182 lpbi->biSize, lpbi->biWidth, lpbi->biHeight, lpbi->biPlanes,
183 lpbi->biBitCount, lpbi->biCompression, lpbi->biSizeImage,
184 lpbi->biXPelsPerMeter, lpbi->biYPelsPerMeter, lpbi->biClrUsed,
185 lpbi->biClrImportant);
186
187 if (wFlags & ~(DDF_BUFFER))
188 {
189 FIXME("wFlags == 0x%08x not handled\n", wFlags & ~(DDF_BUFFER));
190 }
191
192 whdd = (WINE_HDD*)GlobalLock16(hdd);
193 if (!whdd) return FALSE;
194
195 if (whdd->begun)
196 DrawDibEnd(hdd);
197
198 if (lpbi->biCompression) {
199 DWORD size = 0;
200
201 whdd->hic = ICOpen(ICTYPE_VIDEO,lpbi->biCompression,ICMODE_DECOMPRESS);
202 if (!whdd->hic) {
203 WARN("Could not open IC. biCompression == 0x%08lx\n",lpbi->biCompression);
204 ret = FALSE;
205 }
206
207 if (ret) {
208 size = ICDecompressGetFormat(whdd->hic,lpbi,NULL);
209 if (size == ICERR_UNSUPPORTED) {
210 WARN("Codec doesn't support GetFormat, giving up.\n");
211 ret = FALSE;
212 }
213 }
214
215 if (ret) {
216 whdd->lpbiOut = HeapAlloc(GetProcessHeap(),0,size);
217
218 if (ICDecompressGetFormat(whdd->hic,lpbi,whdd->lpbiOut) != ICERR_OK)
219 ret = FALSE;
220 }
221
222 if (ret) {
223 /* FIXME: Use Ex functions if available? */
224 if (ICDecompressBegin(whdd->hic,lpbi,whdd->lpbiOut) != ICERR_OK)
225 ret = FALSE;
226
227 TRACE("biSizeImage == %ld\n",whdd->lpbiOut->biSizeImage);
228 TRACE("biCompression == %ld\n",whdd->lpbiOut->biCompression);
229 TRACE("biBitCount == %d\n",whdd->lpbiOut->biBitCount);
230 }
231 } else {
232 DWORD dwSize;
233 /* No compression */
234 TRACE("Not compressed!\n");
235 dwSize = lpbi->biSize + lpbi->biClrUsed*sizeof(RGBQUAD);
236 whdd->lpbiOut = HeapAlloc(GetProcessHeap(),0,dwSize);
237 memcpy(whdd->lpbiOut,lpbi,dwSize);
238 }
239
240 if (ret) {
241 /*whdd->lpvbuf = HeapAlloc(GetProcessHeap(),0,whdd->lpbiOut->biSizeImage);*/
242
243 whdd->hMemDC = CreateCompatibleDC(hdc);
244 TRACE("Creating: %ld,%p\n",whdd->lpbiOut->biSize,whdd->lpvbits);
245 whdd->hDib = CreateDIBSection(whdd->hMemDC,(BITMAPINFO *)whdd->lpbiOut,DIB_RGB_COLORS,&(whdd->lpvbits),0,0);
246 if (!whdd->hDib) {
247 TRACE("Error: %ld\n",GetLastError());
248 }
249 TRACE("Created: %d,%p\n",whdd->hDib,whdd->lpvbits);
250 whdd->hOldDib = SelectObject(whdd->hMemDC,whdd->hDib);
251 }
252
253 if (ret) {
254 whdd->hdc = hdc;
255 whdd->dxDst = dxDst;
256 whdd->dyDst = dyDst;
257 whdd->lpbi = HeapAlloc(GetProcessHeap(),0,lpbi->biSize);
258 memcpy(whdd->lpbi,lpbi,lpbi->biSize);
259 whdd->dxSrc = dxSrc;
260 whdd->dySrc = dySrc;
261 whdd->begun = TRUE;
262 whdd->hpal = 0;
263 } else {
264 if (whdd->hic)
265 ICClose(whdd->hic);
266 if (whdd->lpbiOut) {
267 HeapFree(GetProcessHeap(),0,whdd->lpbiOut);
268 whdd->lpbiOut = NULL;
269 }
270 }
271
272 GlobalUnlock16(hdd);
273
274 return ret;
275}
276
277/************************************************************************
278 * DrawDibBegin [MSVIDEO.104]
279 */
280BOOL16 VFWAPI DrawDibBegin16(HDRAWDIB16 hdd,
281 HDC16 hdc,
282 INT16 dxDst,
283 INT16 dyDst,
284 LPBITMAPINFOHEADER lpbi,
285 INT16 dxSrc,
286 INT16 dySrc,
287 UINT16 wFlags) {
288 return DrawDibBegin(hdd,hdc,dxDst,dyDst,lpbi,dxSrc,dySrc,wFlags);
289}
290
291/**********************************************************************
292 * DrawDibDraw [MSVFW32.@]
293 */
294BOOL VFWAPI DrawDibDraw(HDRAWDIB hdd, HDC hdc,
295 INT xDst, INT yDst, INT dxDst, INT dyDst,
296 LPBITMAPINFOHEADER lpbi,
297 LPVOID lpBits,
298 INT xSrc, INT ySrc, INT dxSrc, INT dySrc,
299 UINT wFlags
300) {
301 WINE_HDD *whdd;
302 BOOL ret = TRUE;
303
304 TRACE("(%d,0x%lx,%d,%d,%d,%d,%p,%p,%d,%d,%d,%d,0x%08lx)\n",
305 hdd,(DWORD)hdc,xDst,yDst,dxDst,dyDst,lpbi,lpBits,xSrc,ySrc,dxSrc,dySrc,(DWORD)wFlags
306 );
307
308 if (wFlags & ~(DDF_SAME_HDC | DDF_SAME_DRAW | DDF_NOTKEYFRAME |
309 DDF_UPDATE | DDF_DONTDRAW))
310 {
311 FIXME("wFlags == 0x%08lx not handled\n",(DWORD)wFlags);
312 }
313
314 if (!lpBits) {
315 /* Undocumented? */
316 lpBits = (LPSTR)lpbi + (WORD)(lpbi->biSize) + (WORD)(lpbi->biClrUsed*sizeof(RGBQUAD));
317 }
318
319 whdd = GlobalLock16(hdd);
320
321#define CHANGED(x) (whdd->x != x)
322
323 if ((!whdd->begun) || (!(wFlags & DDF_SAME_HDC) && CHANGED(hdc)) || (!(wFlags & DDF_SAME_DRAW) &&
324 (CHANGED(lpbi) || CHANGED(dxSrc) || CHANGED(dySrc) || CHANGED(dxDst) || CHANGED(dyDst)))) {
325 TRACE("Something changed!\n");
326 ret = DrawDibBegin(hdd,hdc,dxDst,dyDst,lpbi,dxSrc,dySrc,0);
327 }
328
329#undef CHANGED
330
331 if ((dxDst == -1) && (dyDst == -1)) {
332 dxDst = dxSrc;
333 dyDst = dySrc;
334 }
335
336 if (!(wFlags & DDF_UPDATE)) {
337 /* biSizeImage may be set to 0 for BI_RGB (uncompressed) bitmaps */
338 if ((lpbi->biCompression == BI_RGB) && (lpbi->biSizeImage == 0))
339 lpbi->biSizeImage = ((lpbi->biWidth * lpbi->biBitCount + 31) / 32) * 4 * lpbi->biHeight;
340
341 if (lpbi->biCompression) {
342 DWORD flags = 0;
343
344 TRACE("Compression == 0x%08lx\n",lpbi->biCompression);
345
346 if (wFlags & DDF_NOTKEYFRAME)
347 flags |= ICDECOMPRESS_NOTKEYFRAME;
348
349 ICDecompress(whdd->hic,flags,lpbi,lpBits,whdd->lpbiOut,whdd->lpvbits);
350 } else {
351 memcpy(whdd->lpvbits,lpBits,lpbi->biSizeImage);
352 }
353 }
354 if (!(wFlags & DDF_DONTDRAW) && whdd->hpal)
355 SelectPalette(hdc,whdd->hpal,FALSE);
356
357 if (!(StretchBlt(whdd->hdc,xDst,yDst,dxDst,dyDst,whdd->hMemDC,xSrc,ySrc,dxSrc,dySrc,SRCCOPY)))
358 ret = FALSE;
359
360 GlobalUnlock16(hdd);
361 return ret;
362}
363
364/**********************************************************************
365 * DrawDibDraw [MSVIDEO.106]
366 */
367BOOL16 VFWAPI DrawDibDraw16(HDRAWDIB16 hdd,
368 HDC16 hdc,
369 INT16 xDst,
370 INT16 yDst,
371 INT16 dxDst,
372 INT16 dyDst,
373 LPBITMAPINFOHEADER lpbi,
374 LPVOID lpBits,
375 INT16 xSrc,
376 INT16 ySrc,
377 INT16 dxSrc,
378 INT16 dySrc,
379 UINT16 wFlags) {
380 return DrawDibDraw(hdd,hdc,xDst,yDst,dxDst,dyDst,lpbi,lpBits,xSrc,ySrc,dxSrc,dySrc,wFlags);
381}
382
383/*************************************************************************
384 * DrawDibStart [MSVFW32.@]
385 */
386BOOL VFWAPI DrawDibStart(HDRAWDIB hdd, DWORD rate) {
387 FIXME("(0x%08lx,%ld), stub\n",(DWORD)hdd,rate);
388 return TRUE;
389}
390
391/*************************************************************************
392 * DrawDibStart [MSVIDEO.118]
393 */
394BOOL16 VFWAPI DrawDibStart16(HDRAWDIB16 hdd, DWORD rate) {
395 return DrawDibStart(hdd,rate);
396}
397
398/*************************************************************************
399 * DrawDibStop [MSVFW32.@]
400 */
401BOOL VFWAPI DrawDibStop(HDRAWDIB hdd) {
402 FIXME("(0x%08lx), stub\n",(DWORD)hdd);
403 return TRUE;
404}
405
406/*************************************************************************
407 * DrawDibStop [MSVIDEO.119]
408 */
409BOOL16 DrawDibStop16(HDRAWDIB16 hdd) {
410 return DrawDibStop(hdd);
411}
412
413/***********************************************************************
414 * DrawDibSetPalette [MSVFW32.@]
415 */
416BOOL VFWAPI DrawDibSetPalette(HDRAWDIB hdd, HPALETTE hpal) {
417 WINE_HDD *whdd;
418
419 TRACE("(0x%08lx,0x%08lx)\n",(DWORD)hdd,(DWORD)hpal);
420
421 whdd = GlobalLock16(hdd);
422 whdd->hpal = hpal;
423
424 if (whdd->begun) {
425 SelectPalette(whdd->hdc,hpal,0);
426 RealizePalette(whdd->hdc);
427 }
428 GlobalUnlock16(hdd);
429 return TRUE;
430}
431
432/***********************************************************************
433 * DrawDibSetPalette [MSVIDEO.110]
434 */
435BOOL16 VFWAPI DrawDibSetPalette16(HDRAWDIB16 hdd, HPALETTE16 hpal) {
436 return DrawDibSetPalette(hdd,hpal);
437}
438
439/***********************************************************************
440 * DrawDibGetPalette [MSVFW32.@]
441 */
442HPALETTE VFWAPI DrawDibGetPalette(HDRAWDIB hdd) {
443 WINE_HDD *whdd;
444 HPALETTE ret;
445
446 TRACE("(0x%08lx)\n",(DWORD)hdd);
447
448 whdd = GlobalLock16(hdd);
449 ret = whdd->hpal;
450 GlobalUnlock16(hdd);
451 return ret;
452}
453
454/***********************************************************************
455 * DrawDibGetPalette [MSVIDEO.108]
456 */
457HPALETTE16 VFWAPI DrawDibGetPalette16(HDRAWDIB16 hdd) {
458 return (HPALETTE16)DrawDibGetPalette(hdd);
459}
460
461/***********************************************************************
462 * DrawDibRealize [MSVFW32.@]
463 */
464UINT VFWAPI DrawDibRealize(HDRAWDIB hdd, HDC hdc, BOOL fBackground) {
465 WINE_HDD *whdd;
466 HPALETTE oldPal;
467 UINT ret = 0;
468
469 FIXME("(%d,0x%08lx,%d), stub\n",hdd,(DWORD)hdc,fBackground);
470
471 whdd = GlobalLock16(hdd);
472
473 if (!whdd || !(whdd->begun)) {
474 ret = 0;
475 goto out;
476 }
477
478 if (!whdd->hpal)
479 whdd->hpal = CreateHalftonePalette(hdc);
480
481 oldPal = SelectPalette(hdc,whdd->hpal,fBackground);
482 ret = RealizePalette(hdc);
483
484 out:
485 GlobalUnlock16(hdd);
486
487 TRACE("=> %u\n",ret);
488 return ret;
489}
490
491/***********************************************************************
492 * DrawDibRealize [MSVIDEO.112]
493 */
494UINT16 VFWAPI DrawDibRealize16(HDRAWDIB16 hdd, HDC16 hdc, BOOL16 fBackground) {
495 return (UINT16)DrawDibRealize(hdd,hdc,fBackground);
496}
Note: See TracBrowser for help on using the repository browser.