计算机图形学实验报告
- 格式:doc
- 大小:612.81 KB
- 文档页数:17
计算机图形学实验报告一、画直线:改进的Bresenham算法1、程序实现环境计算机硬件配置:EasyX绘图库,VC++6.0操作系统:64位Windows7旗舰版编程语言:C2、算法思想各行、各列像素中心构造一组虚拟网格线,按直线从起点到终点的顺序计算直线各垂直网格线的交点,然后确定该列像素中与此交点最近的像素。
该算法的优点在于可以采用增量计算,使得对于每一列,只要检查一个误差项的符号,就可以确定该列所求的像素。
算法步骤:A. 输入直线的两端点P0(x0,y0)和P1(x1,y1)。
B. 计算初始值△x、△y、e=-△x、x=x0、y=y0。
C. 绘制点(x,y)。
D. e更新为e+2△y,判断e的符号。
若e>0,则(x,y)更新为(x+1,y+1),同时将e更新为e-2△x;否则(x,y)更新为(x+1,y)。
E. 当直线没有画完时,重复步骤3和4。
否则结束。
3、程序使用方法用VC++6.0直接编译、链接、运行即可,如需要更改测试数据,可在源代码上更改,不接受输入数据。
4、实验结果及分析合法用例1:(-100,-200)(250,100),图如下实验程序的适用范围:不论斜率如何,对于任意两点均可生成一条直线,包括斜率为0或无穷。
但如果点的范围超过初始化绘图区600*600,则发生截断。
测试情况:合法用例2:(0,100)(200,0),图如下合法用例3:(0,100)(0,-200)(斜率为无穷),图如下不合法用例1:(0,100)(400,0)(即超过600*600的绘图区域,发生了截断,原点(300,300))图如下二、画圆:中点Bresenham算法1、程序实现环境计算机硬件配置:EasyX绘图库,VC++6.0操作系统:64位Windows7旗舰版编程语言:C2、算法思想Bresenham画圆算法又称中点画圆算法,与Bresenham 直线算法一样,其基本的方法是利用判别变量来判断选择最近的像素点,判别变量的数值仅仅用一些加、减和移位运算就可以计算出来。
为了简便起见,考虑一个圆心在坐标原点的圆,而且只计算八分圆周上的点,其余圆周上的点利用对称性就可得到。
故只需要知道圆上的一个点的坐标(x,y),利用八对称性,就能得到另外七个对称点的坐标。
Bresenham画圆算法是用一系列离散的点来近似描述一个圆。
算法步骤:A. 1.输入圆的半径R。
B. 计算初始值d=1-R、x=0、y=R。
C. 绘制点(x,y)及其在八分圆中的另外七个对称点。
D. 判断d的符号。
若d<0,则先将d更新为d+2x+3,再将(x,y)更新为(x+1,y);否则先将d更新为d+2(x-y)+5,再将(x,y)更新为(x+1,y-1)。
E. 当x<y时,重复步骤3和4。
否则结束。
3、程序使用方法用VC++6.0直接编译、链接、运行即可,如需要更改测试数据,可在源代码上更改半径R的值,不接受输入数据。
4、实验结果及分析合法用例1:R=100,图如下实验程序的适用范围:对于所有的0<R<=边界,均可生成一个完整的圆。
如果R<=0,则无显示;R>边界点,则因为R范围超过初始化绘图区域,故发生截断。
测试情况:合法用例:2:R=300(边界),图如下不合法用例1:R=350(超过边界发生截断),图如下不合法用例2:R=0(无显示),图如下三、Bezier 曲线1、程序实现环境计算机硬件配置:EasyX 绘图库,VC++6.0操作系统:64位Windows7旗舰版编程语言:C2、算法思想 (1)绘制三次Bezier 曲线:Bezier 曲线是参数多项式曲线,它由一组控制多边形的顶点唯一定义。
在控制多边形的各个顶点中,只有第一个和最后一个顶点在曲线上,其他的顶点则用以定义曲线的导数、阶次和形状。
给定n+1个控制顶点Pi(i=0~n) ,则Bezier 曲线定义为:P(t)=∑Bi,n(t)Pi t ∈[0,1]其中:Bi,n(t)称为基函数。
Bi,n(t)=Ci nti (1-t)n-i , Ci n=n!/(i!*(n-i)!)三次Bezier 曲线(n=3):]1,0[)1(3)1(3)1()()()()()()(3322120333,323,213,103,03,∈+-+-+-=+++==∑=t P t P t t P t t P t P t BEN P t BEN P t BEN P t BEN t BEN P t p k n k k(2)两段三次Bezier曲线的拼接:有两段Bzier曲线P1(t)和P2(t),其控制多边形顶点分别为P0、P1、P2、P3和Q0、Q1、Q2、Q3,并且有P3=Q0,为了实现G1连续,需有P3-P2=a(Q1-Q0),其中a为比例因子,故实现G1连续的条件是P3和Q0、Q1在同一条直线上,并且P2和Q1应该分部在P3(Q0)的两侧.3、程序使用方法用VC++6.0直接编译、链接、运行即可,如需要更改测试数据,可在源代码上更改,不接受输入数据。
运行后回车即结束。
4、实验结果及分析(1)绘制三次Bezier曲线:合法用例1:(50,400),(140,20),(400,40),(535,420)实验程序的适用范围:对于所有的0<= P(x,y) <=边界,均可生成一个三次Bezier曲线。
如果P(x,y)<0或 P(x,y)>边界点,则因为点范围超过初始化绘图区域,故发生截断,显示不完全,边界为600*600测试情况:合法用例2:(200,400),(140,20),(400,40),(335,120),图如下不合法用例1:(-150,400),(140,-100),(400,40),(535,420),图如下(2)三次Bezier曲线的拼接:合法用例1:P1(50,200),P2(140,20),P3(300,40),P4(350,140)Q1(350,140),Q2(500,440),Q3(600,340),Q4(650,50)实验程序的适用范围:对于所有的0<= P(x,y),Q(x,y)<=边界(700*600) ,当且仅当P2、P3(Q0)、Q1在同一条直线上时,才可生成一个三次Bezier曲线。
如果(x,y)<0或 (x,y)>边界点,则显示不完全;如果P2、P3(Q0)、Q1不在同一条直线上,则拼接出来的线不是三次Bezier曲线。
测试情况:合法用例2:P1(200,400),P2(140,20),P3(400,40),P4(350,140)Q1(350,140),Q2(300,240),Q3(600,340),Q4(650,50)不合法用例1:P1(50,200),P2(140,20),P3(300,40),P4(350,140)Q1(350,140),Q2(500,140),Q3(600,340),Q4(650,50) (P 2、P3(Q0)、Q1不在同一条直线上,则拼接出来的线不是三次Bezier 曲线)四、线段的编码裁剪算法1、程序实现环境计算机硬件配置:EasyX 绘图库,VC++6.0操作系统:64位Windows7旗舰版编程语言:C2、算法思想 算法思想这种算法利用编码的方法,延长窗口边线,使得它们把包含未经裁剪图形的窗口平面区域分成九个区域,如下图所示:顶边线底边线左边线 右边线每个区域用一个4位编码CtCbCrCl 来表示,代码中每一位分别是0或1,是按照窗口边线来确定的,下面给出具体的编码规则,其中最右边的位Cl 是第一位,依次Cr 第二、Cb 第三、Ct 第四位。
则:第一位Cl 置为1—该端点位于窗口左侧;第二位Cr 置为1—该端点位于窗口右侧;第三位Cb 置为1—该端点位于窗口下侧;第四位Ct 置为1—该端点位于窗口上侧;否则,相应位置置为0Cohen-Sutherland 直线裁减算法的步骤如下:(1)当两端点P1(x1,y1)和P2(x2,y2)在区域0000中,即满足点的裁剪不等式:ytyb xr xl W y y W W x x W ≤≤≤≤)2,1()2,1( 则两端点代码C1=C2=0表示均在窗口内,应全部保留。
(2)当两个端点在窗口边线外的同侧位置,则他们的四位代码中,有一相同位,同时位“1”,显然两个端点代码C1和C2按位与运算 C1&C2≠0 .由此可检查判断直线在窗口外,应全部舍弃。
(3)如果直线两端点不满足上述两种情况,不能简单地全部保留或全部舍弃直线时,则需要计算出直线与窗口边线的交点,将直线分段后继续进行检查判断。
这样可以逐段地舍弃位于窗口外地线段,保留剩余在窗口内的线段。
3、程序使用方法 用VC++6.0直接编译、链接、运行,运行时先输入直线的两个端点的坐标,再按enter ,显示窗口和未裁剪的线段,再按enter,显示窗口和裁剪后的线段。
如果要修改数据,在运行后输入即可。
4、实验结果及分析合法用例1:(10,50),(500,360)实验程序的适用范围:对于所有的0<= (x,y)<=边界(600*500) ,均可以实现线段裁剪。
如果(x,y)<0或 (x,y)>边界点,则裁剪前的线段显示不完全,但并不妨碍裁剪。
测试情况:不合法用例1:(-100,0)(200,100)(因为点的坐标超过边界点,故裁剪前的线段显示不完全,但并不妨碍裁剪。
),图如下五、小结经过这次代码实践,我觉得对图形学领悟得更加深刻了。
尤其是看到自己辛辛苦苦编写的代码运行成功,那感觉太美好了。
在用改进的Bresenham算法画直线时,开始只会画0<=k<=1的情况,后来认真琢磨,举一反三后才推导出后续的k适用于所有范围时的情况,这个过程很艰辛,但是我很开心,这是求知与实践的过程,我也为自己感到骄傲。
其实我始终认为,画直线、花园、裁剪等等算法都是很经典的算法,我们必须理解掌握,只有站在前人的肩膀上,我们才能做出更大的发展。
我对3D也很感兴趣,而3D中的特效归根结底,也是由一条条直线、一个个圆圈等基本元素构成的,只有打好了图形学的基础,我们才能在这个领域走得更快更稳。
对于图形学大作业,我觉得老师还可以再让我们做一个类似于综合课设的东西,将所学的基础知识全部用于实践,构建一个动态场景之类的。
这个题目可以当做附加题,有附加分。
非常感谢老师教会我们这么多很有趣的图形学知识,当然老师如果将生活或科技中的一些实例拿给我们展示就更好了,相信有更多的人会对图形学产生兴趣。
而我决定在这一领域做更深的探索与研究了,我发现我很喜欢图形类的东西,包括图形的实现和处理,这门课已经帮助我打下了图形学领域的基础,我可以朝着更深也更有趣的方向前进了。