yade-users team mailing list archive
-
yade-users team
-
Mailing list archive
-
Message #21134
Re: [Question #685375]: Converting polyhedron body to Potential Particle or Potential Block
Question #685375 on Yade changed:
https://answers.launchpad.net/yade/+question/685375
Status: Open => Answered
Vasileios Angelidakis proposed the following answer:
Hi Ali,
In general your code works. Visualisation in qt fails due to a bug, which for now you can avoid. The temporary fix:
- Use len(O.bodies)-1 for the potential block. There is a bug in the visualisation code of the Potential Blocks, which assumes the ids of the Potential Blocks start from 0. Will fix this soon
Some comments on your script:
- For Vector3 types we have built-in functions to do standard calculations among vectors:
- dot product: v1.dot(v2)
- cross product: v1.cross(v2)
- norm (magnitude): v1.norm()
- subtraction: pp3=pp2-pp1 (you needn't do it separately for each item of the Vector3). Same for addition.
- normalize: pp3.normalize()
You can find these and many more if you type: "Vector3." + [tab] in the iPython interface! :)
Regarding the syntax of the PotentialBlocks:
> r=chosenR, R=chosenR
- Better use: r=chosenR, R=0.0. If R=0.0, an automatic value will be calculated, as the distance of the farthest vertices of the particle. You want "r" to be sufficiently small, while "R" to be around the dimensions of the particle.
> k=0.001
- The parameter "k" is not actively used in the PotentialBlocks, so you can set k=0.0 safely (or not even set a value for it at all); just don't spend any time thinking of what value to assign. ;)
> dv=dvalue2-chosenR
> if dv<0:
> vects=[-1*vects[0],-1*vects[1],-1*vects[2]]
> dv=-1*dv
- Check the sign of the "d[i]" values before subtracting "r". If d[i] is negative and you subtract "r", you are actually adding it. For some reason you seem to get the right particle shape here, but I think you should check twice if the particle shape you get is exactly correct (e.g. compare the vertices for the two particles, after assigning for them the same orientation).
- Do not use large "r" values: if dv<0: don't change the sign of dv; instead reduce "r". A change of sign here can lead to a different particle shape
Below some updates I would apply on your script.
All the best,
Vasileios
####################################################
from yade import pack,export,qt,ymport
import numpy as np
import math
import random
######################################################################
#def dotproduct(v1, v2):
# return sum((a*b) for a, b in zip(v1, v2))
#def length(v):
# return math.sqrt(dotproduct(v, v))
#def veccc(pp1,pp2):
# pp3=pp2-pp1 #pp3=[pp2[0]-pp1[0],pp2[1]-pp1[1],pp2[2]-pp1[2]]
# if pp3.norm()>0: # if length(pp3)>0:
# pp3.normalize() # pp3=[pp3[0]/length(pp3),pp3[1]/length(pp3),pp3[2]/length(pp3)]
# return pp3
####################################
### calculate d value of a surface with normal vector and one point
def dvalue(vecn1,pp1):
dd1=-1*(vecn1[0]*pp1[0]+vecn1[1]*pp1[1]+vecn1[2]*pp1[2])
return dd1
################################################################
powderDensity = 2000
distanceToCentre = 0.5
meanSize = 1.0
wallThickness = 0.5*meanSize
O.materials.append(FrictMat(young=-1,poisson=-1,frictionAngle=radians(0.0),density=powderDensity,label='frictionless')) #The normal and shear stifness values are determined in the IPhys functor, thus the young,
########################################
young = 1e9
density=2500
FricDegree1= atan(.6)
m = PolyhedraMat()
m.density = density
m.young = young
m.poisson = 0.25
m.frictionAngle = FricDegree1
c1=polyhedron((
[0.62500000,0.00000000,0.00000000],[0.62500000,0.50000000,0.00000000],[0.65382210,0.50000000,0.29263550],[0.65382210,0.00000000,0.29263550],[0.16342940,0.50000000,0.39018060],[0.16342940,0.00000000,0.39018060],[0.00000000,0.50000000,0.39018060],[0.00000000,0.00000000,0.39018060],[0.00000000,0.50000000,0.00000000],[0.00000000,0.00000000,0.00000000]),material=m)
O.bodies.append(c1)
chosenR=0.0001
for b in O.bodies:
aa=[]
bb=[]
cc=[]
dd=[]
if not isinstance(b.shape,Polyhedra): # skip non-polyhedra bodies
continue
vs = [b.state.pos + b.state.ori*v for v in b.shape.v] # vertices in global coords
face2=b.shape.GetSurfaces()
id1=0
while id1<len(face2):
face11=face2[id1]
if len(face11)>2:
vec1=vs[face11[2]]-vs[face11[1]]; vec1.normalize() #vec1=veccc(vs[face11[2]],vs[face11[1]])
vec2=vs[face11[0]]-vs[face11[1]]; vec2.normalize() #vec2=veccc(vs[face11[0]],vs[face11[1]])
# vects=[]
vects=vec1.cross(vec2) #vects = list(np.cross(vec1, vec2))
dvalue2=dvalue(vects,vs[face11[0]]) # Some dvalue2 values return equal to 0. Check this part of your script once more.
dv=dvalue2-chosenR
if dv<0:
vects=[-1*vects[0],-1*vects[1],-1*vects[2]]
dv=-1*dv
aa.append(vects[0])
bb.append(vects[1])
cc.append(vects[2])
dd.append(dv)
id1=id1+1
#### after that how can put correct values for PotentialBlock() ?????
bbb=Body()
wire=False
color=[0,0.5,1]
highlight=False
bbb.shape=PotentialBlock(k=0.0, r=chosenR, R=0.0, a=aa, b=bb, c=cc, d=dd, id=len(O.bodies)-1)
utils._commonBodySetup(bbb, bbb.shape.volume, bbb.shape.inertia,material='frictionless', pos=[0,0,0], fixed=False)
bbb.state.pos = [-1,0,0]
# bbb.state.ori=Quaternion((0,1,0),pi)
lidID = O.bodies.append(bbb)
###########################################################################
--
You received this question notification because your team yade-users is
an answer contact for Yade.