本来是一件很简单的事情,就是将View上使用OpenGL画出来的数据生成图片让其实现打印的功能,我们知道MFC提供打印的接口是不支持OpenGL的(至少我不清楚),必须将它转成GDI再画在Print的pDC上。

OpenGL一直都有一个函数名字叫:glReadPixels,它能read a block of pixels from the frame buffer,但是谁都没想到它竟然转换成CImage竟然是这样的规则。

http://www.opengl.org/sdk/docs/man/xhtml/glReadPixels.xml中说到:Specify the window coordinates of the first pixel that is read from the frame buffer. This location is the lower left corner of a rectangular block of pixels.  是从左下角开始读,这一条是我始料未及的,一般通常都是从左上角开始的,我至今没想明白为什么它要这样设计。在调用这个函数之前还需要glReadBuffer(GL_BACK_LEFT);这句,如果你想将它设置成GL_FRONT_LEFT似乎还不行,它并不会从左上角开始,真弄不懂这设计者的逻辑。

然后接着下一步就开始往CImage里面写东西了:直接上code:

.h文件中定义:

GLubyte *_print_image_data;
CImage _print_img;

OnPreparePrinting(CPrintInfo* pInfo)

_print_image_data = nullptr;
    glReadBuffer(GL_BACK_LEFT);

OnBeginPrinting(CDC* /*pDC*/, CPrintInfo* /*pInfo*/)

int format = GL_RGB ,components =  , width = m_width, height = m_height;
switch(format) {
case GL_RGB:
components = ; break;
case GL_RGBA:
components = ; break;
case GL_ALPHA:
case GL_LUMINANCE:
components = ; break;
}
_print_image_data = (GLubyte*)malloc(components * width * height);
glReadPixels(, , width, height, format, GL_UNSIGNED_BYTE, _print_image_data);
_print_img.Create(width, height, ); int nPixel = height*width*;
for(int j = ; j <height ; j++)
for(int i = width-; i >=; i--)
{
BYTE b = _print_image_data[--nPixel];
BYTE g = _print_image_data[--nPixel];
BYTE r = _print_image_data[--nPixel];
_print_img.SetPixelRGB(i, j, r,g,b);
}

OnEndPrinting(CDC* /*pDC*/, CPrintInfo* /*pInfo*/)

    free(_print_image_data);
_print_image_data = nullptr;
_print_img.Destroy();

OnPrint(CDC* pDC, CPrintInfo* pInfo)

if(_print_image_data != nullptr)
_print_img.Draw(pDC->m_hDC, , , _print_img.GetWidth()*, _print_img.GetHeight()*);

可以看到那个x、y轴的双层循环的code真是有点怪异,一个++、一个--,但是又必须这样写才能对,希望以后有人再碰到这种情况能够Lucky的找到我这篇blog了吧。

