Tutorials (back to the list of tutorials)

## Physics Simulation and Swarm Examples

### Tension Example 1 (requires iGeo version 7.6.0 or higher)

This page shows an example of use of tension converting lines or curves into strings of tension and applying forces to them.

The first code below shows an algorithm to import curves from an external file and to create particles at divided points on each curve. Then each pair of particles in an array is connected again with tension lines.

The input file used in the code is tension_lines1.3dm.

```import processing.opengl.*;
import igeo.*;

size(480, 360, IG.GL);
IG.bg(0);
IG.open("tension_lines1.3dm");
ICurve[] curves = IG.curves();

int division=30;
double inc = 1.0/division;

for (int i=0; i < curves.length; i++) {
IParticle[] pts = new IParticle[division+1];
for (int j=0; j <= division; j++) { // creating particles
pts[j] = new IParticle( curves[i].pt( j*inc ) ).fric(0.01);
}
pts[0].fix(); // fixing the start point
pts[division].fix(); // fixing the end point
for (int j=0; j < division; j++) { // connecting particles
new ITensionLine(pts[j], pts[j+1]).tension(150).clr(1.0, 0.5).weight(2);
}
curves[i].del();
}
```

The next code applies forces to the tension lines with two attractors, one with attractive force and another with repulsive force.

```import processing.opengl.*;
import igeo.*;

size(480, 360, IG.GL);
IG.bg(0);
IG.open("tension_lines1.3dm");
ICurve[] curves = IG.curves();

new IAttractor(15, 6, 0).intensity(10).linear(30).clr(1.0,0,0).size(8);
new IAttractor(5, 4, 0).intensity(-30).linear(10).clr(1.0,0,0).size(8);

int division=30;
double inc = 1.0/division;

for (int i=0; i < curves.length; i++) {
IParticle[] pts = new IParticle[division+1];
for (int j=0; j <= division; j++) { // creating particles
pts[j] = new IParticle( curves[i].pt( j*inc ) ).fric(0.01);
}
pts[0].fix(); // fixing the start point
pts[division].fix(); // fixing the end point
for (int j=0; j < division; j++) { // connecting particles
new ITensionLine(pts[j], pts[j+1]).tension(150).clr(1.0, 0.5).weight(2);
}
curves[i].del();
}
```

This third code creates instances of swarm agent IBoid class, instead of particle instances. Because of forces between swarm, each node of tension strings attracts each other trying to form clusters but the tension still pulls them apart in certain directions.

```import processing.opengl.*;
import igeo.*;

size(480, 360, IG.GL);
IG.bg(0);
IG.open("tension_lines1.3dm");
ICurve[] curves = IG.curves();

int division=30;
double inc = 1.0/division;

for (int i=0; i < curves.length; i++) {
IBoid[] pts = new IBoid[division+1];
for (int j=0; j <= division; j++) { // creating particles
pts[j] = new IBoid( curves[i].pt( j*inc ) ).fric(0.1);
pts[j].cohesionDist(1);
pts[j].cohesionRatio(10);
pts[j].separationRatio(0);
pts[j].alignmentRatio(0);
}
pts[0].fix(); // fixing the start point
pts[division].fix(); // fixing the end point
for (int j=0; j < division; j++) { // connecting particles
new ITensionLine(pts[j], pts[j+1]).tension(150).clr(1.0, 0.5).weight(2);
}
curves[i].del();
}
```

The next example only changes the input file. When you have random intersecting lines, swarm forces to cluster together are clear. The final lines are result of the balance between gathering swarm forces and smoothing tension forces. The code below also hides points by hide() method.

The input file used in the next code is tension_lines2.3dm.

```import processing.opengl.*;
import igeo.*;

size(480, 360, IG.GL);
IG.bg(0);
IG.open("tension_lines2.3dm");
ICurve[] curves = IG.curves();

int division=50;
double inc = 1.0/division;

for (int i=0; i < curves.length; i++) {
IBoid[] pts = new IBoid[division+1];
for (int j=0; j <= division; j++) { // creating particles
pts[j] = new IBoid( curves[i].pt( j*inc ) ).fric(0.1);
pts[j].cohesionDist(0.5);
pts[j].cohesionRatio(50);
pts[j].separationRatio(0);
pts[j].alignmentRatio(0);
pts[j].hide();
}
pts[0].fix(); // fixing the start point
pts[division].fix(); // fixing the end point
for (int j=0; j < division; j++) { // connecting particles
new ITensionLine(pts[j], pts[j+1]).tension(100).clr(1.0, 0.5).weight(2);
}
curves[i].del();
}
```

This shows the random intersecting input lines.

This is the result when they are in equilibrium.

(back to the list of tutorials)