PyParticles3 0.4.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (100) hide show
  1. pyparticles/__init__.py +26 -0
  2. pyparticles/__main__.py +7 -0
  3. pyparticles/animation/__init__.py +21 -0
  4. pyparticles/animation/animated_cli.py +53 -0
  5. pyparticles/animation/animated_ogl.py +691 -0
  6. pyparticles/animation/animated_ogl_compat.py +243 -0
  7. pyparticles/animation/animated_scatter.py +94 -0
  8. pyparticles/animation/animation.py +251 -0
  9. pyparticles/animation/test_animation.py +310 -0
  10. pyparticles/demo/__init__.py +33 -0
  11. pyparticles/demo/bubble.py +106 -0
  12. pyparticles/demo/electromagnetic_demo.py +128 -0
  13. pyparticles/demo/electrostatic_demo.py +126 -0
  14. pyparticles/demo/fountain.py +478 -0
  15. pyparticles/demo/gas_lennard_jones.py +87 -0
  16. pyparticles/demo/gravity_clusters.py +73 -0
  17. pyparticles/demo/solar_system.py +222 -0
  18. pyparticles/demo/springs.py +141 -0
  19. pyparticles/demo/springs_constr.py +135 -0
  20. pyparticles/demo/test.py +34 -0
  21. pyparticles/forces/__init__.py +21 -0
  22. pyparticles/forces/const_force.py +140 -0
  23. pyparticles/forces/damping.py +174 -0
  24. pyparticles/forces/drag.py +167 -0
  25. pyparticles/forces/electromagnetic.py +105 -0
  26. pyparticles/forces/electromagnetic_field.py +95 -0
  27. pyparticles/forces/electrostatic.py +72 -0
  28. pyparticles/forces/force.py +75 -0
  29. pyparticles/forces/force_constrained.py +32 -0
  30. pyparticles/forces/fused_const_drag.py +445 -0
  31. pyparticles/forces/gravity.py +345 -0
  32. pyparticles/forces/lennard_jones.py +74 -0
  33. pyparticles/forces/linear_spring.py +86 -0
  34. pyparticles/forces/linear_spring_constrained.py +72 -0
  35. pyparticles/forces/multiple_force.py +134 -0
  36. pyparticles/forces/pseudo_bubble.py +226 -0
  37. pyparticles/forces/van_der_waals_force.py +60 -0
  38. pyparticles/forces/vector_field_force.py +52 -0
  39. pyparticles/geometry/__init__.py +21 -0
  40. pyparticles/geometry/dist.py +24 -0
  41. pyparticles/geometry/intersection.py +62 -0
  42. pyparticles/geometry/transformations.py +387 -0
  43. pyparticles/main/__init__.py +21 -0
  44. pyparticles/main/main.py +466 -0
  45. pyparticles/measures/__init__.py +21 -0
  46. pyparticles/measures/elastic_potential_energy.py +67 -0
  47. pyparticles/measures/gravitational_potential_energy.py +69 -0
  48. pyparticles/measures/kinetic_energy.py +68 -0
  49. pyparticles/measures/mass.py +59 -0
  50. pyparticles/measures/measure.py +156 -0
  51. pyparticles/measures/momentum.py +144 -0
  52. pyparticles/measures/total_energy.py +68 -0
  53. pyparticles/ode/__init__.py +21 -0
  54. pyparticles/ode/euler_solver.py +214 -0
  55. pyparticles/ode/euler_solver_constrained.py +49 -0
  56. pyparticles/ode/leapfrog_solver.py +37 -0
  57. pyparticles/ode/leapfrog_solver_constrained.py +53 -0
  58. pyparticles/ode/midpoint_solver.py +43 -0
  59. pyparticles/ode/midpoint_solver_constrained.py +60 -0
  60. pyparticles/ode/ode_solver.py +134 -0
  61. pyparticles/ode/ode_solver_constrained.py +43 -0
  62. pyparticles/ode/runge_kutta_solver.py +79 -0
  63. pyparticles/ode/runge_kutta_solver_constrained.py +98 -0
  64. pyparticles/ode/sim_time.py +56 -0
  65. pyparticles/ode/stormer_verlet_solver.py +50 -0
  66. pyparticles/ode/stormer_verlet_solver_constrained.py +73 -0
  67. pyparticles/ogl/__init__.py +21 -0
  68. pyparticles/ogl/axis_ogl.py +210 -0
  69. pyparticles/ogl/draw_particles_ogl.py +313 -0
  70. pyparticles/ogl/draw_particles_ogl_compat.py +509 -0
  71. pyparticles/ogl/draw_vector_field.py +221 -0
  72. pyparticles/ogl/opencl_gl_vbo.py +485 -0
  73. pyparticles/ogl/trackball.py +131 -0
  74. pyparticles/ogl/translate_scene.py +87 -0
  75. pyparticles/pset/__init__.py +21 -0
  76. pyparticles/pset/boundary.py +69 -0
  77. pyparticles/pset/cluster.py +28 -0
  78. pyparticles/pset/constrained_force_interactions.py +63 -0
  79. pyparticles/pset/constrained_x.py +158 -0
  80. pyparticles/pset/constraint.py +42 -0
  81. pyparticles/pset/default_boundary.py +43 -0
  82. pyparticles/pset/file_cluster.py +131 -0
  83. pyparticles/pset/logger.py +152 -0
  84. pyparticles/pset/octree.py +451 -0
  85. pyparticles/pset/opencl_context.py +374 -0
  86. pyparticles/pset/particles_set.py +499 -0
  87. pyparticles/pset/periodic_boundary.py +36 -0
  88. pyparticles/pset/rand_cluster.py +188 -0
  89. pyparticles/pset/rebound_boundary.py +68 -0
  90. pyparticles/utils/__init__.py +21 -0
  91. pyparticles/utils/parse_args.py +72 -0
  92. pyparticles/utils/problem_config.py +608 -0
  93. pyparticles/utils/pypart_global.py +122 -0
  94. pyparticles/utils/time_formatter.py +50 -0
  95. pyparticles3-0.4.0.dist-info/METADATA +395 -0
  96. pyparticles3-0.4.0.dist-info/RECORD +100 -0
  97. pyparticles3-0.4.0.dist-info/WHEEL +5 -0
  98. pyparticles3-0.4.0.dist-info/entry_points.txt +3 -0
  99. pyparticles3-0.4.0.dist-info/licenses/LICENSE-gpl-3.0.txt +674 -0
  100. pyparticles3-0.4.0.dist-info/top_level.txt +1 -0
