root / PyOpenGLDemo / proesch / nurbs / nurbs.py @ 1
History  View  Annotate  Download (5.6 kB)
1 
#!/usr/bin/env python


2 
# Plot nurbs surface corresponding to a 2D damped oscillation.

3 
# The surface has two holes. A Teapot below the surface is

4 
# visible through these holes.

5 
#

6 
# Copyright (C) 2007 "Peter Roesch" <Peter.Roesch@fhaugsburg.de>

7 
#

8 
# This code is licensed under the PyOpenGL License.

9 
# Details are given in the file license.txt included in this distribution.

10  
11 
import sys 
12 
import math 
13 
from time import sleep 
14 
import traceback 
15  
16 
try:

17 
from OpenGL.GLUT import * 
18 
from OpenGL.GL import * 
19 
from OpenGL.GLU import * 
20 
except ImportError, err: 
21 
traceback.print_exc() 
22 
print ''' Error: PyOpenGL not installed properly!!''' 
23 
sys.exit( ) 
24  
25 
# globals

26 
animationAngle = 0.0

27 
frameRate = 25

28 
curr_time=0.0

29 
nurbsID=0

30  
31 
def animationStep( ): 
32 
"""Update animated parameters"""

33 
global animationAngle

34 
global frameRate

35 
animationAngle += 1

36 
while animationAngle > 360: 
37 
animationAngle = 360

38 
global curr_time

39 
curr_time+=0.05

40 
global nurbsID

41 
glDeleteLists( nurbsID, 1 )

42 
nurbsID = glGenLists( 1 )

43 
glNewList( nurbsID, GL_COMPILE ) 
44 
plotSurface( curr_time ) 
45 
glEndList( ) 
46 
sleep( 1 / float( frameRate ) ) 
47 
glutPostRedisplay( ) 
48  
49 
sigma = 0.5;

50 
twoSigSq = 2. * sigma * sigma;

51  
52 
def dampedOscillation( u, v, t): 
53 
"""Calculation of a R2 > R1 function at position u,v at curr_time t.

54 

55 
A tdependent cosine function is multiplied with a 2D gaussian.

56 
Both functions depend on the distance of (u,v) to the origin."""

57  
58 
distSq = u * u + v * v; 
59 
dist = math.pi * 4 * math.sqrt( distSq );

60 
global twoSigSq

61 
return 0.5 * math.exp(distSq / twoSigSq) * math.cos(dist  t); 
62  
63 
nPts = 15

64 
degree = 4

65 
samplingTolerance=2.0

66 
xMin, xMax, yMin, yMax = 1.0, 1.0, 1.0, 1.0 
67 
xStep = (xMaxxMin)/(nPts1)

68 
yStep = (yMaxyMin)/(nPts1)

69  
70 
# initialise a list representing a regular 2D grid of control points.

71 
controlPoints = [ \ 
72 
[ [ yMin+y*yStep, xMin+x*xStep, 0.0 ] for x in range ( nPts )]\ 
73 
for y in range( nPts ) ] 
74  
75 
# initialise knots ...

76 
knots = [ 0.0 for i in range( degree/2 ) ] +\ 
77 
[ float(i)/(nPts1) for i in range( nPts )] +\ 
78 
[ 1.0 for i in range( (degree+1)/2 ) ] 
79  
80 
# initialise enclosing

81 
enclosing=[ [0.0, 0.0], [1.0, 0.0], [1.0, 1.0], [0.0, 1.0], [0.0, 0.0] ] 
82  
83 
# first trim curve is a circle

84 
angleNum = 16

85 
angles = [ 2*math.pi*float(i)/angleNum for i in range( angleNum ) ] 
86 
radius=0.05

87 
offset=(0.4, 0.6) 
88 
circleDegree=degree 
89 
circlePoints = [ \ 
90 
[ offset[0]+radius*math.cos(theta), offset[1]+radius*math.sin(theta) ]\ 
91 
for theta in angles ] 
92 
for i in range( circleDegree1 ): 
93 
circlePoints = circlePoints + [ circlePoints[i] ] 
94 
knotNum = len( circlePoints ) + circleDegree

95 
circleKnots = [ float(i)/(knotNum1) for i in range( knotNum ) ] 
96  
97 
# second trim curve is a square

98 
squareHolePoints=[ [0.4, 0.4], [0.4, 0.45], [0.45, 0.45],\ 
99 
[0.45, 0.4], [0.4, 0.4] ] 
100  
101 
def updateControlPoints( t ): 
102 
"""Calculate function values for all 2D grid points."""

103 
for row in controlPoints: 
104 
for coord in row: 
105 
coord[2] = dampedOscillation( coord[0], coord[1], t ) 
106  
107 
def plotSurface( t ): 
108 
# display surface

109 
updateControlPoints( t ) 
110 
global controlPoints, knots

111 
global nurb

112  
113 
gluBeginSurface( nurb ) 
114 
gluNurbsSurface ( nurb, knots, knots, controlPoints, GL_MAP2_VERTEX_3 ) 
115  
116 
# trim curve enclosing

