Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

GLUquadrics -- when to create and to delete, efficiency etc.?

158 views
Skip to first unread message

Jonathan Campbell

unread,
Jul 16, 2009, 11:14:50 AM7/16/09
to
I'm programming an OpenGL application within SDL (for a teaching
example). Normally I use GLUT and do not deviate too far from Red book
practice, but with SDL and the framework I'm using here I'm moving out
of my comfort zone.

I have a graphics object which I call Component (a C++ class). Just to
be concrete and clear I'll give the detail that Componet has the
following data members:

private:
std::string name_;
Type t_;
GLfloat matrix_[16];
GLfloat mSpecular_[4], mAmbient_[4], mDiffuse_[4],
mEmission_[4], mShininess_;
GLUquadricObj *q_;
GLfloat r1_, r2_, len_;
int sl_, st_; // slices, stacks
};

In the constructor, I /previously/ had:

// A1
q_ = gluNewQuadric();
gluQuadricDrawStyle(q_, GLU_FILL);
gluQuadricNormals(q_, GLU_SMOOTH);

The quadric was only ever deleted in the ~Component destructor, and that
was only ever called when the program terminated execution.

I had a time triggered 'update'. Then I had a 'draw' which had:

glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, mSpecular_);
// etc.

// A2
gluCylinder(q_, r1_, r2_, len_, sl_, st_);

and this 'draw' gets called about 50 times a second in an animation
loop. The only variables that change during the animation are rotation
angles and translations.

The problem:

Sometimes the quadric appeared and sometimes not --- same executable;
sometimes it disappeared during the execution, all quite randomly.

The solution that I have now is to have no mention of the quadric in the
constructor and to have

// B2
q_ = gluNewQuadric();
gluQuadricDrawStyle(q_, GLU_FILL);
gluQuadricNormals(q_, GLU_SMOOTH);
gluCylinder(q_, r1_, r2_, len_, sl_, st_);
gluDeleteQuadric(q_);

in 'draw'.

Any ideas on why the scheme in // A1, A2 fails (randomly) to show the
quadric.

I wonder is the scheme in // B2 rather inefficient? It 'works', but I
don't want to expose really bad practice in a teaching example.

I /may/ be able to put gluCylinder(q_, r1_, r2_, len_, sl_, st_); in a
display list, but it would be nice to retain the possibility of the
dimensions changing.

TIA,

Jon C.


--
Jonathan Campbell www.jgcampbell.com BT48, UK.

fungus

unread,
Jul 16, 2009, 1:09:07 PM7/16/09
to
On Jul 16, 5:14 pm, Jonathan Campbell <jg.campbell...@gmail.com>
wrote:

>
> The problem:
>
> Sometimes the quadric appeared and sometimes not --- same executable;
> sometimes it disappeared during the execution, all quite randomly.
>

Whenever you see "random" in C++, think "uninitialized variable".


--
<\___/>
/ O O \
\_____/ FTB.

http://www.topaz3d.com/ - New 3D editor for real time simulation

Jonathan Campbell

unread,
Jul 17, 2009, 7:12:18 AM7/17/09
to
fungus wrote:
> On Jul 16, 5:14 pm, Jonathan Campbell <jg.campbell...@gmail.com>
> wrote:
>> The problem:
>>
>> Sometimes the quadric appeared and sometimes not --- same executable;
>> sometimes it disappeared during the execution, all quite randomly.
>>
>
> Whenever you see "random" in C++, think "uninitialized variable".
>

I totally agree.

I've done a prolonged series of experiments ... use ColorMaterial ...
then disable lighting and use plain Color ... create my own object
(instead of a quadric).

The only common factor seems to be my previous use of the quadric and I
cannot see what is uninitialised there.

Would it be normal to place code like this in a 'draw' that gets
executed every frame in an animation? This is what 'works'.

q_ = gluNewQuadric();
gluQuadricDrawStyle(q_, GLU_FILL);
gluQuadricNormals(q_, GLU_SMOOTH);
gluCylinder(q_, r1_, r2_, len_, sl_, st_);
gluDeleteQuadric(q_);

I'd have thought that placing

q_ = gluNewQuadric();
gluQuadricDrawStyle(q_, GLU_FILL);
gluQuadricNormals(q_, GLU_SMOOTH);

in a called-once only initialisation and then

gluCylinder(q_, r1_, r2_, len_, sl_, st_);

in the 'draw' would be more sensible, but it is that which exhibits the
random behaviour.

Best regards,

fungus

unread,
Jul 17, 2009, 8:18:43 AM7/17/09
to
On Jul 17, 1:12 pm, Jonathan Campbell <jg.campbell...@gmail.com>
wrote:
>

> Would it be normal to place code like this in a 'draw' that gets
> executed every frame in an animation? This is what 'works'.
>
>      q_ = gluNewQuadric();
>      ...
>

Obviously it will be slower, the only question is "how much?"

