计算机图形学 编程生成“三次贝塞尔”曲线
三次Bezier曲线原理及实现代码

Bezier曲线原理及实现代码(c++)一、原理:贝塞尔曲线于1962年,由法国工程师皮埃尔·贝塞尔(Pierre Bézier)所广泛发表,他运用贝塞尔曲线来为汽车的主体进行设计。
贝塞尔曲线最初由Paul de Casteljau于1959年运用de Casteljau 算法开发,以稳定数值的方法求出贝塞尔曲线。
线性贝塞尔曲线给定点P0、P1,线性贝塞尔曲线只是一条两点之间的直线。
这条线由下式给出:且其等同于线性插值。
二次方贝塞尔曲线的路径由给定点P0、P1、P2的函数B(t) 追踪:。
TrueType字型就运用了以贝塞尔样条组成的二次贝塞尔曲线。
P0、P1、P2、P3四个点在平面或在三维空间中定义了三次方贝塞尔曲线。
曲线起始于P0走向P1,并从P2的方向来到P3。
一般不会经过P1或P2;这两个点只是在那里提供方向资讯。
P0和P1之间的间距,决定了曲线在转而趋进P3之前,走向P2方向的“长度有多长”。
曲线的参数形式为:。
现代的成象系统,如PostScript、Asymptote和Metafont,运用了以贝塞尔样条组成的三次贝塞尔曲线,用来描绘曲线轮廓。
一般化P0、P1、…、P n,其贝塞尔曲线即。
例如:。
如上公式可如下递归表达:用表示由点P0、P1、…、P n所决定的贝塞尔曲线。
则用平常话来说,阶贝塞尔曲线之间的插值。
一些关于参数曲线的术语,有即多项式又称作n阶的伯恩斯坦基底多项式,定义00 = 1。
点P i称作贝塞尔曲线的控制点。
多边形以带有线的贝塞尔点连接而成,起始于P0并以P n终止,称作贝塞尔多边形(或控制多边形)。
贝塞尔多边形的凸包(convex hull)包含有贝塞尔曲线。
线性贝塞尔曲线函数中的 t 会经过由 P 0 至P 1 的 B(t ) 所描述的曲线。
例如当 t=0.25 时,B(t ) 即一条由点 P 0 至 P 1 路径的四分之一处。
就像由 0 至 1 的连续 t ,B(t ) 描述一条由 P 0 至 P 1 的直线。
OpenGL绘制简单的参数曲线(二)——三次Bezier曲线

