Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    text
    copied!<p>Looks like you're trying to construct a <a href="https://en.wikipedia.org/wiki/Surface_of_revolution" rel="nofollow noreferrer">surface of revolution</a>/<a href="https://en.wikipedia.org/wiki/Solid_of_revolution" rel="nofollow noreferrer">solid of revolution</a>/<a href="https://web.archive.org/web/20070808001022/http://www.delphi3d.net/articles/viewarticle.php?article=lathe.htm" rel="nofollow noreferrer">"lathe object"</a>.</p> <p>A working example:</p> <p><a href="https://i.stack.imgur.com/EGvGt.png" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/EGvGt.png" alt="lathe"></a> <br></p> <pre><code>#include &lt;GL/glut.h&gt; #include &lt;glm/glm.hpp&gt; #include &lt;vector&gt; #include &lt;cmath&gt; using namespace std; using namespace glm; struct Vertex { Vertex( const vec3&amp; position, const vec3&amp; normal ) : position( position ) , normal( normal ) {} vec3 position; vec3 normal; }; // spin the pts array around the Z axis. // pts.x will become the radius, and pts.y will become the height // pts should be sorted by y-coordinate vector&lt; Vertex &gt; Lathe( const vector&lt; vec2 &gt;&amp; pts, unsigned int segments = 32 ) { // precalculate circle points vector&lt; vec2 &gt; circlePts; for( unsigned int i = 0; i &lt;= segments; ++i ) { float angle = ( i / (float)segments ) * 3.14159f * 2.0f; circlePts.push_back( vec2( cos( angle ), sin( angle ) ) ); } // fill each layer typedef vector&lt; vec3 &gt; Layer; typedef vector&lt; Layer &gt; Layers; Layers layers( pts.size(), Layer( circlePts.size() ) ); for( size_t i = 0; i &lt; pts.size(); ++i ) { for( unsigned int j = 0; j &lt; circlePts.size(); ++j ) { layers[i][j] = vec3( circlePts[j] * pts[i].x, pts[i].y ); } } // move through layers generating triangles vector&lt; Vertex &gt; verts; for( size_t i = 1; i &lt; layers.size(); ++i ) { const Layer&amp; prvLayer = layers[ i-1 ]; const Layer&amp; curLayer = layers[ i-0 ]; for( size_t j = 1; j &lt; circlePts.size(); ++j ) { // upper = cur layer // UL -- UR // left | 0 / | right // = j-1 | / 1 | = j-0 // LL -- LR // lower = prv layer const vec3&amp; LL = prvLayer[ j-1 ]; // lower-left const vec3&amp; LR = prvLayer[ j-0 ]; // lower-right const vec3&amp; UL = curLayer[ j-1 ]; // upper-left const vec3&amp; UR = curLayer[ j-0 ]; // upper-right // triangle0: LL -&gt; UR -&gt; UL const vec3 normal0 = normalize( cross( UR - LL, UL - LL ) ); verts.push_back( Vertex( LL, normal0 ) ); verts.push_back( Vertex( UR, normal0 ) ); verts.push_back( Vertex( UL, normal0 ) ); // triangle1: LL -&gt; LR -&gt; UR const vec3 normal1 = normalize( cross( LR - LL, UL - LL ) ); verts.push_back( Vertex( LL, normal1 ) ); verts.push_back( Vertex( LR, normal1 ) ); verts.push_back( Vertex( UR, normal1 ) ); } } return verts; } // mouse state int btn; ivec2 startMouse; ivec2 startRot, curRot; void mouse(int button, int state, int x, int y ) { if( button == GLUT_LEFT_BUTTON &amp;&amp; state == GLUT_DOWN ) { btn = button; startMouse = ivec2( x, glutGet( GLUT_WINDOW_HEIGHT ) - y ); startRot = curRot; } } void motion( int x, int y ) { ivec2 curMouse( x, glutGet( GLUT_WINDOW_HEIGHT ) - y ); if( btn == GLUT_LEFT_BUTTON ) { curRot = startRot + ( curMouse - startMouse ); } glutPostRedisplay(); } vector&lt; Vertex &gt; model; void display() { glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT ); glMatrixMode( GL_PROJECTION ); glLoadIdentity(); double w = glutGet( GLUT_WINDOW_WIDTH ); double h = glutGet( GLUT_WINDOW_HEIGHT ); double ar = w / h; gluPerspective( 60, ar, 0.1, 40 ); glMatrixMode( GL_MODELVIEW ); glLoadIdentity(); glTranslatef( 0, 0, -10 ); glPushMatrix(); glRotatef( curRot.x % 360, 0, 1, 0 ); glRotatef( -curRot.y % 360, 1, 0, 0 ); // draw model if( !model.empty() ) { glColor3ub( 255, 0, 0 ); glEnableClientState( GL_VERTEX_ARRAY ); glEnableClientState( GL_NORMAL_ARRAY ); glVertexPointer( 3, GL_FLOAT, sizeof(Vertex), &amp;model[0].position ); glNormalPointer( GL_FLOAT, sizeof(Vertex), &amp;model[0].normal ); glDrawArrays( GL_TRIANGLES, 0, model.size() ); glDisableClientState( GL_VERTEX_ARRAY ); glDisableClientState( GL_NORMAL_ARRAY ); } // draw bounding cube glDisable( GL_LIGHTING ); glColor3ub( 255, 255, 255 ); glutWireCube( 7 ); glEnable( GL_LIGHTING ); glPopMatrix(); glutSwapBuffers(); } int main( int argc, char **argv ) { vector&lt; vec2 &gt; pts; pts.push_back( vec2( 0.1, -3 ) ); pts.push_back( vec2( 2, -2 ) ); pts.push_back( vec2( 3, -1 ) ); pts.push_back( vec2( 1, 0 ) ); pts.push_back( vec2( 3, 1 ) ); pts.push_back( vec2( 4, 2 ) ); pts.push_back( vec2( 4, 3 ) ); model = Lathe( pts ); glutInit( &amp;argc, argv ); glutInitDisplayMode( GLUT_RGBA | GLUT_DEPTH | GLUT_DOUBLE ); glutInitWindowSize( 640, 480 ); glutCreateWindow( "GLUT" ); glutDisplayFunc( display ); glutMouseFunc( mouse ); glutMotionFunc( motion ); glEnable( GL_DEPTH_TEST ); // set up lighting glShadeModel( GL_SMOOTH ); glEnable( GL_COLOR_MATERIAL ); glColorMaterial( GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE ) ; glLightModeli( GL_LIGHT_MODEL_TWO_SIDE, GL_TRUE ); glEnable( GL_LIGHTING ); // set up "headlamp"-like light glEnable( GL_LIGHT0 ); glMatrixMode( GL_MODELVIEW ); glLoadIdentity(); GLfloat position[] = { 0, 0, 1, 0 }; glLightfv( GL_LIGHT0, GL_POSITION, position ); glPolygonMode( GL_FRONT, GL_FILL ); glPolygonMode( GL_BACK, GL_LINE ); glutMainLoop(); return 0; } </code></pre>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload