这里只讨论对图像像素的处理,cimage类的具体用法查相关资料
#include <atlimage.h>   //VS2010以后不用加这个
 ……………………
CImage  m_Image;     //或CImage*  m_Image;  下面例子程序我用的CImage  m_Image; 只是一个用成员选择符,一个用指针操作,效率上可能有所差异

下面是3种方法:

一、用Cimage类的成员函数进行处理

这里假设你已经加载了图像位图,并与CImage对象m_Image相关联。相关成员函数主要有:

GetPixel 返回像素颜色

SetPixel 设置像素颜色

如:m_Image.SetPixel(  i-1,  j-1,  RGB(rr,gg,bb));

SetPixelRGB 设置像素的红绿蓝

如:m_Image.SetPixelRGB(x,y,avg,avg,avg);

SetColorTable 设置调色板颜色分量(红、绿、蓝)值

GetWidth 宽度(以像素为单位)

GetHeight 高度

1、程序示例

1)一个双线性插值放大程序。

  1. if  (m_Image.IsNull())
  2. return;
  3. // 创建对话框
  4. DlgInterpolation TranPara;
  5. //显示对话框,提示用户设定量
  6. if (TranPara.DoModal() != IDOK)
  7. return;
  8. int k=TranPara.m_inter;
  9. BeginWaitCursor();
  10. CImage  m_Image1;
  11. if (! m_Image1.IsNull())
  12. {
  13. m_Image1.Destroy();
  14. }
  15. m_Image1.Create( m_Image.GetWidth()*k, m_Image.GetHeight()*k, 24,0);
  16. // 四个最临近象素的坐标
  17. int x1, x2;
  18. int y1, y2;
  19. // 四个最临近象素值
  20. unsigned char   f1, f2, f3, f4;
  21. // 二个插值中间值
  22. unsigned char   f12, f34;
  23. //计算结果
  24. int fr,fb,fg;
  25. double  epsilon = 0.001;
  26. COLORREF pixel11,pixel12,pixel21,pixel22;
  27. int nHeight1 = m_Image1.GetHeight();
  28. int nWidth1 = m_Image1.GetWidth();
  29. int nHeight = m_Image.GetHeight();
  30. int nWidth = m_Image.GetWidth();
  31. double m=((double)nWidth1-1)/((double)nWidth-1);
  32. for  (int  i=0;  i<nWidth1;  i++)
  33. {
  34. for  (int  j=0;  j<nHeight1;  j++)
  35. {
  36. double x=double((double)i/m);
  37. double y=double((double)j/m);
  38. //计算四个最临近象素的坐标,+1向右下方移动
  39. x1 = (int) x;
  40. x2 = x1 + 1;
  41. y1 = (int) y;
  42. y2 = y1 + 1;
  43. if( (x < 0) || (x > nWidth - 1) || (y < 0) || (y > nHeight - 1))
  44. {
  45. //要计算的点不在源图范围内,返回-1
  46. continue;
  47. }
  48. else
  49. {
  50. if (fabs(x - nWidth + 1) <= epsilon )
  51. {
  52. // 要计算的点在图像右边缘上
  53. if (fabs(y -nHeight + 1) <= epsilon)
  54. {
  55. // 要计算的点正好是图像最右下角那一个象素,直接返回该点象素值
  56. pixel11 = m_Image.GetPixel(x1,y1);
  57. f1 = (unsigned char)GetRValue(pixel11);
  58. fr=(int)f1;
  59. f1 = (unsigned char)GetGValue(pixel11);
  60. fg=(int)f1;
  61. f1 = (unsigned char)GetBValue(pixel11);
  62. fb=(int)f1;
  63. }
  64. else
  65. {
  66. // 在图像右边缘上且不是最后一点,直接一次插值即可
  67. pixel11 = m_Image.GetPixel(x1,y1);
  68. pixel12 = m_Image.GetPixel(x1,y2);
  69. f1 = (unsigned char)GetRValue(pixel11);
  70. f3 = (unsigned char)GetRValue(pixel12);
  71. fr= (int) (f1 + (y -y1) * (f3 - f1));
  72. f1 = (unsigned char)GetGValue(pixel11);
  73. f3 = (unsigned char)GetGValue(pixel12);
  74. fg= (int) (f1 + (y -y1) * (f3 - f1));
  75. f1 = (unsigned char)GetBValue(pixel11);
  76. f3 = (unsigned char)GetBValue(pixel12);
  77. fb= (int) (f1 + (y -y1) * (f3 - f1));
  78. }
  79. }
  80. else if (fabs(y - nHeight + 1) <= epsilon)
  81. {
  82. // 要计算的点在图像下边缘上且不是最后一点,直接一次插值即可
  83. pixel11 = m_Image.GetPixel(x1,y1);
  84. pixel21 = m_Image.GetPixel(x2,y1);
  85. f1 = (unsigned char)GetRValue(pixel11);
  86. f2 = (unsigned char)GetRValue(pixel21);
  87. fr=(int) (f1 + (x -x1) * (f2 - f1));
  88. f1 = (unsigned char)GetGValue(pixel11);
  89. f2 = (unsigned char)GetGValue(pixel21);
  90. fg=(int) (f1 + (x -x1) * (f2 - f1));
  91. f1 = (unsigned char)GetBValue(pixel11);
  92. f2 = (unsigned char)GetBValue(pixel21);
  93. fb=(int) (f1 + (x -x1) * (f2 - f1));
  94. }
  95. else
  96. {
  97. pixel11 = m_Image.GetPixel(x1,y1);
  98. pixel12 = m_Image.GetPixel(x1,y2);
  99. pixel21 = m_Image.GetPixel(x2,y1);
  100. pixel22 = m_Image.GetPixel(x2,y2);
  101. // 计算四个最临近象素值
  102. f1 = (unsigned char)GetRValue(pixel11);
  103. f2 = (unsigned char)GetRValue(pixel21);
  104. f3 = (unsigned char)GetRValue(pixel12);
  105. f4 = (unsigned char)GetRValue(pixel22);
  106. f12 = (unsigned char) (f1 + (x - x1) * (f2 - f1));
  107. f34 = (unsigned char) (f3 + (x - x1) * (f4 - f3));
  108. fr= (int) (f12 + (y -y1) * (f34 - f12));
  109. f1 = (unsigned char)GetGValue(pixel11);
  110. f2 = (unsigned char)GetGValue(pixel21);
  111. f3 = (unsigned char)GetGValue(pixel12);
  112. f4 = (unsigned char)GetGValue(pixel22);
  113. f12 = (unsigned char) (f1 + (x - x1) * (f2 - f1));
  114. f34 = (unsigned char) (f3 + (x - x1) * (f4 - f3));
  115. fg= (int) (f12 + (y -y1) * (f34 - f12));
  116. f1 = (unsigned char)GetBValue(pixel11);
  117. f2 = (unsigned char)GetBValue(pixel21);
  118. f3 = (unsigned char)GetBValue(pixel12);
  119. f4 = (unsigned char)GetBValue(pixel22);
  120. f12 = (unsigned char) (f1 + (x - x1) * (f2 - f1));
  121. f34 = (unsigned char) (f3 + (x - x1) * (f4 - f3));
  122. fb= (int) (f12 + (y -y1) * (f34 - f12));
  123. }
  124. }
  125. m_Image1.SetPixel(i,j,  RGB(fr,fg,fb));
  126. }
  127. }
  128. m_Image.Destroy();
  129. m_Image.Create( m_Image1.GetWidth(), m_Image1.GetHeight(), 24, 0);
  130. COLORREF pixel;
  131. for  (int  i=0;  i<nWidth1;  i++)
  132. {
  133. for  (int  j=0;  j<nHeight1;  j++)
  134. {
  135. pixel = m_Image1.GetPixel(i,j);
  136. int y=GetRValue(pixel);
  137. int p=GetGValue(pixel);
  138. int b=GetBValue(pixel);
  139. m_Image.SetPixelRGB(i,j,GetRValue(pixel),GetGValue(pixel),GetBValue(pixel));
  140. }
  141. }
  142. m_Image1.Destroy();
  143. Invalidate();
  144. EndWaitCursor();

