myfile2.cpp
上传用户:gtl089a
上传日期:2013-09-05
资源大小:5k
文件大小:21k
源码类别:

图形图像处理

开发平台:

Visual C++

  1. #include "stdafx.h"
  2. #include <math.h>
  3. #include <io.h>
  4. #include <direct.h>
  5. #include "dibapi.h"
  6. #include <complex>
  7. #define DIB_HEADER_MARKER   ((WORD) ('M' << 8) | 'B')
  8. /////////////////////////////////////////////////////////////////////////////////////
  9. // DXF.2003.10.20
  10. // myfile2.cpp
  11. //
  12. // HGLOBAL WINAPI ZoomPixelreplication(HDIB hDib,unsigned char ** PixelData,
  13. // float hzoom,float vzoom)
  14. // 利用像素复制放大缩小图像
  15. // HGLOBAL WINAPI ZoomBilinear(HDIB hDib,unsigned char ** PixelData,
  16. // float hzoom,float vzoom)
  17. // 双线形插值放大缩小图像
  18. // BOOL WINAPI GrayReduce(HDIB hDib,unsigned char ** PixelData,long GrayLevel)
  19. // 图像gray的衰减 
  20. // BOOL WINAPI Reverse(HDIB hDib,unsigned char ** PixelData)
  21. // 灰度图像的反色处理
  22. // BOOL WINAPI TransHalftone(HDIB hDib,unsigned char ** PixelData)
  23. // 图像的halftone处理
  24. // BOOL WINAPI ArithmeticOpr (HDIB hDib,unsigned char ** PixelData,
  25. //    unsigned char ** PixelData2,const CString Opr,
  26. //    const int width,const int height,const double scale,const double factor)
  27. // 图像的算数处理
  28. // BOOL WINAPI TransBw(HDIB hDib,unsigned char ** PixelData);
  29. // 生成黑白图
  30. /////////////////////////////////////////////////////////////////////////////////////
  31. /*///////////////////////////////////////////////////////////////////////////
  32. // HGLOBAL WINAPI ZoomPixelreplication(HDIB hDib,unsigned char ** PixelData,
  33. // float hzoom,float vzoom)
  34. //  利用像素复制放大缩小图像
  35.  * 参数:
  36.  *   HDIB hDib    - 指向源DIB图像句柄
  37.  *  unsigned char ** PixelData 像素数组
  38.  *  float hzoom 水平缩放率
  39.  *  float vzoom 垂直缩放率
  40.  * 返回值:
  41.  *   HGLOBALL               - 运算成功返回缩放后的图像句柄,否则返回NULL。
  42. //////////////////////////////////////////////////////////////////////////*/
  43. HGLOBAL WINAPI ZoomPixelreplication(HDIB hDib,unsigned char ** PixelData,float hzoom,float vzoom)
  44. {
  45. LPBITMAPINFOHEADER lpBi;
  46. lpBi=(LPBITMAPINFOHEADER)::GlobalLock((HGLOBAL) hDib);
  47. // 缩放后新DIB句柄
  48. HDIB hNewDIB;
  49. // 缩放后图像的宽度和高度
  50. LONG lNewWidth=0,lNewHeight=0, lrgb,lNewLineBytes,ltruebit;
  51. // 指向缩放图像的指针
  52. LPSTR lpNewDIB;
  53. unsigned char * hNewData;
  54. LPBITMAPINFOHEADER lpbmi;
  55. // 循环变量(象素在新DIB中的坐标)
  56. LONG i,j,i0,j0,len;
  57. AfxGetApp()->BeginWaitCursor();    
  58. // 计算缩放后的图像实际宽度
  59. lNewWidth = (LONG) (lpBi->biWidth*hzoom);
  60.    if (8==lpBi->biBitCount) len=1;
  61.    if (24==lpBi->biBitCount) len=3;
  62. // 计算新图像每行的字节数
  63. lNewLineBytes = WIDTHBYTES(lNewWidth * 8 * len);
  64. // 计算缩放后的图像高度
  65. lNewHeight = (LONG) (lpBi->biHeight*vzoom);
  66. // 分配内存,以保存新DIB
  67. hNewDIB = (HDIB) ::GlobalAlloc(GHND, lNewLineBytes * lNewHeight + *(LPDWORD)(lpBi)  +
  68.                                ::PaletteSize((LPSTR)lpBi));
  69. // 判断是否内存分配失败
  70. if (hNewDIB == NULL)// 分配内存失败
  71. return NULL;
  72. // 锁定内存
  73. lpNewDIB =  (char * )::GlobalLock((HGLOBAL) hNewDIB);
  74. // 复制DIB信息头和调色板
  75. memcpy(lpNewDIB, (LPSTR)lpBi, *(LPDWORD)(lpBi) + ::PaletteSize((LPSTR)lpBi));
  76. // 找到新DIB象素起始位置
  77. hNewData = (unsigned char*)::FindDIBBits(lpNewDIB);
  78. // 获取指针
  79. lpbmi = (LPBITMAPINFOHEADER)lpNewDIB;
  80. // 更新DIB中图像的高度和宽度
  81. lpbmi->biWidth = lNewWidth;
  82. lpbmi->biHeight = lNewHeight;
  83.    
  84.    for (lrgb=0;lrgb<len;lrgb++)
  85. // 针对图像每行进行操作
  86. for(i = 0; i < lNewHeight; i++)
  87. {
  88. // 针对图像每列进行操作
  89. for(j = 0; j < lNewWidth; j++)
  90. {
  91. i0 = (LONG) (i / vzoom );
  92. j0 = (LONG) (j / hzoom );
  93.     
  94. ltruebit=j0*len+lrgb;
  95. // 判断是否在源图范围内
  96. if( (j0 >= 0) && (j0 < lpBi->biWidth) && (i0 >= 0) && (i0 < lpBi->biHeight))
  97. {
  98. // 为像素赋值
  99. *(hNewData+lNewLineBytes* i + j*len+lrgb) = PixelData[i0][ltruebit];
  100. }
  101. else
  102. { // 对于源图中没有的像素,直接赋值为255
  103. *(hNewData+lNewLineBytes*  i + j*len+lrgb) = 255;
  104. }
  105. }
  106. }
  107. AfxGetApp()->EndWaitCursor();
  108. ::GlobalUnlock((HGLOBAL)hDib);
  109. // 返回
  110. return hNewDIB;
  111. }
  112. /*///////////////////////////////////////////////////////////////////////////
  113. // HGLOBAL WINAPI ZoomBilinear(HDIB hDib,unsigned char ** PixelData,
  114. // float hzoom,float vzoom)
  115. //  双线形插值放大缩小图像
  116.  * 参数:
  117.  *   HDIB hDib    - 指向源DIB图像句柄
  118.  *  unsigned char ** PixelData 像素数组
  119.  *  float hzoom 水平缩放率
  120.  *  float vzoom 垂直缩放率
  121.  * 返回值:
  122.  *   HGLOBALL               - 运算成功返回缩放后的图像句柄,否则返回NULL。
  123. //////////////////////////////////////////////////////////////////////////*/
  124. HGLOBAL WINAPI ZoomBilinear(HDIB hDib,unsigned char ** PixelData,float hzoom,float vzoom){
  125. LPBITMAPINFOHEADER lpBi;
  126. lpBi=(LPBITMAPINFOHEADER)::GlobalLock((HGLOBAL) hDib);
  127. // 缩放后新DIB句柄
  128. HDIB hNewDIB;
  129. // 缩放后图像的宽度和高度
  130. LONG lNewWidth=0,lNewHeight=0, lNewLineBytes;
  131. // 缩放后图像的宽度(lNewWidth',必须是4的倍数)
  132. // 指向缩放图像的指针
  133. LPSTR lpNewDIB;
  134. unsigned char * hNewData;
  135. // 指向BITMAPINFO结构的指针(Win3.0)
  136. LPBITMAPINFOHEADER lpbmi;
  137. // 循环变量(象素在新DIB中的坐标)
  138. LONG i,j,i0,j0,l1,l2,i2,j2;
  139. float  i1,j1;
  140.     
  141. AfxGetApp()->BeginWaitCursor();
  142. // 计算缩放后的图像实际宽度
  143. lNewWidth = (LONG) (lpBi->biWidth*hzoom);
  144. // 计算新图像每行的字节数
  145. lNewLineBytes = WIDTHBYTES(lNewWidth * 8);
  146. // 计算缩放后的图像高度
  147. lNewHeight = (LONG) (lpBi->biHeight*vzoom);
  148. // 分配内存,以保存新DIB
  149. hNewDIB = (HDIB) ::GlobalAlloc(GHND, lNewLineBytes * lNewHeight + *(LPDWORD)(lpBi)  +
  150.                                ::PaletteSize((LPSTR)lpBi));
  151. // 判断是否内存分配失败
  152. if (hNewDIB == NULL)// 分配内存失败
  153. return NULL;
  154. // 锁定内存
  155. lpNewDIB =  (char * )::GlobalLock((HGLOBAL) hNewDIB);
  156. // 复制DIB信息头和调色板
  157. memcpy(lpNewDIB, (LPSTR)lpBi, *(LPDWORD)(lpBi) + ::PaletteSize((LPSTR)lpBi));
  158. // 找到新DIB象素起始位置
  159. hNewData = (unsigned char*)::FindDIBBits(lpNewDIB);
  160. // 获取指针
  161. lpbmi = (LPBITMAPINFOHEADER)lpNewDIB;
  162. // 更新DIB中图像的高度和宽度
  163. lpbmi->biWidth = lNewWidth;
  164. lpbmi->biHeight = lNewHeight;
  165. //已知a,b,c,d四点的灰度,要求e点的灰度,
  166. //可以先在水平方向上由a,b线形插值求出g,c,d线形插值求出f,
  167. //然后在垂直方向上由g,f线形插值求出e 线形插值是基于这样的假设,
  168. //即原图的灰度在两个像素之间是线形变化的,一般情况下,
  169. //这种插值的效果还不错。更精确的方法是采用曲线插值(Curvilinear Interpolation),
  170. //即认为像素之间的灰度变化规律符合某种曲线,但这种处理的计算量是很大的。
  171. // 针对图像每行进行操作
  172. for(i = 0; i < lNewHeight; i++)
  173. {
  174. // 针对图像每列进行操作
  175. for(j = 0; j < lNewWidth; j++)
  176. {
  177. i0 = (LONG) (i / vzoom );
  178. j0 = (LONG) (j / hzoom );
  179. i1 = i / vzoom ;
  180. j1 = j / hzoom ;
  181. // 判断是否在源图范围内
  182.       if ((i0==i1)&&(j0==j1))
  183. *(hNewData+lNewLineBytes*  i + j) = PixelData[i0][j0];
  184.  else
  185.  {
  186. i2 = (LONG) (i / vzoom +0.5);
  187. j2 = (LONG) (j / hzoom +0.5);
  188. if (i2==lpBi->biHeight) i2=lpBi->biHeight-1;
  189. if (j2==lpBi->biWidth) j2=lpBi->biWidth-1;
  190. //f(x1)=(f(x2)-f(x0))*(x1-x0)/(x2-x0)+f(x0); 
  191. l1 = (PixelData[i0][j2]-PixelData[i0][j0])*(j1-j0)/(j2-j0)+PixelData[i0][j0];
  192. l2 = (PixelData[i2][j2]-PixelData[i2][j0])*(j1-j0)/(j2-j0)+PixelData[i2][j0];
  193. if ( (i2!=i0) && (j0!=j2) )
  194. l1 = (l2-l1)*(i1-i0)/(i2-i0)+l1;
  195. else 
  196. l1=PixelData[i0][j0];
  197. *(hNewData+lNewLineBytes*  i + j) = l1;
  198.  }
  199. }
  200. }
  201. ::GlobalUnlock((HGLOBAL)hDib);
  202. AfxGetApp()->EndWaitCursor();
  203. // 返回
  204. return hNewDIB;
  205. }
  206. //////////////////////////////////////////////////////////////////////
  207. //limb算法,生成二维数组
  208. ////////////////////////////////////////////////////////////////////
  209. BYTE **limb(int Level)
  210. {
  211. int i,j, i0,i1;
  212. BYTE ** gray;
  213. BYTE ** graytmp;
  214. i0 = pow(2,Level);
  215. gray = new BYTE*[i0];
  216. //初始化数组
  217. for (i=0;i<i0;i++)
  218. gray[i] = new BYTE[i0];
  219. //BYTE gray1[2][2]={{0,2},{3,1}};
  220. if (1==Level)
  221. {
  222. gray[0][0]=0;
  223. gray[0][1]=2;
  224. gray[1][0]=3;
  225. gray[1][1]=1;
  226. }
  227. else
  228. {
  229. ////////////////////////////////////////////////////////////////////
  230. //根据limb算法生成gray数组
  231. ////////////////////////////////////////////////////////////////////
  232. i1 = pow(2,Level-1);
  233. graytmp = new BYTE*[i1];
  234. //初始化数组
  235. for (i=0;i<i1;i++)
  236. graytmp[i] = new BYTE[i1];
  237. graytmp = limb(Level-1);
  238. for(i=0;i<i1;i++)
  239. for (j=0;j<i1;j++)
  240. gray[i][j] = 4*graytmp[i][j];
  241. for(i=0;i<i1;i++)
  242. for (j=i1;j<i0;j++)
  243. gray[i][j] = 4*graytmp[i][j-i1]+2;
  244. for(i=i1;i<i0;i++)
  245. for (j=0;j<i1;j++)
  246. gray[i][j] = 4*graytmp[i-i1][j]+3;
  247. for(i=i1;i<i0;i++)
  248. for (j=i1;j<i0;j++)
  249. gray[i][j] = 4*graytmp[i-i1][j-i1]+1;
  250.      
  251. }
  252. return gray;
  253. }
  254. /////////////////////////////////////////////////////////////////////
  255. //图像gray的衰减,
  256. //////////////////////////////////////////////////////////////////////
  257. BOOL WINAPI GrayReduce0(HDIB hDib,unsigned char ** PixelData,long GrayLevel)
  258. {
  259. /* LPBITMAPINFOHEADER lpBi;
  260. unsigned char * hData;
  261. lpBi=(LPBITMAPINFOHEADER)GlobalLock((HGLOBAL)hDib);
  262. hData=(unsigned char*)FindDIBBits((LPSTR)lpBi);
  263. int i,j, i0,tmp;
  264. BYTE * gray;
  265. i0 = pow(2,GrayLevel);
  266. gray = new BYTE[i0];
  267. i0--;
  268. ////////////////////////////////////////////////////////////////////
  269. //根据limb算法生成gray数组
  270. ////////////////////////////////////////////////////////////////////
  271.     for (i=0;i<i0;i++)
  272. gray[i]=0;
  273. tmp = 8- GrayLevel;
  274.   for(i=0; i<lpBi->biHeight; i++)
  275. for(j=0; j<lpBi->biWidth; j++) {
  276. ////////////////////////////////////////////////////////
  277.      if ( (PixelData[i][j]>>tmp) > 
  278.  gray[i&i0][j&i0]) //右移后做比较
  279.  *(hData+WIDTHBYTES(lpBi->biWidth*8)*i+j) = (unsigned char)255;
  280.  else
  281.  *(hData+WIDTHBYTES(lpBi->biWidth*8)*i+j) = (unsigned char)0;
  282.                    //根据算法得出结果,写回
  283.  }
  284. ::GlobalUnlock((HGLOBAL)hDib);
  285. i0 = pow(2,GrayLevel);
  286. for(i = 0; i <i0 ; i++) 
  287.     delete [] gray[i];
  288.         
  289. delete [] gray;
  290. ::GlobalUnlock((HGLOBAL)hDib);*/
  291. // 返回
  292. return true;
  293. }
  294. /*///////////////////////////////////////////////////////////////////////////
  295. // BOOL WINAPI GrayReduce(HDIB hDib,unsigned char ** PixelData,long GrayLevel)
  296. //  图像gray的衰减 
  297.  * 参数:
  298.  *   HDIB hDib    - 指向源DIB图像句柄
  299.  *  unsigned char ** PixelData 像素数组
  300.  *  long GrayLevel  灰度的值=2^GrayLevel
  301.  *   返回值:
  302.  *   BOOL               - 运算成功返回TRUE,否则返回FALSE。
  303. //////////////////////////////////////////////////////////////////////////*/
  304. BOOL WINAPI GrayReduce(HDIB hDib,unsigned char ** PixelData,long GrayLevel)
  305. {
  306. LPBITMAPINFOHEADER lpBi;
  307. unsigned char * hData;
  308. lpBi=(LPBITMAPINFOHEADER)GlobalLock((HGLOBAL)hDib);
  309. hData=(unsigned char*)FindDIBBits((LPSTR)lpBi);
  310. long i,j, i0,tmp,lLineBytes;
  311. lLineBytes = WIDTHBYTES(lpBi->biWidth*8);
  312. BYTE ** gray;
  313. i0 = pow(2,GrayLevel)-1;
  314. ////////////////////////////////////////////////////////////////////
  315. //根据limb算法生成gray数组
  316. ////////////////////////////////////////////////////////////////////
  317. gray = limb(GrayLevel);
  318. tmp = 8- (GrayLevel*2);
  319.   for(i=0; i<lpBi->biHeight; i++)
  320. for(j=0; j<lpBi->biWidth; j++) {
  321. ////////////////////////////////////////////////////////
  322.      if ( (PixelData[i][j]>>tmp) > 
  323.  gray[i&i0][j&i0]) //右移后做比较
  324.  *(hData+lLineBytes*i+j) = (unsigned char)255;
  325.  else
  326.  *(hData+lLineBytes*i+j) = (unsigned char)0;
  327.                    //根据算法得出结果,写回
  328.  }
  329. ::GlobalUnlock((HGLOBAL)hDib);
  330. i0 = pow(2,GrayLevel);
  331. for(i = 0; i <i0 ; i++) 
  332.     delete [] gray[i];
  333.         
  334. delete [] gray;
  335. ::GlobalUnlock((HGLOBAL)hDib);
  336. // 返回
  337. return true;
  338. }
  339. /*///////////////////////////////////////////////////////////////////////////
  340. // BOOL WINAPI Reverse(HDIB hDib,unsigned char ** PixelData)
  341. // //灰度图像的反色处理
  342.  * 参数:
  343.  *   HDIB hDib    - 指向源DIB图像句柄
  344.  *  unsigned char ** PixelData 像素数组
  345.  *   返回值:
  346.  *   BOOL               - 运算成功返回TRUE,否则返回FALSE。
  347. //////////////////////////////////////////////////////////////////////////*/
  348. BOOL WINAPI Reverse(HDIB hDib,unsigned char ** PixelData)
  349. {
  350. LPBITMAPINFOHEADER lpBi;
  351. unsigned char * hData;
  352. lpBi=(LPBITMAPINFOHEADER)GlobalLock((HGLOBAL)hDib);
  353. hData=(unsigned char*)FindDIBBits((LPSTR)lpBi);
  354. long i,j,lLineBytes,k;
  355.  
  356. if (lpBi->biBitCount==8) k=1;
  357. if (lpBi->biBitCount==24) k=3;
  358. lLineBytes = WIDTHBYTES(lpBi->biWidth*8*k);
  359. for(i=0; i<lpBi->biHeight; i++)
  360. for(j=0; j<lpBi->biWidth*k; j++) {
  361. *(hData+lLineBytes*i+j)=
  362. (unsigned char)(255-PixelData[i][j]);//根据算法得出结果,写回
  363.  }
  364. ::GlobalUnlock((HGLOBAL)hDib);
  365. return true;
  366. }
  367. /*///////////////////////////////////////////////////////////////////////////
  368. // BOOL WINAPI TransHalftone(HDIB hDib,unsigned char ** PixelData)
  369. // 图像的halftone处理
  370.  * 参数:
  371.  *   HDIB hDib    - 指向源DIB图像句柄
  372.  *  unsigned char ** PixelData 像素数组
  373.  *   返回值:
  374.  *   BOOL               - 运算成功返回TRUE,否则返回FALSE。
  375. //////////////////////////////////////////////////////////////////////////*/
  376. BOOL WINAPI TransHalftone (HDIB hDib,unsigned char ** PixelData)
  377. {
  378. static int  gr[3][3]= {{84,28,140},{224,252,168},{112,196,56}};
  379. LPBITMAPINFOHEADER lpZoomOutBi,lpBi;
  380. unsigned char * hData;
  381. unsigned char * hZoomOutData;
  382. unsigned char tmp;
  383. int lZoomOutLineBytes, lLineBytes;
  384. lpBi=(LPBITMAPINFOHEADER)GlobalLock((HGLOBAL)hDib);
  385. hData=(unsigned char*)FindDIBBits((LPSTR)lpBi);
  386. lLineBytes = WIDTHBYTES(lpBi->biWidth*8);
  387. HDIB hZoomOutDib;
  388. //首先缩小图像宽与高的1/3
  389. hZoomOutDib=(HDIB)ZoomPixelreplication(hDib,PixelData,(float)0.33,(float)0.33);
  390. lpZoomOutBi=(LPBITMAPINFOHEADER)GlobalLock((HGLOBAL)hZoomOutDib);
  391. hZoomOutData=(unsigned char*)FindDIBBits((LPSTR)lpZoomOutBi);
  392. lZoomOutLineBytes=WIDTHBYTES(lpZoomOutBi->biWidth*8);
  393. int i,j,i0,j0,ll=0;
  394. //每个像素对应9个新点
  395. for(i=0; i<lpZoomOutBi->biHeight; i++)
  396. for(j=0; j<lpZoomOutBi->biWidth; j++) 
  397. {
  398. tmp = *(hZoomOutData+i*lZoomOutLineBytes+j);
  399. for (i0=0;i0<3;i0++)
  400. for(j0=0;j0<3;j0++)
  401. if (tmp>=gr[i0][j0])
  402. *(hData+lLineBytes*(i*3+i0)+j*3+j0)=255;
  403. else
  404. *(hData+lLineBytes*(i*3+i0)+j*3+j0)=0;
  405. }
  406. ::GlobalUnlock((HGLOBAL)hZoomOutDib);
  407. ::GlobalFree((HGLOBAL)hZoomOutDib);
  408.     ::GlobalUnlock((HGLOBAL)hDib);
  409. return true;
  410. }
  411. /////////////////////////////////////////////////////////////////////
  412. //将24位的彩色图转为8位灰度图
  413. /////////////////////////////////////////////////////////////////////
  414. BOOL WINAPI Bmp2256 (HDIB hDib,unsigned char ** PixelData,const CString FileName1)
  415. {
  416. CFile file;
  417. CFileException fileException;
  418. LPBITMAPINFOHEADER lpOldBi;
  419. BITMAPINFOHEADER bi;
  420. BITMAPFILEHEADER bh;
  421. RGBQUAD lrgb[256];
  422. HLOCAL hNewDIBBits;
  423. LPSTR lpSrc,lpDst,lpNewDIBBits;
  424. unsigned char lGray;
  425. long lWidth,lHeight, lSize,lLineBytes;
  426. // 循环变量(象素在新DIB中的坐标)
  427. LONG i,j,j0;
  428. AfxGetApp()->BeginWaitCursor();    
  429. if (!file.Open(FileName1, CFile::modeCreate |
  430.       CFile::modeReadWrite | CFile::shareExclusive, &fileException))
  431.   return FALSE;
  432. lpSrc = (LPSTR)::GlobalLock((HGLOBAL) hDib);
  433. lpOldBi=(LPBITMAPINFOHEADER)lpSrc;
  434. lWidth = lpOldBi->biWidth;
  435. lHeight = lpOldBi->biHeight;
  436. // 计算新图像每行的字节数
  437. lLineBytes = WIDTHBYTES(lWidth * 8 );
  438. // 分配内存,以保存新DIB
  439. lSize = lLineBytes * lHeight;
  440. //更新文件头
  441. bh.bfType = DIB_HEADER_MARKER;;
  442. bh.bfSize = lSize+sizeof(bh)+sizeof(bi)+
  443. 256*sizeof(RGBQUAD);
  444. bh.bfReserved1=0;
  445. bh.bfReserved2=0;
  446. bh.bfOffBits = sizeof(bh)+sizeof(bi)+256*sizeof(RGBQUAD);
  447. file.Write(&bh,14);
  448. // 文件信息头
  449. bi.biWidth = lWidth;
  450. bi.biHeight = lHeight;
  451. bi.biBitCount=8;
  452. bi.biSizeImage = lLineBytes * lHeight;
  453. bi.biClrImportant=0;
  454. bi.biClrUsed=0;
  455. bi.biCompression=0;
  456. bi.biPlanes=1;
  457. bi.biSize=40;
  458. file.Write(&bi,40);
  459. ::GlobalUnlock((HGLOBAL)hDib);
  460. // 计算灰度映射表(保存各个颜色的灰度值),并更新DIB调色板
  461. for (i = 0; i < 256; i ++)
  462. {
  463. // 计算该颜色对应的灰度值
  464. lrgb[i].rgbRed = i;
  465. lrgb[i].rgbGreen = i;
  466. lrgb[i].rgbBlue = i;
  467. lrgb[i].rgbReserved = 0;
  468. file.Write(&lrgb[i],sizeof(RGBQUAD));
  469. }
  470. hNewDIBBits = LocalAlloc(LHND, lSize);
  471. if (hNewDIBBits == NULL)
  472. // 分配内存失败
  473. return FALSE;
  474. // 锁定内存
  475. lpNewDIBBits = (char * )LocalLock(hNewDIBBits);
  476. // 初始化新分配的内存,设定初始值为255
  477. lpDst = (char *)lpNewDIBBits;
  478. memset(lpDst, (BYTE)255, lSize);
  479. // 针对图像每行进行操作
  480. for(i = 0; i < lHeight; i++)
  481. // 针对图像每列进行操作
  482. for(j = 0; j < lWidth; j++)
  483. // 为像素赋值
  484. {
  485. j0 = j*3;
  486. lGray =(299*PixelData[i][j0] +
  487. 587*PixelData[i][j0+1] + 
  488. 114*PixelData[i][j0+2])/1000;
  489. *(lpDst+lLineBytes* i + j) = (unsigned char)lGray;
  490. }
  491. file.Write(lpDst,lSize);
  492. file.Close();
  493. // 释放内存
  494. LocalUnlock(hNewDIBBits);
  495. LocalFree(hNewDIBBits);
  496. AfxGetApp()->EndWaitCursor();
  497. return true;
  498. }
  499. /*///////////////////////////////////////////////////////////////////////////
  500. // BOOL WINAPI ArithmeticOpr (HDIB hDib,unsigned char ** PixelData,
  501. //    unsigned char ** PixelData2,const CString Opr,
  502. //    const int width,const int height,const double scale,const double factor)
  503. // 图像的算数处理
  504.  * 参数:
  505.  *   HDIB hDib    - 指向源DIB图像句柄
  506.  *  unsigned char ** PixelData    BK像素数组
  507.  *   unsigned char ** PixelData2   前景像素数组
  508.  *   const CString Opr, 算术操作符号
  509.  *   const int width,           要处理的图像宽度
  510.  *   const int height, 要处理的图像高度
  511.  *   const double scale 加减时为scale
  512.  *   加减(source1+source2)/scale+offset
  513.  *   const double factor        乘法时为 乘法的乘数,加减时为offset
  514.  *   返回值:
  515.  *   BOOL               - 运算成功返回TRUE,否则返回FALSE。
  516. //////////////////////////////////////////////////////////////////////////*/
  517. BOOL WINAPI ArithmeticOpr (HDIB hDib,unsigned char ** PixelData,
  518.    unsigned char ** PixelData2,const CString Opr,
  519.    const int width,const int height,const double scale,
  520.    const double factor)
  521. {
  522. LPBITMAPINFOHEADER lpBi;
  523. unsigned char * hData;
  524. long lLineBytes,len,lrgb,ltruebit;
  525. lpBi=(LPBITMAPINFOHEADER)GlobalLock((HGLOBAL)hDib);
  526. hData=(unsigned char*)FindDIBBits((LPSTR)lpBi);
  527. if (8==lpBi->biBitCount) len=1;
  528.     if (24==lpBi->biBitCount) len=3;
  529. lLineBytes = WIDTHBYTES(lpBi->biWidth*8*len); 
  530. int i,j;
  531. float tmp;
  532. for (lrgb=0;lrgb<3;lrgb++)
  533. for(i=0; i<height; i++)
  534. for(j=0; j<width; j++) 
  535. {
  536. ltruebit=j*len+lrgb;
  537. if (Opr=="*")
  538. tmp = PixelData[i][ltruebit]*factor;
  539. if (Opr=="+")
  540. tmp = (PixelData[i][ltruebit]+PixelData2[i][ltruebit])/scale+factor;
  541. if (Opr=="-")
  542. tmp = (PixelData[i][ltruebit]-PixelData2[i][ltruebit])/scale+factor;
  543. if (tmp>255) tmp=255;
  544. if (tmp<0) tmp=0;
  545. *(hData+lLineBytes*i+ltruebit)=tmp;
  546. }
  547. // delete PixelData2;
  548. ::GlobalUnlock((HGLOBAL)hDib);
  549. return true;
  550. }
  551. /*///////////////////////////////////////////////////////////////////////////
  552. // BOOL WINAPI TransBw(HDIB hDib,unsigned char ** PixelData)
  553. // 生成黑白间隔图
  554.  * 参数:
  555.  *   HDIB hDib    - 指向源DIB图像句柄
  556.  *  unsigned char ** PixelData 像素数组
  557.  *   返回值:
  558.  *   BOOL               - 运算成功返回TRUE,否则返回FALSE。
  559. //////////////////////////////////////////////////////////////////////////*/
  560. HGLOBAL WINAPI TransBw(HDIB hDib)
  561. {
  562. LPBITMAPINFOHEADER lpBi;
  563. unsigned char * hData;
  564. lpBi=(LPBITMAPINFOHEADER)GlobalLock((HGLOBAL)hDib);
  565. hData=(unsigned char*)FindDIBBits((LPSTR)lpBi);
  566. int i,j;
  567. // 新DIB句柄
  568. HDIB hNewDIB;
  569. // 缩放后图像的宽度和高度
  570. LONG lNewWidth=0,lNewHeight=0, lNewLineBytes;
  571. // 图像的宽度(lNewWidth',必须是4的倍数)
  572. // 指向缩放图像的指针
  573. LPSTR lpNewDIB;
  574. unsigned char * hNewData;
  575. // 指向BITMAPINFO结构的指针(Win3.0)
  576. LPBITMAPINFOHEADER lpbmi;
  577. // 循环变量(象素在新DIB中的坐标)
  578.     
  579. AfxGetApp()->BeginWaitCursor();
  580. // 计算缩放后的图像实际宽度
  581. lNewWidth = 256;
  582. // 计算新图像每行的字节数
  583. lNewLineBytes = WIDTHBYTES(lNewWidth * 8);
  584. // 计算缩放后的图像高度
  585. lNewHeight = 256;
  586. // 分配内存,以保存新DIB
  587. hNewDIB = (HDIB) ::GlobalAlloc(GHND, lNewLineBytes * lNewHeight + *(LPDWORD)(lpBi)  +
  588.                                ::PaletteSize((LPSTR)lpBi));
  589. // 判断是否内存分配失败
  590. if (hNewDIB == NULL)// 分配内存失败
  591. return NULL;
  592. // 锁定内存
  593. lpNewDIB =  (char * )::GlobalLock((HGLOBAL) hNewDIB);
  594. // 复制DIB信息头和调色板
  595. memcpy(lpNewDIB, (LPSTR)lpBi, *(LPDWORD)(lpBi) + ::PaletteSize((LPSTR)lpBi));
  596. ::GlobalUnlock((HGLOBAL)hDib);
  597. // 找到新DIB象素起始位置
  598. hNewData = (unsigned char*)::FindDIBBits(lpNewDIB);
  599. // 获取指针
  600. lpbmi = (LPBITMAPINFOHEADER)lpNewDIB;
  601. // 更新DIB中图像的高度和宽度
  602. lpbmi->biWidth = lNewWidth;
  603. lpbmi->biHeight = lNewHeight;
  604. for(i=0; i<lNewWidth; i++)
  605. for(j=0; j<lNewHeight; j++) 
  606. {
  607. if (div(i,2).rem==0)
  608. *(hNewData+lNewLineBytes*j+i)=(unsigned char)(0);
  609. else
  610. *(hNewData+lNewLineBytes*j+i)=(unsigned char)(255);
  611. //根据算法得出结果,写回
  612.  }
  613. AfxGetApp()->EndWaitCursor();
  614. // 返回
  615. return hNewDIB;
  616. }