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,608 @@
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 matplotlib.animation as animation
19
+
20
+
21
+
22
+ from mpl_toolkits.mplot3d import Axes3D
23
+ import matplotlib.pyplot as plt
24
+ import matplotlib
25
+ import numpy as np
26
+
27
+ import pyparticles.animation.animated_scatter as anim
28
+
29
+ import pyparticles.pset.particles_set as ps
30
+
31
+ import pyparticles.animation as pan
32
+
33
+ import pyparticles.pset.rand_cluster as clu
34
+ import pyparticles.forces.gravity as gr
35
+ import pyparticles.ode.euler_solver as els
36
+ import pyparticles.ode.leapfrog_solver as lps
37
+ import pyparticles.ode.runge_kutta_solver as rks
38
+ import pyparticles.ode.stormer_verlet_solver as svs
39
+
40
+ import pyparticles.ode.midpoint_solver as mds
41
+
42
+ import numpy as np
43
+ import pyparticles.pset.periodic_boundary as pb
44
+ import pyparticles.pset.rebound_boundary as rb
45
+ import pyparticles.forces.const_force as cf
46
+ import pyparticles.forces.vector_field_force as vf
47
+ import pyparticles.forces.linear_spring as ls
48
+ import pyparticles.pset.file_cluster as fc
49
+
50
+ import re
51
+ import sys
52
+
53
+ if sys.version_info[0] == 2:
54
+ import ConfigParser
55
+ else:
56
+ import configparser as ConfigParser
57
+
58
+
59
+ import pyparticles.animation.animated_ogl as aogl
60
+
61
+
62
+ """
63
+
64
+ Config file
65
+ ===========
66
+
67
+ Config file description:
68
+
69
+ Section: pset_origin
70
+ --------------------
71
+
72
+ **Define the origin of the particles data set.**
73
+
74
+ **Varibles**
75
+
76
+ ========================== ========================
77
+ Variable Description
78
+ ========================== ========================
79
+ media_origin = [file|rand] Where data the is stored
80
+ file_name = <file> the dataset file name
81
+ ========================== ========================
82
+
83
+ Section: set_config
84
+ -------------------
85
+ **Particles data set configauration**
86
+
87
+ **Varibles:**
88
+
89
+ =========================== ==============================================
90
+ Variable Description
91
+ =========================== ==============================================
92
+ len_unit = <number> How many meters is a unit
93
+ mass_unit = <number> How many Kg is a unit
94
+ boundary = [open|periodic|rebound] The boundary model used in the simulation
95
+ boundary_lim = <#> <#> Define the size of the boundary
96
+ sim_log = <number> The size of the log queue (0 disable the log)
97
+ sim_log_X = [True|False] If sim_log is enabled log the position
98
+ sim_log_V = [True|False] If sim_log is enabled log the velocities
99
+ rand_part_nr = <number> The total number of particles for a rand set
100
+ =========================== ==============================================
101
+
102
+ Note: len_unit & mass_unit are used only for drawing the particles
103
+
104
+ Section: model
105
+ --------------
106
+ **Simulation method and force model**
107
+
108
+ **Varibles:**
109
+
110
+ ============================================================== =====================================
111
+ Variable Description
112
+ ============================================================== =====================================
113
+ force = [gravity|linear_spring|constant_force] Force type used
114
+ ode_solver_name = [euler|runge_kutta|leap_frog|midpoint] Integration method
115
+ time_step = <number> time step used for the integration
116
+ force_const = <number> Force constant, like G
117
+ force_vector= <number> Force vector, for the constant force
118
+ ============================================================== =====================================
119
+
120
+
121
+ Section: animation
122
+ ------------------
123
+ **Simulation control & graphic wiew**
124
+
125
+ **Variables:**
126
+
127
+ ============================================================== =================================================
128
+ Variable Description
129
+ ============================================================== =================================================
130
+ animation_type = [opengl|matplotlib] Setup the output interface
131
+ draw_log = [True|False] Draw the simulation log (if enabled)
132
+ xlim = <number> <number> define the limit of the picture (sometime unused)
133
+ ylim = <number> <number>
134
+ zlim = <number> <number>
135
+ ============================================================== =================================================
136
+
137
+
138
+ Example:
139
+ --------
140
+ ::
141
+
142
+ [pset_origin]
143
+ media_origin = from_file
144
+ file_name = solar_sys.csv
145
+
146
+ [set_config]
147
+ len_unit = 149597870700.0
148
+ mass_unit = 5.9736e24
149
+ boundary = open
150
+
151
+ [model]
152
+ force = gravity
153
+ ode_solver_name = euler
154
+ time_step = 3600
155
+ steps = 1000000
156
+ force_const = 6.67384e-11
157
+ force_vector = 0 0 0
158
+
159
+ [animation]
160
+ animation_type = opengl
161
+ xlim = -5.0 5.0
162
+ ylim = -5.0 5.0
163
+ zlim = -5.0 5.0
164
+
165
+ """
166
+
167
+
168
+ #ConfigParser.ConfigParser.add_comment = lambda self, section, option, value: self.set(section, '# '+option, value)
169
+
170
+
171
+
172
+
173
+ class ParticlesConfig(object):
174
+
175
+ """
176
+ Parse the config files used for generating the problems:
177
+ """
178
+ def __init__(self):
179
+
180
+ self.file_name = ""
181
+
182
+
183
+ self.default = {
184
+ # section pset_origin
185
+ 'media_origin': 'from_file' ,
186
+ 'file_name': 'solar_sys.csv' ,
187
+
188
+ # section set_config
189
+ 'len_unit': '149597870700.0' ,
190
+ 'mass_unit': '5.9736e24' ,
191
+ 'boundary': 'open' ,
192
+ 'boundary_lim': '-7 7' ,
193
+ 'sim_log': '0' ,
194
+ 'sim_log_X': 'True' ,
195
+ 'sim_log_V': 'False' ,
196
+ 'rand_part_nr': '500' ,
197
+
198
+ # section model
199
+ 'force': 'gravity' ,
200
+ 'ode_solver_name': 'euler' ,
201
+ 'time_step': '3600' ,
202
+ 'steps': '1000000' ,
203
+ 'force_const': '6.67384e-11' ,
204
+ 'force_vector': '0 0 0' ,
205
+
206
+ # section animation
207
+ 'animation_type': 'opengl' ,
208
+ 'draw_trajectory': 'False' ,
209
+ 'trajectory_step': '15' ,
210
+ 'xlim': '-5.0 5.0' ,
211
+ 'ylim': '-5.0 5.0' ,
212
+ 'zlim': '-5.0 5.0' ,
213
+
214
+ # section rand_cluster_*
215
+ 'rc_part_nr': '100' ,
216
+ 'rc_centre': '0 0 0' ,
217
+ 'rc_radius': '1.0' ,
218
+ 'rc_mass_rng': '0.5 1.5' ,
219
+ 'rc_vel_rng': '0.5 1.0' ,
220
+ 'rc_vel_mdl': 'no' ,
221
+ 'rc_vel_dir': '0 1 0' ,
222
+ 'rc_r_min': '0.0' ,
223
+ }
224
+
225
+ def write_example_config_file( self , file_name='example_pyparticles_config.cfg' ):
226
+ """ Write a generic config file """
227
+ config = ConfigParser.ConfigParser()
228
+
229
+ config.add_section('pset_origin')
230
+ config.set('pset_origin', 'media_origin', 'from_file')
231
+ config.set('pset_origin', 'file_name', 'solar_sys.csv')
232
+
233
+ config.add_section('set_config')
234
+ config.set('set_config', 'len_unit', '149597870700.0')
235
+ config.set('set_config', 'mass_unit', '5.9736e24')
236
+ config.set('set_config', 'boundary', 'open')
237
+ config.set('set_config', 'boundary_lim', '-7 7')
238
+ config.set('set_config', 'sim_log', '0')
239
+ config.set('set_config', 'sim_log_X', 'True')
240
+ config.set('set_config', 'sim_log_V', 'False')
241
+ config.set('set_config', 'rand_part_nr', '500')
242
+
243
+ config.add_section('model')
244
+ config.set('model', 'force', 'gravity')
245
+ config.set('model', 'ode_solver_name', 'euler')
246
+ config.set('model', 'time_step', '3600')
247
+ config.set('model', 'steps', '1000000')
248
+ config.set('model', 'force_const', '6.67384e-11')
249
+ config.set('model' , 'force_vector' , '0 0 0' )
250
+
251
+
252
+ config.add_section('animation')
253
+ config.set('animation', 'animation_type', 'opengl')
254
+ config.set('animation', 'draw_trajectory', 'False')
255
+ config.set('animation', 'trajectory_step', '15')
256
+ config.set('animation', 'xlim', '-5.0 5.0')
257
+ config.set('animation', 'ylim', '-5.0 5.0')
258
+ config.set('animation', 'zlim', '-5.0 5.0')
259
+
260
+ config.add_section('rand_cluster_any')
261
+ config.set('rand_cluster_any', 'rc_part_nr', '100')
262
+ config.set('rand_cluster_any', 'rc_centre', '0 0 0')
263
+ config.set('rand_cluster_any', 'rc_radius', '1.0')
264
+ config.set('rand_cluster_any', 'rc_mass_rng', '0.5 1.0')
265
+ config.set('rand_cluster_any', 'rc_vel_rng', '0.5 1.0')
266
+ config.set('rand_cluster_any', 'rc_vel_mdl', 'bomb')
267
+ config.set('rand_cluster_any', 'rc_vel_dir', '0 1 0')
268
+ config.set('rand_cluster_any', 'rc_r_min', '0.0')
269
+
270
+ # Writing our configuration file to 'example.cfg'
271
+ with open( file_name , 'wb' ) as configfile:
272
+ config.write(configfile)
273
+
274
+
275
+ ###################################################################
276
+ ## read and parse config file
277
+ ###################################################################
278
+ def read_config( self , file_name ):
279
+ """
280
+ Read the configuration file
281
+ """
282
+
283
+ self.file_name = file_name
284
+
285
+ config = ConfigParser.ConfigParser(self.default)
286
+
287
+ fp = None
288
+
289
+ try :
290
+ fp = open( file_name )
291
+ except IOError:
292
+ print(" Error - config file not fount: %s " % file_name )
293
+ exit()
294
+
295
+ config.readfp( fp )
296
+
297
+ #########################################################
298
+ ## Section pset_origin
299
+ self.media_origin = config.get( 'pset_origin' , 'media_origin' )
300
+ self.pset_file_name = config.get( 'pset_origin' , 'file_name' )
301
+
302
+ #########################################################
303
+ ## Section set_config
304
+ self.len_unit = config.getfloat( 'set_config' , 'len_unit' )
305
+ self.mass_unit = config.getfloat( 'set_config' , 'mass_unit' )
306
+ self.boudary = config.get( 'set_config' , 'boundary' )
307
+ self.boudary_lim = config.get( 'set_config' , 'boundary_lim' )
308
+ self.sim_log = config.getint( 'set_config' , 'sim_log' )
309
+ self.sim_log_X = config.getboolean( 'set_config' , 'sim_log_X' )
310
+ self.sim_log_V = config.getboolean( 'set_config' , 'sim_log_V' )
311
+ self.rand_part_nr= config.getint( 'set_config' , 'rand_part_nr' )
312
+
313
+ #########################################################
314
+ ## Section model
315
+ self.force_name = config.get( 'model' , 'force' )
316
+ self.ode_solver_name = config.get( 'model' , 'ode_solver_name' )
317
+ self.time_step = config.getfloat( 'model' , 'time_step' )
318
+ self.steps = config.getint( 'model' , 'steps' )
319
+ self.force_const = config.get( 'model' , 'force_const' )
320
+
321
+ if self.force_name == "constant_force" :
322
+ self.force_vector = config.get( 'model' , 'force_vector' , '-1 0 0' )
323
+
324
+ ###################################################################
325
+ ## Section animation
326
+ self.animation_type = config.get( 'animation' , 'animation_type' )
327
+ self.draw_trajectory = config.getboolean( 'animation' , 'draw_trajectory' )
328
+ self.trajectory_step = config.getint( 'animation' , 'trajectory_step' )
329
+
330
+ def build_problem( self ):
331
+ """
332
+ Build the main problem and return the four main objects:
333
+ return ( self.animation , self.pset , self.force , self.ode_solver )
334
+ """
335
+ self.get_particle_set()
336
+ self.get_force()
337
+ self.get_ode_solver()
338
+ self.get_animation()
339
+
340
+ return ( self.animation , self.pset , self.force , self.ode_solver )
341
+
342
+ ################################################################################
343
+ def get_particle_set( self ):
344
+ """
345
+ Build and return a set of particles (class: particles_set)
346
+ """
347
+
348
+ print("")
349
+
350
+ self.pset = ps.ParticlesSet()
351
+
352
+ if self.media_origin == "from_file" :
353
+ ff = fc.FileCluster()
354
+ ff.open( self.pset_file_name )
355
+ ff.insert3( self.pset )
356
+ ff.close()
357
+ print( " setup - particles set - file name: %s " % self.pset_file_name )
358
+
359
+ elif self.media_origin == "rand" :
360
+ self.pset.realloc( self.rand_part_nr , dim=3 )
361
+ self.__get_rand_clusters()
362
+ else:
363
+ print(" !! Error - particles set - media origin: %s don't exist " % self.media_origin )
364
+
365
+
366
+ print( " setup - particles set - size: %d " % self.pset.size )
367
+ print( " setup - particles set - dim: %d " % self.pset.dim )
368
+
369
+ self.pset.unit = self.len_unit
370
+ self.pset.mass_unit = self.mass_unit
371
+
372
+ print( " setup - particles set - len unit: %e " % self.pset.unit )
373
+ print( " setup - particles set - len mass unit: %e " % self.pset.mass_unit )
374
+
375
+
376
+
377
+ if self.boudary == "open" :
378
+ self.pset.boundary = None
379
+ print( " setup - particles set - Boundary: open " )
380
+
381
+ elif self.boudary == "periodic" :
382
+ bound = read_str_list( self.boudary_lim )
383
+ self.pset.boundary = pb.PeriodicBoundary( bound=bound , dim=self.pset.dim )
384
+ print( " setup - particles set - Boundary: periodic " )
385
+ print( " setup - particles set - Boundary size : %s " % (bound,) )
386
+
387
+ elif self.boudary == "rebound" :
388
+ bound = read_str_list( self.boudary_lim )
389
+ self.pset.boundary = rb.ReboundBoundary( bound=bound , dim=self.pset.dim )
390
+ print( " setup - particles set - Boundary: rebound " )
391
+ print( " setup - particles set - Boundary size : %s " % (bound,) )
392
+
393
+ if self.sim_log > 0 :
394
+ self.pset.enable_log( log_X=self.sim_log_X , log_V=self.sim_log_V , log_max_size=self.sim_log )
395
+
396
+ print( " setup - particles set - Simulation log size %d " % self.sim_log )
397
+ print( " setup - particles set - Simulation log : X = %r ; V = %r " % ( self.sim_log_X , self.sim_log_V ) )
398
+
399
+ #print( self.pset.X )
400
+ #print( self.pset.M )
401
+ #print( self.pset.V )
402
+
403
+ return self.pset
404
+
405
+ ################################################################################
406
+ def get_force(self):
407
+ """
408
+ Build and return an object for mdeling the force (derived form the abstract class force)
409
+ """
410
+ print("")
411
+
412
+ self.force = None
413
+
414
+ if self.force_name == "gravity" :
415
+ self.force = gr.Gravity( self.pset.size , self.pset.dim , Consts=float(self.force_const) )
416
+
417
+ print( " setup - force - Type: Gravity " )
418
+ print( " setup - force - G: %e " % float(self.force_const) )
419
+
420
+ elif self.force_name == "linear_spring" :
421
+ self.force = ls.LinearSpring( self.pset.size , self.pset.dim , Consts=self.force_const )
422
+
423
+ print( " setup - force - Type: Linear spring " )
424
+ print( " setup - force - K: %e " % float(self.force_const) )
425
+
426
+ elif self.force_name == "constant_force" :
427
+ fv = read_str_list( self.force_vector )
428
+
429
+ self.force = cf.ConstForce( self.pset.size , dim=self.pset.dim , u_force=fv )
430
+
431
+ print( " setup - force - Type: Constant " )
432
+ print( " setup - force - Vect: %e %e %e " % ( float(fv[0]) , float(fv[1]) , float(fv[2]) ) )
433
+
434
+ self.force.set_masses( self.pset.M )
435
+
436
+ return self.force
437
+
438
+ ################################################################################
439
+ def get_ode_solver(self):
440
+ """
441
+ Build and return an object for solving the Newton Law of motion (derived form the abstract class ode_solver)
442
+ """
443
+ print("")
444
+
445
+ self.ode_solver = None
446
+
447
+ if self.ode_solver_name == "euler" :
448
+ self.ode_solver = els.EulerSolver( self.force , self.pset , self.time_step )
449
+
450
+ print( " setup - Integration method: EULER " )
451
+
452
+ elif self.ode_solver_name == "runge_kutta" :
453
+ self.ode_solver = rks.RungeKuttaSolver( self.force , self.pset , self.time_step )
454
+
455
+ print( " setup - Integration method: Runge Kutta " )
456
+
457
+ elif self.ode_solver_name == "leap_frog" :
458
+ self.ode_solver = lps.LeapfrogSolver( self.force , self.pset , self.time_step )
459
+
460
+ print( " setup - Integration method: Leap Frog " )
461
+
462
+ elif self.ode_solver_name == "stormer_verlet" :
463
+ self.ode_solver = svs.StormerVerletSolver( self.force , self.pset , self.time_step )
464
+
465
+ print( " setup - Integration method: Stormer Verlet " )
466
+
467
+ elif self.ode_solver_name == "midpoint" :
468
+ self.ode_solver = mds.MidpointSolver( self.force , self.pset , self.time_step )
469
+
470
+ print( " setup - Integration method: Midpoint " )
471
+
472
+ print( " setup - Integration method - time step: %e " % self.time_step )
473
+ return self.ode_solver
474
+
475
+ ################################################################################
476
+ def get_animation(self):
477
+ """
478
+ Build an Animation object and return the reference to the object
479
+ """
480
+ print("")
481
+
482
+ self.animation = None
483
+
484
+ if self.animation_type == "opengl" :
485
+ self.animation = aogl.AnimatedGl()
486
+
487
+ print(" setup - animation - type: OpenGL")
488
+
489
+
490
+ elif self.animation_type == "matplotlib" :
491
+ self.animation = anim.AnimatedScatter()
492
+
493
+ print(" setup - animation - type: MatPlotlib")
494
+
495
+ if self.draw_trajectory == True :
496
+ self.animation.trajectory = self.draw_trajectory
497
+ self.animation.trajectory_step = self.trajectory_step
498
+
499
+ print(" setup - animation - Draw trajectory : %r " % self.draw_trajectory )
500
+ print(" setup - animation - Trajectory step : %d " % self.trajectory_step )
501
+ if self.sim_log == 0 :
502
+ print(" !! Warning - animation - Trajectory will be not drawn: sim_log is disabled " )
503
+
504
+ self.animation.ode_solver = self.ode_solver
505
+ self.animation.pset = self.pset
506
+ self.animation.steps = self.steps
507
+
508
+
509
+ return self.animation
510
+
511
+ ################################################################################
512
+ def __get_rand_clusters(self):
513
+
514
+
515
+ # 'rc_part_nr': '100' ,
516
+ # 'rc_centre': '0 0 0' ,
517
+ # 'rc_radius': '1.0' ,
518
+ # 'rc_mass_rng': '0.5 1.5' ,
519
+ # 'rc_vel_rng': '0.5 1.0' ,
520
+ # 'rc_vel_mdl': 'const' ,
521
+ # 'rc_vel_dir': '0 1 0' ,
522
+
523
+ config = ConfigParser.ConfigParser(self.default)
524
+ config.read( self.file_name )
525
+
526
+ indx = 0
527
+
528
+ l_sec = config.sections()
529
+
530
+ for se in l_sec :
531
+ m = re.search( r"(^rand_cluster_\w+)" , se )
532
+
533
+ if m != None :
534
+ sect = m.group(1)
535
+ print(" setup - rand cluster - name : %s " % sect )
536
+
537
+ rc_part_nr = config.getfloat( sect , 'rc_part_nr' )
538
+ print(" setup - rand cluster - size : %d " % rc_part_nr )
539
+
540
+ rc_centre = config.get ( sect , 'rc_centre' )
541
+ rc_centre = read_str_list ( rc_centre , to=float )
542
+ print(" setup - rand cluster - centre : %s " % (rc_centre,) )
543
+
544
+ rc_radius = config.getfloat( sect , 'rc_radius' )
545
+ print(" setup - rand cluster - radius : %f " % rc_radius )
546
+
547
+ rc_mass_rng = config.get ( sect , 'rc_mass_rng' )
548
+ rc_mass_rng = read_str_list ( rc_mass_rng , to=float )
549
+ print(" setup - rand cluster - mass range : %s " % (rc_mass_rng,) )
550
+
551
+ rc_vel_rng = config.get ( sect , 'rc_vel_rng' )
552
+ rc_vel_rng = read_str_list ( rc_vel_rng , to=float )
553
+ print(" setup - rand cluster - velocity range : %s " % (rc_vel_rng,) )
554
+
555
+ rc_vel_dir = config.get ( sect , 'rc_vel_dir' )
556
+ rc_vel_dir = read_str_list ( rc_vel_dir , to=float )
557
+ print(" setup - rand cluster - velocity direction : %s " % (rc_vel_dir,) )
558
+
559
+ rc_vel_mdl = config.get ( sect , 'rc_vel_mdl' )
560
+ print(" setup - rand cluster - velocity model : %s " % (rc_vel_mdl,) )
561
+
562
+ rc_r_min = config.getfloat( sect , 'rc_r_min' )
563
+ print(" setup - rand cluster - minimal dist : %f " % rc_r_min )
564
+
565
+ cs = clu.RandCluster()
566
+
567
+ if ( indx + rc_part_nr ) > self.pset.size :
568
+ print(" !! Error the total size of the rand clusters is too big")
569
+ exit()
570
+
571
+ cs.insert3( X=self.pset.X ,
572
+ M=self.pset.M ,
573
+ V=self.pset.V ,
574
+ start_indx=indx ,
575
+ n = int(rc_part_nr) ,
576
+ centre=rc_centre ,
577
+ vel_rng=rc_vel_rng ,
578
+ vel_mdl=rc_vel_mdl ,
579
+ vel_dir=rc_vel_dir ,
580
+ r_min=rc_r_min
581
+ )
582
+
583
+ indx += rc_part_nr
584
+ print("")
585
+
586
+
587
+ def read_str_list( string , to=float ):
588
+
589
+ a = re.split( "\s+" , string )
590
+ c = a.count( "" )
591
+
592
+ for i in range(c):
593
+ a.remove("")
594
+
595
+ r = []
596
+ for i in a :
597
+ r.append( to(i) )
598
+
599
+ return tuple(r)
600
+
601
+
602
+
603
+
604
+
605
+
606
+
607
+
608
+