How can i draw a circle and a ellipse using OpenGL.
void DrawCircle( double r )
{
DrawEllipse( r, r );
}void DrawEllipse( double a, double b )
{
double const TWO_PI = 6.2831853071795865;
int const NSTEPS = 100;double t = 0.; glBegin( GL_LINE_LOOP ); for ( int i = 0; i < NSTEPS; ++i ) { glVertex2d( a * cos( t ), b * sin( t ) ); t += TWO_PI / NSTEPS; } glEnd();
}
Thanks, i wil try it.
When I tried the DrawCircle function, I found that if NSTEPS > 36, the beginning and ending edges of the circle do not line up.
Can anyone explain why I might be seeing this behavior?
Floating point precision errors. Simply change the condition to i<(NSTEPS-1).
[This message has been edited by DFrey (edited 03-25-2002).]
Thanks for the reply DFrey. I tried your suggestion but this did not solve the problem.
To clear things up a bit, it is not that the beginning and ending points of the circle do not connect. Sometimes really wierd things happen. For example, if I set NSTEPS=100, the circle looks like this:
----------*****
------------***
-----–---------**
--------------------*
-----------------—*
--------------------*
-----–*---------
------------***
----------**
A circle with a sideways V in the middle.
I have seen this effect with various circle drawing examples on the web. If I ever go above 36 points, the circle is not drawn correctly.
Thanks for any help,
jpummill
[This message has been edited by jpummill (edited 03-25-2002).]
[This message has been edited by jpummill (edited 03-25-2002).]
[This message has been edited by jpummill (edited 03-25-2002).]
[This message has been edited by jpummill (edited 03-25-2002).]
Then that sounds like a bug in your OpenGL driver, because the above code worked flawlessly for me.
I am trying it on an ATI M1 notebook graphics processor (supports OpenGL). I will try it at home on a GeForce2 MX.
If it does appear to be a driver issue, is this something that should be communicated to ATI???
Also, if anyone is interested, here is the code. Nice and short:
//----------------------------------------
// DRAW A CIRCLE USING GLUT AND OPENGL –
//----------------------------------------
#include <windows.h> // Standard Header For Most Programs
#include <gl/gl.h> // The GL Header File
#include <gl/glut.h> // The GL Utility Toolkit (Glut) Header
#include <stdio.h>
#include <math.h>
void DrawCircle( double );
void DrawEllipse( double, double );
void init ( GLvoid ) // Create Some Everyday Functions
{
glShadeModel(GL_FLAT); // Enable Smooth Shading
glClearColor(0.0f, 0.0f, 0.0f, 0.5f); // Black Background
glClearDepth(1.0f); // Depth Buffer Setup
glEnable(GL_DEPTH_TEST); // Enables Depth Testing
glDepthFunc(GL_LEQUAL); // The Type Of Depth Testing To Do
glEnable ( GL_COLOR_MATERIAL );
glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
}
void display ( void ) // Create The Display Function
{
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); // Clear Screen And Depth Buffer
glLoadIdentity(); // Reset The Current Modelview Matrix
glPolygonMode(GL_FRONT, GL_LINE);
glPolygonMode(GL_BACK, GL_LINE);
glColor3f(0.0f,1.0f,0.0f);
glTranslatef(0.0f, 0.0f, -3.0f);
DrawCircle(1.0);
glutSwapBuffers ( );
// Swap The Buffers To Not Be Left With A Clear Screen
}
void reshape ( int w, int h ) // Create The Reshape Function (the viewport)
{
glViewport ( 0, 0, w, h );
glMatrixMode ( GL_PROJECTION ); // Select The Projection Matrix
glLoadIdentity ( ); // Reset The Projection Matrix
if ( h==0 ) // Calculate The Aspect Ratio Of The Window
gluPerspective ( 80, ( float ) w, 1.0, 5000.0 );
else
gluPerspective ( 80, ( float ) w / ( float ) h, 1.0, 5000.0 );
glMatrixMode ( GL_MODELVIEW ); // Select The Model View Matrix
glLoadIdentity ( ); // Reset The Model View Matrix
}
void keyboard ( unsigned char key, int x, int y ) // Create Keyboard Function
{
switch ( key ) {
case 27: // When Escape Is Pressed…
exit ( 0 ); // Exit The Program
break; // Ready For Next Case
default: // Now Wrap It Up
break;
}
}
void arrow_keys ( int a_keys, int x, int y ) // Create Special Function (required for arrow keys)
{
switch ( a_keys ) {
case GLUT_KEY_UP: // When Up Arrow Is Pressed…
glutFullScreen ( ); // Go Into Full Screen Mode
break;
case GLUT_KEY_DOWN: // When Down Arrow Is Pressed…
glutReshapeWindow ( 640, 480 ); // Go Into A 640 By 480 Window
break;
default:
break;
}
}
void main ( int argc, char** argv ) // Create Main Function For Bringing It All Together
{
glutInit ( &argc, argv ); // Erm Just Write It =)
init ();
glutInitDisplayMode ( GLUT_RGB | GLUT_DOUBLE ); // Display Mode
glutInitWindowSize ( 640, 480 ); // If glutFullScreen wasn’t called this is the window size
glutCreateWindow ( “NeHe’s OpenGL Framework” ); // Window Title (argv[0] for current directory as title)
glutDisplayFunc ( display ); // Matching Earlier Functions To Their Counterparts
glutReshapeFunc ( reshape );
glutKeyboardFunc ( keyboard );
glutSpecialFunc ( arrow_keys );
glutMainLoop ( ); // Initialize The Main Loop
}
//----------------------------------------------------------------------------------------------------------------
//-- Other Functions –
//----------------------------------------------------------------------------------------------------------------
void DrawCircle( double r )
{
DrawEllipse( r, r );
}
void DrawEllipse( double a, double b )
{
double const TWO_PI = 6.2831853071795865;
int const NSTEPS = 100;
double t = 0.;
glBegin( GL_LINE_LOOP );
for ( int i = 0; i < (NSTEPS-1); ++i )
{
glVertex2d( a * cos( t ), b * sin( t ) );
t += TWO_PI / NSTEPS;
}
glEnd();
}
Ok, this is annoying. I just tried the code on my Geforce2 MX at home and it works like a charm. No problems drawing the circle when exceeding 36 points.
So what now. Should I contact Dell and tell them to fix their drivers??? Any hope in that?
I’d suggest:
-
Search some forums for people who are having the same problem… ask them for their machine specs… if there are a number of people with the same problem… look at whats similar in the machines… etc!
-
You could always try it on another machine (that has the same specs as yours)
-
Phone dell and ask if there a fix.
-
Seek further help from openGL creators etc =x