OpenGL glReadPixels 转成 CImage的更多相关文章

  1. 把jpg文件读取到内存char* 再转换成CImage

    网络上找到大神写的转换方法,不过就记下来,学习学习: 当然转成CImage之后就可以从CImage转换成HBITMAP 了 void DrawPic(CDC *pDC,char *buf,int le ...

  2. 现代3D图形编程学习-基础简介(3)-什么是opengl (译)

    本书系列 现代3D图形编程学习 OpenGL是什么 在我们编写openGL程序之前,我们首先需要知道什么是OpenGL. 将OpenGL作为一个API OpenGL 通常被认为是应用程序接口(API) ...

  3. OpenGL中平移、旋转、缩放矩阵堆栈操作

    在OpenGL中,图元的几何变换均为线性变换,通过矩阵变换实现.OpenGL中的坐标用齐次坐标表示,即(x,y,z)表示成(x',y',z',h),其中x=x'/h; y=y'/h; z=z'/h. ...

  4. 建立第一个OpenGL工程(GLUT)

    本文参考了<计算机图形学>(Donald Hearn著)的第2.9节. OpenGL基本函数库用来描述图元.属性.几何变换.观察变换和进行许多其他的操作.OpenGL被设计成与硬件无关,因 ...

  5. [C++][OpenGL]自己写GUI(0)——介绍

    文章可转载,转载请注明出处:http://www.cnblogs.com/collectionne/p/6928612.html.文章未完,如果不在博客园(cnblogs)发现本文,请访问前面的链接查 ...

  6. OpenGL介绍

    OpenGL是一个开放的三维图形软件包,它独立于窗口系统和操作系统,以它为基础开发的应用程序可以十分方便地在各种平台间移植:OpenGL可以与Visual C++紧密接口,便于实现机械手的有关计算和图 ...

  7. 计算机图形学OpenGL中的glLoadIdentity、glTranslatef、glRotatef原理,用法 .(转)

    单位矩阵 对角线上都是1,其余元素皆为0的矩阵. 在矩阵的乘法中,有一种矩阵起着特殊的作用,如同数的乘法中的1,我们称这种矩阵为单位矩阵. 它是个方阵,除左上角到右下角的对角线(称为主对角线)上的元素 ...

  8. OpenGL的前世和今生

    这并不是一个恰当的题目,因为我主要想说的是OpenGL的今生,基于OpenGL3.x一种更现代化的方式.但是把前世和今生放在一起在语言上更加连贯,而且适当的了解过去,会帮助理解现在的OpenGL,以一 ...

  9. GJM : 各大开发游戏引擎

    感谢您的阅读.喜欢的.有用的就请大哥大嫂们高抬贵手"推荐一下"吧!你的精神支持是博主强大的写作动力以及转载收藏动力.欢迎转载! 版权声明:本文原创发表于 [请点击连接前往] ,未经 ...

随机推荐

  1. ProtoBuf练习(五)

    表类型 protobuf语言的maps字段类型相当于C++语言的std::map类型 工程目录结构 $ ls proto/ sample_maps.proto proto文件 $ cat proto/ ...

  2. python网络爬虫之requests库

    Requests库是用Python编写的HTTP客户端.Requests库比urlopen更加方便.可以节约大量的中间处理过程,从而直接抓取网页数据.来看下具体的例子: def request_fun ...

  3. [转]centos7.2 下 nginx 开机启动

    1.在系统服务目录里创建nginx.service文件 vi /lib/systemd/system/nginx.service 内容如下 [Unit] Description=nginx After ...

  4. Java实例——基于jsoup的简单爬虫实现(从智联获取工作信息)

    这几天在学习Java解析xml,突然想到Dom能不能解析html,结果试了半天行不通,然后就去查了一些资料,发现很多人都在用Jsoup解析html文件,然后研究了一下,写了一个简单的实例,感觉还有很多 ...

  5. LibreOJ #6192. 「美团 CodeM 复赛」城市网络

    #6192. 「美团 CodeM 复赛」城市网络 内存限制:64 MiB时间限制:500 ms标准输入输出 题目类型:传统评测方式:文本比较 上传者: sqc 提交提交记录统计讨论测试数据   题目描 ...

  6. Collection、泛型

    Collection.泛型 Collection.泛型 Collection.泛型 Collection.泛型 Collection.泛型 Collection.泛型 Collection.泛型

  7. 备份与恢复:MySQL系列之十二

    一.备份策略赘述 1.备份的类型 类型1: 热备份:读写不受影响(MyISAM不支持热备,InnoDB支持热备) 温备份:仅可以执行读操作 冷备份:离线备份,读写操作均中止 类型2: 物理备份:复制数 ...

  8. C 语言实例 - 计算一个数的 n 次方

    C 语言实例 - 计算一个数的 n 次方 计算一个数的 n 次方,例如: ,其中 为基数, 为指数. 实例 - 使用 while #include <stdio.h> int main() ...

  9. 黑马MySQL数据库学习day03 级联 多表查询 连接和子查询 表约束

    /* 存在外键的表 删表限制: 1.先删除从表,再删除主表.(不能直接删除主表,主表被从表引用,尽管实际可能还没有记录引用) 建表限制: 1.必须先建主表,再建从表(没有主表,从表无法建立外键关系) ...

  10. Luogu P2833 等式 我是傻子x2

    又因为调一道水题而浪费时间...不过细节太多了$qwq$,暴露出自己代码能力的不足$QAQ$ 设$d=gcd(a,b)$,这题不是显然先解出来特解,即解出 $\frac{a}{d}x_0+\frac{ ...