2)处理视频帧

  1. ……
  2. Defog(imageprosses, nimgWidth, nimgheigt);/*我加的一个雾天图像增强的动态库,imageprosses是视频的一帧,输入imageprosses处理,并输出imageprosses*/
  3. int  rr  =  0,  gg  =  0,  bb  =  0;
  4. for  (int i  =  0;  i  < nimgWidth;  i++)
  5. {
  6. for  (int j  =  1;  j  <= nimgheigt;  j++)
  7. {
  8. bb=(int)imageprosses[3*i*j];
  9. gg=(int)imageprosses[3*i*j+1];
  10. rr=(int)imageprosses[3*i*j+2];
  11. m_Image.SetPixel(i,  j-1,  RGB(rr,gg,bb));/*设置一帧图像的像素值用来显示*/
  12. }
  13. }
  14. ……

2、比较:非常慢。一个图像数据一般很大的,函数调用、参数传递会更加耗时。

二、直接对内存进行操作

相关成员函数:

GetPitch 行距

GetBPP 每像素位数,用时记得GetBPP()/8

GetBits 返回图像像素数据指针

1、程序示例

  1. ……
  2. Defog(imageprosses, nimgWidth, nimgheigt);
  3. //调用cimage类
  4. if  (m_Image.IsNull())
  5. m_Image.Create( nimgWidth, nimgheigt, 24,0);
  6. //地址访问方式
  7. byte* pRealData;
  8. //首地址
  9. pRealData=(byte*)m_Image.GetBits();
  10. //行距
  11. int pit=m_Image.GetPitch();
  12. for  (int i  =  0;  i  <nimgWidth;  i++)
  13. {
  14. for  (int j  =  0;  j  < nimgheigt;  j++)
  15. {
  16. *(pRealData + pit*j+ i*3)=(int)imageprosses[3*(nimgheigt-1-j)*nimgWidth+3*i];
  17. *(pRealData + pit*j +i*3 +1)=(int)imageprosses[3*(nimgheigt-1-j)*nimgWidth+3*i+1];
  18. *(pRealData + pit*j + i*3 +2)=(int)imageprosses[3*(nimgheigt-1-j)*nimgWidth+3*i+2];
  19. }
  20. }
  21. m_Image.Draw(pDC->m_hDC,0,0,nWidth,nheigt);
  22. ……

