Bezier Patches, OpenGL, Rational Bezier Curves




CS216

Chris Pollett

Feb 9, 2010

Outline

Joining Bezier Patches

Subdividing Bezier Patches

two Bezier patches, one subdivided, one not resulting in a crack

Quiz

Which of the following statements is true?

  1. A line intersects a general Bezier curve at most the same number of times it intersects its control polygon.
  2. A Hermite representation makes use of four control points.
  3. A typical degree three Bezier patch can be specified with eight control points.

OpenGL and Bezier Curves and Patches

OpenGL Bezier Curve Example

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

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

#ifdef __APPLE__ //for MAC
/*
 I created my project under xcode. I chose new C++ tool as the kind of project.
 Then under External frameworks and libraries 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;


/*-----------------------------------------------*/
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.
 Drawing a Bezier curve with glMap1* functions 
 RECEIVES: nothing
 RETURNS: nothing
 REMARKS: 
 */
{
	
	GLfloat ctrlPts[4][3] = {{-40.0, -40.0, 0.0}, 
        {-10.0, 200.0, 0.0}, {10.0, -200.0, 0.0}, 
		{40.0, 40.0, 0.0}};

	glMap1f (GL_MAP1_VERTEX_3, 
                  0.0 /* uMin*/, 1.0 /* uMax*/, 3 /* stride*/, 4 /*num points */,
	          *ctrlPts);
	glEnable(GL_MAP1_VERTEX_3);
	
	GLint k;
	
	// draw curve in blue
	glColor3f(0.0, 0.0, 1.0);
	
	glBegin(GL_LINE_STRIP);
	   for (k = 0; k <= 50; k++) {
		   glEvalCoord1f(GLfloat(k)/50.0);
	   }
	glEnd();
	
	// draw control points in red
	glColor3f(1.0, 0.0, 0.0);
	glPointSize( 5.0 );
	
	glBegin(GL_POINTS);
	for (k = 0; k < 4; k++) {
		glVertex3fv(&ctrlPts[k][0]);
	}
	glEnd();
	
	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(-300, 300, -300, 300);
	
	glClear(GL_COLOR_BUFFER_BIT);
}

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

Example Screenshot

a cubic Bezier curve

Remarks

Bézier Patch Code

/******************************************************
 * Project:         CS216 Bezier Patch 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<windows.h> //for windows
#include <GL/glut.h>
#include <GL/glu.h>
#endif

#ifdef __APPLE__ //for MAC
/*
 I created my project under xcode. I chose new C++ tool as the kind of project.
 Then under External frameworks and libraries 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;

/*
 CONSTANTS
 */

//Camera constants
const GLfloat CAMERA_X = -5.0; //camera's position (looks at origin)
const GLfloat CAMERA_Y = -3.0;
const GLfloat CAMERA_Z = 10.0;
const GLfloat UP_X = 0.0; //camera's up vector
const GLfloat UP_Y = 1.0;
const GLfloat UP_Z = 0.0;

//View Volume
const GLfloat NEAR_CLIP = 2.0;
const GLfloat FAR_CLIP = 100;

/*
 GLOBALS
 */
GLsizei winWidth = 500, winHeight = 500; // used for size of window
GLsizei initX = 50, initY = 50; // used for initial position of window


/*-----------------------------------------------*/
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.
 Drawing a Bezier curve with glMap1* functions 
 RECEIVES: nothing
 RETURNS: nothing
 REMARKS:   
 */
{
	
	GLfloat ctrlPts[4][4][3] = {
	  {{-1.5, -1.5, 4.0}, {-.5, -1.5, 2.0}, 
		  {-.5, -1.5, -1.0}, {1.5, -1.5, 2.0} }, 
	  {{-1.5, -.5, 1.0}, {-.5, -.5, 3.0}, 
		  {.5, -.5, 0.0}, {1.5, -.5, 1.0} }, 
	  {{-1.5, .5, 4.0}, {-.5, .5, 0.0}, 
		  {.5, .5, 3.0}, {1.5, .5, 4.0} }, 
	  {{-1.5, 1.5, -2.0}, {-.5, 1.5, -2.0}, 
		  {.5, 1.5, 0.0}, {1.5, 1.5, -1.0} } 

	};
	
	glMap2f (GL_MAP2_VERTEX_3, 0.0 /* uMin*/, 1.0 /* uMax*/, 3 /* u stride*/, 4 /*num points u*/,
			0.0 /* vMin*/, 1.0 /* vMax*/, 12 /*v stride*/, 4, &ctrlPts[0][0][0]);
	glEnable(GL_MAP2_VERTEX_3);
	
	GLint k, j;

	//draw patch in read
	glColor3f(1.0, 0.0, 0.0);
	glMapGrid2f(50, 0.0, 1.0, 50, 0.0, 1.0);
	glEvalMesh2(GL_FILL, 0, 50, 0, 50);
	
	// draw curves on patch in blue
	glColor3f(0.0, 0.0, 1.0);
	
    for (k = 0 ; k <= 8; k++) {
		glBegin(GL_LINE_STRIP);
		for (j = 0; j <= 40; j++) {
			glEvalCoord2f(GLfloat(j)/40.0, GLfloat(k)/8.0);
		}
		glEnd();
		
		glBegin(GL_LINE_STRIP);
		for (j = 0; j <= 40; j++) {
			glEvalCoord2f(GLfloat(k)/8.0, GLfloat(j)/40.0);
		}
		glEnd();
		
	}


	
	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:    
 */
{	
	glViewport(0, 0, newWidth, newHeight);
	
	glMatrixMode(GL_PROJECTION);
	glLoadIdentity();
	glFrustum(-1.0, 1.0, -1.0, 1.0, NEAR_CLIP, FAR_CLIP);

    gluLookAt(CAMERA_X, CAMERA_Y, CAMERA_Z, 0.0, 0.0, 0.0, UP_X, UP_Y, UP_Z);
	
	glClear(GL_COLOR_BUFFER_BIT);

	glMatrixMode(GL_MODELVIEW);
	glLoadIdentity();

	
}

int main(int argc, char** argv)
{
	glutInit(&argc, argv);
	glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB);
	glutInitWindowPosition(initX, initY);
	glutInitWindowSize(winWidth, winHeight);
	glutCreateWindow("An Example Bezier Patch");
	
	init();
	glutDisplayFunc(drawBezier);
	glutReshapeFunc(winReshapeFn);
	glutMainLoop();
	return 0;
}

Example Screenshot

a cubic Bezier Patch

Rational Bezier Curves

More on Rational Bezier Curves

Let's look at (a) of the last slide in more detail...

Rational Bezier Curves and Points at Infinity

Let's look at (d) of a couple slides back in more detail...