> I'd have thought that placing
>
>      q_ = gluNewQuadric();
>      gluQuadricDrawStyle(q_, GLU_FILL);
>      gluQuadricNormals(q_, GLU_SMOOTH);
>
> in a called-once only initialisation and then
>
>      gluCylinder(q_, r1_, r2_, len_, sl_, st_);
>
> in the 'draw' would be more sensible,  but it is that which exhibits the
> random behaviour.
>

You might be doing something bad in another part of
your program. Try writing a minimal program which does
only this, nothing more.

Miles Bader

unread,
Jul 17, 2009, 10:52:22 PM7/17/09
to
fungus <opengl...@artlum.com> writes:
>> Sometimes the quadric appeared and sometimes not --- same executable;
>> sometimes it disappeared during the execution, all quite randomly.
>
> Whenever you see "random" in C++, think "uninitialized variable".

... and for detecting uninitialized variables/structure fields/anything,
valgrind is an amazingly useful (and just generally amazing) tool.

Even if your program doesn't appear to have any bugs, it's good practice
to run it under valgrind occasionally -- it's very likely it will find
something.

-miles

--
"... The revolution will be no re-run brothers; The revolution will be live."

Jonathan Campbell

unread,
Jul 19, 2009, 9:17:47 AM7/19/09
to
Miles Bader wrote:
> fungus <opengl...@artlum.com> writes:
>>> Sometimes the quadric appeared and sometimes not --- same executable;
>>> sometimes it disappeared during the execution, all quite randomly.
>> Whenever you see "random" in C++, think "uninitialized variable".
>
> ... and for detecting uninitialized variables/structure fields/anything,
> valgrind is an amazingly useful (and just generally amazing) tool.
>

Yes, damned amazing! Though I despaired at having to read a manual, the
output gave me enough to narrow my suspicions.

> Even if your program doesn't appear to have any bugs, it's good practice
> to run it under valgrind occasionally -- it's very likely it will find
> something.
>

Bingo, I think I have it.

class Component{
...


private:
std::string name_;
Type t_;
GLfloat matrix_[16];
GLfloat mSpecular_[4], mAmbient_[4], mDiffuse_[4],
mEmission_[4], mShininess_;
GLUquadricObj *q_;
GLfloat r1_, r2_, len_;
int sl_, st_; // slices, stacks
};

Component::Component(){
...
setMAmbient(grey6);
setMShininess(30.0);

q_ = gluNewQuadric();
gluQuadricDrawStyle(q_, GLU_FILL);
gluQuadricNormals(q_, GLU_SMOOTH);

r1_ = r2_ = 1.0f;
len_ = 2.0f;
sl_ = st_ = 10;
}

Then in the class (Scene) that uses Component

comp = Component();

thereby invoking the constructor immediately followed by the assignment
operator, which is the default compiler-supplied one, i.e. 'q_' get
copied, but not what it points to, and what it points to gets destroyed
immediately after the copy/assign.

The following seems to correct the problem:

Scene() : comp(Component()){

though I guess I should disable the assignment operator by making it
private.

So it was an uninitialised variable! Oh dear.

And apologies for the incompetent debugger's lament "but it cannot be ...".

Very many thanks,

Jonathan Campbell

unread,
Jul 19, 2009, 9:24:34 AM7/19/09
to
Jonathan Campbell wrote:
> Miles Bader wrote:
>> fungus <opengl...@artlum.com> writes:
>>>> Sometimes the quadric appeared and sometimes not --- same executable;
>>>> sometimes it disappeared during the execution, all quite randomly.
>>> Whenever you see "random" in C++, think "uninitialized variable".
>>
>> ... and for detecting uninitialized variables/structure fields/anything,
>> valgrind is an amazingly useful (and just generally amazing) tool.
>>
>
> Yes, damned amazing! Though I despaired at having to read a manual, the
> output gave me enough to narrow my suspicions.
>
[...]

BTW, to people who may wish to use valgrind in a Linux/g++ environment,
I think you need to ask g++ to generate debugging information in order
to get source line numbers in diagnostics, i.e.

g++ -g -W -Wall -ansi -pedantic ...

Jonathan Campbell

unread,
Jul 19, 2009, 5:36:17 PM7/19/09
to
Jonathan Campbell wrote:
> Miles Bader wrote:
>> fungus <opengl...@artlum.com> writes:
>>>> Sometimes the quadric appeared and sometimes not --- same executable;
>>>> sometimes it disappeared during the execution, all quite randomly.
>>> Whenever you see "random" in C++, think "uninitialized variable".
[...]

> comp = Component();
>
> thereby invoking the constructor immediately followed by the assignment
> operator, which is the default compiler-supplied one, i.e. 'q_' get
> copied, but not what it points to, and what it points to gets destroyed
> immediately after the copy/assign.
>

... gets destroyed by the destructor acting on the temporary, that is.

J.C.

0 new messages