# All files / src/parsers/utils assignBonds.ts

94.11% Statements 64/68
88.88% Branches 16/18
100% Functions 2/2
93.22% Lines 55/59

Press n or j to go to the next uncovered block, b, p or k for the previous block.

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119

    321x

    15041x

    321x
    321x

    321x
    15041x
    15041x
    15041x
    15041x
    15041x
    977x

    15041x
    2127x

    15041x
    4076x

    15041x

    321x
    14976x
    58247x
    58247x
    263160x

    263160x

    20726x
    20726x
    20726x
    18862x
    18862x
    18862x
    18862x
    1864x

    1864x

    321x

    321x

    977x
    977x

    2127x
    2127x

    4076x
    4076x

    4076x
    15041x
    15041x
    176836x
    176836x
    72906x
    70360x
    70360x
    70360x
    70360x

    4076x
    52988x
    52988x

    38012x

    14976x
    14976x

     import { areConnected } from "./areConnected";

    /*
     * @param {AtomSpec[]} atoms
     */
    export function assignBonds(atoms) {
      // assign bonds - yuck, can't count on connect records

      for (var i = 0, n = atoms.length; i < n; i++) {
        // Don't reindex if atoms are already indexed
        if (!atoms[i].index) atoms[i].index = i;
      }

      var grid = {};
      var MAX_BOND_LENGTH = 4.95; // (largest bond length, Cs) 2.25 * 2 * 1.1 (fudge factor)

      for (var index = 0; index < atoms.length; index++) {
        var atom = atoms[index];
        var x = Math.floor(atom.x / MAX_BOND_LENGTH);
        var y = Math.floor(atom.y / MAX_BOND_LENGTH);
        var z = Math.floor(atom.z / MAX_BOND_LENGTH);
        if (!grid[x]) {
          grid[x] = {};
        }
        if (!grid[x][y]) {
          grid[x][y] = {};
        }
        if (!grid[x][y][z]) {
          grid[x][y][z] = [];
        }

        grid[x][y][z].push(atom);
      }

      var findConnections = function (points, otherPoints) {
        for (var i = 0; i < points.length; i++) {
          var atom1 = points[i];
          for (var j = 0; j < otherPoints.length; j++) {
            var atom2 = otherPoints[j];

            if (areConnected(atom1, atom2)) {
              //gracefully handle one-sided bonds
              var a2i = atom1.bonds.indexOf(atom2.index);
              var a1i = atom2.bonds.indexOf(atom1.index);
              if (a2i == -1 && a1i == -1) {
                atom1.bonds.push(atom2.index);
                atom1.bondOrder.push(1);
                atom2.bonds.push(atom1.index);
                atom2.bondOrder.push(1);
              } else Iif (a2i == -1) {
                atom1.bonds.push(atom2.index);
                atom1.bondOrder.push(atom2.bondOrder[a1i]);
              } else Iif (a1i == -1) {
                atom2.bonds.push(atom1.index);
                atom2.bondOrder.push(atom1.bondOrder[a2i]);
              }
            }
          }
        }
      };

      /*const*/ var OFFSETS = [
        { x: 0, y: 0, z: 1 },
        { x: 0, y: 1, z: -1 },
        { x: 0, y: 1, z: 0 },
        { x: 0, y: 1, z: 1 },
        { x: 1, y: -1, z: -1 },
        { x: 1, y: -1, z: 0 },
        { x: 1, y: -1, z: 1 },
        { x: 1, y: 0, z: -1 },
        { x: 1, y: 0, z: 0 },
        { x: 1, y: 0, z: 1 },
        { x: 1, y: 1, z: -1 },
        { x: 1, y: 1, z: 0 },
        { x: 1, y: 1, z: 1 },
      ];
      for (let x in grid) {
        // @ts-ignore
        x = parseInt(x);
        for (let y in grid[x]) {
          // @ts-ignore
          y = parseInt(y);
          for (let z in grid[x][y]) {
            // @ts-ignore
            z = parseInt(z);
            let points = grid[x][y][z];

            for (let i = 0; i < points.length; i++) {
              let atom1 = points[i];
              for (let j = i + 1; j < points.length; j++) {
                let atom2 = points[j];
                if (areConnected(atom1, atom2)) {
                  if (atom1.bonds.indexOf(atom2.index) == -1) {
                    atom1.bonds.push(atom2.index);
                    atom1.bondOrder.push(1);
                    atom2.bonds.push(atom1.index);
                    atom2.bondOrder.push(1);
                  }
                }
              }
            }

            for (let o = 0; o < OFFSETS.length; o++) {
              let offset = OFFSETS[o];
              if (
                !grid[x + offset.x] ||
                !grid[x + offset.x][y + offset.y] ||
                !grid[x + offset.x][y + offset.y][z + offset.z]
              )
                continue;

              let otherPoints = grid[x + offset.x][y + offset.y][z + offset.z];
              findConnections(points, otherPoints);
            }
          }
        }
      }
    }