OpenGL绘制简单的参数曲线(⼆)——三次Bezier曲线 今天我们来介绍三次Bezier曲线,这曲线⽹上资料⾮常多,我这⾥只是简单介绍下原理。
在⼆维空间中(三维也类似),给定n+1个点P0、P1、... 、P n。
参数t的n次的Bezier曲线是:图1 我们根据上⾯式⼦可以推出⼀次、⼆次、三次贝塞尔曲线,下⾯是⼀次贝塞尔曲线:图2 下⾯是⼆次贝塞尔曲线,表⽰的是从P0P1线段取Q0,P1P2线段取Q1,每⼀个Q0Q1都是曲线的切向量:图3 下⾯是三次贝塞尔曲线,表⽰的是从P0P1线段取Q0,P1P2线段取Q1,P2P3线段取Q2,再从Q0Q1取R0,Q1Q2取R1,每⼀个R0R1都是曲线的切向量:图4 这样就给出了公式,下⾯贴出三次Beizer曲线的代码,同样可以⼿动调节参数,⼤家参考⼀下。
#include <math.h>#include <gl/glut.h>#include <iostream>using namespace std;int xCoord[4], yCoord[4];int num = 0;bool finishBeizer = false;bool mouseLeftDown = false;bool mouseRightDown = false;/*计算Bezier曲线*/void Bezier(int n){float f1, f2, f3, f4;float deltaT = 1.0 / n;float T;glBegin(GL_LINE_STRIP);for (int i = 0; i <= n; i++) {T = i * deltaT;f1 = (1-T) *(1- T) * (1-T);f2 = 3 * T * (1-T) * (1- T);f3 = 3 * T * T * (1-T);f4 = T * T * T;glVertex2f( f1*xCoord[0] + f2*xCoord[1] + f3*xCoord[2] + f4*xCoord[3], f1*yCoord[0] + f2*yCoord[1] + f3*yCoord[2] + f4*yCoord[3]);}glEnd();}/*⽤⿏标进⾏绘制,完成后可改变控制点,拖动即可*/void display(){glClear(GL_COLOR_BUFFER_BIT);glLineWidth(1.5);glColor3f (1.0, 0.0, 0.0);glBegin(GL_LINE_STRIP);for (int i = 0; i < num; i++)glVertex3f (xCoord[i], yCoord[i], 0.0);glEnd();glColor3f (0.0, 0.0, 1.0);if (num == 4)Bezier(20);glPointSize(10.0f);glBegin(GL_POINTS);glVertex2f(xCoord[0], yCoord[0]);glVertex2f(xCoord[1], yCoord[1]);glVertex2f(xCoord[2], yCoord[2]);glVertex2f(xCoord[3], yCoord[3]);glEnd();glFlush();glutSwapBuffers();}void init(){glClearColor(1.0, 1.0, 1.0, 0.0);glShadeModel(GL_FLAT);}void myReshape(int w, int h){glViewport(0, 0, (GLsizei)w, (GLsizei)h);glMatrixMode(GL_PROJECTION);glLoadIdentity();gluOrtho2D(0.0, (GLsizei)w, (GLsizei)h, 0.0);glMatrixMode(GL_MODELVIEW);glLoadIdentity();}void mouse(int button, int state, int x, int y){if (!finishBeizer){if (button == GLUT_LEFT_BUTTON && state == GLUT_DOWN){xCoord[num] = x;yCoord[num] = y;num++;if (num == 4)finishBeizer = true;glutPostRedisplay();}}else{if (button == GLUT_LEFT_BUTTON && state == GLUT_DOWN) {mouseLeftDown = true;}if (button == GLUT_LEFT_BUTTON && state == GLUT_UP){mouseLeftDown = false;}if (button == GLUT_RIGHT_BUTTON && state == GLUT_DOWN) {mouseRightDown = true;}if (button == GLUT_RIGHT_BUTTON && state == GLUT_UP){mouseRightDown = false;}}}double distance(int x1, int y1, int x2, int y2){return sqrt((x1-x2) * (x1 -x2) + (y1-y2) * (y1-y2));}void motion(int x, int y){if (mouseLeftDown){if (distance(xCoord[1], yCoord[1], x, y) < 20){xCoord[1] = x;yCoord[1] = y;}if (distance(xCoord[2], yCoord[2], x, y) < 20){xCoord[2] = x;yCoord[2] = y;}}glutPostRedisplay();}int main(int argc, char** argv){glutInit(&argc, argv);glutInitDisplayMode (GLUT_DOUBLE | GLUT_RGB );glutInitWindowSize (450, 450);glutInitWindowPosition (200, 200);glutCreateWindow ("hello");init ();glutDisplayFunc(display);glutReshapeFunc(myReshape);glutMouseFunc(mouse);glutMotionFunc(motion);glutMainLoop();return 0;}。
使用起止点和两个控制点生成三阶贝塞尔曲线