2、比较: 对地址直接操作最快,不需要多余的转换。

三、用数组进行处理

如果处理比较复杂的话,可把所有点颜色全部读到一个二维数组里面,然后对这个数组进行读写和处理。 再把处理后的图像显示出来。最方便的是可以进行一些自己需要的预处理,比如我是这样做的。

首先定义一个相关头文件和源文件处理相关内存操作

//MYIMAGE.h

  1. #if !defined(MyIMAGE)
  2. #define MyIMAGE
  3. #if _MSC_VER > 1000
  4. #pragma once
  5. #endif // _MSC_VER > 1000
  6. #include "windows.h"
  7. // 灰度图
  8. typedef byte **MYIMAGE;/*二维数组的数组名就是一个指向指针的指针,a的作用相当于**a,而a->[0],相当于a[0][0]*/
  9. //彩色图
  10. typedef struct MYCOLORIMAGESTRUCT
  11. {
  12. MYIMAGE r, g, b;
  13. }MYCOLORIMAGE;
  14. ////// 8bit图像操作
  15. // 8bit图像分配
  16. MYIMAGE MyImageAlloc(int height,int width);
  17. // 8bit图像释放
  18. void MyImageFree(MYIMAGE a, int height);
  19. // 8bit图像拷贝
  20. bool MyImageCopy(MYIMAGE dest, MYIMAGE source, int width, int height);
  21. // 8bit图像设置
  22. void MyImageSet(MYIMAGE a, int value, int width, int height);
  23. ////// 24bit图像操作
  24. // 24bit图像分配
  25. MYCOLORIMAGE MyColorImageAlloc(int height,int width);
  26. // 24bit图像释放
  27. void MyColorImageFree(MYCOLORIMAGE a, int height);
  28. // 24bit图像拷贝
  29. bool MyColorImageCopy(MYCOLORIMAGE dest, MYCOLORIMAGE source, int width, int height);
  30. // 24bit图像设置
  31. void MyColorImagSet(MYCOLORIMAGE a, int value, int width, int height);
  32. // 彩色图像转灰度图象
  33. bool MyColorToGray(MYIMAGE outGrayImg, MYCOLORIMAGE inColorImg, int width, int Height);
  34. #endif MyIMAGE

