'''
Test loading and saving woo objects in various formats
'''
import woo
import unittest
from woo.core import *
from woo.dem import *
from minieigen import *
[docs]class TestDemField(unittest.TestCase):
[docs] def testGuessMoving(self):
'DEM: correctly guess that Node.dem needs motion integration'
d=DemData(blocked='',mass=0)
self.assertTrue(d.guessMoving()==False) # zero mass, don't move
d=DemData(blocked='xyz',mass=0)
self.assertTrue(d.guessMoving()==False) # zero mass, don't move
d=DemData(blocked='xyzXY',mass=1)
self.assertTrue(d.guessMoving()==True) # something not blocked, move
d=DemData(blocked='xyzXYZ',mass=1)
self.assertTrue(d.guessMoving()==False) # everything blocked, not move
d=DemData(blocked='xyzXYZ',vel=(1,1,1),mass=1)
self.assertTrue(d.guessMoving()==True) # velocity assigned, move
[docs]class TestImpose(unittest.TestCase):
[docs] def testCombinedImpose(self):
'DEM: CombinedImpose created from Impose()+Impose()'
a,b,c=CircularOrbit(),ReadForce(),ConstantForce()
d=a+b
# normal + normal, instantiates CombinedImpose
self.assertTrue(d.imps==[a,b])
self.assertTrue(d.what==(a.what | b.what)) # what is OR'd from imps
# flattening additions
# combined + combined
self.assertTrue((d+d).imps==[a,b,a,b])
# combined + normal
self.assertTrue((d+c).imps==[a,b,c])
# normal + combined
self.assertTrue((c+d).imps==[c,a,b])
[docs] def testCombinedImposeFunction(self):
'DEM: CombinedImpose combines impositions'
a=VariableAlignedRotation(axis=0,timeAngVel=[(0,0),(1,1),(2,1)],wrap=False)
b=VariableVelocity3d(times=[0,1,2],vels=[(0,0,0),(3,3,3),(3,3,3)])
c=InfCylinder.make((0,0,0),radius=.2,axis=1)
c.impose=a+b # impose both
S=woo.core.Scene(fields=[DemField(par=[c])],engines=DemField.minimalEngines(verletDist=0.),dt=1e-3,stopAtTime=1.2)
S.run(); S.wait()
self.assertTrue(c.vel==Vector3(3,3,3))
self.assertTrue(c.angVel[0]==1.)
[docs] def testUselessRotationImpose(self):
'DEM: selfTest error when imposing rotation on aspherical particles (would have no effect)'
for i in VariableAlignedRotation(axis=0,timeAngVel=[(0,0)]),InterpolatedMotion(),Local6Dofs(whats=(0,0,0,1,1,1)),VariableVelocity3d(times=[0,1],vels=[(0,0,0),(0,0,0)],angVels=[(0,0,0),(0,0,0)]):
a=Capsule.make((0,0,0),radius=.3,shaft=.6,ori=Quaternion((1,0,0),1))
a.impose=i
S=woo.core.Scene(fields=[DemField(par=[a])],engines=DemField.minimalEngines(verletDist=0.))
self.assertRaises(RuntimeError,lambda : S.selfTest())
[docs] def testInterpolatedMotion(self):
'DEM: InterpolatedMotion computes correct position and rotation'
import math
a=Capsule.make((0,0,0),radius=.3,shaft=.6,ori=Quaternion.Identity)
p1,p2=Vector3(1,1,1),Vector3(0,0,0)
q1,q2=Quaternion((.3,.4,.5),3.1415).normalized(),Quaternion((-.5,-.4,1),-.7).normalized()
a.impose=InterpolatedMotion(poss=[a.pos,p1,p2],oris=[a.ori,q1,q2],times=[0,.2,.4])
a.blocked='xyzXYZ' # must be blocked otherwise we get an error from selfTest
S=woo.core.Scene(fields=[DemField(par=[a])],engines=DemField.minimalEngines(verletDist=0),dt=1e-1)
S.run(10,True) # run in fg
dAngle=(q2.conjugate()*a.ori).toAxisAngle()[1]
if dAngle>math.pi: dAngle-=2*math.pi
dPos=(a.pos-p2).norm()
self.assertAlmostEqual(dAngle,0)
self.assertAlmostEqual(dPos,0)
[docs] def testVariableVelocity3d_rot(self):
'DEM: VariableVelocity3d imposition (angular velocity)'
a=Sphere.make((0,0,0),radius=.3)
t1,omega1=.2,1
a.impose=VariableVelocity3d(times=[0,t1],vels=[(0,0,0),(0,0,0)],angVels=[(0,0,0),(omega1,0,0)])
S=woo.core.Scene(fields=[DemField(par=[a])],engines=DemField.minimalEngines(verletDist=0.),stopAtTime=t1,dt=1e-4)
S.run(wait=True)
self.assertAlmostEqual(S.dem.nodes[0].ori.toAxisAngle()[1],.5*omega1*t1,delta=1e-3)