好便宜建站,ideo设计公司官网,湛江网站建设制作费用,建湖网站开发第1关#xff1a;OpenGL点的绘制
一. 任务描述
根据下面要求#xff0c;在右侧修改代码#xff0c;绘制出预期输出的图片。平台会对你编写的代码进行测试。
1.本关任务
熟悉编程环境#xff1b; 了解光栅图形显示器的特点#xff1b; 了解计算机绘图的特点#xff1b…第1关OpenGL点的绘制
一. 任务描述
根据下面要求在右侧修改代码绘制出预期输出的图片。平台会对你编写的代码进行测试。
1.本关任务
熟悉编程环境 了解光栅图形显示器的特点 了解计算机绘图的特点 进行编程以OpenGL为开发平台设计程序以能够在屏幕上生成三个坐标、颜色和尺寸一定的点。
2.预期输出 3.具体要求
(1) 背景色为黑色用 glClearColor()来完成 (2) 渲染的点的直径设置为 3 (3) 选用 GL_POINTS 作为图形类型 (4) 三个点的颜色分别为1.0f, 0.0f, 0.0f), (0.0f,1.0f,0.0f), (0.0f,0.0f,1.0f) (5) 三个点对应的顶点坐标分别为-0.4f,-0.4f), (0.0f,0.0f), (0.4f,0.4f)。
二. 相关知识
为了完成本关任务你需要掌握Freeglut 库的基本用法与虚拟机代码的使用方法。
1.FreeGlut简介
先介绍下Glut库。GLUT最初由MarkKilgard编写从OpenGL Redbook红宝书第二版起就用来作为示例程序的支持环境直到第八版为止注第九版开始改为GLFW。从那时起GLUT因为其简单、可用性广、可移植性强被广泛应用于各种OpenGL实际应用中。Glut最新版本为3.7版大致在1998年8月停止维护和更新同时其代码也没有开源。Freeglut是Glut库(OpenGL Utility ToolkitOpenGL实用工具包)的免费开源替代品。它是由Pawel W. Olszta在1999年12月创建最新版本为2015年3月的3.0版本。
2.基本语法
常用的程序设计语言如C、C、Pascal、Fortran和Java等都支持OpenGL的开发。这里只讨论C版本下OpenGL的语法。
OpenGL基本函数均使用gl作为函数名的前缀如glClearColor()实用函数则使用glu作为函数名的前缀如gluSphere()。
OpenGL基本常量的名字以GL_开头如GL_LINE_LOOP实用常量的名字以GLU_开头如GLU_FILL。
一些函数如glColor*()定义颜色值函数名后可以接不同的后缀以支持不同的数据类型和格式。如glColor3b(…)、glColor3d(…)、glColor3f(…)和glColor3bv(…)等这几个函数在功能上是相似的只是适用于不同的数据类型和格式其中3表示该函数带有三个参数b、d、f分别表示参数的类型是字节型、双精度浮点型和单精度浮点型v则表示这些参数是以向量形式出现的。
为便于移植OpenGL定义了一些自己的数据类型如GLfloat、GLvoid它们其实就是C语言中的float和void。在gl.h文件中可以看到以下定义 typedef float GLfloat;typedef void GLvoid;
3.freeglut库的基本函数
(1) 初始化函数 glutInit(int*argc,char**argv)
参数
Argc一个指针指向从 main函数传递过来的没更改的 argc 变量。Argv一个指针指向从 main函数传递过来的没更改的 argv 变量。
(2) 初始化窗口位置 glutInitWindowPosition(int x, int y)
(3) 初始化窗口大小 glutInitWindowSize(int x, int y)
(4) 创建窗口 glutCreateWindow(char *title) 参数 title窗口标题 (5) 绘图函数 display(void) (6) 窗口重绘函数 glutDisplayFunc(display) 参数 display:调用的函数名称 (7) 指定刷新颜色缓冲区时所用的颜色 glClearColor(float x1, float x2, float x3, float x4) (8) 刷新颜色缓冲区 glClear(GL_COLOR_BUFFER_BIT) (9) 指定栅格化点的直径 glPointSize(int x) (10) 指定绘制图形的类型 glBegin((GLenum mode) 参数 mode图形类型 (11) 设置颜色 glColor3f(float x, float y, float z) (12) 设置顶点坐标 glVertex2f(float x, float y) (13) 指定的类型结束与 glBegin 相对 glEnd() (14) 清空缓冲区 glFlush() (15) 所有的与“事件”有关的函数调用无限循环 glutMainLoop()
4.状态机制
OpenGL的工作方式是一种状态机制它可以进行各种状态或模式设置这些状态或模式在重新改变它们之前一直有效。例如当前颜色就是一个状态变量在这个状态改变之前绘制的每个像素都将使用该颜色直到当前颜色被设置为其他颜色为止。
OpenGL中大量使用了这种状态机制如颜色模式、投影模式、单双显示缓存区的设置、背景色的设置、光源的位置和特性等。许多状态变量可以通过glEnable()、glDisable()这两个函数来设置成有效或无效状态如是否设置光照、是否进行深度检测等在被设置成有效状态之后绝大部分状态变量都有一个默认值。
通常情况下可以用下列四个函数来获取某个状态变量的值glGetBooleanv、glGetDouble、glGetFloatv和glGetIntegerv。究竟选择哪个函数应该根据所要获得的返回值的数据类型来决定。还有些状态变量有特殊的查询函数如glGetLight*、glGetError和glPolygonStipple等。另外使用glPushAttrib和glPopAttrib函数可以存储和恢复最近的状态变量的值。只要有可能都应该使用这些函数因为它们比其他查询函数的效率更高。
5.OpenGL的坐标系统
如下图所示OpengGL坐标与绘图区坐标关系如下 绘图区的中心点(0.0,0.0,0.0) 绘图区的右上角点(1.0,1.0,0.0) 绘图区的左下角点(-1.0, 1.0,0.0)。 开始你的任务吧祝评测通过
三、实验代码
// 提示写完代码请保存之后再进行评测
#include GL/freeglut.h
#includestdio.h// 评测代码所用头文件-开始
#includeopencv2/core/core.hpp
#includeopencv2/highgui/highgui.hpp
#includeopencv2/imgproc/imgproc.hpp
// 评测代码所用头文件-结束void myDisplay(void)
{// 请在此添加你的代码/********** Begin ********/glClearColor(0.0,0.0,0.0,0.0);//清除颜色,并设为黑色glPointSize(3);//一个点占据三个像素,直径为3glBegin(GL_POINTS);//开始绘制点glColor3f(1.0,0.0,0.0);//红色glVertex2f(-0.4,-0.4);//设置点坐标glColor3f(0.0,1.0,0.0);//绿色glVertex2f(0.0,0.0);//glColor3f(0.0,0.0,1.0);//蓝色glVertex2f(0.4,0.4);//glEnd();//指定的类型结束/********** End **********/glFlush();
}int main(int argc, char *argv[])
{glutInit(argc, argv);glutInitWindowPosition(100, 100);glutInitWindowSize(400, 400);glutCreateWindow(Hello Point!);glutDisplayFunc(myDisplay);glutMainLoopEvent(); /*************以下为评测代码与本次实验内容无关请勿修改**************/GLubyte* pPixelData (GLubyte*)malloc(400 * 400 * 3);//分配内存GLint viewport[4] {0}; glReadBuffer(GL_FRONT);glPixelStorei(GL_UNPACK_ALIGNMENT, 4);glGetIntegerv(GL_VIEWPORT, viewport);glReadPixels(viewport[0], viewport[1], viewport[2], viewport[3], GL_RGB, GL_UNSIGNED_BYTE, pPixelData);cv::Mat img;std::vectorcv::Mat imgPlanes;img.create(400, 400, CV_8UC3);cv::split(img, imgPlanes);for(int i 0; i 400; i ) {unsigned char* plane0Ptr imgPlanes[0].ptrunsigned char(i);unsigned char* plane1Ptr imgPlanes[1].ptrunsigned char(i);unsigned char* plane2Ptr imgPlanes[2].ptrunsigned char(i);for(int j 0; j 400; j ) {int k 3 * (i * 400 j);plane2Ptr[j] pPixelData[k];plane1Ptr[j] pPixelData[k1];plane0Ptr[j] pPixelData[k2];}}cv::merge(imgPlanes, img);cv::flip(img, img ,0); cv::namedWindow(openglGrab);cv::imshow(openglGrab, img);//cv::waitKey();cv::imwrite(../img_step1/test.jpg, img);return 0;
}