//MYIMAGE.cpp

  1. #include "StdAfx.h"
  2. #include "MYIMAGE.h"
  3. //灰度图像
  4. /**************my分配内存空间***************/
  5. MYIMAGE MyImageAlloc(int height,int width)
  6. {
  7. MYIMAGE a = (MYIMAGE) new MYIMAGE*[height];//数组指针
  8. int i;
  9. byte* pTemp;
  10. pTemp = new UCHAR[height*width];
  11. for(i = 0; i < height; i++)
  12. {
  13. a[i] = pTemp + width * i;
  14. }
  15. return a;
  16. }
  17. /*********释放内存空间***************/
  18. void MyImageFree(MYIMAGE a, int height)
  19. {
  20. delete[] a[0];
  21. delete a;
  22. }
  23. /*******拷贝************/
  24. bool MyImageCopy(MYIMAGE dest, MYIMAGE source, int width, int height)
  25. {
  26. if(dest == NULL || source == NULL || width <= 0 || height <= 0)
  27. return false;
  28. int i = 0;
  29. for(i = 0; i < height; i++)
  30. {
  31. memcpy(dest[i], source[i], sizeof(UCHAR) * width);
  32. }
  33. return true;
  34. }
  35. /*******赋值*******/
  36. void MyImageSet(MYIMAGE a, int value, int width, int height)
  37. {
  38. int i;
  39. for(i = 0; i < height; i++)
  40. {
  41. memset(a[i], value, sizeof(UCHAR) * width);
  42. }
  43. }
  44. //彩色图像
  45. /**************my彩色图像分配内存空间**********************/
  46. MYCOLORIMAGE MyColorImageAlloc(int height,int width)
  47. {
  48. //MYCOLORIMAGE a = (MYCOLORIMAGE) new char[sizeof(MYIMAGE) * 3];
  49. MYCOLORIMAGE a;
  50. a.r = MyImageAlloc(height,width);
  51. a.g = MyImageAlloc(height,width);
  52. a.b = MyImageAlloc(height,width);
  53. return a;
  54. }
  55. /****************my彩色图像空间内存释放*********************/
  56. void MyColorImageFree(MYCOLORIMAGE a, int height)
  57. {
  58. /*
  59. MyImageFree(a->r, height);
  60. MyImageFree(a->g, height);
  61. MyImageFree(a->b, height);
  62. delete a;
  63. */
  64. MyImageFree(a.r, height);
  65. MyImageFree(a.g, height);
  66. MyImageFree(a.b, height);
  67. }
  68. /***************my彩色图像拷贝******************/
  69. bool MyColorImageCopy(MYCOLORIMAGE dest, MYCOLORIMAGE source, int width, int height)
  70. {
  71. /*
  72. if(dest == NULL || source == NULL || width <= 0 || height <= 0)
  73. return false;
  74. int i = 0;
  75. for(i = 0; i < height; i++)
  76. {
  77. memcpy(dest->r[i], source->r[i], sizeof(UCHAR) * width);
  78. memcpy(dest->g[i], source->g[i], sizeof(UCHAR) * width);
  79. memcpy(dest->b[i], source->b[i], sizeof(UCHAR) * width);
  80. }
  81. return true;
  82. */
  83. if(dest.r == NULL || source.r == NULL || width <= 0 || height <= 0)
  84. return false;
  85. for(int i = 0; i < height; i++)
  86. {
  87. memcpy(dest.r[i], source.r[i], sizeof(UCHAR) * width);
  88. memcpy(dest.g[i], source.g[i], sizeof(UCHAR) * width);
  89. memcpy(dest.b[i], source.b[i], sizeof(UCHAR) * width);
  90. }
  91. return true;
  92. }
  93. /**********my彩色图像赋值*****************/
  94. void MyColorImagSet(MYCOLORIMAGE a, int value, int width, int height)
  95. {
  96. int i;
  97. for(i = 0; i < height; i++)
  98. {
  99. memset(a.r[i], value, sizeof(UCHAR) * width);
  100. memset(a.g[i], value, sizeof(UCHAR) * width);
  101. memset(a.b[i], value, sizeof(UCHAR) * width);
  102. }
  103. }
  104. /**********my彩色图转为灰度图**************/
  105. bool MyColorToGray(MYIMAGE outGrayImg, MYCOLORIMAGE inColorImg, int width, int Height)
  106. {
  107. if(outGrayImg == NULL || inColorImg.r == NULL || width <= 0 || Height <= 0)
  108. return false;
  109. for(int j = 0; j < Height; j++)
  110. {
  111. for(int i = 0; i < width; i++)
  112. {
  113. outGrayImg[j][i] = (int)(0.3 * inColorImg.r[j][i] + 0.59 * inColorImg.g[j][i] + 0.11 * inColorImg.b[j][i]);
  114. }
  115. }
  116. return TRUE;
  117. }