117 
gluBeginTrim( nurb ) 
118 
global enclosing

119 
gluPwlCurve( nurb, enclosing, GLU_MAP1_TRIM_2 ) 
120 
gluEndTrim( nurb ) 
121  
122 
# trim using square

123 
gluBeginTrim( nurb ) 
124 
global squareHolePoints

125 
gluPwlCurve( nurb, squareHolePoints, GLU_MAP1_TRIM_2 ) 
126 
gluEndTrim( nurb ) 
127 

128 
# trim using circle

129 
gluBeginTrim( nurb ) 
130 
global circlePoints, circleKnots

131 
gluNurbsCurve ( nurb, circleKnots, circlePoints, GLU_MAP1_TRIM_2 ) 
132 
gluEndTrim( nurb ) 
133  
134 
gluEndSurface( nurb ) 
135 

136  
137 
def display( ): 
138 
"""Glut display function."""

139 
glClear( GL_COLOR_BUFFER_BIT  GL_DEPTH_BUFFER_BIT ) 
140 
glMatrixMode( GL_PROJECTION ) 
141 
glLoadIdentity( ) 
142 
xSize, ySize = glutGet( GLUT_WINDOW_WIDTH ), glutGet( GLUT_WINDOW_HEIGHT ) 
143 
gluPerspective(60, float(xSize) / float(ySize), 0.1, 50) 
144 
glMatrixMode( GL_MODELVIEW ) 
145 
glLoadIdentity( ) 
146 
glPushMatrix( ) 
147 
glTranslatef( 0, 0, 3 ) 
148 
glRotatef( 30, 1, .3, 0) 
149 
glRotatef( animationAngle, 0, 0, 1 ) 
150  
151 
glMaterialfv( GL_FRONT_AND_BACK, GL_AMBIENT, [0.2, 0.2, 0.2, 1] ) 
152 
glMaterialfv( GL_FRONT_AND_BACK, GL_DIFFUSE, [0.7, 0.7, 0.7, 1] ) 
153 
glCallList( nurbsID ) 
154  
155 
glPopMatrix( ) 
156 
glMaterialfv( GL_FRONT_AND_BACK, GL_AMBIENT, [0.0, 0.0, 0.2, 1] ) 
157 
glMaterialfv( GL_FRONT_AND_BACK, GL_DIFFUSE, [0.0, 0.0, 0.7, 1] ) 
158 
glTranslatef( 0.0, 0.0, 12.0 ) 
159 
glCallList( teapotID ) 
160 
glutSwapBuffers( ) 
161  
162 
teapotID=0

163 
nurb=None

164 
def init( ): 
165 
"""Glut init function."""

166 
glClearColor ( 0, 0, 0, 0 ) 
167 
glEnable( GL_DEPTH_TEST ) 
168 
glShadeModel( GL_SMOOTH ) 
169 
glEnable( GL_LIGHTING ) 
170 
glEnable( GL_LIGHT0 ) 
171 
glLightModeli( GL_LIGHT_MODEL_TWO_SIDE, 0 )

172 
glLightfv( GL_LIGHT0, GL_POSITION, [2, 0, 10, 1] ) 
173 
lA = 0.8; glLightfv( GL_LIGHT0, GL_AMBIENT, [lA, lA, lA, 1] ) 
174 
lD = 1; glLightfv( GL_LIGHT0, GL_DIFFUSE, [lD, lD, lD, 1] ) 
175 
lS = 1; glLightfv( GL_LIGHT0, GL_SPECULAR, [lS, lS, lS, 1] ) 
176 
glMaterialfv( GL_FRONT_AND_BACK, GL_SPECULAR, [0.5, 0.5, 0.5, 1] ) 
177 
glMaterialf( GL_FRONT_AND_BACK, GL_SHININESS, 50 )

178 
glEnable( GL_AUTO_NORMAL ) 
179 
global nurb

180 
nurb = gluNewNurbsRenderer() 
181 
global samplingTolerance

182 
gluNurbsProperty(nurb, GLU_SAMPLING_TOLERANCE, samplingTolerance) 
183 
gluNurbsProperty(nurb, GLU_DISPLAY_MODE, GLU_FILL) 
184 
global teapotID

185 
teapotID = glGenLists( 1 )

186 
glNewList( teapotID, GL_COMPILE ) 
187 
glutSolidTeapot( 1.0 )

188 
glEndList( ) 
189 
global nurbsID

190 
nurbsID = glGenLists( 1 )

191 
glNewList( nurbsID, GL_COMPILE ) 
192 
global curr_time

193 
plotSurface( curr_time ) 
194 
glEndList( ) 
195  
196 
glutInit( sys.argv ) 
197 
glutInitDisplayMode( GLUT_DOUBLE  GLUT_RGB  GLUT_DEPTH ) 
198 
glutInitWindowSize( 250, 250 ) 
199 
glutInitWindowPosition( 100, 100 ) 
200 
glutCreateWindow( sys.argv[0] )

201 
init( ) 
202 
glutDisplayFunc( display ) 
203 
glutIdleFunc( animationStep ) 
204 
glutMainLoop( ) 