PDA

View Full Version : 3D shapes with stippled edges when hidden



schtroumpfbleu
08-27-2010, 08:43 AM
Hi guys,

I'm new to OpenGL. I've read tutorials and stuff and I think I understand some stuff already, but there's one thing I have no clue how to do.

What I want to do is draw a 3D shape, let's say a cube. The desired behavior would be to draw only its edges, with the "hidden" edges being drawn as stippled lines, and the non-hidden edges being drawn with full (normal) lines.

Is there a simple way to do that, i.e. a way without me having to compute what parts of the cube are hidden or not?

For now, I do:

// allows blending
glEnable (GL_BLEND);
glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);

// draw the cube
glColor4f(1.0, 1.0, 0.0, 0.3);
glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
drawQuad();

// draw the wireframe of the cube
glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
glEnable(GL_LINE_STIPPLE);
glLineStipple(1, 50000);
drawQuad();


And the drawQuad method:

void drawQuad() {

float w = 1.0f;
float h = 1.0f;
float d = 2.0f;

glBegin(GL_QUADS);
glVertex3f(0,0,0);
glVertex3f(w,0,0);
glVertex3f(w,h,0);
glVertex3f(0,h,0);
glEnd();
// glColor3f (1.0, 1.0, 0.5);
glBegin(GL_QUADS);
glVertex3f(0,h,0);
glVertex3f(w,h,0);
glVertex3f(w,h,d);
glVertex3f(0,h,d);
glEnd();
// glColor3f (1.0, 1.0, 0.0);
glBegin(GL_QUADS);
glVertex3f(0,0,d);
glVertex3f(w,0,d);
glVertex3f(w,h,d);
glVertex3f(0,h,d);
glEnd();
// glColor3f (1.0, 0.5, 0.0);
glBegin(GL_QUADS);
glVertex3f(0,0,0);
glVertex3f(w,0,0);
glVertex3f(w,0,d);
glVertex3f(0,0,d);
glEnd();
// glColor3f (1.0, 0.0, 0.0);
glBegin(GL_QUADS);
glVertex3f(w,0,0);
glVertex3f(w,0,d);
glVertex3f(w,h,d);
glVertex3f(w,h,0);
glEnd();
// glColor3f (0.5, 0.0, 0.0);
glBegin(GL_QUADS);
glVertex3f(0,0,0);
glVertex3f(0,0,d);
glVertex3f(0,h,d);
glVertex3f(0,h,0);
glEnd();

}

Any help or pointer to a start of solution would be highly appreciated. Sorry if this is trivial...

Sebastien

david_f_knight
08-27-2010, 09:48 AM
No, it's not trivial (or obvious), but it's also not hard.

Keep in mind, OpenGL is a raster (i.e., framebuffer based) rendering API, and the framebuffer can be used quite flexibly to do all kinds of things.

You could solve your problem by rendering it in multiple passes. First, render the solid part of your object with GL_QUADS. Here's the clever part: disable writing to the color buffers before rendering your GL_QUADS. In other words, render only to the depth buffer.

For your second pass you will render all your edges with the hidden line stipple pattern you desire, but this time enable writing to the color buffers but disable the depth buffer. In other words, every edge will be visible without regard to whether it is hidden or not.

For your third pass, render all your edges a second time, but this time disable the line stipple pattern so lines are solid/continuous, and enable the depth buffer. (You could also disable writing to the enabled depth buffer if you wish for a slight performance improvement.) This pass will draw only your visible/non-hidden edges in the color buffers.

schtroumpfbleu
08-30-2010, 09:37 AM
Thanks so much, it worked perfectly!