1 /* tube, Copyright (c) 2001, 2003, 2007 Jamie Zawinski <jwz@jwz.org>
2 * Utility functions to create tubes and cones in GL.
4 * Permission to use, copy, modify, distribute, and sell this software and its
5 * documentation for any purpose is hereby granted without fee, provided that
6 * the above copyright notice appear in all copies and that both that
7 * copyright notice and this permission notice appear in supporting
8 * documentation. No representations are made about the suitability of this
9 * software for any purpose. It is provided "as is" without express or
22 # include <OpenGL/gl.h>
30 unit_tube (int faces, int smooth, int caps_p, int wire_p)
34 GLfloat step = M_PI * 2 / faces;
37 GLfloat x, y, x0=0, y0=0;
43 glBegin (wire_p ? GL_LINES : (smooth ? GL_QUAD_STRIP : GL_QUADS));
57 for (i = 0; i < faces; i++)
62 glNormal3f(x0, 0, y0);
86 for (z = 0; z <= 1; z++)
88 glFrontFace(z == 0 ? GL_CCW : GL_CW);
89 glNormal3f(0, (z == 0 ? -1 : 1), 0);
90 glBegin(wire_p ? GL_LINE_LOOP : GL_TRIANGLE_FAN);
91 if (! wire_p) glVertex3f(0, z, 0);
92 for (i = 0, th = 0; i <= faces; i++)
107 unit_cone (int faces, int smooth, int cap_p, int wire_p)
111 GLfloat step = M_PI * 2 / faces;
114 GLfloat x, y, x0, y0;
119 glBegin(wire_p ? GL_LINES : GL_TRIANGLES);
127 for (i = 0; i < faces; i++)
129 glNormal3f(x0, 0, y0);
132 if (smooth) glNormal3f(x, 0, y);
141 if (smooth) glNormal3f(x, 0, y);
152 glNormal3f(0, -1, 0);
153 glBegin(wire_p ? GL_LINE_LOOP : GL_TRIANGLE_FAN);
154 if (! wire_p) glVertex3f(0, 0, 0);
155 for (i = 0, th = 0; i <= faces; i++)
157 GLfloat x = cos (th);
158 GLfloat y = sin (th);
170 tube_1 (GLfloat x1, GLfloat y1, GLfloat z1,
171 GLfloat x2, GLfloat y2, GLfloat z2,
172 GLfloat diameter, GLfloat cap_size,
173 int faces, int smooth, int caps_p, int wire_p,
176 GLfloat length, X, Y, Z;
179 if (diameter <= 0) abort();
185 if (X == 0 && Y == 0 && Z == 0)
188 length = sqrt (X*X + Y*Y + Z*Z);
192 glTranslatef(x1, y1, z1);
193 glRotatef (-atan2 (X, Y) * (180 / M_PI), 0, 0, 1);
194 glRotatef ( atan2 (Z, sqrt(X*X + Y*Y)) * (180 / M_PI), 1, 0, 0);
195 glScalef (diameter, length, diameter);
197 /* extend the endpoints of the tube by the cap size in both directions */
200 GLfloat c = cap_size/length;
201 glTranslatef (0, -c, 0);
202 glScalef (1, 1+c+c, 1);
206 polys = unit_cone (faces, smooth, caps_p, wire_p);
208 polys = unit_tube (faces, smooth, caps_p, wire_p);
216 tube (GLfloat x1, GLfloat y1, GLfloat z1,
217 GLfloat x2, GLfloat y2, GLfloat z2,
218 GLfloat diameter, GLfloat cap_size,
219 int faces, int smooth, int caps_p, int wire_p)
221 return tube_1 (x1, y1, z1, x2, y2, z2, diameter, cap_size,
222 faces, smooth, caps_p, wire_p,
228 cone (GLfloat x1, GLfloat y1, GLfloat z1,
229 GLfloat x2, GLfloat y2, GLfloat z2,
230 GLfloat diameter, GLfloat cap_size,
231 int faces, int smooth, int cap_p, int wire_p)
233 return tube_1 (x1, y1, z1, x2, y2, z2, diameter, cap_size,
234 faces, smooth, cap_p, wire_p,