然后一些预处理操作,如格式间转换:

//ImageTransform.h

  1. #if !defined(ImageTransform)
  2. #define ImageTransform
  3. #if _MSC_VER > 1000
  4. #pragma once
  5. #endif // _MSC_VER > 1000
  6. //#include "ximage.h"
  7. #include "MYIMAGE.h"
  8. #include "atlimage.h"
  9. //CImage到MYIMAGE之间的格式转换
  10. //灰度
  11. // CImage转换成MYIMAGE
  12. BOOL CxImageToMYIMAGE(MYIMAGE destpImgbuf, CImage&  sourpCxImage, int nImgWidth, int nImgHeight);
  13. // MYIMAGE转换成CImage
  14. BOOL MYIMAGEToCxImage(CImage&  destpCxImage,  MYIMAGE sourpImgbuf, int nImgWidth, int nImgHeight);
  15. //彩色
  16. // CImage转换成MYCOLORIMAGE
  17. BOOL CxxImageToMYIMAGE(MYCOLORIMAGE destpImgbuf, CImage&  sourpCxImage, int nImgWidth, int nImgHeight);
  18. // MYCOLORIMAGE转换成CImage
  19. BOOL MYIMAGEToCxxImage(CImage&  destpCxImage,  MYCOLORIMAGE sourpImgbuf, int nImgWidth, int nImgHeight);
  20. #endif ImageTransform

