// y1 is perp to bond and x
z.normalize();
x.scaleAdd(2.828f, x, z); // 2*sqrt(2)
if (pt != 3) {
x.normalize();
AxisAngle4f a = new AxisAngle4f(z.x, z.y, z.z,
(pt == 2 ? 1 : -1) * 2.09439507f); // PI*2/3
Matrix3f m = new Matrix3f();
m.setIdentity();
m.set(a);
m.transform(x);
}
z.set(x);
x.cross(vTemp, z);
break;
}
// not "sp3" -- sp2 or lone pair
vTemp.cross(x, z); //x and vTemp are now perpendicular to z
switch (attached[0].getCovalentBondCount()) {
case 1:
if (attached[0].getValence() != 2) {
// C-t-C
break;
}
// C=C, no other atoms
// fall through
case 2:
// R-C=C* or C=C=C*
// get third atom
boolean isCumulated = false;
Atom a0 = attached[0];
x.set(z);
vTemp.set(vRef);
while (a0 != null && a0.getCovalentBondCount() == 2) {
Bond[] bonds = a0.bonds;
Atom a = null;
isCumulated = !isCumulated;
for (int i = 0; i < bonds.length; i++)
if (bonds[i].isCovalent()) {
a = bonds[i].getOtherAtom(a0);
if (a != atom) {
vTemp.sub(a, a0);
break;
}
}
vTemp.cross(vTemp, x);
if (vTemp.length() > 0.1f || a.getCovalentBondCount() != 2)
break;
atom = a0;
a0 = a;
}
if (vTemp.length() > 0.1f) {
z.cross(vTemp, x);
// C=C or RC=C
z.normalize();
if (pt == 1)
z.scale(-1);
z.scale(sqrt3_2);
z.scaleAdd(0.5f, x, z);
if (isP) {
vTemp.cross(z, x);
z.set(vTemp);
vTemp.set(x);
}
x.cross(vTemp, z);
} else {
z.set(x);
x.cross(vRef, x);
}
break;
case 3:
// special case, for example R2C=O oxygen
getHybridizationAndAxes(attached[0].index, x, vTemp, "pz", false,
doAlignZ);
vTemp.set(x);
if (isSp2) { // align z as sp2 orbital
//System.out.println("draw v1 vector @{ {_O}[1]} @{point" + x + "}");
//System.out.println("draw v2 vector @{ {_O}[1]} @{point" + z + "} color red");
x.cross(x, z);
if (pt == 1)
x.scale(-1);
x.scale(sqrt3_2);
z.scaleAdd(0.5f, z, x);
} else {
vTemp.set(z);
z.set(x);
}
x.cross(vTemp, z);
break;
}
break;
case 2:
// two attached atoms -- check for linearity
if (z.length() < 0.1f) {
// linear A--X--B
if (!lcaoType.equals("pz")) {
Atom a = attached[0];
boolean ok = (a.getCovalentBondCount() == 3);
if (!ok)
ok = ((a = attached[1]).getCovalentBondCount() == 3);
if (ok) {
// special case, for example R2C=C=CR2 central carbon
getHybridizationAndAxes(a.index, x, z, "pz", false, doAlignZ);