Python Tutorials | (back to the list of tutorials) |
add_library('igeo') def setup() : size(480,360,IG.GL) IG.duration(360) num=200 for i in range(num): pos = IG.v(100,0,0).rot(2*PI*i/num) vel = IG.v(-40,0,0).rot(2*PI*i/num) MyParticle(pos, vel).fric(0.012).hsb(1.0/num*i,1,1) for i in range(8) : Attractor(IRand.pt(-120,-120,0,80,80,0)).clr(1.0,0,0) class Attractor(IPointAgent) : threshold = 100 gravity = 300.0 minDist = 1.0 def __init__(self, v) : IPointAgent.__init__(self, v) def interact(self, agents) : for agent in agents : if isinstance(agent, MyParticle) : dif = self.pos().dif(agent.pos()) dist = dif.len() if dist < Attractor.threshold : if dist < Attractor.minDist : dist = Attractor.minDist strength = Attractor.gravity/dist #the closer the larger force = dif.len(strength) agent.push(force) class MyParticle(IParticle) : def __init__(self, p, v) : IParticle.__init__(self,p,v) self.prevPos = None def update(self) : curPos = self.pos().cp() if self.prevPos is not None : ICurve(self.prevPos, curPos).clr(self.clr()) self.prevPos = curPos
The next code below adds interaction method in MyParticle to introduce gravity between particles themselves. The particles are taking forces not only towards the attractor agents but also other particle agents.
add_library('igeo') def setup() : size(480,360,IG.GL) IG.duration(450) num=100 for i in range(num) : if IRand.pct(97) : pos = IG.v(100,0,0).rot(2*PI*i/num) vel = IG.v(-20,0,0).rot(2*PI*i/num) MyParticle(pos, vel).fric(0.001).hsb(1.0/num*i,1,1) for i in range(3) : Attractor(IRand.pt(-120,-120,0,80,80,0)).clr(1.0,0,0) class Attractor(IPointAgent) : threshold = 100 gravity = 300.0 minDist = 1.0 def __init__(self, v) : IPointAgent.__init__(self, v) def interact(self, agents) : for agent in agents : if isinstance(agent, MyParticle) : dif = self.pos().dif(agent.pos()) dist = dif.len() if dist < Attractor.threshold : if dist < Attractor.minDist : dist = Attractor.minDist strength = Attractor.gravity/dist #the closer the larger force = dif.len(strength) agent.push(force) class MyParticle(IParticle) : threshold = 30 gravity = 2.0 def __init__(self, p, v) : IParticle.__init__(self,p,v) self.prevPos = None def interact(self, agents) : center = None num = 0 for agent in agents : if isinstance(agent, MyParticle) : if agent is not self : if agent.pos().dist(self.pos()) < MyParticle.threshold : if center is None : center = agent.pos().dup() else : center.add(agent.pos()) num += 1 if num > 0 : center.div(num) force = center.dif(self.pos()).mul(MyParticle.gravity) self.push(force) def update(self) : curPos = self.pos().cp() if self.prevPos is not None : ICurve(self.prevPos, curPos).clr(self.clr()) self.prevPos = curPos
The code below shows behavior of the particle agents with self gravity among the particles without any external attractors. It also changes the initial configuration of particle agents putting them on two lines.
add_library('igeo') def setup() : size(480,360,IG.GL) IG.duration(250) num=100 for i in range(num) : for j in range(2) : if IRand.pct(70) : pos = IG.v(i, j*100, 0) vel = IG.v(0, (30-j*55), 0) MyParticle(pos,vel).fric(0.008).clr(IRand.clr()) class MyParticle(IParticle) : threshold = 15 gravity = 25.0 def __init__(self, p, v) : IParticle.__init__(self,p,v) self.prevPos = None def interact(self, agents) : center = None num = 0 for agent in agents : if isinstance(agent, MyParticle) : if agent is not self : if agent.pos().dist(self.pos()) < MyParticle.threshold : if center is None : center = agent.pos().dup() else : center.add(agent.pos()) num += 1 if num > 0 : center.div(num) force = center.dif(self.pos()).mul(MyParticle.gravity) self.push(force) def update(self) : curPos = self.pos().cp() if self.prevPos is not None : ICurve(self.prevPos, curPos).clr(self.clr()) self.prevPos = curPos