Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

2590 lines
72 KiB

  1. /*++
  2. Copyright (c) 1996-1999 Microsoft Corporation
  3. Module Name
  4. Abstract:
  5. Lingyun Wang
  6. Author:
  7. Enviornment:
  8. User Mode
  9. Revision History:
  10. --*/
  11. #include "precomp.hxx"
  12. #pragma hdrstop
  13. extern PFNTRANSBLT gpfnTransparentBlt;
  14. extern PFNTRANSDIB gpfnTransparentDIBits;
  15. #if (_WIN32_WINNT == 0x400)
  16. typedef struct _LOGPALETTE2
  17. {
  18. USHORT PalVersion;
  19. USHORT PalNumEntries;
  20. PALETTEENTRY palPalEntry[2];
  21. } LOGPALETTE2;
  22. typedef struct _LOGPALETTE16
  23. {
  24. USHORT PalVersion;
  25. USHORT PalNumEntries;
  26. PALETTEENTRY palPalEntry[16];
  27. } LOGPALETTE16;
  28. typedef struct _LOGPALETTE256
  29. {
  30. USHORT PalVersion;
  31. USHORT PalNumEntries;
  32. PALETTEENTRY palPalEntry[256];
  33. } LOGPALETTE256;
  34. /******************************Public*Routine******************************\
  35. * StartPixel
  36. * Give a scanline pointer and position of a pixel, return the byte address
  37. * of where the pixel is at depending on the format
  38. *
  39. * History:
  40. * 2-Dec-1996 -by- Lingyun Wang [lingyunw]
  41. * Wrote it.
  42. \**************************************************************************/
  43. PBYTE StartPixel (
  44. PBYTE pjBits,
  45. ULONG xStart,
  46. ULONG iBitmapFormat
  47. )
  48. {
  49. PBYTE pjStart = pjBits;
  50. //
  51. // getting the starting pixel
  52. //
  53. switch (iBitmapFormat)
  54. {
  55. case 1:
  56. pjStart = pjBits + (xStart >> 3);
  57. break;
  58. case 4:
  59. pjStart = pjBits + (xStart >> 1);
  60. break;
  61. case 8:
  62. pjStart = pjBits + xStart;
  63. break;
  64. case 16:
  65. pjStart = pjBits + 2*xStart;
  66. break;
  67. case 24:
  68. pjStart = pjBits + 3*xStart;
  69. break;
  70. case 32:
  71. pjStart = pjBits+4*xStart;
  72. break;
  73. default:
  74. WARNING ("Startpixel -- bad iFormatSrc\n");
  75. }
  76. return (pjStart);
  77. }
  78. /******************************Public*Routine******************************\
  79. * vTransparentIdentityCopy4
  80. *
  81. * Doing a transparent copy on two same size 4BPP format DIBs
  82. *
  83. * Returns:
  84. * VOID.
  85. *
  86. * History:
  87. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  88. * Wrote it.
  89. \**************************************************************************/
  90. VOID vTransparentIdentityCopy4 (
  91. PDIBINFO pDibInfoDst,
  92. PDIBINFO pDibInfoSrc,
  93. ULONG TransColor)
  94. {
  95. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  96. + (pDibInfoDst->rclDIB.left >> 1);
  97. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  98. + (pDibInfoSrc->rclDIB.left >> 1);
  99. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  100. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  101. PBYTE pjDstTemp;
  102. PBYTE pjSrcTemp;
  103. LONG cxTemp;
  104. BYTE jSrc=0;
  105. BYTE jDst=0;
  106. LONG iSrc, iDst;
  107. while(cy--)
  108. {
  109. cxTemp = cx;
  110. iSrc = pDibInfoSrc->rclDIB.left;
  111. iDst = pDibInfoDst->rclDIB.left;
  112. pjSrcTemp = pjSrc;
  113. pjDstTemp = pjDst;
  114. while (cxTemp--)
  115. {
  116. if (iSrc & 0x00000001)
  117. {
  118. jSrc = *pjSrcTemp & 0x0F;
  119. pjSrcTemp++;
  120. }
  121. else
  122. {
  123. jSrc = (*pjSrcTemp & 0xF0)>>4;
  124. }
  125. iSrc++;
  126. if (iDst & 0x00000001)
  127. {
  128. if (jSrc != (BYTE)TransColor)
  129. {
  130. jDst |= jSrc & 0x0F;
  131. }
  132. else
  133. {
  134. jDst |= *pjDstTemp & 0x0F;
  135. }
  136. *pjDstTemp++ = jDst;
  137. jDst = 0;
  138. }
  139. else
  140. {
  141. if (jSrc != (BYTE)TransColor)
  142. {
  143. jDst |= (jSrc << 4);
  144. }
  145. else
  146. {
  147. jDst |= *pjDstTemp & 0xF0;
  148. }
  149. }
  150. iDst++;
  151. }
  152. pjDst += pDibInfoDst->stride;
  153. pjSrc += pDibInfoSrc->stride;
  154. }
  155. }
  156. /******************************Public*Routine******************************\
  157. * vTransparentS4D1
  158. *
  159. * Doing a transparent copy from 4PP to 1BPP
  160. *
  161. * Returns:
  162. * VOID.
  163. *
  164. * History:
  165. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  166. * Wrote it.
  167. \**************************************************************************/
  168. VOID vTransparentS4D1 (
  169. PDIBINFO pDibInfoDst,
  170. PDIBINFO pDibInfoSrc,
  171. ULONG TransColor)
  172. {
  173. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  174. + (pDibInfoDst->rclDIB.left >> 3);
  175. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  176. + (pDibInfoSrc->rclDIB.left >> 1);
  177. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  178. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  179. PBYTE pjDstTemp;
  180. PBYTE pjSrcTemp;
  181. BYTE jSrc, jDst;
  182. LONG cxTemp;
  183. BYTE rgbBlue, rgbGreen, rgbRed;
  184. LONG iSrc, iDst;
  185. LOGPALETTE2 logPal2;
  186. HPALETTE hPal;
  187. LONG i;
  188. ULONG rgbColor;
  189. BYTE xlate[16];
  190. //
  191. // build up our xlate table
  192. //
  193. logPal2.PalVersion = 0x300;
  194. logPal2.PalNumEntries = 2;
  195. for (i = 0; i < 2; i++)
  196. {
  197. logPal2.palPalEntry[i].peRed = pDibInfoDst->pbmi->bmiColors[i].rgbRed;
  198. logPal2.palPalEntry[i].peGreen = pDibInfoDst->pbmi->bmiColors[i].rgbGreen;
  199. logPal2.palPalEntry[i].peBlue = pDibInfoDst->pbmi->bmiColors[i].rgbBlue;
  200. logPal2.palPalEntry[i].peFlags = 0;
  201. }
  202. hPal = CreatePalette ((LOGPALETTE *)&logPal2);
  203. for (i = 0; i<16; i++)
  204. {
  205. rgbColor = RGB(pDibInfoSrc->pbmi->bmiColors[i].rgbRed, pDibInfoSrc->pbmi->bmiColors[i].rgbGreen,
  206. pDibInfoSrc->pbmi->bmiColors[i].rgbBlue);
  207. xlate[i] = (BYTE)GetNearestPaletteIndex(hPal, rgbColor);
  208. }
  209. while(cy--)
  210. {
  211. cxTemp = cx;
  212. iSrc = pDibInfoSrc->rclDIB.left;
  213. iDst = pDibInfoDst->rclDIB.left & 0x07;
  214. pjDstTemp = pjDst;
  215. jDst = *pjDstTemp >> (8 - iDst);
  216. pjSrcTemp = pjSrc;
  217. while (cxTemp--)
  218. {
  219. if (iSrc & 0x00000001)
  220. {
  221. jSrc = *pjSrcTemp & 0x0F;
  222. pjSrcTemp++;
  223. }
  224. else
  225. {
  226. jSrc = (*pjSrcTemp & 0xF0)>>4;
  227. }
  228. iSrc++;
  229. //
  230. // put one pixel in the dest
  231. //
  232. if (jSrc != TransColor)
  233. {
  234. jDst |= xlate[jSrc]; //0 OR 1
  235. }
  236. else
  237. {
  238. jDst |= 1-xlate[jSrc];
  239. }
  240. jDst <<1;
  241. iDst++;
  242. if (!(iDst & 0x07))
  243. {
  244. *(pjDstTemp++) = jDst;
  245. jDst = 0;
  246. }
  247. }
  248. if (iDst & 0x00000007)
  249. {
  250. // We need to build up the last pel correctly.
  251. BYTE jMask = (BYTE) (0x000000FF >> (iDst & 0x00000007));
  252. jDst = (BYTE) (jDst << (8 - (iDst & 0x00000007)));
  253. *pjDstTemp = (BYTE) ((*pjDstTemp & jMask) | (jDst & ~jMask));
  254. }
  255. pjDst += pDibInfoDst->stride;
  256. pjSrc += pDibInfoSrc->stride;
  257. }
  258. }
  259. /******************************Public*Routine******************************\
  260. * vTransparentS4D4
  261. *
  262. * Doing a transparent copy from 4PP to 4bpp non identity
  263. *
  264. * Returns:
  265. * VOID.
  266. *
  267. * History:
  268. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  269. * Wrote it.
  270. \**************************************************************************/
  271. VOID vTransparentS4D4 (
  272. PDIBINFO pDibInfoDst,
  273. PDIBINFO pDibInfoSrc,
  274. ULONG TransColor)
  275. {
  276. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  277. + (pDibInfoDst->rclDIB.left >> 1);
  278. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  279. + (pDibInfoSrc->rclDIB.left >> 1);
  280. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  281. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  282. PBYTE pjDstTemp;
  283. PBYTE pjSrcTemp;
  284. BYTE jSrc, jDst;
  285. BYTE rgbBlue, rgbGreen, rgbRed;
  286. LONG iSrc, iDst;
  287. LOGPALETTE16 logPal16;
  288. HPALETTE hPal;
  289. LONG i;
  290. ULONG cxTemp;
  291. ULONG rgbColor;
  292. BYTE xlate[16];
  293. //
  294. // build up translate table
  295. //
  296. logPal16.PalVersion = 0x300;
  297. logPal16.PalNumEntries = 16;
  298. for (i = 0; i < 16; i++)
  299. {
  300. logPal16.palPalEntry[i].peRed = pDibInfoDst->pbmi->bmiColors[i].rgbRed;
  301. logPal16.palPalEntry[i].peGreen = pDibInfoDst->pbmi->bmiColors[i].rgbGreen;
  302. logPal16.palPalEntry[i].peBlue = pDibInfoDst->pbmi->bmiColors[i].rgbBlue;
  303. logPal16.palPalEntry[i].peFlags = 0;
  304. }
  305. hPal = CreatePalette ((LOGPALETTE *)&logPal16);
  306. for (i = 0; i<16; i++)
  307. {
  308. rgbColor = RGB(pDibInfoSrc->pbmi->bmiColors[i].rgbRed, pDibInfoSrc->pbmi->bmiColors[i].rgbGreen,
  309. pDibInfoSrc->pbmi->bmiColors[i].rgbBlue);
  310. xlate[i] = (BYTE)GetNearestPaletteIndex(hPal, rgbColor);
  311. }
  312. while(cy--)
  313. {
  314. cxTemp = cx;
  315. iSrc = pDibInfoSrc->rclDIB.left;
  316. iDst = pDibInfoDst->rclDIB.left;
  317. pjDstTemp = pjDst;
  318. pjSrcTemp = pjSrc;
  319. while (cxTemp--)
  320. {
  321. if (iSrc & 0x00000001)
  322. {
  323. jSrc = *pjSrcTemp & 0x0F;
  324. pjSrcTemp++;
  325. }
  326. else
  327. {
  328. jSrc = (*pjSrcTemp & 0xF0)>>4;
  329. }
  330. iSrc++;
  331. if (iDst & 0x00000001)
  332. {
  333. if (jSrc != (BYTE)TransColor)
  334. {
  335. jDst |= xlate[jSrc] & 0x0F;
  336. }
  337. else
  338. {
  339. jDst |= *pjDstTemp & 0x0F;
  340. }
  341. *pjDstTemp++ = jDst;
  342. jDst = 0;
  343. }
  344. else
  345. {
  346. if (jSrc != (BYTE)TransColor)
  347. {
  348. jDst |= (xlate[jSrc] << 4);
  349. }
  350. else
  351. {
  352. jDst |= *pjDstTemp & 0xF0;
  353. }
  354. }
  355. iDst++;
  356. }
  357. pjDst += pDibInfoDst->stride;
  358. pjSrc += pDibInfoSrc->stride;
  359. }
  360. }
  361. /******************************Public*Routine******************************\
  362. * vTransparentS4D8
  363. *
  364. * Doing a transparent copy from 4PP to 8bpp
  365. *
  366. * Returns:
  367. * VOID.
  368. *
  369. * History:
  370. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  371. * Wrote it.
  372. \**************************************************************************/
  373. VOID vTransparentS4D8 (
  374. PDIBINFO pDibInfoDst,
  375. PDIBINFO pDibInfoSrc,
  376. ULONG TransColor)
  377. {
  378. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top;
  379. + pDibInfoDst->rclDIB.left;
  380. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  381. + (pDibInfoSrc->rclDIB.left >> 1);
  382. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  383. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  384. PBYTE pjDstTemp;
  385. PBYTE pjSrcTemp;
  386. BYTE jSrc;
  387. LONG cxTemp;
  388. BYTE rgbBlue, rgbGreen, rgbRed;
  389. LONG iSrc;
  390. LOGPALETTE256 logPal256;
  391. HPALETTE hPal;
  392. LONG i;
  393. ULONG rgbColor;
  394. BYTE xlate[16];
  395. logPal256.PalVersion = 0x300;
  396. logPal256.PalNumEntries = 256;
  397. for (i = 0; i < 256; i++)
  398. {
  399. logPal256.palPalEntry[i].peRed = pDibInfoDst->pbmi->bmiColors[i].rgbRed;
  400. logPal256.palPalEntry[i].peGreen = pDibInfoDst->pbmi->bmiColors[i].rgbGreen;
  401. logPal256.palPalEntry[i].peBlue = pDibInfoDst->pbmi->bmiColors[i].rgbBlue;
  402. logPal256.palPalEntry[i].peFlags = 0;
  403. }
  404. hPal = CreatePalette ((LOGPALETTE *)&logPal256);
  405. for (i = 0; i<16; i++)
  406. {
  407. rgbColor = RGB(pDibInfoSrc->pbmi->bmiColors[i].rgbRed, pDibInfoSrc->pbmi->bmiColors[i].rgbGreen,
  408. pDibInfoSrc->pbmi->bmiColors[i].rgbBlue);
  409. xlate[i] = (BYTE)GetNearestPaletteIndex(hPal, rgbColor);
  410. //Dprintf("i=%x, rgbColor = 0x%08x, xlate[i] = %x", i, rgbColor, xlate[i]);
  411. }
  412. while(cy--)
  413. {
  414. cxTemp = cx;
  415. iSrc = pDibInfoSrc->rclDIB.left;
  416. pjDstTemp = pjDst;
  417. pjSrcTemp = pjSrc;
  418. while (cxTemp--)
  419. {
  420. if (iSrc & 0x00000001)
  421. {
  422. jSrc = *pjSrcTemp & 0x0F;
  423. pjSrcTemp++;
  424. }
  425. else
  426. {
  427. jSrc = (*pjSrcTemp & 0xF0)>>4;
  428. }
  429. iSrc++;
  430. if (jSrc != (BYTE)TransColor)
  431. {
  432. *pjDstTemp = xlate[jSrc];
  433. }
  434. pjDstTemp++;
  435. }
  436. pjDst += pDibInfoDst->stride;
  437. pjSrc += pDibInfoSrc->stride;
  438. }
  439. }
  440. /******************************Public*Routine******************************\
  441. * vTransparentS4D16
  442. *
  443. * Doing a transparent copy from 4BPP to 16BPP
  444. *
  445. * Returns:
  446. * VOID.
  447. *
  448. * History:
  449. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  450. * Wrote it.
  451. \**************************************************************************/
  452. VOID vTransparentS4D16 (
  453. PDIBINFO pDibInfoDst,
  454. PDIBINFO pDibInfoSrc,
  455. ULONG TransColor)
  456. {
  457. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  458. + pDibInfoDst->rclDIB.left*2;
  459. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  460. + (pDibInfoSrc->rclDIB.left >> 1);
  461. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  462. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  463. PBYTE pjDstTemp;
  464. PBYTE pjSrcTemp;
  465. BYTE jSrc;
  466. LONG cxTemp;
  467. BYTE rgbBlue, rgbGreen, rgbRed;
  468. LONG iSrc, iDst;
  469. while(cy--)
  470. {
  471. cxTemp = cx;
  472. iSrc = pDibInfoSrc->rclDIB.left;
  473. iDst = pDibInfoDst->rclDIB.left;
  474. pjDstTemp = pjDst;
  475. pjSrcTemp = pjSrc;
  476. while (cxTemp--)
  477. {
  478. if (iSrc & 0x00000001)
  479. {
  480. jSrc = *pjSrcTemp & 0x0F;
  481. pjSrcTemp++;
  482. }
  483. else
  484. {
  485. jSrc = (*pjSrcTemp & 0xF0)>>4;
  486. }
  487. iSrc++;
  488. if (jSrc != (BYTE)TransColor)
  489. {
  490. rgbBlue = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbBlue;
  491. rgbGreen = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbGreen;
  492. rgbRed = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbRed;
  493. //
  494. // figure out 5-5-5 or 5-6-5
  495. //
  496. if (pDibInfoDst->pbmi->bmiHeader.biCompression == BI_BITFIELDS)
  497. {
  498. //5-5-5
  499. if (*(DWORD *)&pDibInfoDst->pbmi->bmiColors[1] == 0x03E0)
  500. {
  501. *(PUSHORT)pjDstTemp = (USHORT)rgbBlue >> 3;
  502. *(PUSHORT)pjDstTemp |= (USHORT)(rgbGreen >> 3) << 5;
  503. *(PUSHORT)pjDstTemp |= (USHORT)(rgbRed >> 3) << 10;
  504. }
  505. // 5-6-5
  506. else if (*(DWORD *)&pDibInfoDst->pbmi->bmiColors[1] == 0x07E0)
  507. {
  508. *(PUSHORT)pjDstTemp = (USHORT)rgbBlue >> 3;
  509. *(PUSHORT)pjDstTemp |= (USHORT)(rgbGreen >> 2) << 5;
  510. *(PUSHORT)pjDstTemp |= (USHORT)(rgbRed >> 3) << 11;
  511. }
  512. else
  513. {
  514. WARNING ("unsupported BITFIELDS\n");
  515. }
  516. }
  517. else
  518. {
  519. *(PUSHORT)pjDstTemp = (USHORT)rgbBlue >> 3;
  520. *(PUSHORT)pjDstTemp |= (USHORT)(rgbGreen >> 3) << 5;
  521. *(PUSHORT)pjDstTemp |= (USHORT)(rgbRed >> 3) << 10;
  522. }
  523. }
  524. pjDstTemp += 2;
  525. }
  526. pjDst += pDibInfoDst->stride;
  527. pjSrc += pDibInfoSrc->stride;
  528. }
  529. }
  530. /******************************Public*Routine******************************\
  531. * vTransparentS4D24
  532. *
  533. * Doing a transparent copy from 4BPP to 24BPP
  534. *
  535. * Returns:
  536. * VOID.
  537. *
  538. * History:
  539. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  540. * Wrote it.
  541. \**************************************************************************/
  542. VOID vTransparentS4D24 (
  543. PDIBINFO pDibInfoDst,
  544. PDIBINFO pDibInfoSrc,
  545. ULONG TransColor)
  546. {
  547. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  548. + pDibInfoDst->rclDIB.left*3;
  549. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  550. + (pDibInfoSrc->rclDIB.left >> 1);
  551. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  552. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  553. PBYTE pjDstTemp;
  554. PBYTE pjSrcTemp;
  555. LONG cxTemp;
  556. BYTE jSrc;
  557. LONG iSrc, iDst;
  558. BYTE rgbBlue, rgbGreen, rgbRed;
  559. while(cy--)
  560. {
  561. cxTemp = cx;
  562. pjDstTemp = pjDst;
  563. pjSrcTemp = pjSrc;
  564. iSrc = pDibInfoSrc->rclDIB.left;
  565. iDst = pDibInfoDst->rclDIB.left;
  566. while (cxTemp--)
  567. {
  568. if (iSrc & 0x00000001)
  569. {
  570. jSrc = *pjSrcTemp & 0x0F;
  571. pjSrcTemp++;
  572. }
  573. else
  574. {
  575. jSrc = (*pjSrcTemp & 0xF0)>>4;
  576. }
  577. iSrc++;
  578. if (jSrc != (BYTE)TransColor)
  579. {
  580. rgbBlue = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbBlue;
  581. rgbGreen = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbGreen;
  582. rgbRed = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbRed;
  583. *(pjDstTemp++) = (BYTE) rgbBlue;
  584. *(pjDstTemp++) = (BYTE) rgbGreen;
  585. *(pjDstTemp++) = (BYTE) rgbRed;
  586. }
  587. else
  588. {
  589. pjDstTemp += 3;
  590. }
  591. }
  592. pjDst += pDibInfoDst->stride;
  593. pjSrc += pDibInfoSrc->stride;
  594. }
  595. }
  596. /******************************Public*Routine******************************\
  597. * vTransparentS4D32
  598. *
  599. * Doing a transparent copy from 4BPP to 32BPP
  600. *
  601. * Returns:
  602. * VOID.
  603. *
  604. * History:
  605. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  606. * Wrote it.
  607. \**************************************************************************/
  608. VOID vTransparentS4D32 (
  609. PDIBINFO pDibInfoDst,
  610. PDIBINFO pDibInfoSrc,
  611. ULONG TransColor)
  612. {
  613. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  614. + pDibInfoDst->rclDIB.left*4;
  615. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  616. + (pDibInfoSrc->rclDIB.left >> 1);
  617. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  618. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  619. PBYTE pjDstTemp;
  620. PBYTE pjSrcTemp;
  621. LONG cxTemp;
  622. BYTE jSrc;
  623. LONG iSrc, iDst;
  624. BYTE rgbBlue, rgbGreen, rgbRed;
  625. while(cy--)
  626. {
  627. cxTemp = cx;
  628. pjDstTemp = pjDst;
  629. pjSrcTemp = pjSrc;
  630. iSrc = pDibInfoSrc->rclDIB.left;
  631. iDst = pDibInfoDst->rclDIB.left;
  632. while (cxTemp--)
  633. {
  634. if (iSrc & 0x00000001)
  635. {
  636. jSrc = *pjSrcTemp & 0x0F;
  637. pjSrcTemp++;
  638. }
  639. else
  640. {
  641. jSrc = (*pjSrcTemp & 0xF0)>>4;
  642. }
  643. iSrc++;
  644. if (jSrc != (BYTE)TransColor)
  645. {
  646. rgbBlue = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbBlue;
  647. rgbGreen = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbGreen;
  648. rgbRed = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbRed;
  649. *(PULONG)pjDstTemp = (DWORD) (rgbBlue | (WORD)rgbGreen << 8 | (DWORD)rgbRed << 16);
  650. }
  651. pjDstTemp += 4;
  652. }
  653. pjDst += pDibInfoDst->stride;
  654. pjSrc += pDibInfoSrc->stride;
  655. }
  656. }
  657. /******************************Public*Routine******************************\
  658. * vTransparentS8D16
  659. *
  660. * Doing a transparent copy from 8BPP to 16BPP
  661. *
  662. * Returns:
  663. * VOID.
  664. *
  665. * History:
  666. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  667. * Wrote it.
  668. \**************************************************************************/
  669. VOID vTransparentS8D16 (
  670. PDIBINFO pDibInfoDst,
  671. PDIBINFO pDibInfoSrc,
  672. ULONG TransColor)
  673. {
  674. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  675. + pDibInfoDst->rclDIB.left*2;
  676. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  677. + pDibInfoSrc->rclDIB.left;
  678. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  679. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  680. PBYTE pjDstTemp;
  681. PBYTE pjSrcTemp;
  682. BYTE jSrc;
  683. LONG cxTemp;
  684. BYTE rgbBlue, rgbGreen, rgbRed;
  685. while(cy--)
  686. {
  687. cxTemp = cx;
  688. pjDstTemp = pjDst;
  689. pjSrcTemp = pjSrc;
  690. while (cxTemp--)
  691. {
  692. jSrc = *pjSrcTemp++;
  693. //
  694. // put one pixel in the dest
  695. //
  696. if (jSrc != (BYTE)TransColor)
  697. {
  698. rgbBlue = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbBlue;
  699. rgbGreen = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbGreen;
  700. rgbRed = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbRed;
  701. //
  702. // figure out 5-5-5 or 5-6-5
  703. //
  704. if (pDibInfoDst->pbmi->bmiHeader.biCompression == BI_BITFIELDS)
  705. {
  706. //5-5-5
  707. if (*(DWORD *)&pDibInfoDst->pbmi->bmiColors[1] == 0x03E0)
  708. {
  709. *(PUSHORT)pjDstTemp = (USHORT)rgbBlue >> 3;
  710. *(PUSHORT)pjDstTemp |= (USHORT)(rgbGreen >> 3) << 5;
  711. *(PUSHORT)pjDstTemp |= (USHORT)(rgbRed >> 3) << 10;
  712. }
  713. // 5-6-5
  714. else if (*(DWORD *)&pDibInfoDst->pbmi->bmiColors[1] == 0x07E0)
  715. {
  716. *(PUSHORT)pjDstTemp = (USHORT)rgbBlue >> 3;
  717. *(PUSHORT)pjDstTemp |= (USHORT)(rgbGreen >> 2) << 5;
  718. *(PUSHORT)pjDstTemp |= (USHORT)(rgbRed >> 3) << 11;
  719. }
  720. else
  721. {
  722. WARNING ("unsupported BITFIELDS\n");
  723. }
  724. }
  725. else
  726. {
  727. *(PUSHORT)pjDstTemp = (USHORT)rgbBlue >> 3;
  728. *(PUSHORT)pjDstTemp |= (USHORT)(rgbGreen >> 3) << 5;
  729. *(PUSHORT)pjDstTemp |= (USHORT)(rgbRed >> 3) << 10;
  730. }
  731. }
  732. pjDstTemp += 2;
  733. }
  734. pjDst += pDibInfoDst->stride;
  735. pjSrc += pDibInfoSrc->stride;
  736. }
  737. }
  738. /******************************Public*Routine******************************\
  739. * vTransparentS8D24
  740. *
  741. * Doing a transparent copy from 8BPP to 16BPP
  742. *
  743. * Returns:
  744. * VOID.
  745. *
  746. * History:
  747. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  748. * Wrote it.
  749. \**************************************************************************/
  750. VOID vTransparentS8D24 (
  751. PDIBINFO pDibInfoDst,
  752. PDIBINFO pDibInfoSrc,
  753. ULONG TransColor)
  754. {
  755. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  756. + pDibInfoDst->rclDIB.left*3;
  757. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  758. + pDibInfoSrc->rclDIB.left;
  759. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  760. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  761. PBYTE pjDstTemp;
  762. PBYTE pjSrcTemp;
  763. BYTE jSrc;
  764. LONG cxTemp;
  765. BYTE rgbBlue, rgbGreen, rgbRed;
  766. while(cy--)
  767. {
  768. cxTemp = cx;
  769. pjDstTemp = pjDst;
  770. pjSrcTemp = pjSrc;
  771. while (cxTemp--)
  772. {
  773. jSrc = *pjSrcTemp++;
  774. if (jSrc != (BYTE)TransColor)
  775. {
  776. rgbBlue = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbBlue;
  777. rgbGreen = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbGreen;
  778. rgbRed = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbRed;
  779. *(pjDstTemp++) = (BYTE) rgbBlue;
  780. *(pjDstTemp++) = (BYTE) rgbGreen;
  781. *(pjDstTemp++) = (BYTE) rgbRed;
  782. }
  783. else
  784. {
  785. pjDstTemp += 3;
  786. }
  787. }
  788. pjDst += pDibInfoDst->stride;
  789. pjSrc += pDibInfoSrc->stride;
  790. }
  791. }
  792. /******************************Public*Routine******************************\
  793. * vTransparentS8D32
  794. *
  795. * Doing a transparent copy from 8BPP to 32BPP
  796. *
  797. * Returns:
  798. * VOID.
  799. *
  800. * History:
  801. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  802. * Wrote it.
  803. \**************************************************************************/
  804. VOID vTransparentS8D32 (
  805. PDIBINFO pDibInfoDst,
  806. PDIBINFO pDibInfoSrc,
  807. ULONG TransColor)
  808. {
  809. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  810. + pDibInfoDst->rclDIB.left*4;
  811. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  812. + pDibInfoSrc->rclDIB.left;
  813. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  814. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  815. PBYTE pjDstTemp;
  816. PBYTE pjSrcTemp;
  817. BYTE jSrc;
  818. LONG cxTemp;
  819. BYTE rgbBlue, rgbGreen, rgbRed;
  820. while(cy--)
  821. {
  822. cxTemp = cx;
  823. pjDstTemp = pjDst;
  824. pjSrcTemp = pjSrc;
  825. while (cxTemp--)
  826. {
  827. jSrc = *pjSrcTemp++;
  828. if (jSrc != (BYTE)TransColor)
  829. {
  830. rgbBlue = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbBlue;
  831. rgbGreen = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbGreen;
  832. rgbRed = pDibInfoSrc->pbmi->bmiColors[jSrc].rgbRed;
  833. *(PULONG)pjDstTemp = (DWORD) (rgbBlue | (WORD)rgbGreen << 8 | (DWORD)rgbRed << 16);
  834. }
  835. pjDstTemp += 4;
  836. }
  837. pjDst += pDibInfoDst->stride;
  838. pjSrc += pDibInfoSrc->stride;
  839. }
  840. }
  841. /******************************Public*Routine******************************\
  842. * vTransparentS8D1
  843. *
  844. * Doing a transparent copy from 8BPP to other 1,16,24,32bpp format DIBs
  845. *
  846. * Returns:
  847. * VOID.
  848. *
  849. * History:
  850. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  851. * Wrote it.
  852. \**************************************************************************/
  853. VOID vTransparentS8D1 (
  854. PDIBINFO pDibInfoDst,
  855. PDIBINFO pDibInfoSrc,
  856. ULONG TransColor)
  857. {
  858. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top;
  859. pjDst = StartPixel (pjDst, pDibInfoDst->rclDIB.left, pDibInfoDst->pbmi->bmiHeader.biBitCount);
  860. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  861. + pDibInfoSrc->rclDIB.left;
  862. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  863. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  864. PBYTE pjDstTemp;
  865. PBYTE pjSrcTemp;
  866. BYTE jSrc;
  867. LONG cxTemp;
  868. HDC hdc;
  869. HBITMAP hbm;
  870. ULONG ulWidthDst, ulHeightDst, ulWidthSrc, ulHeightSrc;
  871. BYTE pByte[32];
  872. INT i, j;
  873. BYTE pByteSrc[256];
  874. LONG iDst;
  875. BYTE jDst;
  876. //
  877. // build the color translation table
  878. //
  879. hdc = CreateCompatibleDC (pDibInfoDst->hdc);
  880. //
  881. // save the original width/height
  882. //
  883. ulWidthDst = pDibInfoDst->pbmi->bmiHeader.biWidth;
  884. ulHeightDst = pDibInfoDst->pbmi->bmiHeader.biHeight;
  885. pDibInfoDst->pbmi->bmiHeader.biWidth = 256;
  886. pDibInfoDst->pbmi->bmiHeader.biHeight = 1;
  887. //
  888. // Create a 256X1 DIB
  889. //
  890. hbm = CreateDIBSection(hdc, (PBITMAPINFO)pDibInfoDst->pbmi, DIB_RGB_COLORS, (PVOID *)&pByte, NULL, 0);
  891. if (!hdc || !hbm)
  892. {
  893. WARNING ("failed to create hdc or hbm\n");
  894. }
  895. SelectObject (hdc, hbm);
  896. for (i = 0; i < 256; i++)
  897. {
  898. pByteSrc[i] = i;
  899. }
  900. ulWidthSrc = pDibInfoSrc->pbmi->bmiHeader.biWidth;
  901. ulHeightSrc = pDibInfoSrc->pbmi->bmiHeader.biHeight;
  902. pDibInfoSrc->pbmi->bmiHeader.biWidth = 256;
  903. pDibInfoSrc->pbmi->bmiHeader.biHeight = 1;
  904. SetDIBits(hdc, hbm, 0, 1, pByteSrc, (PBITMAPINFO)pDibInfoSrc->pbmi,pDibInfoSrc->iUsage);
  905. //
  906. // retore bitmap width/height
  907. //
  908. pDibInfoSrc->pbmi->bmiHeader.biWidth = ulWidthSrc;
  909. pDibInfoSrc->pbmi->bmiHeader.biHeight = ulHeightSrc;
  910. pDibInfoDst->pbmi->bmiHeader.biWidth = ulWidthDst;
  911. pDibInfoDst->pbmi->bmiHeader.biHeight = ulHeightDst;
  912. //
  913. // now pByte contains all the 256 color mappings, just need to split them up
  914. //
  915. BYTE bTmp = 0;
  916. while(cy--)
  917. {
  918. cxTemp = cx;
  919. pjDstTemp = pjDst;
  920. pjSrcTemp = pjSrc;
  921. iDst = pDibInfoDst->rclDIB.left & 0x07;
  922. jDst = *pjDstTemp >> (7 - iDst);
  923. while (cxTemp--)
  924. {
  925. jSrc = *pjSrcTemp++;
  926. //
  927. // put one pixel in the dest
  928. //
  929. bTmp = pByte[jSrc >> 3];
  930. bTmp >>= 7 - (jSrc & 0x07);
  931. if (jSrc != TransColor)
  932. {
  933. jDst |= bTmp;
  934. }
  935. else
  936. {
  937. jDst |= 1-bTmp;
  938. }
  939. jDst <<= 1;
  940. iDst++;
  941. if (!(iDst & 0x07))
  942. {
  943. *(pjDstTemp++) = jDst;
  944. jDst = 0;
  945. }
  946. }
  947. pjDst += pDibInfoDst->stride;
  948. pjSrc += pDibInfoSrc->stride;
  949. }
  950. }
  951. /******************************Public*Routine******************************\
  952. * vTransparentS8D4
  953. *
  954. * Doing a transparent copy from 8BPP to other 1,16,24,32bpp format DIBs
  955. *
  956. * Returns:
  957. * VOID.
  958. *
  959. * History:
  960. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  961. * Wrote it.
  962. \**************************************************************************/
  963. VOID vTransparentS8D4 (
  964. PDIBINFO pDibInfoDst,
  965. PDIBINFO pDibInfoSrc,
  966. ULONG TransColor)
  967. {
  968. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top;
  969. pjDst = StartPixel (pjDst, pDibInfoDst->rclDIB.left, pDibInfoDst->pbmi->bmiHeader.biBitCount);
  970. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  971. + pDibInfoSrc->rclDIB.left;
  972. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  973. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  974. PBYTE pjDstTemp;
  975. PBYTE pjSrcTemp;
  976. BYTE jSrc;
  977. LONG cxTemp;
  978. HDC hdc;
  979. HBITMAP hbm;
  980. ULONG ulWidthDst, ulHeightDst, ulWidthSrc, ulHeightSrc;
  981. BYTE pByte[128];
  982. INT i, j;
  983. BYTE xlate[256];
  984. BYTE pByteSrc[256];
  985. LONG iDst;
  986. //
  987. // build the color translation table
  988. //
  989. hdc = CreateCompatibleDC (pDibInfoDst->hdc);
  990. //
  991. // save the original width/height
  992. //
  993. ulWidthDst = pDibInfoDst->pbmi->bmiHeader.biWidth;
  994. ulHeightDst = pDibInfoDst->pbmi->bmiHeader.biHeight;
  995. pDibInfoDst->pbmi->bmiHeader.biWidth = 256;
  996. pDibInfoDst->pbmi->bmiHeader.biHeight = 1;
  997. //
  998. // Create a 256X1 DIB
  999. //
  1000. hbm = CreateDIBSection(hdc, (PBITMAPINFO)pDibInfoDst->pbmi, DIB_RGB_COLORS, (PVOID *)&pByte, NULL, 0);
  1001. if (!hdc || !hbm)
  1002. {
  1003. WARNING ("failed to create hdc or hbm\n");
  1004. }
  1005. SelectObject (hdc, hbm);
  1006. for (i = 0; i < 256; i++)
  1007. {
  1008. pByteSrc[i] = i;
  1009. }
  1010. ulWidthSrc = pDibInfoSrc->pbmi->bmiHeader.biWidth;
  1011. ulHeightSrc = pDibInfoSrc->pbmi->bmiHeader.biHeight;
  1012. pDibInfoSrc->pbmi->bmiHeader.biWidth = 256;
  1013. pDibInfoSrc->pbmi->bmiHeader.biHeight = 1;
  1014. SetDIBits(hdc, hbm, 0, 1, pByteSrc, (PBITMAPINFO)pDibInfoSrc->pbmi,DIB_RGB_COLORS);
  1015. //
  1016. // retore bitmap width/height
  1017. //
  1018. pDibInfoSrc->pbmi->bmiHeader.biWidth = ulWidthSrc;
  1019. pDibInfoSrc->pbmi->bmiHeader.biHeight = ulHeightSrc;
  1020. pDibInfoDst->pbmi->bmiHeader.biWidth = ulWidthDst;
  1021. pDibInfoDst->pbmi->bmiHeader.biHeight = ulHeightDst;
  1022. //
  1023. // now pByte contains all the 256 color mappings, just need to split them up
  1024. //
  1025. j = 0;
  1026. for (i = 0; i < 128; i++)
  1027. {
  1028. xlate[j] = (pByte[i] & 0xF0) >> 4;
  1029. xlate[j++] = pByte[i] & 0x0F;
  1030. }
  1031. BYTE jDst;
  1032. while(cy--)
  1033. {
  1034. cxTemp = cx;
  1035. iDst = pDibInfoDst->rclDIB.left;
  1036. pjDstTemp = pjDst;
  1037. pjSrcTemp = pjSrc;
  1038. while (cxTemp--)
  1039. {
  1040. jSrc = *pjSrcTemp++;
  1041. if (iDst & 0x00000001)
  1042. {
  1043. if (jSrc != (BYTE)TransColor)
  1044. {
  1045. jDst |= (xlate[jSrc] & 0x0F);
  1046. }
  1047. else
  1048. {
  1049. jDst |= (*pjDstTemp & 0x0F);
  1050. }
  1051. *pjDstTemp = jDst;
  1052. jDst = 0;
  1053. pjDstTemp++;
  1054. }
  1055. else
  1056. {
  1057. if (jSrc != (BYTE)TransColor)
  1058. {
  1059. jDst |= (xlate[jSrc] & 0x0F)<< 4;
  1060. }
  1061. else
  1062. {
  1063. jDst |= (*pjDstTemp & 0x0F) << 4;
  1064. }
  1065. }
  1066. iDst++;
  1067. }
  1068. pjDst += pDibInfoDst->stride;
  1069. pjSrc += pDibInfoSrc->stride;
  1070. }
  1071. }
  1072. /******************************Public*Routine******************************\
  1073. * vTransparentIdentityCopy8
  1074. *
  1075. * Doing a transparent copy on two same size 8BPP format DIBs
  1076. *
  1077. * Returns:
  1078. * VOID.
  1079. *
  1080. * History:
  1081. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  1082. * Wrote it.
  1083. \**************************************************************************/
  1084. VOID vTransparentIdentityCopy8 (
  1085. PDIBINFO pDibInfoDst,
  1086. PDIBINFO pDibInfoSrc,
  1087. ULONG TransColor)
  1088. {
  1089. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  1090. + pDibInfoDst->rclDIB.left;
  1091. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  1092. + pDibInfoSrc->rclDIB.left;
  1093. LONG cx = pDibInfoSrc->rclDIB.right - pDibInfoSrc->rclDIB.left;
  1094. LONG cy = pDibInfoSrc->rclDIB.bottom - pDibInfoSrc->rclDIB.top;
  1095. PBYTE pjDstTemp;
  1096. PBYTE pjSrcTemp;
  1097. LONG cxTemp;
  1098. while(cy--)
  1099. {
  1100. cxTemp = cx;
  1101. pjDstTemp = pjDst;
  1102. pjSrcTemp = pjSrc;
  1103. while (cxTemp--)
  1104. {
  1105. if (*pjSrcTemp != (BYTE)TransColor)
  1106. {
  1107. *pjDstTemp = *pjSrcTemp;
  1108. }
  1109. pjDstTemp++;
  1110. pjSrcTemp++;
  1111. }
  1112. pjDst += pDibInfoDst->stride;
  1113. pjSrc += pDibInfoSrc->stride;
  1114. }
  1115. }
  1116. /******************************Public*Routine******************************\
  1117. * vTransparentS8D8
  1118. *
  1119. * Doing a transparent copy on two same size 8BPP format DIBs
  1120. *
  1121. * Returns:
  1122. * VOID.
  1123. *
  1124. * History:
  1125. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  1126. * Wrote it.
  1127. \**************************************************************************/
  1128. VOID vTransparentS8D8 (
  1129. PDIBINFO pDibInfoDst,
  1130. PDIBINFO pDibInfoSrc,
  1131. ULONG TransColor)
  1132. {
  1133. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  1134. + pDibInfoDst->rclDIB.left;
  1135. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  1136. + pDibInfoSrc->rclDIB.left;
  1137. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  1138. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  1139. PBYTE pjDstTemp;
  1140. PBYTE pjSrcTemp;
  1141. LONG cxTemp;
  1142. HDC hdc;
  1143. HBITMAP hbm;
  1144. ULONG ulWidthDst, ulHeightDst, ulWidthSrc, ulHeightSrc;
  1145. INT i, j;
  1146. BYTE pByteSrc[256];
  1147. PBYTE pxlate;
  1148. LONG iDst;
  1149. //
  1150. // build the color translation table
  1151. //
  1152. hdc = CreateCompatibleDC (pDibInfoDst->hdc);
  1153. //
  1154. // save the original width/height
  1155. //
  1156. ulWidthDst = pDibInfoDst->pbmi->bmiHeader.biWidth;
  1157. ulHeightDst = pDibInfoDst->pbmi->bmiHeader.biHeight;
  1158. pDibInfoDst->pbmi->bmiHeader.biWidth = 256;
  1159. pDibInfoDst->pbmi->bmiHeader.biHeight = 1;
  1160. //
  1161. // Create a 256X1 DIB
  1162. //
  1163. hbm = CreateDIBSection(hdc, (PBITMAPINFO)pDibInfoDst->pbmi, DIB_RGB_COLORS, (PVOID *)&pxlate, NULL, 0);
  1164. if (!hdc || !hbm)
  1165. {
  1166. WARNING ("failed to create hdc or hbm\n");
  1167. }
  1168. SelectObject (hdc, hbm);
  1169. for (i = 0; i < 256; i++)
  1170. {
  1171. pByteSrc[i] = i;
  1172. }
  1173. ulWidthSrc = pDibInfoSrc->pbmi->bmiHeader.biWidth;
  1174. ulHeightSrc = pDibInfoSrc->pbmi->bmiHeader.biHeight;
  1175. pDibInfoSrc->pbmi->bmiHeader.biWidth = 256;
  1176. pDibInfoSrc->pbmi->bmiHeader.biHeight = 1;
  1177. SetDIBits(hdc, hbm, 0, 1, pByteSrc, (PBITMAPINFO)pDibInfoSrc->pbmi,DIB_RGB_COLORS);
  1178. //
  1179. // retore bitmap width/height
  1180. //
  1181. pDibInfoSrc->pbmi->bmiHeader.biWidth = ulWidthSrc;
  1182. pDibInfoSrc->pbmi->bmiHeader.biHeight = ulHeightSrc;
  1183. pDibInfoDst->pbmi->bmiHeader.biWidth = ulWidthDst;
  1184. pDibInfoDst->pbmi->bmiHeader.biHeight = ulHeightDst;
  1185. while(cy--)
  1186. {
  1187. cxTemp = cx;
  1188. pjDstTemp = pjDst;
  1189. pjSrcTemp = pjSrc;
  1190. while (cxTemp--)
  1191. {
  1192. if (*pjSrcTemp != (BYTE)TransColor)
  1193. {
  1194. *pjDstTemp = pxlate[*pjSrcTemp];
  1195. }
  1196. pjDstTemp++;
  1197. pjSrcTemp++;
  1198. }
  1199. pjDst += pDibInfoDst->stride;
  1200. pjSrc += pDibInfoSrc->stride;
  1201. }
  1202. DeleteObject (hbm);
  1203. DeleteDC (hdc);
  1204. }
  1205. #if 0
  1206. /******************************Public*Routine******************************\
  1207. * vTransparentIdentityCopy16
  1208. *
  1209. * Doing a transparent copy on two same size 16BPP format DIBs
  1210. *
  1211. * Returns:
  1212. * VOID.
  1213. *
  1214. * History:
  1215. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  1216. * Wrote it.
  1217. \**************************************************************************/
  1218. VOID vTransparentIdentityCopy16 (
  1219. PDIBINFO pDibInfoDst,
  1220. PDIBINFO pDibInfoSrc,
  1221. ULONG TransColor)
  1222. {
  1223. PUSHORT pusDst = (PUSHORT)((PBYTE)pDibInfoDst->pvBase + pDibInfoDst->rclDIB.top*pDibInfoDst->stride)
  1224. + pDibInfoDst->rclDIB.left;
  1225. PUSHORT pusSrc = (PUSHORT)((PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->rclDIB.top*pDibInfoDst->stride)
  1226. + pDibInfoSrc->rclDIB.left;
  1227. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  1228. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  1229. PUSHORT pusDstTemp;
  1230. PUSHORT pusSrcTemp;
  1231. LONG cxTemp;
  1232. while(cy--)
  1233. {
  1234. cxTemp = cx;
  1235. pusDstTemp = pusDst;
  1236. pusSrcTemp = pusSrc;
  1237. while (cxTemp--)
  1238. {
  1239. if (*pusSrcTemp != (USHORT)TransColor)
  1240. {
  1241. *pusDstTemp = *pusSrcTemp;
  1242. }
  1243. pusDstTemp++;
  1244. pusSrcTemp++;
  1245. }
  1246. pusDst = (PUSHORT)((PBYTE)pusDst + pDibInfoDst->stride);
  1247. pusSrc = (PUSHORT)((PBYTE)pusSrc + pDibInfoSrc->stride);
  1248. }
  1249. }
  1250. /******************************Public*Routine******************************\
  1251. * vTransparentIdentityCopy24
  1252. *
  1253. * Doing a transparent copy on two same size 8BPP format DIBs
  1254. *
  1255. * Returns:
  1256. * VOID.
  1257. *
  1258. * History:
  1259. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  1260. * Wrote it.
  1261. \**************************************************************************/
  1262. VOID vTransparentIdentityCopy24 (
  1263. PDIBINFO pDibInfoDst,
  1264. PDIBINFO pDibInfoSrc,
  1265. ULONG TransColor)
  1266. {
  1267. PBYTE pjDst = (PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top
  1268. + pDibInfoDst->rclDIB.left*3;
  1269. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top
  1270. + pDibInfoSrc->rclDIB.left*3;
  1271. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  1272. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  1273. PBYTE pjDstTemp;
  1274. PBYTE pjSrcTemp;
  1275. ULONG ulTemp;
  1276. LONG cxTemp;
  1277. while(cy--)
  1278. {
  1279. cxTemp = cx;
  1280. pjDstTemp = pjDst;
  1281. pjSrcTemp = pjSrc;
  1282. while (cxTemp--)
  1283. {
  1284. ulTemp = (ULONG) *(pjSrcTemp + 2);
  1285. ulTemp = ulTemp << 8;
  1286. ulTemp |= (ULONG) *(pjSrcTemp + 1);
  1287. ulTemp = ulTemp << 8;
  1288. ulTemp |= (ULONG) *pjSrcTemp;
  1289. if (ulTemp != TransColor)
  1290. {
  1291. *(pjDstTemp++) = (BYTE) ulTemp;
  1292. *(pjDstTemp++) = (BYTE) (ulTemp >> 8);
  1293. *(pjDstTemp++) = (BYTE) (ulTemp >> 16);
  1294. }
  1295. else
  1296. {
  1297. pjDstTemp += 3;
  1298. }
  1299. pjSrcTemp += 3;
  1300. }
  1301. pjDst += pDibInfoDst->stride;
  1302. pjSrc += pDibInfoSrc->stride;
  1303. }
  1304. }
  1305. /******************************Public*Routine******************************\
  1306. * vTransparentIdentityCopy32
  1307. *
  1308. * Doing a transparent copy on two same size 32BPP format DIBs
  1309. *
  1310. * Returns:
  1311. * VOID.
  1312. *
  1313. * History:
  1314. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  1315. * Wrote it.
  1316. \**************************************************************************/
  1317. VOID vTransparentIdentityCopy32 (
  1318. PDIBINFO pDibInfoDst,
  1319. PDIBINFO pDibInfoSrc,
  1320. ULONG TransColor)
  1321. {
  1322. PULONG pulDst = (PULONG)((PBYTE)pDibInfoDst->pvBase + pDibInfoDst->stride*pDibInfoDst->rclDIB.top)
  1323. + pDibInfoDst->rclDIB.left;
  1324. PULONG pulSrc = (PULONG)((PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->stride*pDibInfoSrc->rclDIB.top)
  1325. + pDibInfoSrc->rclDIB.left;
  1326. LONG cx = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  1327. LONG cy = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  1328. PULONG pulDstTemp;
  1329. PULONG pulSrcTemp;
  1330. LONG cxTemp;
  1331. while(cy--)
  1332. {
  1333. cxTemp = cx;
  1334. pulDstTemp = pulDst;
  1335. pulSrcTemp = pulSrc;
  1336. while (cxTemp--)
  1337. {
  1338. // mask off highest byte -- workaround Memphis problem
  1339. if ((*pulSrcTemp & 0x00FFFFFF) != TransColor)
  1340. {
  1341. *pulDstTemp = *pulSrcTemp;
  1342. }
  1343. pulDstTemp++;
  1344. pulSrcTemp++;
  1345. }
  1346. pulDst = (PULONG)((PBYTE)pulDst + pDibInfoDst->stride);
  1347. pulSrc = (PULONG)((PBYTE)pulSrc + pDibInfoSrc->stride);
  1348. }
  1349. }
  1350. #endif
  1351. /******************************Public*Routine******************************\
  1352. * MapTransparentColor
  1353. *
  1354. * Getting the correct transparent color mapped to the specified DIB format
  1355. * by creating a solid brush on the colorref, then PatBlt to a 1X1 DIB, the
  1356. * resulting pixel is the mapped transparent color
  1357. *
  1358. * Returns:
  1359. * VOID.
  1360. *
  1361. * History:
  1362. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  1363. * Wrote it.
  1364. \**************************************************************************/
  1365. DWORD MapTransparentColor(
  1366. PDIBINFO pDibInfo,
  1367. COLORREF Color
  1368. )
  1369. {
  1370. HBRUSH hbr, hbrDefault;
  1371. HBITMAP hbm, hbmDefault;
  1372. HDC hdcTemp;
  1373. UINT iUsage;
  1374. PVOID pvBits = NULL;
  1375. DWORD trancolor;
  1376. ULONG ulWidth, ulHeight;
  1377. hdcTemp = CreateCompatibleDC(pDibInfo->hdc);
  1378. hbr = CreateSolidBrush (Color);
  1379. //
  1380. // save the original width/height
  1381. //
  1382. ulWidth = pDibInfo->pbmi->bmiHeader.biWidth;
  1383. ulHeight = pDibInfo->pbmi->bmiHeader.biHeight;
  1384. pDibInfo->pbmi->bmiHeader.biWidth = 1;
  1385. pDibInfo->pbmi->bmiHeader.biHeight = 1;
  1386. //
  1387. // Create a 1X1 DIB
  1388. //
  1389. hbm = CreateDIBSection(hdcTemp, (PBITMAPINFO)pDibInfo->pbmi, DIB_RGB_COLORS, &pvBits, NULL, 0);
  1390. if (hbm && hbr)
  1391. {
  1392. hbmDefault = (HBITMAP)SelectObject (hdcTemp, hbm);
  1393. hbrDefault = (HBRUSH)SelectObject (hdcTemp, hbr);
  1394. PatBlt (hdcTemp, 0, 0, 1, 1, PATCOPY);
  1395. SelectObject (hdcTemp, hbrDefault);
  1396. SelectObject (hdcTemp, hbmDefault);
  1397. }
  1398. if (pvBits)
  1399. {
  1400. switch (pDibInfo->pbmi->bmiHeader.biBitCount)
  1401. {
  1402. case 4:
  1403. trancolor = *(BYTE *)pvBits;
  1404. trancolor = (DWORD)(((BYTE)trancolor) & 0xF0) >>4;
  1405. break;
  1406. case 8:
  1407. trancolor = (DWORD)(*(BYTE *)pvBits);
  1408. trancolor &= 0x000000FF;
  1409. break;
  1410. case 16:
  1411. trancolor = (DWORD)(*(USHORT *)pvBits);
  1412. trancolor &= 0x0000FFFF;
  1413. break;
  1414. case 24:
  1415. trancolor = *(DWORD *)pvBits;
  1416. trancolor &= 0x00FFFFFF;
  1417. break;
  1418. case 32:
  1419. trancolor = *(DWORD *)pvBits;
  1420. trancolor &= 0x00FFFFFF;
  1421. break;
  1422. }
  1423. }
  1424. pDibInfo->pbmi->bmiHeader.biWidth = ulWidth;
  1425. pDibInfo->pbmi->bmiHeader.biHeight = ulHeight;
  1426. //
  1427. // cleanup
  1428. //
  1429. DeleteObject (hbm);
  1430. DeleteObject (hbr);
  1431. DeleteObject(hdcTemp);
  1432. return (trancolor);
  1433. }
  1434. /******************************Public*Routine******************************\
  1435. * DIBMapTransparentColor
  1436. *
  1437. * Getting the correct transparent color mapped to the specified DIB format
  1438. * This is only for DIB_PAL_COLORS passed into transparentDIBits
  1439. *
  1440. * Returns:
  1441. * VOID.
  1442. *
  1443. * History:
  1444. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  1445. * Wrote it.
  1446. \**************************************************************************/
  1447. DWORD DIBMapTransparentColor(
  1448. PDIBINFO pDibInfoDst,
  1449. PDIBINFO pDibInfoSrc,
  1450. COLORREF Color
  1451. )
  1452. {
  1453. HBITMAP hbm, hbmDefault;
  1454. HDC hdcTemp;
  1455. UINT iUsage;
  1456. PVOID pvBits;
  1457. DWORD trancolor;
  1458. ULONG ulWidth, ulHeight;
  1459. hdcTemp = CreateCompatibleDC(pDibInfoDst->hdc);
  1460. //
  1461. // save the original width/height
  1462. //
  1463. ulWidth = pDibInfoDst->pbmi->bmiHeader.biWidth;
  1464. ulHeight = pDibInfoDst->pbmi->bmiHeader.biHeight;
  1465. pDibInfoDst->pbmi->bmiHeader.biWidth = 1;
  1466. pDibInfoDst->pbmi->bmiHeader.biHeight = 1;
  1467. //
  1468. // Create a 1X1 DIB
  1469. //
  1470. hbm = CreateDIBSection(hdcTemp, (PBITMAPINFO)pDibInfoDst->pbmi, DIB_RGB_COLORS, &pvBits, NULL, 0);
  1471. if (hbm)
  1472. {
  1473. hbmDefault = (HBITMAP)SelectObject (hdcTemp, hbm);
  1474. StretchDIBits (hdcTemp,
  1475. 0,
  1476. 0,
  1477. 1,
  1478. 1,
  1479. 0,
  1480. 0,
  1481. 1,
  1482. 1,
  1483. &Color,
  1484. pDibInfoSrc->pbmi,
  1485. pDibInfoSrc->iUsage,
  1486. SRCCOPY);
  1487. SelectObject (hdcTemp, hbmDefault);
  1488. }
  1489. if (pvBits)
  1490. {
  1491. switch (pDibInfoDst->pbmi->bmiHeader.biBitCount)
  1492. {
  1493. case 4:
  1494. trancolor = *(BYTE *)pvBits;
  1495. trancolor = (DWORD)(((BYTE)trancolor) & 0xF0) >>4;
  1496. break;
  1497. case 8:
  1498. trancolor = (DWORD)(*(BYTE *)pvBits);
  1499. trancolor &= 0x000000FF;
  1500. break;
  1501. case 16:
  1502. trancolor = (DWORD)(*(USHORT *)pvBits);
  1503. trancolor &= 0x0000FFFF;
  1504. break;
  1505. case 24:
  1506. trancolor = *(DWORD *)pvBits;
  1507. trancolor &= 0x00FFFFFF;
  1508. break;
  1509. case 32:
  1510. trancolor = *(DWORD *)pvBits;
  1511. trancolor &= 0x00FFFFFF;
  1512. break;
  1513. }
  1514. }
  1515. pDibInfoDst->pbmi->bmiHeader.biWidth = ulWidth;
  1516. pDibInfoDst->pbmi->bmiHeader.biHeight = ulHeight;
  1517. //
  1518. // cleanup
  1519. //
  1520. DeleteObject (hbm);
  1521. DeleteObject(hdcTemp);
  1522. return (trancolor);
  1523. }
  1524. /******************************Public*Routine******************************\
  1525. * vTransparentMapCopy
  1526. *
  1527. * Map the Dest surface to 32bpp and does transparent on to that
  1528. *
  1529. * Returns:
  1530. * VOID.
  1531. *
  1532. * History:
  1533. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  1534. * Wrote it.
  1535. \**************************************************************************/
  1536. VOID vTransparentMapCopy (
  1537. PDIBINFO pDibInfoDst,
  1538. PDIBINFO pDibInfoSrc,
  1539. ULONG TransColor)
  1540. {
  1541. HDC hdc = pDibInfoSrc->hdc;
  1542. ULONG cxDst = pDibInfoDst->rclDIB.right - pDibInfoDst->rclDIB.left;
  1543. ULONG cyDst = pDibInfoDst->rclDIB.bottom - pDibInfoDst->rclDIB.top;
  1544. HBITMAP hbm;
  1545. PVOID pBits;
  1546. ULONG cBytes = sizeof(BITMAPINFO) + sizeof(RGBQUAD) * 255;
  1547. PBITMAPINFO pbmi;
  1548. PVOID p = LOCALALLOC(cBytes);
  1549. if (!p)
  1550. {
  1551. WARNING("MapCopy fail to alloc mem\n");
  1552. return ;
  1553. }
  1554. ZeroMemory (p,cBytes);
  1555. pbmi = (PBITMAPINFO)p;
  1556. vCopyBitmapInfo (pbmi, pDibInfoDst->pbmi);
  1557. hdc = CreateCompatibleDC (hdc);
  1558. pbmi->bmiHeader.biBitCount = 32;
  1559. // create a dib using 32 format
  1560. hbm = CreateCompatibleDIB (hdc, cxDst, cyDst, &pBits, pbmi);
  1561. SetDIBits (hdc, hbm, 0, cyDst, pDibInfoDst->pvBits, pDibInfoDst->pbmi, DIB_RGB_COLORS);
  1562. vCopyBitmapInfo (pDibInfoDst->pbmi,pbmi);
  1563. GetCompatibleDIBInfo (hbm, &pDibInfoDst->pvBase, &pDibInfoDst->stride);
  1564. pDibInfoDst->pvBits = pBits;
  1565. if (pDibInfoSrc->pbmi->bmiHeader.biBitCount == 8)
  1566. {
  1567. vTransparentS8D32 (pDibInfoDst, pDibInfoSrc, TransColor);
  1568. }
  1569. else if (pDibInfoSrc->pbmi->bmiHeader.biBitCount == 4)
  1570. {
  1571. vTransparentS4D32 (pDibInfoDst, pDibInfoSrc, TransColor);
  1572. }
  1573. if (p)
  1574. {
  1575. LOCALFREE (p);
  1576. }
  1577. }
  1578. /******************************Public*Routine******************************\
  1579. * ReadScanLine
  1580. * read the scanline until it hits a transparent color pixel
  1581. *
  1582. * History:
  1583. * 26-Nov-1996 -by- Lingyun Wang [lingyunw]
  1584. * Wrote it.
  1585. \**************************************************************************/
  1586. ULONG ReadScanLine(
  1587. PBYTE pjSrc,
  1588. ULONG xStart,
  1589. ULONG xEnd,
  1590. ULONG iFormat,
  1591. ULONG TransparentColor)
  1592. {
  1593. ULONG cx = xEnd-xStart;
  1594. ULONG Shift = (iFormat - 3 > 0) ? iFormat : 1;
  1595. ULONG iPos;
  1596. ULONG ulSrc;
  1597. BOOL bStop = FALSE;
  1598. pjSrc = StartPixel (pjSrc, xStart, iFormat);
  1599. //
  1600. // performance can be improved by breaking this routine into many
  1601. // dealing with different format so that we can save two comparsions
  1602. // for each pixel operation. But working set size will be large
  1603. //
  1604. iPos = xStart;
  1605. //
  1606. // read one pixel at a time and compare it to the transparent color
  1607. // if it matches the transparent color, come out
  1608. //
  1609. while ((iPos < xEnd) && !bStop)
  1610. {
  1611. //
  1612. // get a pixel from source and compare is to the transparent color
  1613. //
  1614. switch (iFormat)
  1615. {
  1616. case 1:
  1617. ulSrc = *pjSrc & 0x00000001;
  1618. *pjSrc >>= 1;
  1619. if (!(iPos & 0x00000007) )
  1620. pjSrc++;
  1621. break;
  1622. case 4:
  1623. if (iPos & 0x00000001)
  1624. {
  1625. ulSrc = *pjSrc & 0x0F;
  1626. pjSrc++;
  1627. }
  1628. else
  1629. {
  1630. ulSrc = (*pjSrc & 0xF0)>>4;
  1631. }
  1632. break;
  1633. case 8:
  1634. ulSrc = (ULONG) *pjSrc;
  1635. pjSrc++;
  1636. break;
  1637. case 16:
  1638. ulSrc = (ULONG) *((PUSHORT)pjSrc);
  1639. pjSrc += 2;
  1640. break;
  1641. case 24:
  1642. ulSrc = *(pjSrc + 2);
  1643. ulSrc = ulSrc << 8;
  1644. ulSrc |= (ULONG) *(pjSrc + 1);
  1645. ulSrc = ulSrc << 8;
  1646. ulSrc |= (ULONG) *pjSrc;
  1647. pjSrc += 3;
  1648. break;
  1649. case 32:
  1650. ulSrc = *(PULONG)(pjSrc);
  1651. pjSrc +=4;
  1652. break;
  1653. default:
  1654. WARNING ("vTransparentScan -- bad iFormatSrc\n");
  1655. return(0);
  1656. } /*switch*/
  1657. if (ulSrc == TransparentColor)
  1658. bStop = TRUE;
  1659. iPos++;
  1660. }
  1661. return (iPos);
  1662. }
  1663. /******************************Public*Routine******************************\
  1664. * SkipScanLine
  1665. * read the scanline until it hits a non-transparent color pixel
  1666. *
  1667. * History:
  1668. * 26-Nov-1996 -by- Lingyun Wang [lingyunw]
  1669. * Wrote it.
  1670. \**************************************************************************/
  1671. ULONG SkipScanLine(
  1672. PBYTE pjSrc,
  1673. ULONG xStart,
  1674. ULONG xEnd,
  1675. ULONG iFormat,
  1676. ULONG TransparentColor)
  1677. {
  1678. ULONG Shift = (iFormat - 3 > 0) ? iFormat : 1;
  1679. ULONG iPos = xStart;
  1680. ULONG ulSrc;
  1681. BOOL bStop = FALSE;
  1682. pjSrc = StartPixel (pjSrc, xStart, iFormat);
  1683. //
  1684. // performance can be improved by breaking this routine into many
  1685. // dealing with different format so that we can save two comparsions
  1686. // for each pixel operation. But working set size will be large
  1687. //
  1688. //
  1689. // read one pixel at a time and compare it to the transparent color
  1690. // if it matches the transparent color, come out
  1691. //
  1692. while ((iPos < xEnd) && !bStop)
  1693. {
  1694. //
  1695. // get a pixel from source and compare is to the transparent color
  1696. //
  1697. switch (iFormat)
  1698. {
  1699. case 1:
  1700. ulSrc = *pjSrc & 0x00000001;
  1701. *pjSrc >>= 1;
  1702. if (!(iPos & 0x00000007) )
  1703. pjSrc++;
  1704. break;
  1705. case 4:
  1706. if (iPos & 0x00000001)
  1707. {
  1708. ulSrc = *pjSrc & 0x0F;
  1709. pjSrc++;
  1710. }
  1711. else
  1712. {
  1713. ulSrc = (*pjSrc & 0xF0)>>4;
  1714. }
  1715. break;
  1716. case 8:
  1717. ulSrc = (ULONG) *pjSrc;
  1718. pjSrc++;
  1719. break;
  1720. case 16:
  1721. ulSrc = (ULONG) *((PUSHORT)pjSrc);
  1722. pjSrc += 2;
  1723. break;
  1724. case 24:
  1725. ulSrc = *(pjSrc + 2);
  1726. ulSrc = ulSrc << 8;
  1727. ulSrc |= (ULONG) *(pjSrc + 1);
  1728. ulSrc = ulSrc << 8;
  1729. ulSrc |= (ULONG) *pjSrc;
  1730. pjSrc += 3;
  1731. break;
  1732. case 32:
  1733. ulSrc = *(PULONG)(pjSrc);
  1734. pjSrc +=4;
  1735. break;
  1736. default:
  1737. WARNING ("vTransparentScan -- bad iFormatSrc\n");
  1738. return (0);
  1739. } /*switch*/
  1740. if (ulSrc != TransparentColor)
  1741. bStop = TRUE;
  1742. iPos++; // move to the next pixel
  1743. }
  1744. return (iPos);
  1745. }
  1746. /******************************Public*Routine******************************\
  1747. * VOID vTransparentCopyScan
  1748. *
  1749. * Read a scanline at a time and send the non-transparent pixel scans over
  1750. *
  1751. * History:
  1752. * 2-Dec-1996 -by- Lingyun Wang [lingyunw]
  1753. * Wrote it.
  1754. \**************************************************************************/
  1755. VOID vTransparentCopyScan (
  1756. PDIBINFO pDibInfoDst,
  1757. PDIBINFO pDibInfoSrc,
  1758. ULONG TransparentColor)
  1759. {
  1760. ULONG xStart;
  1761. ULONG cx = pDibInfoSrc->rclDIB.right - pDibInfoSrc->rclDIB.left;
  1762. ULONG cy = pDibInfoSrc->rclDIB.bottom - pDibInfoSrc->rclDIB.top;
  1763. ULONG xEnd;
  1764. ULONG xSrc;
  1765. ULONG ySrc = pDibInfoSrc->rclDIB.bottom;
  1766. ULONG xDst;
  1767. ULONG yDst = pDibInfoDst->rclBounds.top;
  1768. ULONG xStop, xReStart;
  1769. PBYTE pjSrc = (PBYTE)pDibInfoSrc->pvBase + pDibInfoSrc->rclDIB.top*pDibInfoSrc->stride;
  1770. //
  1771. // we only allow 4bpp,8bpp src for now
  1772. //
  1773. if ((pDibInfoSrc->pbmi->bmiHeader.biBitCount != 4) ||
  1774. (pDibInfoSrc->pbmi->bmiHeader.biBitCount != 8))
  1775. return;
  1776. while (cy--)
  1777. {
  1778. xStart = pDibInfoSrc->rclDIB.left;
  1779. xEnd = xStart + cx;
  1780. xSrc = pDibInfoSrc->rclDIB.left;
  1781. xDst = pDibInfoDst->rclBounds.left;
  1782. while (xStart < xEnd)
  1783. {
  1784. xStop = ReadScanLine((PBYTE)pjSrc,
  1785. xStart,
  1786. xEnd,
  1787. pDibInfoSrc->pbmi->bmiHeader.biBitCount,
  1788. TransparentColor);
  1789. if (xStop-1 > xStart)
  1790. {
  1791. //
  1792. // send the partial scan line over
  1793. //
  1794. StretchDIBits (
  1795. pDibInfoDst->hdc,
  1796. xDst,
  1797. yDst,
  1798. xStop-xStart-1, //width
  1799. 1,
  1800. xSrc-1,
  1801. ySrc-1,
  1802. xStop-xStart-1,
  1803. 1,
  1804. (PBYTE)pDibInfoSrc->pvBits,
  1805. pDibInfoSrc->pbmi,
  1806. DIB_RGB_COLORS,
  1807. SRCCOPY);
  1808. }
  1809. //get to the next non transparent pixel
  1810. xReStart = SkipScanLine((PBYTE)pjSrc,
  1811. xStop-1,
  1812. xEnd,
  1813. pDibInfoSrc->pbmi->bmiHeader.biBitCount,
  1814. TransparentColor);
  1815. xDst = xDst + xReStart-xStart;
  1816. xSrc = xReStart;
  1817. xStart = xReStart;
  1818. }
  1819. pjSrc += pDibInfoSrc->stride;
  1820. ySrc--;
  1821. yDst++;
  1822. }
  1823. }
  1824. /******************************Public*Routine******************************\
  1825. * WinTransparentBlt
  1826. *
  1827. * Returns:
  1828. * BOOL.
  1829. *
  1830. * History:
  1831. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  1832. * Wrote it.
  1833. \**************************************************************************/
  1834. BOOL
  1835. WinTransparentBlt(
  1836. HDC hdcDst,
  1837. int xDst,
  1838. int yDst,
  1839. int cxDst,
  1840. int cyDst,
  1841. HDC hdcSrc,
  1842. int xSrc,
  1843. int ySrc,
  1844. int cxSrc,
  1845. int cySrc,
  1846. UINT TransColor
  1847. )
  1848. {
  1849. BOOL bRet = TRUE;
  1850. DIBINFO DibInfoDst, DibInfoSrc;
  1851. PDIBINFO pDibInfoDst, pDibInfoSrc;
  1852. BOOL bReadable;
  1853. //
  1854. // parameter checking
  1855. //
  1856. if (cxDst < 0 || cyDst < 0 || cxSrc < 0 || cySrc < 0)
  1857. {
  1858. WARNING("bad parameters\n");
  1859. return (FALSE);
  1860. }
  1861. pDibInfoDst = &DibInfoDst;
  1862. ZeroMemory (pDibInfoDst, sizeof(DIBINFO));
  1863. if (!bInitDIBINFO (hdcDst, xDst, yDst, cxDst, cyDst, pDibInfoDst))
  1864. return (FALSE);
  1865. pDibInfoSrc = &DibInfoSrc;
  1866. ZeroMemory (pDibInfoSrc, sizeof(DIBINFO));
  1867. if (!bInitDIBINFO (hdcSrc, xSrc, ySrc, cxSrc, cySrc, pDibInfoSrc))
  1868. return (FALSE);
  1869. bRet = bSetupBitmapInfos (pDibInfoDst, pDibInfoSrc);
  1870. if (bRet)
  1871. {
  1872. TransColor = MapTransparentColor (pDibInfoSrc, TransColor);
  1873. bRet = bGetSrcDIBits(pDibInfoDst, pDibInfoSrc, SOURCE_TRAN, TransColor);
  1874. if (bRet)
  1875. {
  1876. bRet = bGetDstDIBits (pDibInfoDst, &bReadable, SOURCE_TRAN);
  1877. if (bRet)
  1878. {
  1879. if (bReadable)
  1880. {
  1881. switch (pDibInfoSrc->pbmi->bmiHeader.biBitCount)
  1882. {
  1883. case 4:
  1884. if (bSameDIBformat(pDibInfoDst->pbmi,pDibInfoSrc->pbmi))
  1885. {
  1886. vTransparentIdentityCopy4 (pDibInfoDst, pDibInfoSrc, TransColor);
  1887. }
  1888. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 4)
  1889. {
  1890. vTransparentS4D4 (pDibInfoDst, pDibInfoSrc, TransColor);
  1891. }
  1892. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 8)
  1893. {
  1894. vTransparentS4D8(pDibInfoDst, pDibInfoSrc, TransColor);
  1895. }
  1896. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 16)
  1897. {
  1898. vTransparentS4D16 (pDibInfoDst, pDibInfoSrc, TransColor);
  1899. }
  1900. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 24)
  1901. {
  1902. vTransparentS4D24 (pDibInfoDst, pDibInfoSrc, TransColor);
  1903. }
  1904. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 32)
  1905. {
  1906. vTransparentS4D32 (pDibInfoDst, pDibInfoSrc, TransColor);
  1907. }
  1908. else
  1909. { //1
  1910. vTransparentMapCopy (pDibInfoDst, pDibInfoSrc, TransColor);
  1911. }
  1912. break;
  1913. case 8:
  1914. if (bSameDIBformat(pDibInfoDst->pbmi,pDibInfoSrc->pbmi))
  1915. {
  1916. vTransparentIdentityCopy8 (pDibInfoDst, pDibInfoSrc, TransColor);
  1917. }
  1918. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 8)
  1919. {
  1920. vTransparentS8D8 (pDibInfoDst, pDibInfoSrc, TransColor);
  1921. }
  1922. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 16)
  1923. {
  1924. vTransparentS8D16 (pDibInfoDst, pDibInfoSrc, TransColor);
  1925. }
  1926. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 24)
  1927. {
  1928. vTransparentS8D24 (pDibInfoDst, pDibInfoSrc, TransColor);
  1929. }
  1930. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 32)
  1931. {
  1932. vTransparentS8D32 (pDibInfoDst, pDibInfoSrc, TransColor);
  1933. }
  1934. else
  1935. {
  1936. //1, 4
  1937. vTransparentMapCopy (pDibInfoDst, pDibInfoSrc, TransColor);
  1938. }
  1939. break;
  1940. default:
  1941. WARNING ("src format not currently supported\n");
  1942. bRet = FALSE;
  1943. goto CleanUp;
  1944. break;
  1945. }
  1946. //
  1947. // if we have created a temp destination DIB, send the final result to destination
  1948. //
  1949. bRet = bSendDIBINFO (hdcDst, pDibInfoDst);
  1950. }
  1951. else
  1952. {
  1953. //
  1954. // non-readable dest surface
  1955. //
  1956. vTransparentCopyScan (pDibInfoDst, pDibInfoSrc, TransColor);
  1957. }
  1958. }
  1959. else
  1960. {
  1961. WARNING ("GetSrcDIBits failed\n");
  1962. bRet = FALSE;
  1963. }
  1964. }
  1965. }
  1966. else
  1967. {
  1968. WARNING ("GetDstDIBits failed \n");
  1969. bRet = FALSE;
  1970. }
  1971. //
  1972. // clean up
  1973. //
  1974. CleanUp:
  1975. vCleanupDIBINFO (pDibInfoDst);
  1976. vCleanupDIBINFO (pDibInfoSrc);
  1977. return (bRet);
  1978. }
  1979. /******************************Public*Routine******************************\
  1980. * WinTransparentDIBits
  1981. *
  1982. * Returns:
  1983. * BOOL.
  1984. *
  1985. * History:
  1986. * 09-Dec-1996 -by- Lingyun Wang [lingyunw]
  1987. * Wrote it.
  1988. \**************************************************************************/
  1989. BOOL
  1990. WinTransparentDIBits(
  1991. HDC hdcDst,
  1992. int xDst,
  1993. int yDst,
  1994. int cxDst,
  1995. int cyDst,
  1996. CONST VOID * lpBits,
  1997. CONST BITMAPINFO *lpBitsInfo,
  1998. UINT iUsage,
  1999. int xSrc,
  2000. int ySrc,
  2001. int cxSrc,
  2002. int cySrc,
  2003. UINT TransColor
  2004. )
  2005. {
  2006. BOOL bRet = TRUE;
  2007. DIBINFO DibInfoDst, DibInfoSrc;
  2008. PDIBINFO pDibInfoDst, pDibInfoSrc;
  2009. BOOL bReadable;
  2010. //
  2011. // parameter checking
  2012. //
  2013. if (cxDst < 0 || cyDst < 0)
  2014. {
  2015. WARNING("bad parameters\n");
  2016. return (FALSE);
  2017. }
  2018. pDibInfoDst = &DibInfoDst;
  2019. ZeroMemory (pDibInfoDst, sizeof(DIBINFO));
  2020. if (!bInitDIBINFO (hdcDst, xDst, yDst, cxDst, cyDst, pDibInfoDst))
  2021. return (FALSE);
  2022. pDibInfoSrc = &DibInfoSrc;
  2023. ZeroMemory (pDibInfoSrc, sizeof(DIBINFO));
  2024. if (!bDIBInitDIBINFO ((PBITMAPINFO)lpBitsInfo, lpBits, xSrc, ySrc, cxSrc, cySrc, pDibInfoSrc))
  2025. return (FALSE);
  2026. pDibInfoSrc->iUsage = iUsage;
  2027. bRet = bSetupBitmapInfos (pDibInfoDst, pDibInfoSrc);
  2028. if (bRet)
  2029. {
  2030. // TransColor will only be index
  2031. TransColor = TransColor & 0x00FF;
  2032. bRet = bDIBGetSrcDIBits (pDibInfoDst, pDibInfoSrc, SOURCE_TRAN, TransColor);
  2033. if (bRet)
  2034. {
  2035. bRet = bGetDstDIBits (pDibInfoDst, &bReadable, SOURCE_TRAN);
  2036. if (bRet)
  2037. {
  2038. if (bReadable)
  2039. {
  2040. switch (pDibInfoSrc->pbmi->bmiHeader.biBitCount)
  2041. {
  2042. case 4:
  2043. if (bSameDIBformat(pDibInfoDst->pbmi,pDibInfoSrc->pbmi))
  2044. {
  2045. vTransparentIdentityCopy4 (pDibInfoDst, pDibInfoSrc, TransColor);
  2046. }
  2047. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 4)
  2048. {
  2049. vTransparentS4D4 (pDibInfoDst, pDibInfoSrc, TransColor);
  2050. }
  2051. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 8)
  2052. {
  2053. vTransparentS4D8(pDibInfoDst, pDibInfoSrc, TransColor);
  2054. }
  2055. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 16)
  2056. {
  2057. vTransparentS4D16 (pDibInfoDst, pDibInfoSrc, TransColor);
  2058. }
  2059. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 24)
  2060. {
  2061. vTransparentS4D24 (pDibInfoDst, pDibInfoSrc, TransColor);
  2062. }
  2063. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 32)
  2064. {
  2065. vTransparentS4D32 (pDibInfoDst, pDibInfoSrc, TransColor);
  2066. }
  2067. else
  2068. { //1
  2069. vTransparentMapCopy (pDibInfoDst, pDibInfoSrc, TransColor);
  2070. }
  2071. break;
  2072. case 8:
  2073. if (bSameDIBformat(pDibInfoDst->pbmi,pDibInfoSrc->pbmi))
  2074. {
  2075. vTransparentIdentityCopy8 (pDibInfoDst, pDibInfoSrc, TransColor);
  2076. }
  2077. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 8)
  2078. {
  2079. vTransparentS8D8 (pDibInfoDst, pDibInfoSrc, TransColor);
  2080. }
  2081. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 16)
  2082. {
  2083. vTransparentS8D16 (pDibInfoDst, pDibInfoSrc, TransColor);
  2084. }
  2085. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 24)
  2086. {
  2087. vTransparentS8D24 (pDibInfoDst, pDibInfoSrc, TransColor);
  2088. }
  2089. else if (pDibInfoDst->pbmi->bmiHeader.biBitCount == 32)
  2090. {
  2091. vTransparentS8D32 (pDibInfoDst, pDibInfoSrc, TransColor);
  2092. }
  2093. else
  2094. {
  2095. //1, 4
  2096. vTransparentMapCopy (pDibInfoDst, pDibInfoSrc, TransColor);
  2097. }
  2098. break;
  2099. default:
  2100. WARNING ("BAD bitmap format\n");
  2101. bRet = FALSE;
  2102. goto CleanUp;
  2103. break;
  2104. }
  2105. //
  2106. // if we have created a temp destination DIB, send the final result to destination
  2107. //
  2108. bRet = bSendDIBINFO (hdcDst, pDibInfoDst);
  2109. }
  2110. else
  2111. {
  2112. //
  2113. // non-readable dest surface
  2114. //
  2115. vTransparentCopyScan (pDibInfoDst, pDibInfoSrc, TransColor);
  2116. }
  2117. }
  2118. else
  2119. {
  2120. WARNING ("GetSrcDIBits failed\n");
  2121. bRet = FALSE;
  2122. }
  2123. }
  2124. }
  2125. else
  2126. {
  2127. WARNING ("GetDstDIBits failed \n");
  2128. bRet = FALSE;
  2129. }
  2130. //
  2131. // clean up
  2132. //
  2133. CleanUp:
  2134. vCleanupDIBINFO (pDibInfoDst);
  2135. vCleanupDIBINFO (pDibInfoSrc);
  2136. return (bRet);
  2137. }
  2138. #endif
  2139. BOOL
  2140. TransparentBlt(
  2141. HDC hdcDest,
  2142. int DstX,
  2143. int DstY,
  2144. int DstCx,
  2145. int DstCy,
  2146. HDC hSrc,
  2147. int SrcX,
  2148. int SrcY,
  2149. int SrcCx,
  2150. int SrcCy,
  2151. UINT Color
  2152. )
  2153. {
  2154. BOOL bRet = FALSE;
  2155. bRet = gpfnTransparentBlt(
  2156. hdcDest,
  2157. DstX,
  2158. DstY,
  2159. DstCx,
  2160. DstCy,
  2161. (HDC)hSrc,
  2162. SrcX,
  2163. SrcY,
  2164. SrcCx,
  2165. SrcCy,
  2166. Color
  2167. );
  2168. return(bRet);
  2169. }
  2170. BOOL
  2171. TransparentDIBits(
  2172. HDC hdcDest,
  2173. int DstX,
  2174. int DstY,
  2175. int DstCx,
  2176. int DstCy,
  2177. CONST VOID *lpBits,
  2178. CONST BITMAPINFO *lpBitsInfo,
  2179. UINT iUsage,
  2180. int SrcX,
  2181. int SrcY,
  2182. int SrcCx,
  2183. int SrcCy,
  2184. UINT Color
  2185. )
  2186. {
  2187. BOOL bRet = FALSE;
  2188. bRet = gpfnTransparentDIBits(
  2189. hdcDest,
  2190. DstX,
  2191. DstY,
  2192. DstCx,
  2193. DstCy,
  2194. lpBits,
  2195. lpBitsInfo,
  2196. iUsage,
  2197. SrcX,
  2198. SrcY,
  2199. SrcCx,
  2200. SrcCy,
  2201. Color
  2202. );
  2203. return(bRet);
  2204. }