Finding where a bond broke

Asked by mrhappy on 2020-02-20

Hi,

In my model, I have 3D spheres aligned in the x-y plane (100 by 100). Each sphere is bonded with its neighboring spheres. There is a precrack in the model and I am applying a force field within the precrack. Once the model runs, the crack opens up and starts to propagate. Within the simulation I want to do the following:

If a new bond breaks:
        El1 = #element#1;
        El2 = #element#2;
        O.forces.setPermF(El1,(0,0.01000*O.time,0))
        O.forces.setPermF(El2,(0,-0.01000*O.time,0))

I hope you understand. Basically, once a bond breaks, I want to apply a force on the 2 element that the bond broke between. I know that I have to write a function script. If you can just tell me how to get the if condition activated once a new bond breaks and how to get the element numbers, that would be off great help.

Thanks!

# SIMULATION LOOP
O.engines=[
    PyRunner(command='addPlotData1()',iterPeriod=1),
    PyRunner(command='saveData1()',iterPeriod=1000),
    PyRunner(command='saveData2()',iterPeriod=1000),
    PyRunner(command='ForceBC1()',iterPeriod=1),
    PyRunner(command='ForceBC2()',iterPeriod=1),
    ForceResetter(),
    InsertionSortCollider([Bo1_Sphere_Aabb()]),
    InteractionLoop(
        [Ig2_Sphere_Sphere_ScGeom(interactionDetectionFactor=intR)],
        [Ip2_JCFpmMat_JCFpmMat_JCFpmPhys(cohesiveTresholdIteration=1)],
        [Law2_ScGeom_JCFpmPhys_JointedCohesiveFrictionalPM()]
    ),
    GlobalStiffnessTimeStepper(active=1,timeStepUpdateInterval=10,timestepSafetyCoefficient=0.5, defaultDt=utils.PWaveTimeStep()),
    NewtonIntegrator(damping= 0.80),
]

Question information

Language:
English Edit question
Status:
Solved
For:
Yade Edit question
Assignee:
No assignee Edit question
Solved by:
mrhappy
Solved:
2020-02-21
Last query:
2020-02-21
Last reply:
2020-02-20
Robert Caulk (rcaulk) said : #1

I guess you could keep a list of non-cohesive interaction IDs. Get a new list of non-cohesive interaction ids at each time step and compare the two lists. Any ID that is on the new list is a newly broken bond. Then you can apply your force logic to the bodies associated with that bond.

Jan Stránský (honzik) said : #2

Just a performance hint, use python set (not list) for this kind of task. In your case, storing (i.id1,i.id2) tuple into the set should perform well. You can then easily do set difference to find broken bonds.
cheers
Jan

Robert Caulk (rcaulk) said : #3

Good to know, Jan ;-)

mrhappy (mrhappy) said : #4

Thank you guys!
I will try it now.

Robert Caulk (rcaulk) said : #5

Would love to see your final solution posted to this thread for future users ;-)

mrhappy (mrhappy) said : #6

Here is my final solution:
#SET This stores all connections. 1 means intact and 0 means broken.
Connectivity = [[5000, 4900, 1],
[5001, 4901, 1],
[5002, 4902, 1],
[5003, 4903, 1],
[5004, 4904, 1],
[5005, 4905, 0],
[5006, 4906, 0],
[5007, 4907, 1],
[5008, 4908, 1],
]

#This function is called every loop to check which bond has broken
def BreakingBonds():
 CurrentBonds = 0
  for i in O.interactions:
        CurrentBonds+=1
 if Bonds0 > CurrentBonds:
  global Bonds0
  Bonds0 = Bonds0 - 1
  print("BROKEN!")
        m = 0
        for row in Connectivity:
                if (Connectivity[m][2] == 1):
                        if (O.interactions[Connectivity[m][1],Connectivity[m][0]].phys.isBroken == True):
                             Connectivity[m][2] = 0
                m = m + 1