/** * Take four atoms, and return Stereo.CLOCKWISE or Stereo.ANTI_CLOCKWISE. * The first atom is the one pointing towards the observer. * * @param atom1 the atom pointing towards the observer * @param atom2 the second atom (points away) * @param atom3 the third atom (points away) * @param atom4 the fourth atom (points away) * @return clockwise or anticlockwise */ public static Stereo getStereo(IAtom atom1, IAtom atom2, IAtom atom3, IAtom atom4) { // a normal is calculated for the base atoms (2, 3, 4) and compared to // the first atom. PLUS indicates ACW. TetrahedralSign sign = StereoTool.getHandedness(atom2, atom3, atom4, atom1); if (sign == TetrahedralSign.PLUS) { return Stereo.ANTI_CLOCKWISE; } else { return Stereo.CLOCKWISE; } }
private static TetrahedralSign getHandedness(Point3d pointA, Point3d pointB, Point3d pointC, Point3d pointD) { // assumes anti-clockwise for a right-handed system Vector3d normal = StereoTool.getNormal(pointA, pointB, pointC); // it doesn't matter which of points {A,B,C} is used return StereoTool.getHandedness(normal, pointA, pointD); }
/** * Gets the tetrahedral handedness of four atoms - three of which form the * 'base' of the tetrahedron, and the other the apex. Note that it assumes * a right-handed coordinate system, and that the points {A,B,C} are in * a counter-clockwise order in the plane they share. * * @param baseAtomA the first atom in the base of the tetrahedron * @param baseAtomB the second atom in the base of the tetrahedron * @param baseAtomC the third atom in the base of the tetrahedron * @param apexAtom the atom in the point of the tetrahedron * @return the sign of the tetrahedron */ public static TetrahedralSign getHandedness(IAtom baseAtomA, IAtom baseAtomB, IAtom baseAtomC, IAtom apexAtom) { Point3d pointA = baseAtomA.getPoint3d(); Point3d pointB = baseAtomB.getPoint3d(); Point3d pointC = baseAtomC.getPoint3d(); Point3d pointD = apexAtom.getPoint3d(); return StereoTool.getHandedness(pointA, pointB, pointC, pointD); }
TetrahedralSign handednessCDEA = StereoTool.getHandedness(normal, pointC, pointF); TetrahedralSign handednessCDEF = StereoTool.getHandedness(normal, pointC, pointA);
@Test public void tetrahedralMinusAtomsAboveXYTest() { // above the XY plane IAtom baseA = new Atom("C", new Point3d(0, 0, 1)); IAtom baseB = new Atom("C", new Point3d(1, 0, 1)); IAtom baseC = new Atom("C", new Point3d(1, 1, 1)); IAtom negativeApex = new Atom("C", new Point3d(0.5, 0.5, -1)); TetrahedralSign tetSign = StereoTool.getHandedness(baseA, baseB, baseC, negativeApex); Assert.assertEquals(TetrahedralSign.MINUS, tetSign); }
@Test public void tetrahedralPlusAtomsAboveXYTest() { // above the XY plane IAtom baseA = new Atom("C", new Point3d(0, 0, 1)); IAtom baseB = new Atom("C", new Point3d(1, 0, 1)); IAtom baseC = new Atom("C", new Point3d(1, 1, 1)); IAtom positiveApex = new Atom("C", new Point3d(0.5, 0.5, 2)); TetrahedralSign tetSign = StereoTool.getHandedness(baseA, baseB, baseC, positiveApex); Assert.assertEquals(TetrahedralSign.PLUS, tetSign); }
@Test public void tetrahedralPlusAtomsAboveXYClockwiseTest() { // above the XY plane IAtom baseA = new Atom("C", new Point3d(0, 0, 1)); IAtom baseB = new Atom("C", new Point3d(1, 0, 1)); IAtom baseC = new Atom("C", new Point3d(1, 1, 1)); IAtom positiveApex = new Atom("C", new Point3d(0.5, 0.5, 2)); TetrahedralSign tetSign = StereoTool.getHandedness(baseC, baseB, baseA, positiveApex); Assert.assertEquals(TetrahedralSign.MINUS, tetSign); }
@Test public void tetrahedralPlusAtomsBelowXYTest() { // below the XY plane IAtom baseA = new Atom("C", new Point3d(0, 0, -1)); IAtom baseB = new Atom("C", new Point3d(1, 0, -1)); IAtom baseC = new Atom("C", new Point3d(1, 1, -1)); IAtom positiveApex = new Atom("C", new Point3d(0.5, 0.5, 0)); TetrahedralSign tetSign = StereoTool.getHandedness(baseA, baseB, baseC, positiveApex); Assert.assertEquals(TetrahedralSign.PLUS, tetSign); }
@Test public void tetrahedralMinusAtomsBelowXYTest() { // below the XY plane IAtom baseA = new Atom("C", new Point3d(0, 0, -1)); IAtom baseB = new Atom("C", new Point3d(1, 0, -1)); IAtom baseC = new Atom("C", new Point3d(1, 1, -1)); IAtom negativeApex = new Atom("C", new Point3d(0.5, 0.5, -2)); TetrahedralSign tetSign = StereoTool.getHandedness(baseA, baseB, baseC, negativeApex); Assert.assertEquals(TetrahedralSign.MINUS, tetSign); }