@@ -0,0 +1,50 @@
1
+ # PyParticles : Particles simulation in python
2
+ # Copyright (C) 2012 Simone Riva
3
+ #
4
+ # This program is free software: you can redistribute it and/or modify
5
+ # it under the terms of the GNU General Public License as published by
6
+ # the Free Software Foundation, either version 3 of the License, or
7
+ # (at your option) any later version.
8
+ #
9
+ # This program is distributed in the hope that it will be useful,
10
+ # but WITHOUT ANY WARRANTY; without even the implied warranty of
11
+ # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
+ # GNU General Public License for more details.
13
+ #
14
+ # You should have received a copy of the GNU General Public License
15
+ # along with this program. If not, see <http://www.gnu.org/licenses/>.
16
+
17
+
18
+ import numpy as np
19
+ import pyparticles.ode.ode_solver as os
20
+ import pyparticles.pset.particles_set as ps
21
+
22
+ class StormerVerletSolver( os.OdeSolver ) :
23
+ def __init__( self , force , p_set , dt ):
24
+ super(StormerVerletSolver,self).__init__( force , p_set , dt )
25
+ self.__pset_m1 = ps.ParticlesSet( p_set.size , p_set.dim , mass=False , velocity=False )
26
+ self.__pset_tmp = ps.ParticlesSet( p_set.size , p_set.dim , mass=False , velocity=False )
27
+
28
+
29
+ def __step__( self , dt ):
30
+
31
+ self.force.update_force( self.pset )
32
+
33
+ if self.steps_cnt == 1 :
34
+
35
+ # for the firse step we use the Euler method
36
+ self.__pset_m1.X[:] = self.pset.X[:]
37
+ self.pset.V[:] = self.pset.V + self.force.A * dt
38
+ self.pset.X[:] = self.pset.X + self.pset.V * dt
39
+
40
+ else :
41
+
42
+ self.__pset_tmp.X[:] = self.pset.X
43
+
44
+ self.pset.X[:] = 2.0*self.pset.X[:] - self.__pset_m1.X[:] + self.force.A[:] * dt**2.0
45
+ self.pset.V[:] = ( self.__pset_tmp.X[:] - self.__pset_m1.X[:] ) / dt
46
+
47
+ self.__pset_m1.X[:] = self.__pset_tmp.X[:]
48
+
49
+
50
+ self.pset.update_boundary()
@@ -0,0 +1,73 @@
1
+ # PyParticles : Particles simulation in python
2
+ # Copyright (C) 2012 Simone Riva
3
+ #
4
+ # This program is free software: you can redistribute it and/or modify
5
+ # it under the terms of the GNU General Public License as published by
6
+ # the Free Software Foundation, either version 3 of the License, or
7
+ # (at your option) any later version.
8
+ #
9
+ # This program is distributed in the hope that it will be useful,
10
+ # but WITHOUT ANY WARRANTY; without even the implied warranty of
11
+ # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
+ # GNU General Public License for more details.
13
+ #
14
+ # You should have received a copy of the GNU General Public License
15
+ # along with this program. If not, see <http://www.gnu.org/licenses/>.
16
+
17
+
18
+ import numpy as np
19
+ import pyparticles.ode.ode_solver_constrained as osc
20
+ import pyparticles.pset.particles_set as ps
21
+
22
+
23
+ class StormerVerletSolverConstrained( osc.OdeSolverConstrained ) :
24
+ def __init__( self , force , p_set , dt , x_constraint=None , v_constraint=None ):
25
+ super(StormerVerletSolverConstrained,self).__init__( force , p_set , dt , x_constraint=None , v_constraint=None )
26
+
27
+ self.__pset_m1 = ps.ParticlesSet( p_set.size , p_set.dim , mass=False , velocity=False )
28
+ self.__pset_tmp = ps.ParticlesSet( p_set.size , p_set.dim , mass=False , velocity=False )
29
+
30
+ if x_constraint != None :
31
+ self.x_constraint = x_constraint
32
+
33
+ def get_x_constraint(self):
34
+ return super(StormerVerletSolverConstrained,self).get_x_constraint()
35
+
36
+ def set_x_constraint(self , xc ):
37
+ super(StormerVerletSolverConstrained,self).set_x_constraint( xc )
38
+
39
+ self.__free_inx = self.x_constraint.get_cx_free_indicies()
40
+ self.__csrt_inx = self.x_constraint.get_cx_indicies()
41
+
42
+ x_constraint = property( get_x_constraint , set_x_constraint , doc="get and set the current positionals constraints" )
43
+
44
+
45
+ def __step__( self , dt ):
46
+
47
+ self.force.update_force( self.pset )
48
+
49
+ if self.steps_cnt == 1 :
50
+
51
+ # for the firse step we use the Euler method
52
+ self.__pset_m1.X[:] = self.pset.X[:]
53
+
54
+ self.pset.V[self.__free_inx,:] = self.pset.V[self.__free_inx,:] + self.force.A[self.__free_inx,:] * dt
55
+ self.pset.X[self.__free_inx,:] = self.pset.X[self.__free_inx,:] + self.pset.V[self.__free_inx,:] * dt
56
+
57
+ self.pset.V[self.__csrt_inx,:] = 0.0
58
+
59
+ else :
60
+
61
+ self.__pset_tmp.X[:] = self.pset.X[:]
62
+
63
+ self.pset.X[self.__free_inx,:] = 2.0*self.pset.X[self.__free_inx,:] - self.__pset_m1.X[self.__free_inx,:] + self.force.A[self.__free_inx,:] * dt**2.0
64
+ self.pset.V[self.__free_inx,:] = ( self.__pset_tmp.X[self.__free_inx,:] - self.__pset_m1.X[self.__free_inx,:] ) / dt
65
+
66
+ self.__pset_m1.X[:] = self.__pset_tmp.X[:]
67
+
68
+ self.pset.V[self.__csrt_inx,:] = 0.0
69
+
70
+ self.pset.update_boundary()
71
+
72
+
73
+
@@ -0,0 +1,21 @@
1
+ # PyParticles : Particles simulation in python
2
+ #Copyright (C) 2012 Simone Riva
3
+ #
4
+ #This program is free software: you can redistribute it and/or modify
5
+ #it under the terms of the GNU General Public License as published by
6
+ #the Free Software Foundation, either version 3 of the License, or
7
+ #(at your option) any later version.
8
+ #
9
+ #This program is distributed in the hope that it will be useful,
10
+ #but WITHOUT ANY WARRANTY; without even the implied warranty of
11
+ #MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
+ #GNU General Public License for more details.
13
+ #
14
+ #You should have received a copy of the GNU General Public License
15
+ #along with this program. If not, see <http://www.gnu.org/licenses/>.
16
+
17
+
18
+ import os
19
+ import glob
20
+
21
+ __all__ = [ os.path.splitext( os.path.basename(f) )[0] for f in glob.glob(os.path.dirname(os.path.abspath(__file__))+"/*.py")]
@@ -0,0 +1,210 @@
1
+ # PyParticles : Particles simulation in python
2
+ # Copyright (C) 2012 Simone Riva
3
+ #
4
+ # This program is free software: you can redistribute it and/or modify
5
+ # it under the terms of the GNU General Public License as published by
6
+ # the Free Software Foundation, either version 3 of the License, or
7
+ # (at your option) any later version.
8
+ #
9
+ # This program is distributed in the hope that it will be useful,
10
+ # but WITHOUT ANY WARRANTY; without even the implied warranty of
11
+ # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
+ # GNU General Public License for more details.
13
+ #
14
+ # You should have received a copy of the GNU General Public License
15
+ # along with this program. If not, see <http://www.gnu.org/licenses/>.
16
+
17
+
18
+ import numpy as np
19
+
20
+ import pyparticles.geometry.transformations as tr
21
+
22
+ from OpenGL.GL import *
23
+
24
+
25
+ class AxisOgl(object):
26
+ def __init__(self):
27
+ self.__arrow_len = 5.0
28
+ self.__dl_axis = None
29
+
30
+ def __del__(self):
31
+ if self.__dl_axis != None :
32
+ glDeleteLists( self.__dl_axis , 1 )
33
+
34
+ def ogl_init( self ):
35
+
36
+ self.__dl_axis = glGenLists(1)
37
+
38
+ glNewList( self.__dl_axis , GL_COMPILE );
39
+ self.draw_axis_procedure()
40
+ glEndList()
41
+
42
+
43
+ def get_axis_len(self):
44
+ return self.__arrow_len
45
+
46
+ def set_axis_len( self , leng ):
47
+ self.__arrow_len = leng
48
+
49
+ axis_len = property( get_axis_len , set_axis_len )
50
+
51
+ def draw_axis( self ):
52
+ glCallList( self.__dl_axis )
53
+
54
+
55
+ def draw_axis_procedure(self):
56
+ self.draw_arrow( ( 1.0 , 0.0 , 0.0 ) , "x" )
57
+ self.draw_arrow( ( 0.0 , 1.0 , 0.0 ) , "y" )
58
+ self.draw_arrow( ( 0.0 , 0.0 , 1.0 ) , "z" )
59
+
60
+ self.draw_arrow( ( 1.0 , 0.0 , 0.0 ) , "-x" )
61
+ self.draw_arrow( ( 0.0 , 1.0 , 0.0 ) , "-y" )
62
+ self.draw_arrow( ( 0.0 , 0.0 , 1.0 ) , "-z" )
63
+
64
+ for pl in self.axis_planes_codes():
65
+ self.draw_plane( pl )
66
+
67
+ def axis_planes_codes(self):
68
+ return [ "xy" , "x-y" , "-xy" , "-x-y" , "xz" , "x-z" , "-xz" , "-x-z" , "yz" , "y-z" , "-yz" , "-y-z" ]
69
+
70
+
71
+ def draw_plane( self , plane="xy", color=( 0.7 , 0.7 , 0.7 , 0.3 ) , leng=None ):
72
+
73
+ if leng == None :
74
+ leng = self.axis_len
75
+
76
+
77
+ t = tr.Transformations()
78
+ t.set_points_tuple_size(2)
79
+
80
+ if plane == "xy" :
81
+ t.rotX( np.radians(0) )
82
+ elif plane == "yz" :
83
+ t.rotY( np.radians(90) )
84
+ elif plane == "xz" :
85
+ t.rotX( np.radians(90) )
86
+ elif plane == "-yz" :
87
+ t.rotX( np.radians(180) )
88
+ t.rotY( np.radians(90) )
89
+ elif plane == "-y-z" :
90
+ t.rotX( np.radians(180) )
91
+ t.rotY( np.radians(-90) )
92
+ elif plane == "y-z" :
93
+ t.rotY( np.radians(-90) )
94
+ elif plane == "x-y" :
95
+ t.rotX( np.radians(180) )
96
+ elif plane == "-x-y" :
97
+ t.rotX( np.radians(180) )
98
+ t.rotY( np.radians(180) )
99
+ elif plane == "x-z" :
100
+ t.rotX( np.radians(-90) )
101
+ elif plane == "-x-z" :
102
+ t.rotX( np.radians(-90) )
103
+ t.rotZ( np.radians(180) )
104
+ elif plane == "-xz" :
105
+ t.rotX( np.radians(90) )
106
+ t.rotZ( np.radians(180) )
107
+ elif plane == "-x-z" :
108
+ t.rotX( np.radians(-90) )
109
+ t.rotZ( np.radians(180) )
110
+ elif plane == "-xy" :
111
+ t.rotY( np.radians(180) )
112
+
113
+ for i in range( 1 , int(leng) ):
114
+ t.append_point( [ float(i) , 0.0 , 0.0 ] )
115
+ t.append_point( [ float(i) , leng , 0.0 ] )
116
+
117
+ t.append_point( [ 0.0 , float(i) , 0.0 ] )
118
+ t.append_point( [ leng , float(i) , 0.0 ] )
119
+
120
+ glColor4f( color[0] , color[1] , color[2] , color[3] )
121
+
122
+ glBegin(GL_LINES)
123
+
124
+ for pts in t :
125
+ glVertex3fv( pts[0] )
126
+ glVertex3fv( pts[1] )
127
+
128
+ glEnd()
129
+
130
+
131
+ #t.set_points_tuple_size(4)
132
+ #
133
+ #t.append_point( [ 0.0 , 0.0 , 1.0 ] )
134
+ #t.append_point( [ 0.0 , 0.0 , 0.0 ] )
135
+ #t.append_point( [ leng , 0.0 , 0.0 ] )
136
+ #t.append_point( [ leng , leng , 0.0 ] )
137
+ #
138
+ #t.append_point( [ 0.0 , 0.0 , 1.0 ] )
139
+ #t.append_point( [ 0.0 , 0.0 , 0.0 ] )
140
+ #t.append_point( [ leng , leng , 0.0 ] )
141
+ #t.append_point( [ 0.0 , leng , 0.0 ] )
142
+ #
143
+ #glPolygonMode(GL_FRONT_AND_BACK, GL_FILL)
144
+ #
145
+ #glColor4f( color[0] , color[1] , color[2] , 1.0 )
146
+ #
147
+ #glBegin( GL_TRIANGLES )
148
+ #for pts in t :
149
+ # glNormal3fv( pts[0] )
150
+ # glVertex3fv( pts[1] )
151
+ # glVertex3fv( pts[2] )
152
+ # glVertex3fv( pts[3] )
153
+ #glEnd()
154
+
155
+
156
+
157
+
158
+ def draw_arrow( self , color , axis , leng=None ):
159
+
160
+ if leng == None :
161
+ leng = self.axis_len
162
+
163
+ arrh = leng * 0.1
164
+ arrp = leng - arrh
165
+
166
+ dash = leng * 0.03
167
+
168
+ t = tr.Transformations()
169
+ t.set_points_tuple_size(2)
170
+
171
+ if axis == "x" :
172
+ t.rotX( np.radians(0) )
173
+ elif axis == "y" :
174
+ t.rotZ( np.radians(90) )
175
+ elif axis == "z" :
176
+ t.rotY( np.radians(-90) )
177
+ if axis == "-x" :
178
+ t.rotZ( np.radians(180) )
179
+ elif axis == "-y" :
180
+ t.rotZ( np.radians(-90) )
181
+ elif axis == "-z" :
182
+ t.rotY( np.radians(90) )
183
+
184
+ t.append_point( np.array( [ 0.0 , 0.0 , 0.0 ] ) )
185
+ t.append_point( np.array( [ leng , 0.0 , 0.0 ] ) )
186
+
187
+ t.append_point( np.array( [ leng , 0.0 , 0.0 ] ) )
188
+ t.append_point( np.array( [ arrp , -arrh , 0.0 ] ) )
189
+
190
+ t.append_point( np.array( [ leng , 0.0 , 0.0 ] ) )
191
+ t.append_point( np.array( [ arrp , arrh , 0.0 ] ) )
192
+
193
+ for i in range( 1 , int(leng) ):
194
+ t.append_point( [ float(i) , dash , 0.0 ] )
195
+ t.append_point( [ float(i) , -dash , 0.0 ] )
196
+
197
+ glColor3f( color[0] , color[1] , color[2] )
198
+
199
+ glBegin(GL_LINES)
200
+
201
+ for pts in t :
202
+ glVertex3fv( pts[0] )
203
+ glVertex3fv( pts[1] )
204
+
205
+
206
+ glEnd()
207
+
208
+
209
+
210
+
@@ -0,0 +1,313 @@
1
+
2
+ # PyParticles : Particles simulation in python
3
+ # Copyright (C) 2012 Simone Riva
4
+ #
5
+ # This program is free software: you can redistribute it and/or modify
6
+ # it under the terms of the GNU General Public License as published by
7
+ # the Free Software Foundation, either version 3 of the License, or
8
+ # (at your option) any later version.
9
+ #
10
+ # This program is distributed in the hope that it will be useful,
11
+ # but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13
+ # GNU General Public License for more details.
14
+ #
15
+ # You should have received a copy of the GNU General Public License
16
+ # along with this program. If not, see <http://www.gnu.org/licenses/>.
17
+
18
+ import pyparticles.pset.particles_set as ps
19
+
20
+ import numpy as np
21
+
22
+ from OpenGL.GL import *
23
+ from OpenGL.GLUT import *
24
+ from OpenGL.GLU import *
25
+
26
+
27
+ def charged_particles_color( pset , i ):
28
+ a = 0.4
29
+
30
+ if pset.Q[i] > 0.0 :
31
+ return ( 1.0 , a , a , 1.0 )
32
+ elif pset.Q[i] < 0.0 :
33
+ return ( a , a , 1.0 , 1.0 )
34
+ else :
35
+ return ( a , a , a , 1.0 )
36
+
37
+
38
+ def rand_vect_colors( RGBA , pset ):
39
+ RGBA[:] = np.random.rand( pset.size , 4 )
40
+
41
+
42
+ def charged_particles_vect_color( RGBA , pset ):
43
+ a = 0.4
44
+
45
+ i, foo = np.where( pset.Q > 0.0 )
46
+ RGBA[ i , : ] = np.array( [ 1.0 , a , a , 1.0 ] )
47
+
48
+ i, foo = np.where( pset.Q < 0.0 )
49
+ RGBA[ i , : ] = np.array( [ a , a , 1.0 , 1.0 ] )
50
+
51
+ i, foo = np.where( pset.Q == 0.0 )
52
+ RGBA[ i , : ] = np.array( [ a , a , a , 1.0 ] )
53
+
54
+
55
+ class DrawParticlesGL(object):
56
+
57
+ DRAW_MODEL_LOOP = 0
58
+ DRAW_MODEL_VECTOR = 1
59
+
60
+ PARTICLE_MODEL_POINT = "point"
61
+ PARTICLE_MODEL_SPHERE = "sphere"
62
+ PARTICLE_MODEL_TEAPOT = "teapot"
63
+
64
+ def __init__( self , pset=None ):
65
+ self.pset = pset
66
+ self.__trajectory = False
67
+ self.__trajectory_step = 1
68
+
69
+ self.__color_fun = lambda pset , i : ( 1.0 , 1.0 , 1.0 , 1.0 )
70
+
71
+ self.__vect_color_fun = None
72
+ self.__vect_color_fun_fl = False
73
+
74
+ self.__draw_particle = self.draw_particle
75
+
76
+ self.__sph_dl = None
77
+ self.__tea_dl = None
78
+ self.__pt_dl = None
79
+
80
+ self.__draw_model = self.DRAW_MODEL_LOOP
81
+
82
+ self.__init_vect_fl = False
83
+
84
+ self.__log_indices = None
85
+ self.__log_array = None
86
+
87
+
88
+ def __del__(self):
89
+ if self.__sph_dl != None :
90
+ glDeleteLists( self.__sph_dl , 1 )
91
+
92
+ if self.__tea_dl != None :
93
+ glDeleteLists( self.__tea_dl , 1 )
94
+
95
+ if self.__pt_dl != None :
96
+ glDeleteLists( self.__pt_dl , 1 )
97
+
98
+
99
+ def ogl_init(self):
100
+ """
101
+ Initialize opengl display lists (must be called after glutInit!)
102
+ """
103
+ self.init_sphere_dl()
104
+ self.init_teapot_dl()
105
+
106
+
107
+ #######################
108
+ def get_pset(self):
109
+ return self.__pset
110
+
111
+ def set_pset(self , pset):
112
+ self.__pset = pset
113
+
114
+ pset = property( get_pset , set_pset )
115
+
116
+ ########################
117
+ def set_color_fun( self , fun ):
118
+ self.__color_fun = fun
119
+
120
+ def get_color_fun( self , fun ):
121
+ return self.__color_fun
122
+
123
+ color_fun = property( get_color_fun , set_color_fun , doc="Set and get the function for calculating the particle color:\n"
124
+ " definition of the function color,"
125
+ " it take as args a particle_set obj. and the particle index "
126
+ " \n (R,G,B,A) = cfun( pset , index ) " )
127
+
128
+ def set_vect_color_fun( self , fun ):
129
+ self.__vect_color_fun = fun
130
+
131
+ def get_vect_color_fun( self , fun ):
132
+ return self.__vect_color_fun
133
+
134
+ vect_color_fun = property( get_vect_color_fun , set_vect_color_fun , doc="get and set the vector color function")
135
+
136
+
137
+ def get_trajectory( self ) :
138
+ return self.__trajectory
139
+
140
+ def set_trajectory( self , tr ):
141
+ self.__trajectory = tr
142
+
143
+ trajectory = property( get_trajectory , set_trajectory , doc="enable or disable the trajectory" )
144
+
145
+
146
+ def get_trajectory_step( self ) :
147
+ return self.__trajectory_step
148
+
149
+ def set_trajectory_step( self , trs ):
150
+ self.__trajectory_step = trs
151
+
152
+ trajectory_step = property( get_trajectory_step , set_trajectory_step , doc="set or get the step for drawing the trajectory" )
153
+
154
+
155
+ def init_sphere_dl(self):
156
+ self.__sph_dl = glGenLists(1)
157
+ glNewList( self.__sph_dl , GL_COMPILE );
158
+ glutSolidSphere( 1.0 , 10 , 10 )
159
+ glEndList()
160
+
161
+
162
+ def init_teapot_dl(self):
163
+ self.__tea_dl = glGenLists(1)
164
+ glNewList( self.__tea_dl , GL_COMPILE );
165
+ glutSolidTeapot( 1.0 )
166
+ glEndList()
167
+
168
+
169
+
170
+ def set_particle_model( self , model="" , user_fun=None ):
171
+
172
+ if model == "point" :
173
+ self.__draw_particle = self.draw_particle
174
+ elif model == "sphere" :
175
+ self.__draw_particle = self.draw_particle_sphere
176
+ elif model == "teapot" :
177
+ self.__draw_particle = self.draw_particle_teapot
178
+
179
+
180
+ def set_draw_model( self , model ):
181
+ self.__draw_model = model
182
+
183
+
184
+ def draw_trajectory(self):
185
+
186
+ if self.pset.log_size < self.trajectory_step + 1 :
187
+ return
188
+
189
+ if self.__log_indices == None :
190
+ self.__log_indices = self.pset.get_log_indices_segments( True )
191
+ self.__log_array = np.zeros( ( self.pset.log_max_size , self.pset.dim ) )
192
+
193
+ unit = self.pset.unit
194
+ glLineWidth( 1.0 )
195
+
196
+ for i in range( self.pset.size ):
197
+ glColor4f( *self.__color_fun( self.pset , i ) )
198
+
199
+ glEnableClientState(GL_VERTEX_ARRAY)
200
+
201
+ ( b , e ) = self.pset.read_log_array( i , ( self.__log_array, ) )
202
+
203
+ glVertexPointer( 3 , GL_FLOAT , 0 , self.__log_array / unit )
204
+
205
+ glDrawElements( GL_LINES , e , GL_UNSIGNED_INT , self.__log_indices )
206
+
207
+ glDisableClientState(GL_VERTEX_ARRAY)
208
+
209
+
210
+ def get_pcolor(self):
211
+ return
212
+
213
+
214
+ def draw_particle( self , pset , i ):
215
+ glPointSize( 0.01 + self.pset.M[i] / self.pset.mass_unit )
216
+ glColor4f( *self.__color_fun( pset , i ) )
217
+
218
+ glBegin(GL_POINTS)
219
+
220
+ glVertex3f( self.pset.X[i,0] / self.pset.unit ,
221
+ self.pset.X[i,1] / self.pset.unit ,
222
+ self.pset.X[i,2] / self.pset.unit )
223
+
224
+ glEnd()
225
+
226
+
227
+ def draw_particle_sphere( self , pset , i ):
228
+
229
+ radius = 0.5 * ( 0.05 + 0.1 / ( 1.0 + np.exp( -self.pset.M[i] / self.pset.mass_unit ) ) )
230
+
231
+ glColor4f( *self.__color_fun( pset , i ) )
232
+ glPushMatrix()
233
+ glTranslatef( self.pset.X[i,0] / self.pset.unit ,
234
+ self.pset.X[i,1] / self.pset.unit ,
235
+ self.pset.X[i,2] / self.pset.unit )
236
+
237
+ glScalef( radius , radius , radius )
238
+ glCallList( self.__sph_dl )
239
+
240
+ glPopMatrix()
241
+
242
+
243
+ def draw_particle_teapot( self , pset , i ):
244
+
245
+ radius = 0.5 * ( 0.05 + 0.1 / ( 1.0 + np.exp( -self.pset.M[i] / self.pset.mass_unit ) ) )
246
+
247
+ glColor4f( *self.__color_fun( pset , i ) )
248
+ glPushMatrix()
249
+ glTranslatef( self.pset.X[i,0] / self.pset.unit ,
250
+ self.pset.X[i,1] / self.pset.unit ,
251
+ self.pset.X[i,2] / self.pset.unit )
252
+
253
+ glScalef( radius , radius , radius )
254
+ glCallList( self.__tea_dl )
255
+
256
+ glPopMatrix()
257
+
258
+ def _draw_vectorized(self):
259
+
260
+ if not self.__init_vect_fl :
261
+ self.__indices = np.arange( self.pset.size * 3 , dtype=np.uint )
262
+ self.__init_vect_fl = True
263
+
264
+ if not self.__vect_color_fun_fl and self.__vect_color_fun != None :
265
+ self.__color_vect = np.zeros(( self.pset.size , 4 ))
266
+ self.__vect_color_fun( self.__color_vect , self.pset )
267
+ self.__vect_color_fun_fl = True
268
+
269
+ #glColor4f( *self.__color_fun( self.pset , 1 ) )
270
+
271
+ if self.__vect_color_fun_fl :
272
+ glEnableClientState(GL_COLOR_ARRAY)
273
+
274
+ glEnableClientState(GL_VERTEX_ARRAY)
275
+
276
+ if self.__vect_color_fun_fl :
277
+ glColorPointer( 4 , GL_FLOAT , 0 , self.__color_vect )
278
+
279
+ glVertexPointer( 3 , GL_FLOAT , 0 , self.pset.X / self.pset.unit )
280
+ glDrawElements( GL_POINTS , self.pset.size , GL_UNSIGNED_INT , self.__indices )
281
+
282
+ glDisableClientState(GL_VERTEX_ARRAY)
283
+
284
+ if self.__vect_color_fun_fl :
285
+ glDisableClientState(GL_COLOR_ARRAY)
286
+
287
+
288
+ def draw(self):
289
+
290
+ if self.__draw_model == self.DRAW_MODEL_LOOP :
291
+ glPointParameterf( GL_POINT_SIZE_MAX , 10.0 )
292
+ glPointParameterf( GL_POINT_SIZE_MIN , 4.0 )
293
+
294
+ glEnable(GL_POINT_SMOOTH)
295
+
296
+ for i in range( self.pset.size ):
297
+ self.__draw_particle( self.pset , i )
298
+
299
+ if self.pset.log_X_enabled and self.trajectory :
300
+ self.draw_trajectory()
301
+
302
+ elif self.__draw_model == self.DRAW_MODEL_VECTOR :
303
+ self._draw_vectorized()
304
+
305
+
306
+
307
+
308
+
309
+
310
+
311
+
312
+
313
+