//ImageTransform.cpp

  1. #include "StdAfx.h"
  2. #include "ImageTransform.h"
  3. //灰度
  4. //  CImage转换成MYIMAGE
  5. BOOL CxImageToMYIMAGE(MYIMAGE destpImgbuf, CImage&  sourpCxImage, int nImgWidth, int nImgHeight)
  6. {
  7. // 参数检查
  8. if(destpImgbuf == NULL || sourpCxImage == NULL || nImgWidth <= 0 || nImgHeight <= 0)
  9. return FALSE;
  10. int i, j;
  11. COLORREF rgb;
  12. //8位灰度图转存为8位灰度图
  13. if(sourpCxImage.GetBPP()/8 ==1)
  14. {
  15. for(j = 0; j < nImgHeight; j++)
  16. {
  17. for(i = 0; i < nImgWidth; i++)
  18. {
  19. destpImgbuf[j][i] = (byte)sourpCxImage.GetPixel(i, j);
  20. }
  21. }
  22. }
  23. //24位灰度图象转换为8位灰度图
  24. else if(sourpCxImage.GetBPP()/8==3)
  25. {
  26. for(j = 0; j < nImgHeight; j++)
  27. {
  28. for(i = 0; i < nImgWidth; i++)
  29. {
  30. rgb = sourpCxImage.GetPixel(i, j);
  31. destpImgbuf[j][i] = GetRValue(rgb);
  32. }
  33. }
  34. }
  35. return TRUE;
  36. }
  37. // MYIMAGE转换成CImage
  38. BOOL MYIMAGEToCxImage(CImage& destpCxImage, MYIMAGE sourpImgbuf, int nImgWidth, int nImgHeight)
  39. {
  40. // 参数检查
  41. if(destpCxImage == NULL || sourpImgbuf == NULL || nImgWidth <= 0 || nImgHeight <= 0)
  42. return FALSE;
  43. int i, j;
  44. //8位灰度图转换为24位灰度图
  45. for(j = 0; j < nImgHeight; j++)
  46. {
  47. for(i = 0; i < nImgWidth; i++)
  48. {
  49. destpCxImage.SetPixelRGB(i, j, sourpImgbuf[j][i],sourpImgbuf[j][i],sourpImgbuf[j][i]);
  50. }
  51. }
  52. return TRUE;
  53. }
  54. //24位真彩色
  55. //CImage转换成MYCOLORIMAGE
  56. BOOL CxxImageToMYIMAGE(MYCOLORIMAGE destpImgbuf, CImage& sourpCxImage, int nImgWidth, int nImgHeight)
  57. {
  58. // 参数检查
  59. if(destpImgbuf.r == NULL || sourpCxImage == NULL || nImgWidth <= 0 || nImgHeight <= 0)
  60. return FALSE;
  61. int i, j;
  62. COLORREF rgb;
  63. //24位转换为24位存储
  64. for(j = 0; j < nImgHeight; j++)
  65. {
  66. for(i = 0; i < nImgWidth; i++)
  67. {
  68. rgb=sourpCxImage.GetPixel(i, j);
  69. destpImgbuf.r[j][i] = GetRValue(rgb);
  70. destpImgbuf.g[j][i] = GetGValue(rgb) ;
  71. destpImgbuf.b[j][i] = GetBValue(rgb) ;
  72. }
  73. }
  74. return TRUE;
  75. }
  76. //MYCOLORIMAGE转换成CImage
  77. BOOL MYIMAGEToCxxImage(CImage& destpCxImage, MYCOLORIMAGE sourpImgbuf, int nImgWidth, int nImgHeight)
  78. {
  79. // 参数检查
  80. if(destpCxImage == NULL || sourpImgbuf.r == NULL || nImgWidth <= 0 || nImgHeight <= 0)
  81. return FALSE;
  82. int i, j;
  83. //24位转换为24位存储
  84. for(j = 0; j < nImgHeight; j++)
  85. {
  86. for(i = 0; i < nImgWidth; i++)
  87. {
  88. destpCxImage.SetPixelRGB(i, j,sourpImgbuf.r[j][i],sourpImgbuf.g[j][i],sourpImgbuf.b[j][i]);
  89. }
  90. }
  91. return TRUE;
  92. }

