首先是Windows10 + Visual Studio 2019 搭建OpenGL环境可以查看如下链接:

萌新向!!!Windows10 + Visual Studio 2019 搭建OpenGL环境(图文教程) - 哔哩哔哩 (bilibili.com)

//使用PC端浏览器打开,Android端似乎被删除了

一、计算机图形学第二章作业

1、题目描述

第二章 作业

1. 编程实现DDA、中点画线和Bresenham算法,对比它们的效率。

2. 编程实现中点画圆法。(重点关注算法原理和伪代码)

2、题目一

2.1关于DDA的实现

2.1.1算法原理

原理:根据直线的参数微分方程计有dy=m*dx

Step1:首先将给定端点作为了输入参数;

Step2:其次初始化,初值加上0.5保证精度;

Step3:比较起止点的水平以及垂直的差值较大的大数作为计算步数steps;

Step4:然后每步计算dx,dy分别为差数并除以steps;

Step5:最后,从起始点开始来确定相邻两点间的增量并且进行递推计算。

2.1.2算法实现

具体代码如下:

#include <Windows.h>
#include <GL/glut.h>
#include <stdlib.h>
#include <stdio.h>
#include <cmath>void DDAline()
{int x1=101,y1=101,x2=499,y2=499;int steps;float m, x, y, dx, dy;x = x1 + 0.5f;y = y1 + 0.5f;steps = abs(x2 - x1) > abs(y2 - y1) ? abs(x2 - x1) : abs(y2 - y1);dx = (float)(x2 - x1) / steps;dy = (float)(y2 - y1) / steps;//计算直线斜率和截距m = (float)(y2 - y1) / (float)(x2 - x1);float b = y2 - m * x2;glClear(GL_COLOR_BUFFER_BIT);glPointSize(1.0f);glBegin(GL_POINTS);for (int i = 0; i < steps; i++) {glVertex2f((x + 400 / 2)/400.0-1.6, (400 / 2 - y)/400.0+0.5);x=x+dx;y=y+dy;}glEnd();glFlush();
}int main(int argc, char * argv[])
{glutInit(&argc, argv);glutInitDisplayMode(GLUT_RGB | GLUT_SINGLE);glutInitWindowPosition(100, 100);glutInitWindowSize(400, 400);glutCreateWindow("DrawLineByDDA");glutDisplayFunc(&DDAline);glutMainLoop();return 0;
}

2.1.3结果展示

2.2中点画线

2.2.1算法原理

原理:构造判别式:d=F(M)=F(xp+1,yp+0.5) =a(xp+1)+b(yp+0.5)+c

其中a=y0-y1, b=x1-x0, c=x0 y 1-x1 y 0

当d<0,M 在L(Q点 )下方,取右上方P 2为下一个象素

当d>0,M 在L(Q点 )上方,取右下方P 1为下一个象素

当d=0,选P 1 或 P 2均可,约定取P 1为下一个象素

Step1:画线从(x0, y0 )开始,d的初值 d 0=F(x0+1, y0+0.5)=F(x0, y0)+a+0.5b =a+0.5b。 a=y0-y1, b=x1-x0

可以用2d代替d来摆脱小数,提高效率。

Step2:令 d 0=2a+b, d1=2a, d2=2a+2b,我们有如下算法 。

Step3:若当前象素处于d ³ 0情况,则取正右方象素P1 (xp+1, yp), 要判下一个象素位置,应计算 d 1=F(xp+2, yp+0.5)=a(xp+2)+b(yp+0.5)=d+a; 增量为a

• 若d<0时,则取右上方象素P 2 (xp+1, yp+1)。要判断再下一象素,则要计算 d 2= F(xp+2, yp+1.5)=a(xp+2)+b(yp+1.5)+c=d+a+b ;增量为a+b

Step4:画出对应的点

2.2.2算法实现

具体代码如下:

