#2 The wire cone needs some work

closed
nobody
None
3
2003-12-12
2003-06-30
John F. Fay
No

The "freeglut" wire cone does not look like the GLUT
wire cone. There are several differences, one of which
is that the "freeglut" cone draws the base.

Discussion

  • John F. Fay
    John F. Fay
    2003-06-30

    • priority: 5 --> 3
     
  • Nigel Stewart
    Nigel Stewart
    2003-09-30

    Logged In: YES
    user_id=338692

    I've identified a number of issues with glutSolidCone()
    which are along the lines of the Sourceforge bug
    763247 - The wire cone needs some work.

    1. With back-face culling enabled half of the surface
    triangles disappear - the winding is not consistant.

    2. FreeGLUT draws a base for the cone, while GLUT does
    not. For compatibility, FreeGLUT should not draw the
    base either, I suppose.

    3. GLUT uses quads to cover the cone surface, while
    the FreeGLUT implementation is using triangles.

    4. The FreeGLUT cone implementation makes excessive use
    of glBegin/glEnd blocks and does not make use of
    fans or strips.

     
  • Nigel Stewart
    Nigel Stewart
    2003-09-30

    Logged In: YES
    user_id=338692

    Suggested replacement for glutSolidCone
    ---------------------

    void FGAPIENTRY glutSolidCone( GLdouble base, GLdouble
    height, GLint slices, GLint stacks )
    {
    int i, j;

    /*
    * Radial angle of each slice
    */

    const double angle = -2 * M_PI / (double) slices;

    /*
    * Step in z and radius as stacks
    * are drawn.
    */

    double z0,z1;
    double r0,r1;

    const double zStep = height/stacks;
    const double rStep = base/stacks;

    /*
    * Scaling factors for vertex normals
    */

    const double cosn = ( height / sqrt ( height * height +
    base * base ));
    const double sinn = ( base / sqrt ( height * height +
    base * base ));

    /*
    * Pre-computed lookup table of cos and sin values forming
    a cirle
    */

    double *sint = NULL;
    double *cost = NULL;

    cost = (double *) calloc( sizeof(double), slices + 1);
    sint = (double *) calloc( sizeof(double), slices + 1);

    assert(cost);
    assert(sint);

    for (j=0; j<=slices; j++)
    {
    cost[j] = cos(angle*j);
    sint[j] = sin(angle*j);
    }

    /*
    * Cover the circular base with a triangle fan...
    */

    z0 = 0.0;
    z1 = zStep;

    r0 = base;
    r1 = r0 - rStep;

    glBegin(GL_TRIANGLE_FAN);
    glNormal3d(0.0, 0.0, -1.0 );
    glVertex3d(0.0, 0.0, z0 );

    for( j=0; j<=slices; j++ )
    glVertex3d( cost[j]*r0, sint[j]*r0, z0 );

    glEnd();

    /*
    * Cover each stack with a quad strip, except the top stack
    */

    glBegin( GL_QUAD_STRIP );

    for( i=0; i<stacks-1; i++ )
    {
    for( j=0; j<=slices; j++ )
    {
    glNormal3d( cost[j]*sinn, sint[j]*sinn, cosn );
    glVertex3d( cost[j]*r0, sint[j]*r0, z0 );
    glVertex3d( cost[j]*r1, sint[j]*r1, z1 );
    }

    z0 = z1; z1 += zStep;
    r0 = r1; r1 -= rStep;
    }

    glEnd();

    /*
    * The top stack is covered with individual triangles
    */
    glBegin(GL_TRIANGLES);

    glNormal3d(cost[0]*sinn, sint[0]*sinn, cosn);

    for( j=0; j<slices; j++ )
    {
    glVertex3d(cost[j+0]*r0, sint[j+0]*r0, z0 );
    glVertex3d(0, 0, z1 );
    glNormal3d(cost[j+1]*sinn, sint[j+1]*sinn, cosn );
    glVertex3d(cost[j+1]*r0, sint[j+1]*r0, z0 );
    }

    glEnd();

    /*
    * Release sin/cos tables
    */
    free(sint);
    free(cost);
    }

     
  • Nigel Stewart
    Nigel Stewart
    2003-09-30

    Logged In: YES
    user_id=338692

    > General quibble:
    >
    > I think that assert() does NOT replace error-checking.
    assert() can
    > go away with compile-time options. This allocation should
    always be
    > checked. I would suggest replacing assert() with
    conventional if()-
    > based pointer-checks.

    Good point. In my defense, there are 8 other callocs in
    freeglut_geometry that have no included error-checking.

    assert(cost);
    assert(sint);

    if (!cost || !sint)
    {
    free(cost);
    free(sint);
    return;
    }

     
  • Nigel Stewart
    Nigel Stewart
    2003-09-30

    Logged In: YES
    user_id=338692

    > I suggest printing a message to {stderr}, and perhaps calling
    > abort(). (For the former, I think that there's an fgError()
    > function that might be better than writing directly to
    {stderr}.
    > Yes?)

    OK!

    >>assert(cost);
    >>assert(sint);
    >>
    >>if (!cost || !sint)
    >>{
    >> free(cost);
    >> free(sint);
    >> fgError("Failed to allocate memory in glutSolidCone");
    >> return;
    >>}

     
  • Nigel Stewart
    Nigel Stewart
    2003-10-02

    Logged In: YES
    user_id=338692

    An updated solid and wire cone has been attached to:
    RFE [ 814984 ] FreeGLUT should have a cylinder shape

     
  • Nigel Stewart
    Nigel Stewart
    2003-12-03

    Logged In: YES
    user_id=338692

    Resolved in the recent CVS updates and (upcoming) 2.0.2

     
  • John F. Fay
    John F. Fay
    2003-12-12

    Logged In: YES
    user_id=70811

    This has been fixed.

     
  • John F. Fay
    John F. Fay
    2003-12-12

    • status: open --> closed