一、概述在计算机图形学中,贝塞尔曲线是一种常用的曲线生成算法,可用于实现平滑曲线的绘制。
贝塞尔曲线的生成依赖于控制点和起止点的位置,我们可以利用这些点来控制曲线的形状和轨迹。
本文将介绍如何使用起止点和两个控制点来生成三阶贝塞尔曲线,并详细讨论其中的数学原理和算法实现。
二、贝塞尔曲线简介贝塞尔曲线由保罗·德·卡斯楚(Paul de Casteljau)于1959年推广,它是一种参数化的曲线,可以用于描述平滑曲线的轨迹。
贝塞尔曲线的生成依赖于若干控制点,通过这些点可以控制曲线的形状和轨迹。
一般来说,贝塞尔曲线可以分为一阶、二阶、三阶……n阶贝塞尔曲线,本文将主要讨论三阶贝塞尔曲线的生成。
三、三阶贝塞尔曲线的数学原理对于三阶贝塞尔曲线,假设有四个控制点P0、P1、P2和P3,其中P0为起始点,P3为终止点。
我们需要通过两个额外的控制点P1和P2来控制曲线的形状。
具体而言,三阶贝塞尔曲线可以通过如下公式来表示:B(t) = (1-t)^3 * P0 + 3*(1-t)^2 * t * P1 + 3*(1-t) * t^2 * P2 + t^3 * P3其中,t为参数,取值范围通常为[0,1],用来控制曲线上点的位置。
当t为0时,曲线通过P0(起始点);当t为1时,曲线通过P3(终止点)。
而当0<t<1时,曲线则由P0、P1、P2和P3共同决定。
四、三阶贝塞尔曲线的生成算法现在我们来介绍如何通过起止点和两个控制点来生成三阶贝塞尔曲线的具体算法。
假设我们已经有起止点P0和P3,以及两个控制点P1和P2。
接下来,我们可以通过如下步骤来计算曲线上的点。
1. 将参数t划分为若干个小段,如0.01、0.02、0.03……0.99。
2. 对于每个t值,利用上述的贝塞尔曲线公式,计算出曲线上对应的点B(t)。
3. 将所有计算得到的点B(t)连接起来,就可以得到整条曲线的轨迹。
通过以上算法,我们可以利用起止点和两个控制点来生成一条平滑的三阶贝塞尔曲线。
java 三次贝塞尔曲线 坐标

题目:深度探讨Java三次贝塞尔曲线坐标在计算机图形学中,贝塞尔曲线是一种平滑曲线,它使用一系列控制点来定义曲线的形状。
贝塞尔曲线可以分为一次、二次和三次贝塞尔曲线,其中三次贝塞尔曲线由四个控制点定义。
在Java编程中,我们经常会遇到需要使用三次贝塞尔曲线的情况,比如绘制复杂的图形或动画。
对于三次贝塞尔曲线的坐标计算十分重要。
在本文中,我将对Java三次贝塞尔曲线的坐标进行深入探讨,以帮助你更好地理解和应用这一概念。
1. 三次贝塞尔曲线简介三次贝塞尔曲线由四个控制点P0、P1、P2和P3定义,起点为P0,终点为P3,而P1和P2分别为起点和终点之间的两个控制点。
曲线上的点由参数t决定,参数t的取值范围通常是[0, 1],而曲线上的点则可以由下式计算得出:B(t) = (1-t)^3 * P0 + 3*(1-t)^2 * t * P1 +3*(1-t) * t^2 * P2 + t^3 * P3其中B(t)为曲线上的点,P0、P1、P2、P3为控制点。
在实际应用中,我们需要计算曲线上的点来绘制曲线或进行其他操作,因此掌握如何计算三次贝塞尔曲线的坐标是非常重要的。
2. 计算三次贝塞尔曲线坐标要计算三次贝塞尔曲线上的点,可以使用上面的B(t)公式来进行计算。
通常情况下,我们需要以一定的步长逐步计算曲线上的点,以便绘制出完整的曲线。
具体来讲,可以使用以下的伪代码来计算三次贝塞尔曲线上的点:```for t in range(0, 1, step):x = (1-t)^3 * P0.x + 3*(1-t)^2 * t * P1.x +3*(1-t) * t^2 * P2.x + t^3 * P3.xy = (1-t)^3 * P0.y + 3*(1-t)^2 * t * P1.y +3*(1-t) * t^2 * P2.y + t^3 * P3.y// 使用(x, y)绘制点或进行其他操作```在上面的伪代码中,我们使用了一个循环来遍历参数t的取值范围,并通过B(t)公式来计算曲线上的点的坐标。
C语言代码,Bezier三次曲线