#include <Windows.h>
#include <GL/glut.h>
#include <stdlib.h>
#include <stdio.h>
#include <cmath>float X[65536], Y[65536];
int cnt = 0;void MidPointline(int x1, int y1, int x2, int y2)
{int a, b, d1, d2, d, x, y;a = y1 - y2;b = x2 - x1;d = 2 * a + b;d1 = 2 * a;d2 = 2 * (a + b);x = x1; y = y1;X[0] = x;Y[0] = y;cnt++;while (x < x2){if (d < 0){x++;y++;d += d2;}else{x++;d += d1;}X[cnt] = x;Y[cnt] = y;cnt++;}
}void midPoints()
{glClear(GL_COLOR_BUFFER_BIT);glPointSize(1.0f);glBegin(GL_POINTS);for (int i = 0; i < cnt; i++) {glVertex2f((X[i] + 400 / 2) / 400.0 - 1.6, (400 / 2 - Y[i]) / 400.0 + 0.5);}glEnd();glFlush();
}int main(int argc, char* argv[])
{MidPointline(101, 101, 499, 499);glutInit(&argc, argv);glutInitDisplayMode(GLUT_RGB | GLUT_SINGLE);glutInitWindowPosition(100, 100);glutInitWindowSize(400, 400);glutCreateWindow("DrawLineBymidPoints");glutDisplayFunc(&midPoints);glutMainLoop();return 0;
}

2.2.3结果展示

2.3实现Bresenham算法

2.3.1算法原理

原理如下:

Step1:设定interChange、Xsign、Ysign便于判断位置并计算误差初值e = 2 * min - max;(min和max分别为水平距离和垂直距离的最值)

Step2:设置点(Xi, Yi) 的颜色值,并求下一误差ei+1;

If ei >= 0 then ei+1 =ei+m-1;

else ei+1 = ei + m;

Step3:根据不同象限,确定X和Y变化符号的正负,进行下一次(2)(3)循环直至结束;

2.3.2算法实现

#include <Windows.h>
#include <GL/glut.h>
#include <stdlib.h>
#include <stdio.h>
#include <cmath>void B()
{int x1 = 101, y1 = 101, x2 = 499, y2 = 499;int x, y, dx, dy, e, xSign, ySign, interChange = 0;dx = abs(x2 - x1);dy = abs(y2 - y1);float m = (float)(y2 - y1) / (float)(x2 - x1);float b = y2 - m * x2;if (dx < dy) {int temp;interChange = 1;temp = dx;dx = dy;dy = temp;}xSign = (x2 > x1) ? 1 : -1;ySign = (y2 > y1) ? 1 : -1;x = x1;y = y1;e = 2 * dy - dx;glClear(GL_COLOR_BUFFER_BIT);glPointSize(1.0f);glBegin(GL_POINTS);for (int i = 0; i <= dx; i++) {glVertex2f((x + 400.0 / 2) / 400.0 - 1.6, (400.0 / 2 - y) / 400.0 + 0.5);if (e > 0) {e = e - 2 * dx;if (interChange)x += xSign;elsey += ySign;}if (interChange)y += ySign;elsex += xSign;e = e + 2 * dy;}glEnd();glFlush();
}int main(int argc, char* argv[])
{glutInit(&argc, argv);glutInitDisplayMode(GLUT_RGB | GLUT_SINGLE);glutInitWindowPosition(100, 100);glutInitWindowSize(400, 400);glutCreateWindow("DrawLineByBresenham");glutDisplayFunc(&B);glutMainLoop();return 0;
}

2.3.3结果展示

2.4三种方法效率的比较

DDA算法:

复杂度:加法+取整

优点:避免了y=kx+b 方程中的浮点乘法。

缺点:需浮点数加法及取整运算,不利于硬件实现。

中点算法:

中点算法与DDA相比,主要是加法运算和浮点数运算,但是优化后,省去了浮点运算。

主要优点:算法简单,无乘除,只有移位操作,尤其适用硬件实现

Bresenham算法:

Bresenham算法是计算机图形学使用最广泛的直线光栅化算法。Bresenham算法是每个象素只需一个整数加法,其优点还有就是可以用于其他二次曲线。

3、题目二

3.1算法原理

中点画圆法利用的也是类似于Bresenham直线算法的思想,利用判别式选择像素,只需做简单的整数运算。

在平面直角坐标系的四个象限中第二象限的1/8圆为例,若确定了一个像素点为($x_{p},y_{p}$),那么下一个点要么是右方的P1,要么是右下方的P2。