1、程序示例,一个Laplacian算子进行锐化的例子。

  1. //模版系数取1
  2. if  (m_Image.IsNull())
  3. return;
  4. BeginWaitCursor();
  5. if  (!m_Img.IsNull())
  6. m_Img.Destroy();
  7. m_Img.Create( m_Image.GetWidth(), m_Image.GetHeight(), 24,0);
  8. int  nWidth  =  m_Image.GetWidth();
  9. int  nHeight  =  m_Image.GetHeight();
  10. MYIMAGE RData=NULL;
  11. MYIMAGE GData=NULL;
  12. MYIMAGE BData=NULL;
  13. RData=MyImageAlloc(nHeight,nWidth);
  14. GData=MyImageAlloc(nHeight,nWidth);
  15. BData=MyImageAlloc(nHeight,nWidth);
  16. COLORREF color ;
  17. for(int j = 0;j<nWidth;j++)
  18. for(int i = 0;i<nHeight; i++)
  19. {
  20. color = m_Image.GetPixel(j,i);
  21. RData[i][j]= GetRValue(color);
  22. GData[i][j]= GetGValue(color);
  23. BData[i][j]= GetBValue(color);
  24. }
  25. int  templ[9]  =  {0,-1,0,-1,4,-1,0,-1,0};
  26. for  (int i  =  1;  i  <  nWidth-1;  i++)
  27. {
  28. for  (int j  =  1;  j  <  nHeight-1;  j++)
  29. {
  30. int  r =  0,  g=  0,  b =  0;
  31. int  index  =  0;
  32. //模版1
  33. for  (int  col  =  -1;  col  <=  1;  col++)
  34. {
  35. for  (int  row  =  -1;  row  <=  1;  row++)
  36. {
  37. r+=  RData[j+row][i+col] * templ[index];
  38. g+=  GData[j+row][i+col] * templ[index];
  39. b+=  BData[j+row][i+col] * templ[index];
  40. index++;
  41. }
  42. }
  43. if   (  r  <  0  )  r  =  -r;
  44. else  if (  r  >  255  )  r  =  255;
  45. if   (  g  <  0  )  g  = -g;
  46. else  if  (  g  >  255  )  g  =  255;
  47. if  (  b  <  0  )  b  = -b;
  48. else  if  (  b  >  255  )  b  =  255;
  49. m_Img.SetPixelRGB(i,j,r,g,b);
  50. }
  51. }
  52. MyImageFree(RData, nHeight);
  53. MyImageFree(GData, nHeight);
  54. MyImageFree(BData, nHeight);
  55. Invalidate();
  56. EndWaitCursor();

2、比较:比较方便也比较快