lineto(x,y);
}
}
void main()
{
static double p[4][2]={50,400,140,20,400,40,635,420};
const NO=3;
int i;
int driver=DETECT,mode;
initgraph(&driver,&mode,"C://tools/tc2.0");//初始化图形系统
Bezier三次曲线实验报告
一:实验目的
用C语言实现Bezier三次曲线原理的划线
二:实验环境
VC6.0
三:实验人数
一人
四:实验内容
Bezier曲线生成的原理和步骤都在程序上给了注释
五:实验步骤
#include <stdio.h>
#include <graphiห้องสมุดไป่ตู้s.h>
#include <conio.h>
//该方法为Bezier三阶的曲线原理
void bezier_3(int color, double p[4][2])
{
double t,t1,t2,xt,yt;
int rate=200,x,y;
setcolor(color);
moveto(p[0][0],p[0][1]);
for (t=0;t<=1;t+=1.0/rate)
bezier_3(LIGHTRED,p);//调用函数,并传递实参颜色、坐标
getch();
closegraph();
}
六:实验问题及解决
用到了很多C语言库自带的函数,通过,进行了学习;如果大家在编译的时候没有#include <graphics.h>请大家安装一个文件
三次Bezier曲线

作业三:三次Bezier曲线1. 设计要求:1.在程序窗口中建立坐标系2.输入控制点,绘制出三次Bezier曲线3.四个控制点间依次用细线连接4.在程序窗口显示四个控制点的位置并标出2. 设计思路:先在草稿纸上算出三次Bezier曲线的函数表达式: (0≤u≤1)=a×+b×+c×u+d其中a、b、c、d的值为:a=(-) + 3 × - 3 × +b=3× - 6 × + 3 ×c=(-3) × + 3 ×d=将、、、中的(x,y)坐标值分别代入a、b、c、d中得到、、、和、、、则:=×+×+×u+ (1)=×+×+×u+ (2)根据以上结果(1)和(2)编程求得当u取不同值时所得到的点P(u)。
再将各点用线连接起来即可拟合三次Bezier曲。
3. 设计过程:以下是用VB编三次Bezier曲线时的源代码:其中显示四个控制点的思路是将控制点在x和y方向的坐标值都增大1,然后再与控制点用粗实线连接起来。
这样一来在窗口中显示的即为一个较大的实点。
Function drawcs() '此模块为建立坐标系Dim k As IntegerPictDraw.DrawWidth = 1: PictDraw.FontSize = 9 '设置线宽和字体 PictDraw.Line (-400, 0)-(400, 0), RGB(100, 100, 100)PictDraw.Line (0, -300)-(0, 300), RGB(100, 100, 100)For k = (-360) To 360 Step 40PictDraw.Line (k, -5)-(k, 0): PictDraw.CurrentX = k - 20: PictDraw.CurrentY = 5: PictDraw.Print kNext kFor k = (-280) To -40 Step 40PictDraw.Line (5, k)-(0, k): PictDraw.CurrentX = -40: PictDraw.CurrentY = k - 10: PictDraw.Print (-1) * kNext kFor k = (40) To 280 Step 40PictDraw.Line (5, k)-(0, k): PictDraw.CurrentX = -40: PictDraw.CurrentY = k - 10: PictDraw.Print (-1) * kNext kEnd FunctionPrivate Sub Form_Load()PictDraw.AutoRedraw = TruePictDraw.ScaleWidth = 800PictDraw.ScaleHeight = 600Text1.Text = -300: Text2.Text = -250: Text3.Text = 300: Text4.Text = -250Text5.Text = -300: Text6.Text = 250: Text7.Text = 300: Text8.Text = 250 '作为初始值,便于测试drawcsEnd SubPrivate Sub cmdCancle_Click()PictDraw.Clsdrawcs '清除屏幕后,重建坐标系End SubPrivate Sub delet_Click() '此模块为清除输入框中的值 Text1.Text = ""Text2.Text = ""Text3.Text = ""Text4.Text = ""Text5.Text = ""Text6.Text = ""Text7.Text = ""Text8.Text = ""End SubPrivate Sub cmdDraw_Click() '此模块为画三次Bezier曲线Dim px(4) As Double '定义控制点的x坐标的数组Dim py(4) As Double '定义控制点的y坐标的数组Dim a1, b1, c1, d1 As Double '定义x系数Dim a2, b2, c2, d2 As Double '定义y系数Dim x, y, u As Double '定义曲线中的自变量u和变量x,y Dim i As IntegerIf (Not IsNumeric(Text1) Or Not IsNumeric(Text2) Or Not IsNumeric(Text3) Or Not IsNumeric(Text4) _Or Not IsNumeric(Text5) Or Not IsNumeric(Text6) Or Not IsNumeric(Text7) Or Not IsNumeric(Text8)) ThenText1.Text = "": Text2.Text = ""Text3.Text = "": Text4.Text = ""Text5.Text = "": Text6.Text = ""Text7.Text = "": Text8.Text = ""Text1.SetFocus '判断输入框中的字符是否为数字,如果为数字执行else开始画图Elsepx(0) = Text1.Text: py(0) = Text2.Textpx(1) = Text3.Text: py(1) = Text4.Textpx(2) = Text5.Text: py(2) = Text6.Textpx(3) = Text7.Text: py(3) = Text8.TextPictDraw.FontSize = 18 '设置字体,为显示输入的四个点设置字体大小PictDraw.CurrentX = px(0): PictDraw.CurrentY = (-1) * py(0): PictDraw.Print "P"; 0For i = 0 To 2PictDraw.DrawWidth = 1PictDraw.Line (px(i), (-1) * py(i))-(px(i + 1), (-1) * py(i + 1)), RGB(0, 0, 255): PictDraw.Print "P"; i + 1Next iFor i = 0 To 3PictDraw.DrawWidth = 7PictDraw.Line (px(i), (-1) * py(i))-(px(i) + 1, (-1) * py(i) - 1)Next ia1 = -px(0) + 3 * px(1) - 3 * px(2) + px(3) '计算x和y的参数 b1 = 3 * px(0) - 6 * px(1) + 3 * px(2)c1 = -3 * px(0) + 3 * px(1)d1 = px(0)a2 = -py(0) + 3 * py(1) - 3 * py(2) + py(3)b2 = 3 * py(0) - 6 * py(1) + 3 * py(2)c2 = -3 * py(0) + 3 * py(1)d2 = py(0)For u = 0 To 1 Step 0.001 '每当u增加0.001求一次x和y x = a1 * u * u * u + b1 * u * u + c1 * u + d1 '求x的值y = (-1) * (a2 * u * u * u + b2 * u * u + c2 * u + d2) '求y的值 If u = 0 ThenPictDraw.CurrentX = x '设置画线起点PictDraw.CurrentY = yElsePictDraw.DrawWidth = 2PictDraw.Line -(x, y), RGB(255, 0, 0) '连点成线End IfNext uEnd IfEnd SubPrivate Sub cmdEnd_Click() '退出窗口程序EndEnd Sub4. 设计截图:图四.三次Bezier曲线截图。
三次Bezier曲线

三次Bezier曲线一、程序设计功能:1.设计绘图窗口,能实现数据的多次输入;2.具有多次绘图功能,能实现不同数据的绘图;3.具有清屏功能,在画完该次图形后,清除图像并重建坐标系,4.具有数据完整性检测功能,当数据输入不完整时,通过弹窗提示用户数据输入不完整。
二、程序设计思想:先在草稿纸上求出三次Bezier曲线的各坐标参数前的系数表达式:a1 = -px(0) + 3 * px(1) - 3 * px(2) + px(3)b1 = 3 * px(0) - 6 * px(1) + 3 * px(2)c1 = -3 * px(0) + 3 * px(1)d1 = px(0)a2 = -py(0) + 3 * py(1) - 3 * py(2) + py(3)b2 = 3 * py(0) - 6 * py(1) + 3 * py(2)c2 = -3 * py(0) + 3 * py(1)d2 = py(0)然后根据三次Bezier曲线的特点来定义为以u为变量的函数,然后根据取点速率的不同来绘制相应四个顶点的曲线。
三、程序代码:Private Sub Command1_Click()Picture1.DrawWidth = 2Picture1.FontSize = 12 '此处定义绘制坐标系时的字体大小,因为后面程序要用到字体设置,故此处字体设置要重新声明,不可用系统默认的字体,否则再次绘制图形时,坐标由于字体过大而很难看Picture1.Scale (-300, 300)-(300, -300) '定义PictureBox坐标系Picture1.Line (-300, 0)-(300, 0)Picture1.Line (0, 300)-(0, -300) 'VB编译系统中,其默认的是在Form(窗体)中画图,当需要在其他属性框中画图时,需要加上其对应的属性框名称Picture1.CurrentX = 270: Picture1.CurrentY = 40: Picture1.Print "X"Picture1.CurrentX = 15: Picture1.CurrentY = 285: Picture1.Print "Y"Picture1.FontSize = 9 '坐标上的数字字体小一些For i = -280 To 280 Step 40Picture1.Line (i, 0)-(i, 8)Picture1.CurrentX = i - 12: Picture1.CurrentY = -5: Picture1.Print iNext iFor j = -280 To -40 Step 40Picture1.Line (0, j)-(8, j)Picture1.CurrentX = -28: Picture1.CurrentY = j + 10: Picture1.Print jNext jFor j = 40 To 280 Step 40Picture1.Line (0, j)-(8, j)Picture1.CurrentX = -28: Picture1.CurrentY = j + 10: Picture1.Print jNext jDim px(4) As Double '定义控制点的x坐标的数组Dim py(4) As Double '定义控制点的y坐标的数组Dim a1, b1, c1, d1 As Double '定义x系数Dim a2, b2, c2, d2 As Double '定义y系数Dim x, y, u As Double '定义曲线中的自变量u和变量x,yIf (Not IsNumeric(Text1) Or Not IsNumeric(Text2) Or Not IsNumeric(Text3) Or Not IsNumeric(Text4) _Or Not IsNumeric(Text5) Or Not IsNumeric(Text6) Or Not IsNumeric(Text7) Or Not IsNumeric(Text8)) ThenMsgBox "对不起!系统检测到数据输入不完整,请您输入完整后绘图。
16个控制点的三次bezier曲面代码

1. 概述贝塞尔曲线是计算机绘图中常用的一种曲线类型,它具有良好的光滑性和控制性。
在三维图形学中,三次贝塞尔曲面作为一种重要的曲面类型,经常被用于建模和渲染复杂的曲面形状。
本文将介绍使用16个控制点构建三次贝塞尔曲面的代码实现。
2. 贝塞尔曲面的数学原理贝塞尔曲面是由多个贝塞尔曲线在参数空间上的一种延伸,它可以由控制点和基函数来表示。
在三维空间中,三次贝塞尔曲面可以由16个控制点来定义,这些控制点确定了曲面在参数空间上的形状。
3. 三次贝塞尔曲面的代码实现在计算机图形学中,我们可以通过编程的方式来实现三次贝塞尔曲面的绘制。
下面是一个使用OpenGL库实现三次贝塞尔曲面的伪代码:```c// 定义16个控制点Point controlPoints[4][4];// 计算基函数float B(int i, float t) {if (i == 0) {return (1 - t) * (1 - t) * (1 - t);} else if (i == 1) {return 3 * t * (1 - t) * (1 - t);} else if (i == 2) {return 3 * t * t * (1 - t);} else {return t * t * t;}}// 计算三次贝塞尔曲面上的点Point evaluateBezierSurface(float u, float v) { Point p(0, 0, 0);for (int i = 0; i < 4; i++) {for (int j = 0; j < 4; j++) {p += controlPoints[i][j] * B(i, u) * B(j, v); }}return p;}// 绘制三次贝塞尔曲面void drawBezierSurface() {for (float u = 0; u <= 1; u += 0.01) {glBegin(GL_LINE_STRIP);for (float v = 0; v <= 1; v += 0.01) {Point p = evaluateBezierSurface(u, v); glVertex3f(p.x, p.y, p.z);}glEnd();}for (float v = 0; v <= 1; v += 0.01) {glBegin(GL_LINE_STRIP);for (float u = 0; u <= 1; u += 0.01) {Point p = evaluateBezierSurface(u, v); glVertex3f(p.x, p.y, p.z);}glEnd();}}```4. 代码解析上述代码中,首先定义了16个控制点,然后通过基函数计算得到三次贝塞尔曲面上的点,最后通过OpenGL库中的函数来绘制曲面。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
集美大学
计算机工程学院实验报告
课程名称计算机图形学教程
实验名称实验五、编程生成“三次贝塞尔”曲
线
实验类型设计型
学号
日期12月12日地点
成绩教师
一、实验目的:
一方面,让学生对自由曲线的生成算法有更深入的理解,特别是对于曲线的逼近,能够通过实验编程来验证书上所提供的算法思想:另一方面,在图形程序设计方法(如设计各种各样的图形)、绘图函数的使用以及C和C++语言编程环境、程序的调试和测试方面受到比较系统和严格的训练。
二、实验内容:
运用所学的三次贝塞尔曲线生成的算法,根据以下数据点[x, y]:[50, 100] [80, 230] [100, 270] [140, 160] [180, 50] [240, 65] [270, 120] [330, 230] [380, 230] [430, 150]计算出结果,并实现三段贝塞尔在屏幕上显示的功能
三、实验要求:
(1)3段三次贝塞尔曲线在衔接点上要连续,曲线整体效果要光滑。
(2)整个图形轮廓要清晰,色彩要分明
四、实验环境:
1.PC,CPU:P4 2.0GHz以上,内存:512M,硬盘:40GB以上;
2.操作系统:Microsoft Windows 2000 /2003/XP;
3.软件:VC或JAVA等。
五、实验内容及完成情况:
#include "graphics.h"
#include "conio.h"
#include "stdio.h"
typedef struct
{
double x,y;
} DPOINT; //定义结构体
class Bezier //定义Bezier类
{
private:
DPOINT* bP;
int m_maxIndex;
void drawFrame();
void drawCurve();
void drawCurve(int p0,int p1,int p2,int p3);
public:
Bezier(DPOINT* p,int len); //定义构造函数
void draw();
};
Bezier::Bezier(DPOINT* p,int len) //构造函数的实现{
this ->bP=p;
m_maxIndex=len-1;
}
void Bezier::draw() //通过公有函数调用私有函数{
drawFrame();
drawCurve();
}
void Bezier::drawFrame() //其功能是绘制出多边形和各个端点{
setcolor(12);
for(int i=0;i<m_maxIndex;i++)
{
line( bP[i].x, bP[i].y, bP[i+1].x, bP[i+1].y ); //绘制多边形
circle(bP[i].x, bP[i].y,5); //绘制各个端点
}
circle(bP[m_maxIndex].x,bP[m_maxIndex].y,5);
}
void Bezier::drawCurve() //实现多段Bezier曲线绘制的功能{
for(int i=0;i<=m_maxIndex-3;i+=3)
{
drawCurve(i,i+1,i+2,i+3);
}
}
void Bezier::drawCurve(int p0,int p1,int p2,int p3) //实现绘制某一段Bezier曲线的功能
{
double tmpx=0.0;
double tmpy=0.0;
double t=0.0;
for(;t<=1.0;t+=0.001)
{
tmpx=(-bP[p0].x+3*bP[p1].x-3*bP[p2].x+bP[p3].x)*t*t*t+ (3*bP[p0].x-6*bP[p1].x+3*bP[p2].x)*t*t+(-3*bP[p0].x+3*bP[ p1].x)*t+bP[p0].x;
tmpy=(-bP[p0].y+3*bP[p1].y-3*bP[p2].y+bP[p3].y)*t*t*t+ (3*bP[p0].y-6*bP[p1].y+3*bP[p2].y)*t*t+(-3*bP[p0].y+3*bP[ p1].y)*t+bP[p0].y;
putpixel(tmpx,tmpy,3);
}
}
void main() //主函数的实现
{
int graphdriver=DETECT,graphmode;
initgraph(&graphdriver,&graphmode,"E:\\tc3\\bgi");
setbkcolor(0);
outtextxy(10,20,"n\n\n\n\n\n\ jisuan1013 2010810070 chengaowei");
DPOINT* p;
p=new DPOINT[10];
p[0].x=50.0;
p[0].y=100.0;
p[1].x=80.0;
p[1].y=230.0;
p[2].x=100.0;
p[2].y=270.0;
p[3].x=140.0;
p[3].y=160.0;
p[4].x=180.0;
p[4].y=50.0;
p[5].x=240.0;
p[5].y=65.0;
p[6].x=270.0;
p[6].y=120.0;
p[7].x=330.0;
p[7].y=230.0;
p[8].x=380.0;
p[8].y=230.0;
p[9].x=430.0;
p[9].y=150.0;
Bezier bzr(p,10);
bzr.draw();
delete p;
getch();
closegraph();
}
运行结果:
六、实验总结:
通过这次实验,让我对自由曲线的生成算法有更深入的理解,特别是对于曲线的逼近,能够通过实验编程来验证书上所提供的算法思想,在图形程序设计方法(如
设计各种各样的图形)、绘图函数的使用以及C和C++语言编程环境、程序的调试和测试方面受到比较系统和严格的训练。