构造函数一个函数F(x,y)=$x^{2}$+$y^{2}$-$R^{2}$,当F大于0时,点在圆外,反之则在圆内。

图中的M是P1和P2的中点,所以M=($x_{p}$+1,$y_{p}-0.5$),当F(M)<0时,M在圆内,说明P1离圆弧更近,反之M在圆外,P2更近。

根据以上原理,可构造判别式:

当$d_{p}$<0时,取P1为下一像素,下一像素判别式为:

当$d_{p}$>0时,取P2为下一像素,下一像素判别式为:

我们按顺时针方式生成八分圆,所以第一个像素为(0,R),初始判别式为:

1.25-R可以简化成1-R,去除浮点数运算,因为运算过程中增量都为整数,所以减去0.25是不会影响符号的。

3.2算法实现

#include <Windows.h>
#include <GL/glut.h>
#include <stdlib.h>
#include <stdio.h>
#include <cmath>float X[65536], Y[65536];
const float R = 400.0;
int cnt = 0;void CirclePoints(int x, int y, int offx, int offy)//利用对称性画整圆
{X[cnt] = (x + offx) / R; Y[cnt] = (y + offy) / R;cnt++;X[cnt] = (y + offx) / R; Y[cnt] = (x + offy) / R;cnt++;X[cnt] = (x + offx) / R; Y[cnt] = (-y + offy) / R;cnt++;X[cnt] = (-y + offx) / R; Y[cnt] = (x + offy) / R;cnt++;X[cnt] = (-x + offx) / R; Y[cnt] = (y + offy) / R;cnt++;X[cnt] = (y + offx) / R; Y[cnt] = (-x + offy) / R;cnt++;X[cnt] = (-x + offx) / R; Y[cnt] = (-y + offy) / R;cnt++;X[cnt] = (-y + offx) / R; Y[cnt] = (-x + offy) / R;cnt++;
}void MidPointCircle(int x1, int y1, int r)
{int x, y, e;x = 0; y = r; e = 1 - r;CirclePoints(x, y, x1, y1);while (x <= y){if (e < 0)e += 2 * x + 3;else{e += 2 * (x - y) + 5;y--;}x++;CirclePoints(x, y, x1, y1);}
}void B()
{glClear(GL_COLOR_BUFFER_BIT);glPointSize(1.0f);glBegin(GL_POINTS);for(int i=0;i<cnt;i++)glVertex2f(X[i],Y[i]);glEnd();glFlush();
}int main(int argc, char* argv[])
{MidPointCircle(0, 0, 380);glutInit(&argc, argv);glutInitDisplayMode(GLUT_RGB | GLUT_SINGLE);glutInitWindowPosition(100, 100);glutInitWindowSize(400, 400);glutCreateWindow("DrawMidPointCircle");glutDisplayFunc(&B);glutMainLoop();return 0;
}

3.3结果展示

二、参考资料

[1]萌新向!!!Windows10 + Visual Studio 2019 搭建OpenGL环境(图文教程) - 哔哩哔哩 (bilibili.com)

[2]三种直线段绘制方法:DDA算法、B算法和中点分割法_独苍的博客-CSDN博客

[3]图形学入门(2)——圆生成算法(中点画圆法) - 走看看 (zoukankan.com)

