private void TranslatePoints(int atmIdx, Vector3[][] points, int pointDensity, IAtom atom, Vector3 cp) { var totalRadius = PeriodicTable.GetVdwRadius(atom.Symbol).Value + solventRadius; var area = 4 * Math.PI * (totalRadius * totalRadius) * points.Length / pointDensity; double sumx = 0.0; double sumy = 0.0; double sumz = 0.0; foreach (var point in points) { var p = point[1]; sumx += p.X; sumy += p.Y; sumz += p.Z; } var vconst = 4.0 / 3.0 * Math.PI / (double)pointDensity; var dotp1 = (atom.Point3D.Value.X - cp.X) * sumx + (atom.Point3D.Value.Y - cp.Y) * sumy + (atom.Point3D.Value.Z - cp.Z) * sumz; var volume = vconst * (totalRadius * totalRadius) * dotp1 + (totalRadius * totalRadius * totalRadius) * points.Length; this.areas[atmIdx] = area; this.volumes[atmIdx] = volume; var tmp = new List <Vector3>(); foreach (var point in points) { tmp.Add(point[0]); } this.surfPoints[atmIdx] = tmp; }
/// <summary> /// Initialize the surface, generating the points on the accessible surface /// area of each atom as well as calculating the surface area of each atom. /// </summary> private void Init() { // invariants foreach (var atom in atoms) { if (atom.Point3D == null) { throw new ArgumentException("One or more atoms had no 3D coordinate set"); } } // get r_f and geometric center var cp = new Vector3(0, 0, 0); double maxRadius = 0; foreach (var atom in atoms) { var vdwr = PeriodicTable.GetVdwRadius(atom.Symbol).Value; if (vdwr + solventRadius > maxRadius) { maxRadius = PeriodicTable.GetVdwRadius(atom.Symbol).Value + solventRadius; } cp.X = cp.X + atom.Point3D.Value.X; cp.Y = cp.Y + atom.Point3D.Value.Y; cp.Z = cp.Z + atom.Point3D.Value.Z; } cp.X = cp.X / atoms.Length; cp.Y = cp.Y / atoms.Length; cp.Z = cp.Z / atoms.Length; // do the tesselation var tess = new Tessellate("ico", tesslevel); tess.DoTessellate(); Trace.TraceInformation($"Got tesselation, number of triangles = {tess.GetNumberOfTriangles()}"); // get neighbor list var nbrlist = new NeighborList(atoms, maxRadius + solventRadius); Trace.TraceInformation("Got neighbor list"); // loop over atoms and get surface points this.surfPoints = new List <Vector3> [atoms.Length]; this.areas = new double[atoms.Length]; this.volumes = new double[atoms.Length]; for (int i = 0; i < atoms.Length; i++) { var pointDensity = tess.GetNumberOfTriangles() * 3; var points = AtomicSurfacePoints(nbrlist, i, atoms[i], tess); TranslatePoints(i, points, pointDensity, atoms[i], cp); } Trace.TraceInformation("Obtained points, areas and volumes"); }
/// <summary> /// Method assigns the atoms of a biopolymer to the grid. For every atom /// the corresponding grid point is identified and set to the value /// of the proteinInterior variable. /// The atom radius and solvent radius is accounted for with the variables: /// double rAtom, and double rSolvent. /// </summary> /// <exception cref="Exception"></exception> public void AssignProteinToGrid() { // 1. Step: Set all grid points to solvent accessible this.Grid = GridGenerator.InitializeGrid(this.Grid, 0); // 2. Step Grid points inaccessible to solvent are assigend a value of -1 // set grid points around (r_atom+r_solv) to -1 Vector3 gridPoint; int checkGridPoints = 0; double vdWRadius = 0; int[] dim = gridGenerator.Dim; int[] minMax = { 0, 0, 0, 0, 0, 0 }; foreach (var atom in Protein.Atoms) { var patom = (PDBAtom)atom; if (patom.HetAtom.Value) { continue; } gridPoint = gridGenerator.GetGridPointFrom3dCoordinates(patom.Point3D.Value); this.Grid[(int)gridPoint.X][(int)gridPoint.Y][(int)gridPoint.Z] = -1; vdWRadius = PeriodicTable.GetVdwRadius(patom.Symbol).Value; if (vdWRadius == 0) { vdWRadius = RAtom; } checkGridPoints = (int)(((vdWRadius + RSolvent) / gridGenerator.LatticeConstant) - AtomCheckRadius); if (checkGridPoints < 0) { checkGridPoints = 0; } minMax[0] = (int)gridPoint.X - checkGridPoints; minMax[1] = (int)gridPoint.X + checkGridPoints; minMax[2] = (int)gridPoint.Y - checkGridPoints; minMax[3] = (int)gridPoint.Y + checkGridPoints; minMax[4] = (int)gridPoint.Z - checkGridPoints; minMax[5] = (int)gridPoint.Z + checkGridPoints; minMax = CheckBoundaries(minMax, dim); for (int x = minMax[0]; x <= minMax[1]; x++) { for (int y = minMax[2]; y <= minMax[3]; y++) { for (int z = minMax[4]; z <= minMax[5]; z++) { this.Grid[x][y][z] = this.Grid[x][y][z] - 1; } } } }// for atoms.Length }
private Vector3[][] AtomicSurfacePoints(NeighborList nbrlist, int currAtomIdx, IAtom atom, Tessellate tess) { var totalRadius = PeriodicTable.GetVdwRadius(atom.Symbol).Value + solventRadius; var totalRadius2 = totalRadius * totalRadius; var twiceTotalRadius = 2 * totalRadius; var nlist = nbrlist.GetNeighbors(currAtomIdx); var data = Arrays.CreateJagged <double>(nlist.Length, 4); for (int i = 0; i < nlist.Length; i++) { var x12 = atoms[nlist[i]].Point3D.Value.X - atom.Point3D.Value.X; var y12 = atoms[nlist[i]].Point3D.Value.Y - atom.Point3D.Value.Y; var z12 = atoms[nlist[i]].Point3D.Value.Z - atom.Point3D.Value.Z; var d2 = x12 * x12 + y12 * y12 + z12 * z12; var tmp = PeriodicTable.GetVdwRadius(atoms[nlist[i]].Symbol).Value + solventRadius; tmp = tmp * tmp; var thresh = (d2 + totalRadius2 - tmp) / twiceTotalRadius; data[i][0] = x12; data[i][1] = y12; data[i][2] = z12; data[i][3] = thresh; } var tessPoints = tess.GetTessAsPoint3ds(); var points = new List <Vector3[]>(); foreach (var pt in tessPoints) { bool buried = false; foreach (var datum in data) { if (datum[0] * pt.X + datum[1] * pt.Y + datum[2] * pt.Z > datum[3]) { buried = true; break; } } if (!buried) { var tmp = new Vector3[2]; tmp[0] = new Vector3( totalRadius * pt.X + atom.Point3D.Value.X, totalRadius * pt.Y + atom.Point3D.Value.Y, totalRadius * pt.Z + atom.Point3D.Value.Z); tmp[1] = pt; points.Add(tmp); } } // the first column contains the transformed points // and the second column contains the points from the // original unit tesselation var ret = Arrays.CreateJagged <Vector3>(points.Count, 2); for (int i = 0; i < points.Count; i++) { var tmp = points[i]; ret[i][0] = tmp[0]; ret[i][1] = tmp[1]; } return(ret); }
/// <summary> /// This method calculate the van der Waals radius of an atom. /// </summary> /// <returns>The Van der Waals radius of the atom</returns> public Result Calculate(IAtom atom) { var vdwradius = PeriodicTable.GetVdwRadius(atom.AtomicNumber); return(new Result(vdwradius.Value)); }