package name.mjw.jamber;
import javax.vecmath.Vector3d;
/**
* Bond object representing a harmonic bonded interaction between two atoms
*
* @author mjw
*
*/
public class Bond extends ForceFieldTerm {
/**
* Atom i in in a bond
*/
private Atom i;
/**
* Atom j in in a bond
*/
private Atom j;
/**
* Harmonic Force constant of the bond in kcal/(mol Angstrom**2)
*/
private double forceConstant;
/**
* Equilibrium length of bond in Angstroms
*/
private double equilibriumLength;
/**
* Harmonic bond
*
* @param i
* Atom i in bond
* @param j
* Atom j in bond
* @param equilibriumLength
* Equilibrium length of bond in Angstroms
* @param forceConstant
* Harmonic Force constant of the bond in kcal/(mol Angstrom**2)
*/
public Bond(Atom i, Atom j, double equilibriumLength, double forceConstant) {
this.setAtomI(i);
this.setAtomJ(j);
this.setEquilibriumLength(equilibriumLength);
this.setForceConstant(forceConstant);
}
/**
* Set the force constant of the bond in kcal/(mol Angstrom**2)
*/
private void setForceConstant(double forceConstant) {
this.forceConstant = forceConstant;
}
/**
* Gets the force constant of the bond in kcal/(mol Angstrom**2)
*/
public double getForceConstant() {
return forceConstant;
}
/**
* Sets the equilibrium length of the bond in Angstroms
*/
private void setEquilibriumLength(double equilibriumLength) {
this.equilibriumLength = equilibriumLength;
}
/**
* Returns the equilibrium length of the bond in Angstroms
*/
public double getEquilibriumLength() {
return equilibriumLength;
}
/**
* Returns the current length of the bond in Angstroms
*/
public double getCurrentLength() {
Vector3d dist = new Vector3d();
dist.sub(i.getPosition(), j.getPosition());
return dist.length();
}
/**
* Returns the potential energy of the bond in kcal/mol
*/
public double getPotentialEnergy() {
return forceConstant
* square((getCurrentLength() - equilibriumLength));
}
/**
* Returns the current (scalar) gradient of the potential energy term
* This is the analytical derivative of the potential energy at this length
*/
public double getAnalyticalGradient() {
return 2 * forceConstant * (this.getCurrentLength() - this.equilibriumLength);
}
/**
* Calculates and imparts the vector force of the bond to its member atoms
*/
public void evaluateForce() {
Vector3d temp3d = new Vector3d();
temp3d.sub(i.getPosition(), j.getPosition());
double unitForce = this.getAnalyticalGradient() / temp3d.length();
temp3d.scale(unitForce);
i.addForce(temp3d);
j.subForce(temp3d);
}
/**
* Sets atom i of the bond
*/
private void setAtomI(Atom i) {
this.i = i;
}
/**
* Gets atom i of the bond
*/
public Atom getI() {
return i;
}
/**
* Sets atom j of the bond
*/
private void setAtomJ(Atom j) {
this.j = j;
}
/**
* Gets atom j of the bond
*/
public Atom getJ() {
return j;
}
public String toString() {
StringBuilder result = new StringBuilder();
String NEW_LINE = System.getProperty("line.separator");
result.append(this.getClass().getName()).append(" Object {").append(NEW_LINE);
result.append(String.format(" Atoms:\t\t\t\t\t\t%-2s-%-2s",
i.getName(),
j.getName())).append(NEW_LINE);
result.append(String.format(" AtomTypes:\t\t\t\t\t%-2s-%-2s",
i.getAMBERAtomType(),
j.getAMBERAtomType())).append(NEW_LINE);
result.append(" forceConstant (kcal/(mol Angstrom**2)): \t").append(forceConstant).append(NEW_LINE);
result.append(" equilibriumLength (A): \t\t\t").append(equilibriumLength).append(NEW_LINE);
result.append(" current length (A) : \t\t\t\t").append(this.getCurrentLength()).append(NEW_LINE);
result.append(" current potential contribution (kcal/mol): \t").append(this.getPotentialEnergy()).append(NEW_LINE);
result.append("}");
return result.toString();
}
}