[XJTUSE]计算机图形学第二章作业,使用OpenGL编程实现DDA、中点画线和Bresenham算法和中点画圆法相关推荐

  1. 计算机图形学第二次作业:画三角形

    文章目录 1.画三角形 Step: 代码重点部分 详细算法及函数解释可见源代码`firstsol.cpp`注释 2.画红绿蓝三角形 代码重点部分 详细算法及函数解释可见源代码`secondsol.cp ...

  2. 【XJTUSE计算机图形学】第二章 光栅图形学(1)

    文章目录 [XJTUSE计算机图形学]第二章 光栅图形学(1) 1.基本概念 2.直线段的扫描转换算法 数值微分(DDA)法 增量算法 中点画线法[重点] Bresenham算法[重点 很有可能会考] ...

  3. 【XJTUSE计算机图形学】第一章 绪论

    禁止转载 文章目录 [XJTUSE计算机图形学]第一章 绪论 1.1 研究内容 1.图形系统的主要任务 2.计算机图形学的研究对象 3.图形的要素[填空题] 4.图形图像表示法 5.图形研究例子 6. ...

  4. 【XJTUSE计算机图形学】第三章 几何造型技术(2)——Bezier 曲线与曲面

    文章目录 [XJTUSE计算机图形学]第三章 几何造型技术(2)--Bezier 曲线与曲面 Bezier 曲线与曲面 Bezier 曲线的定义与性质 定义 习题 Bernstein基函数性质 Bez ...

  5. 【XJTUSE计算机图形学】第三章 几何造型技术(1)——参数曲线和曲面

    文章目录 [XJTUSE计算机图形学]第三章 几何造型技术(1)--参数曲线和曲面 参数曲线和曲面 曲线曲面参数表示 非参数表示 参数表示 曲线的基本概念 插值.拟合和光顺(掌握概念) 参数化 概念 ...

  6. 计算机导论重写算法,计算机导论第二章.ppt

    <计算机导论第二章.ppt>由会员分享,可在线阅读,更多相关<计算机导论第二章.ppt(66页珍藏版)>请在人人文库网上搜索. 1.1.第二章计算机系统的组成2.1四个功能部件 ...

  7. 现代计算机工作模式是由科学家,计算机概论各章作业.doc

    计算机概论各章作业 第一章 1.一个完整的计算机系统应该包括 ______. A)主机.键盘.鼠标和显示器 B)硬件系统和软件系统 C)主机和其他外部设备 D)系统软件和应用软件 2.计算机之 ...

  8. 第二章计算机网络答案,《计算机网络》第二章-作业参考答案

    版权声明:以上文章中所选用的图片及文字来源于网络以及用户投稿,由于未联系到知识产权人或未发现有关知识产权的登记,如有知识产权人并不愿意我们使用,如果有侵权请立即联系:55525090@qq.com,我 ...

  9. 计算机图像学试题,北交20秋《计算机图形学》在线作业二题目

    北交20秋<计算机图形学>在线作业二题目 2020-10-13 10:10:52 154 有学员问关于北交20秋<计算机图形学>在线作业二题目的题目的参考答案和解析,具体如下: ...

最新文章

  1. 自学python有哪些方向-Python新手入门应该注意的一些问题以及学习方向
  2. 51nod 1435 位数阶乘 (手动计算)
  3. UIButton或UILabel加个下划线
  4. 360容器平台监控实践
  5. Ajax学习总结(2)——Ajax参数详解及使用场景介绍
  6. Hashtable几种常用的遍历方法
  7. Axure RP9 自学之路1-软件初识
  8. 低字节+高字节+字地址+大端序+小端序全辨析
  9. CentOS6.5下lv调整空间大小
  10. java中json转map
  11. 深度思考比勤奋更重要
  12. python3大小写转换函数_python字符串大小写转换
  13. Python打包为exe文件
  14. cdr怎么把矩形去掉一个边_如何把一个矩形的四个角变形?
  15. 文件服务器属于固定资产吗,服务器内存属于固定资产吗
  16. 中国石斑鱼养殖产量不断上升,捕捞产量逐渐下降「图」
  17. 心理、意识和其他状态
  18. 【区块链 | Merkle】使用Merkle Tree空投,白名单验证
  19. 如何学好python
  20. “你的期望薪资是多少?” 月薪3万的他是这样回答的......

热门文章

  1. 虚拟场景+AR特效,世优科技助力京东手机华为新品发布会MR直播
  2. Codeforces869E The Untended Antiquity
  3. 链接元宇宙,开启新纪元
  4. 河北工业大学城市学院2019级 Java企业级系统管理期末复习资料
  5. 别让你20多岁的活法,毁掉你30岁后的人生
  6. 校友会小程序开发笔记十八:为浏览记录(我的足迹)模块的设计与实现
  7. 实验一 Java编程基础
  8. fastposter 2.2.0 新版本发布 电商级海报生成器
  9. unity游戏开发毕设_《毕业设计(论文)-基于Unity游戏引擎的游戏设计》.doc
  10. “创新雷神号”卫星成功发射,华为云分布式云原生“天地一体”首次组网成功