Cimage类处理图像像素(数据)的3种方式(转)的更多相关文章

  1. C#中的bitmap类和图像像素值获取方法

    一.Bitmap类 Bitmap对象封装了GDI+中的一个位图,此位图由图形图像及其属性的像素数据组成.因此Bitmap是用于处理由像素数据定义的图像的对象.该类的主要方法和属性如下: 1. GetP ...

  2. c#图像处理入门(-bitmap类和图像像素值获取方法) 转

    一.Bitmap类 Bitmap对象封装了GDI+中的一个位图,此位图由图形图像及其属性的像素数据组成.因此Bitmap是用于处理由像素数据定义的图像的对象.该类的主要方法和属性如下: 1. GetP ...

  3. c#图像处理入门(-bitmap类和图像像素值获取方法)

    c#图像处理入门 -bitmap类和图像像素值获取方法 一.Bitmap类 Bitmap对象封装了GDI+中的一个位图,此位图由图形图像及其属性的像素数据组成.因此Bitmap是用于处理由像素数据定义 ...

  4. javacpp-FFmpeg系列之2:通用拉流解码器,支持视频拉流解码并转换为YUV、BGR24或RGB24等图像像素数据

    javacpp-ffmpeg系列: javacpp-FFmpeg系列之1:视频拉流解码成YUVJ420P,并保存为jpg图片 javacpp-FFmpeg系列之2:通用拉流解码器,支持视频拉流解码并转 ...

  5. Linux就这个范儿 第15章 七种武器 linux 同步IO: sync、fsync与fdatasync Linux中的内存大页面huge page/large page David Cutler Linux读写内存数据的三种方式

    Linux就这个范儿 第15章 七种武器  linux 同步IO: sync.fsync与fdatasync   Linux中的内存大页面huge page/large page  David Cut ...

  6. 讨论HTTP POST 提交数据的几种方式

    转自:http://www.cnblogs.com/softidea/p/5745369.html HTTP/1.1 协议规定的 HTTP 请求方法有 OPTIONS.GET.HEAD.POST.PU ...

  7. EF5+MVC4系列(7) 后台SelectListItem传值给前台显示Select下拉框;后台Action接收浏览器传值的4种方式; 后台Action向前台View视图传递数据的四种方式(ViewDate,TempDate,ViewBag,Model (实际是ViewDate.Model传值))

    一:后台使用SelectListItem 传值给前台显示Select下拉框 我们先来看数据库的订单表,里面有3条订单,他们的用户id对应了 UserInfo用户表的数据,现在我们要做的是添加一个Ord ...

  8. 【代码笔记】iOS-向服务器传JSON数据的两种方式

    一,代码. - (void)viewDidLoad { [super viewDidLoad]; // Do any additional setup after loading the view. ...

  9. ios网络学习------4 UIWebView的加载本地数据的三种方式

    ios网络学习------4 UIWebView的加载本地数据的三种方式 分类: IOS2014-06-27 12:56 959人阅读 评论(0) 收藏 举报 UIWebView是IOS内置的浏览器, ...

  10. .NET MVC控制器向视图传递数据的四种方式

    .NET MVC控制器向视图传递数据的四种方式: 1.ViewBag  ViewBag.Mvc="mvc"; 2.ViewData ViewBag["Mvc"] ...

随机推荐

  1. mysql拼接多条字段

    转 未合并情况 SELECTa.id,b.name AS "role"FROM sys_user aINNER JOIN sys_user_role c ON a.id=c.use ...

  2. vue.js----之前端路由(二)

    上一篇我们已经把vue框架搭好了,接下来我们进行路由模块 在src目录下新建router.js 添加如下代码 1 /** 2 * Created by sioxa on 2016/10/29 0029 ...

  3. GUI程序中使用Write语句调试

    Lazarus GUI程序中使用Write语句调试 比如像VB 下的 Debug.print 可直接在立即窗口中打印出调试内容 其实可以使用 WriteLn('XXXX ', XXX); Write( ...

  4. docker部署opengauss

    下载二进制包到/opt/software/ wget https://opengauss.obs.cn-south-1.myhuaweicloud.com/1.1.0/x86/openGauss-1. ...

  5. Ubuntu 20.04 :“a start job is running for hold until boot process finishes”

    A start job is running for Hold until boot process finishes up (xxx min xxx s/no limit) ubuntu20.04开 ...

  6. 个人css样式_2: 渐变色

    css的魅惑力 css渐变色用途还是 比较广的. ---------------------------- 效果图: html代码(三个div): <div class="div1&q ...

  7. 可收集ALC问题[A non-collectible assembly may not reference a collectible assembly.]

    ITask程序集在共享类库中定义,初衷是任务调度程序,创建新的可卸载ALC以供每一个任务运行,此时会出现两个问题: 任务调度程序加载了任务程序后,任务程序中的ITask类型和任务调度程序中的ITask ...

  8. centos7添加swap区

    背景:拿到服务器后,部署了多个服务,内存还剩下5G左右,但是在使用的过程中,内存会突然爆满,然后服务器个别服务由于内存不够而终止进程 分析:通过free命令查看内存使用状况,发现Swap区为0,也就是 ...

  9. 浅谈组件二封-vue

    目录 组件二封不是换一种写法 组件二封应当具备哪些条件 我认为的二封应当有哪些作用 二封的好处 先来一个列表页demo来看看效果(Vue2) 本文仅仅针对vue系列做探讨, 项目倾向于大量增删改查的后 ...

  10. Android移动端性能测试工具mobileperf

    简介:mobileperf是阿里开源的一个python PC 工具,可以收集Android性能数据: cpu.内存.流畅度.fps.logcat日志.流量.进程线程数.进程启动日志,mobileper ...