protected void recurseRepulsion(Cell cell, Vector3 delta) { if (intersection(cell)) { if (cell.isLeaf()) { Iterator<? extends Particle> i = cell.getParticles(); while (i.hasNext()) { NodeParticle node = (NodeParticle) i.next(); if (node != this) { delta.set(node.pos.x - pos.x, node.pos.y - pos.y, box.is3D ? node.pos.z - pos.z : 0); double len = delta.normalize(); if (len > 0) // && len < ( box.k * box.viewZone ) ) { if (len < box.k) len = box.k; // XXX NEW To prevent infinite // repulsion. double factor = len != 0 ? ((box.K2 / (len * len)) * node.weight) : 0.00001; box.energies.accumulateEnergy(factor); // TODO check // this repE += factor; delta.scalarMult(-factor); disp.add(delta); } } } } else { int div = cell.getSpace().getDivisions(); for (int i = 0; i < div; i++) recurseRepulsion(cell.getSub(i), delta); } } else { if (cell != this.cell) { BarycenterCellData bary = (BarycenterCellData) cell.getData(); double dist = bary.distanceFrom(pos); double size = cell.getSpace().getSize(); if ((!cell.isLeaf()) && ((size / dist) > box.theta)) { int div = cell.getSpace().getDivisions(); for (int i = 0; i < div; i++) recurseRepulsion(cell.getSub(i), delta); } else { if (bary.weight != 0) { // System.err.printf( // "applying bary %s [depth=%d weight=%d]%n", // cell.getId(), cell.getDepth(), (int)bary.weight ); delta.set( bary.center.x - pos.x, bary.center.y - pos.y, box.is3D ? bary.center.z - pos.z : 0); double len = delta.normalize(); if (len > 0) { if (len < box.k) len = box.k; // XXX NEW To prevent infinite // repulsion. double factor = len != 0 ? ((box.K2 / (len * len)) * (bary.weight)) : 0.00001f; box.energies.accumulateEnergy(factor); delta.scalarMult(-factor); repE += factor; disp.add(delta); } } } } } }