Bezier Curves of General Degree




CS216

Chris Pollett

Feb 2, 2010

Outline

Introduction

Example OpenGL Program

/******************************************************
 * Project:         CS216 Bezier Test
 * File:            main.cpp          
 * Purpose:         Code to point plot a simple Bezier Curve
 * Start date:      Feb. 1, 2010
 * Programmer:      Chris Pollett
 *
 * Remarks: Adapted from Hearn and Baker (3rd edition)
 *
 *******************************************************/

#ifdef WIN32
#include <GL/glut.h>
#endif

#ifdef __APPLE__ //for MAC
/*
 I created my project under xcode. I chose new C++ tool as the kind of project.
 Then I added the two frameworks:
 OpenGL.framework and GLUT.framework. (Frameworks are in /Library/Frameworks)
 
 */
#include <OpenGL/gl.h> 
#include <OpenGL/glu.h>
#include <GLUT/glut.h>
#endif

#ifdef linux // for linux
/*My compile line was:
 g++ -I /usr/X11R6/include -L /usr/X11R6/lib -lglut -lGL \
 -lGLU -lX11 -lXmu -lXi -lm name.cpp -o name
 */
#include <GL/glut.h>
#include <GL/glu.h>
#endif

#include <cstdlib>
#include <cmath>
#include <iostream>

using namespace std;

/*
 CLASS DEFINITIONS
*/

/*-----------------------------------------------*/
class Point2D
/*
 PURPOSE: Encapsulates the notions of a point (x,y) on the screen
*/

{
  public:
    GLfloat x, y;	 
};

/*-----------------------------------------------*/
void plotPoint (Point2D p)
/*
 PURPOSE: plots a point in 2D
 RECEIVES: p the point object to plot
 RETURNS: nothing
 REMARKS:    
 */
{
	glBegin(GL_POINTS);
	   glVertex2f(p.x, p.y);
	glEnd();
}

/*-----------------------------------------------*/
void binomialCoefficients(GLint n, GLint *C)
/*
 PURPOSE: fills in a reference with binomial coefficient values
 RECEIVES: n - says we will compute n choose k for k <= n
           C - reference to fill in with these values
 RETURNS: nothing
 REMARKS:    
 */
{
	GLint k;
	GLint j;
	
	for(k = 0; k <= n; k++) 
	{
		C[k] = 1;
		for (j = n; j >= k + 1; j--)
		{
			C[k] *= j;
		}
		
		for (j =n - k ; j >= 2; j--) {
			C[k] /= j;
		}
	}
}

/*-----------------------------------------------*/
void computeBezierCurvePoint(GLfloat u, Point2D *p, GLint nCtrlPts, Point2D *ctrlPts, GLint *C)
/*
 PURPOSE: computes a point on the given Bezier Curve
 RECEIVES: u -  a value between 0, 1 saying when on the curve
           p - address of a point to hold the result
		   nCtrlPts - number of control points in the curve
           ctrlPts - reference to the actual control points
		   C - array storing binomial coefficients.
 RETURNS: nothing
 REMARKS:    
 */
{
	GLint k; 
	GLint n = nCtrlPts - 1;
	GLfloat blendingFunction;
	
	p->x = 0.0;
	p->y = 0.0;
	
	for (k=0; k < nCtrlPts; k++) {
		blendingFunction = C[k] * pow(u, k) * pow(1 - u, n - k);
		p->x += ctrlPts[k].x * blendingFunction;
		p->y += ctrlPts[k].y * blendingFunction;		
	}
	
	
}

/*
 GLUT AND DRIVER CODE
 */

/*-----------------------------------------------*/
void init(void)
/*
 PURPOSE: Used to initializes our OpenGL window        
 RECEIVES: Nothing
 RETURNS:  Nothing
 REMARKS:  Nothing  
 */
{
	glClearColor(1.0, 1.0, 1.0, 0.0);
}


/*-----------------------------------------------*/
void drawBezier(void)
/*
 PURPOSE: GLUT display callback function for this program.
 Demo point drawing a Bezier curve 
 RECEIVES: nothing
 RETURNS: nothing
 REMARKS:    
 */
{

	GLint nCtrlPts = 4;
	GLint nBezCurvePts = 1000;
	Point2D bezierPoint;
	Point2D ctrlPts[4] = {{-40.0, -40.0}, {-10.0, 200.0}, {10.0, -200.0}, {40.0, 40.0}};
	GLfloat u;
	GLint *C, k;
	
	C= new GLint[nCtrlPts];
	binomialCoefficients(nCtrlPts - 1, C);
	
	glClear(GL_COLOR_BUFFER_BIT);
	
	glColor3f(1.0, 0.0, 0.0);
	
	//here's where we draw the strings to the screen

	for (k =0; k < nBezCurvePts; k++) 
	{
		u = ((GLfloat) k)/ ((GLfloat) nBezCurvePts);
		cout << "u = " << u << "\n";
		computeBezierCurvePoint( u, &bezierPoint, nCtrlPts, ctrlPts, C);
		cout << "  pt.x" << bezierPoint.x << " pt.y" << bezierPoint.y << "\n";
		plotPoint(bezierPoint);
	}
	
	delete [] C;
	glFlush();
}


/*-----------------------------------------------*/
void winReshapeFn(int newWidth, int newHeight)
/*
 PURPOSE: Resizes/redisplays the contents of the current window
 RECEIVES: newWidth, newHeight -- the new dimensions (ignored)
 RETURNS: nothing
 REMARKS:    
 */
{	
	glMatrixMode(GL_PROJECTION);
	glLoadIdentity();
	gluOrtho2D(-50, 50, -50, 50);
	
	glClear(GL_COLOR_BUFFER_BIT);
}

int main(int argc, char** argv)
{
	glutInit(&argc, argv);
	glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB);
	glutInitWindowPosition(50, 50);
	glutInitWindowSize(500, 500);
	glutCreateWindow("An Example OpenGL Program");
	
	init();
	glutDisplayFunc(drawBezier);
	glutReshapeFunc(winReshapeFn);
	glutMainLoop();
	return 0;
}

OpenGL Example Running

A Screenshot of the OpenGL code running

Remarks

Quiz

Which of the following statements is true?

  1. All control points of a Bezier curve lie on the curve.
  2. The sum of all the blending functions for a Bezier curve totals to 1.
  3. De Casteljau's Method cannot be used to find all of the points on a Bezier curve where u is between 0 and 1.

Hermite Polynomials

More on Hermite Polynomials

Bezier Curves of General Degree

More Bézier Curves of General Degree

Properties of Bezier Curves of General Degree