biotite 1.0.1__cp311-cp311-win_amd64.whl → 1.2.0__cp311-cp311-win_amd64.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of biotite might be problematic. Click here for more details.

Files changed (177) hide show
  1. biotite/application/application.py +3 -3
  2. biotite/application/autodock/app.py +1 -1
  3. biotite/application/blast/webapp.py +1 -1
  4. biotite/application/clustalo/app.py +1 -1
  5. biotite/application/dssp/app.py +13 -3
  6. biotite/application/localapp.py +36 -2
  7. biotite/application/msaapp.py +10 -10
  8. biotite/application/muscle/app3.py +5 -18
  9. biotite/application/muscle/app5.py +5 -5
  10. biotite/application/sra/app.py +0 -5
  11. biotite/application/util.py +22 -2
  12. biotite/application/viennarna/rnaalifold.py +8 -8
  13. biotite/application/viennarna/rnaplot.py +9 -3
  14. biotite/application/viennarna/util.py +1 -1
  15. biotite/application/webapp.py +1 -1
  16. biotite/database/afdb/__init__.py +12 -0
  17. biotite/database/afdb/download.py +191 -0
  18. biotite/database/entrez/dbnames.py +10 -0
  19. biotite/database/entrez/download.py +9 -10
  20. biotite/database/entrez/key.py +1 -1
  21. biotite/database/entrez/query.py +5 -4
  22. biotite/database/pubchem/download.py +6 -6
  23. biotite/database/pubchem/error.py +10 -0
  24. biotite/database/pubchem/query.py +12 -23
  25. biotite/database/rcsb/download.py +3 -2
  26. biotite/database/rcsb/query.py +8 -9
  27. biotite/database/uniprot/check.py +22 -17
  28. biotite/database/uniprot/download.py +3 -6
  29. biotite/database/uniprot/query.py +4 -5
  30. biotite/file.py +14 -2
  31. biotite/interface/__init__.py +19 -0
  32. biotite/interface/openmm/__init__.py +16 -0
  33. biotite/interface/openmm/state.py +93 -0
  34. biotite/interface/openmm/system.py +227 -0
  35. biotite/interface/pymol/__init__.py +198 -0
  36. biotite/interface/pymol/cgo.py +346 -0
  37. biotite/interface/pymol/convert.py +185 -0
  38. biotite/interface/pymol/display.py +267 -0
  39. biotite/interface/pymol/object.py +1226 -0
  40. biotite/interface/pymol/shapes.py +178 -0
  41. biotite/interface/pymol/startup.py +169 -0
  42. biotite/interface/rdkit/__init__.py +15 -0
  43. biotite/interface/rdkit/mol.py +490 -0
  44. biotite/interface/version.py +71 -0
  45. biotite/interface/warning.py +19 -0
  46. biotite/sequence/align/__init__.py +0 -4
  47. biotite/sequence/align/alignment.py +49 -14
  48. biotite/sequence/align/banded.cp311-win_amd64.pyd +0 -0
  49. biotite/sequence/align/banded.pyx +26 -26
  50. biotite/sequence/align/cigar.py +2 -2
  51. biotite/sequence/align/kmeralphabet.cp311-win_amd64.pyd +0 -0
  52. biotite/sequence/align/kmeralphabet.pyx +19 -2
  53. biotite/sequence/align/kmersimilarity.cp311-win_amd64.pyd +0 -0
  54. biotite/sequence/align/kmertable.cp311-win_amd64.pyd +0 -0
  55. biotite/sequence/align/kmertable.pyx +58 -48
  56. biotite/sequence/align/localgapped.cp311-win_amd64.pyd +0 -0
  57. biotite/sequence/align/localgapped.pyx +47 -47
  58. biotite/sequence/align/localungapped.cp311-win_amd64.pyd +0 -0
  59. biotite/sequence/align/localungapped.pyx +10 -10
  60. biotite/sequence/align/matrix.py +284 -57
  61. biotite/sequence/align/matrix_data/3Di.mat +24 -0
  62. biotite/sequence/align/matrix_data/PB.license +21 -0
  63. biotite/sequence/align/matrix_data/PB.mat +18 -0
  64. biotite/sequence/align/multiple.cp311-win_amd64.pyd +0 -0
  65. biotite/sequence/align/pairwise.cp311-win_amd64.pyd +0 -0
  66. biotite/sequence/align/pairwise.pyx +35 -35
  67. biotite/sequence/align/permutation.cp311-win_amd64.pyd +0 -0
  68. biotite/sequence/align/selector.cp311-win_amd64.pyd +0 -0
  69. biotite/sequence/align/selector.pyx +2 -2
  70. biotite/sequence/align/statistics.py +1 -1
  71. biotite/sequence/align/tracetable.cp311-win_amd64.pyd +0 -0
  72. biotite/sequence/alphabet.py +5 -2
  73. biotite/sequence/annotation.py +19 -13
  74. biotite/sequence/codec.cp311-win_amd64.pyd +0 -0
  75. biotite/sequence/codon.py +1 -2
  76. biotite/sequence/graphics/alignment.py +25 -39
  77. biotite/sequence/graphics/color_schemes/3di_flower.json +48 -0
  78. biotite/sequence/graphics/color_schemes/pb_flower.json +2 -1
  79. biotite/sequence/graphics/colorschemes.py +44 -11
  80. biotite/sequence/graphics/dendrogram.py +4 -2
  81. biotite/sequence/graphics/features.py +2 -2
  82. biotite/sequence/graphics/logo.py +10 -12
  83. biotite/sequence/io/fasta/convert.py +1 -2
  84. biotite/sequence/io/fasta/file.py +1 -1
  85. biotite/sequence/io/fastq/file.py +3 -3
  86. biotite/sequence/io/genbank/file.py +3 -3
  87. biotite/sequence/io/genbank/sequence.py +2 -0
  88. biotite/sequence/io/gff/convert.py +1 -1
  89. biotite/sequence/io/gff/file.py +1 -2
  90. biotite/sequence/phylo/nj.cp311-win_amd64.pyd +0 -0
  91. biotite/sequence/phylo/tree.cp311-win_amd64.pyd +0 -0
  92. biotite/sequence/phylo/upgma.cp311-win_amd64.pyd +0 -0
  93. biotite/sequence/profile.py +105 -29
  94. biotite/sequence/search.py +0 -1
  95. biotite/sequence/seqtypes.py +136 -8
  96. biotite/sequence/sequence.py +1 -2
  97. biotite/setup_ccd.py +197 -0
  98. biotite/structure/__init__.py +6 -3
  99. biotite/structure/alphabet/__init__.py +25 -0
  100. biotite/structure/alphabet/encoder.py +332 -0
  101. biotite/structure/alphabet/encoder_weights_3di.kerasify +0 -0
  102. biotite/structure/alphabet/i3d.py +109 -0
  103. biotite/structure/alphabet/layers.py +86 -0
  104. biotite/structure/alphabet/pb.license +21 -0
  105. biotite/structure/alphabet/pb.py +170 -0
  106. biotite/structure/alphabet/unkerasify.py +128 -0
  107. biotite/structure/atoms.py +163 -66
  108. biotite/structure/basepairs.py +26 -26
  109. biotite/structure/bonds.cp311-win_amd64.pyd +0 -0
  110. biotite/structure/bonds.pyx +79 -25
  111. biotite/structure/box.py +19 -21
  112. biotite/structure/celllist.cp311-win_amd64.pyd +0 -0
  113. biotite/structure/celllist.pyx +83 -67
  114. biotite/structure/chains.py +5 -37
  115. biotite/structure/charges.cp311-win_amd64.pyd +0 -0
  116. biotite/structure/compare.py +420 -13
  117. biotite/structure/density.py +1 -1
  118. biotite/structure/dotbracket.py +27 -28
  119. biotite/structure/filter.py +8 -8
  120. biotite/structure/geometry.py +74 -127
  121. biotite/structure/hbond.py +17 -19
  122. biotite/structure/info/__init__.py +1 -0
  123. biotite/structure/info/atoms.py +24 -15
  124. biotite/structure/info/bonds.py +12 -6
  125. biotite/structure/info/ccd.py +125 -34
  126. biotite/structure/info/{ccd/components.bcif → components.bcif} +0 -0
  127. biotite/structure/info/groups.py +62 -19
  128. biotite/structure/info/masses.py +9 -6
  129. biotite/structure/info/misc.py +15 -22
  130. biotite/structure/info/radii.py +92 -22
  131. biotite/structure/info/standardize.py +4 -4
  132. biotite/structure/integrity.py +4 -6
  133. biotite/structure/io/general.py +2 -2
  134. biotite/structure/io/gro/file.py +8 -9
  135. biotite/structure/io/mol/convert.py +1 -1
  136. biotite/structure/io/mol/ctab.py +33 -28
  137. biotite/structure/io/mol/mol.py +1 -1
  138. biotite/structure/io/mol/sdf.py +80 -53
  139. biotite/structure/io/pdb/convert.py +4 -3
  140. biotite/structure/io/pdb/file.py +85 -25
  141. biotite/structure/io/pdb/hybrid36.cp311-win_amd64.pyd +0 -0
  142. biotite/structure/io/pdbqt/file.py +36 -36
  143. biotite/structure/io/pdbx/__init__.py +1 -0
  144. biotite/structure/io/pdbx/bcif.py +54 -15
  145. biotite/structure/io/pdbx/cif.py +92 -66
  146. biotite/structure/io/pdbx/component.py +15 -4
  147. biotite/structure/io/pdbx/compress.py +321 -0
  148. biotite/structure/io/pdbx/convert.py +410 -75
  149. biotite/structure/io/pdbx/encoding.cp311-win_amd64.pyd +0 -0
  150. biotite/structure/io/pdbx/encoding.pyx +98 -17
  151. biotite/structure/io/trajfile.py +9 -6
  152. biotite/structure/io/util.py +38 -0
  153. biotite/structure/mechanics.py +0 -1
  154. biotite/structure/molecules.py +141 -156
  155. biotite/structure/pseudoknots.py +7 -13
  156. biotite/structure/repair.py +2 -4
  157. biotite/structure/residues.py +13 -24
  158. biotite/structure/rings.py +335 -0
  159. biotite/structure/sasa.cp311-win_amd64.pyd +0 -0
  160. biotite/structure/sasa.pyx +2 -1
  161. biotite/structure/segments.py +69 -11
  162. biotite/structure/sequence.py +0 -1
  163. biotite/structure/sse.py +0 -2
  164. biotite/structure/superimpose.py +74 -62
  165. biotite/structure/tm.py +581 -0
  166. biotite/structure/transform.py +12 -25
  167. biotite/structure/util.py +76 -4
  168. biotite/version.py +9 -4
  169. biotite/visualize.py +111 -1
  170. {biotite-1.0.1.dist-info → biotite-1.2.0.dist-info}/METADATA +6 -2
  171. {biotite-1.0.1.dist-info → biotite-1.2.0.dist-info}/RECORD +173 -143
  172. biotite/structure/info/ccd/README.rst +0 -8
  173. biotite/structure/info/ccd/amino_acids.txt +0 -1663
  174. biotite/structure/info/ccd/carbohydrates.txt +0 -1135
  175. biotite/structure/info/ccd/nucleotides.txt +0 -798
  176. {biotite-1.0.1.dist-info → biotite-1.2.0.dist-info}/WHEEL +0 -0
  177. {biotite-1.0.1.dist-info → biotite-1.2.0.dist-info}/licenses/LICENSE.rst +0 -0
@@ -25,10 +25,12 @@ __all__ = [
25
25
  import numpy as np
26
26
  from biotite.structure.atoms import AtomArray, AtomArrayStack, coord
27
27
  from biotite.structure.box import coord_to_fraction, fraction_to_coord, is_orthogonal
28
- from biotite.structure.chains import chain_iter
29
- from biotite.structure.error import BadStructureError
30
- from biotite.structure.filter import filter_peptide_backbone
31
- from biotite.structure.util import norm_vector, vector_dot
28
+ from biotite.structure.filter import filter_amino_acids
29
+ from biotite.structure.util import (
30
+ coord_for_atom_name_per_residue,
31
+ norm_vector,
32
+ vector_dot,
33
+ )
32
34
 
33
35
 
34
36
  def displacement(atoms1, atoms2, box=None):
@@ -58,9 +60,9 @@ def displacement(atoms1, atoms2, box=None):
58
60
  The displacement vector(s). The shape is equal to the shape of
59
61
  the input `atoms` with the highest dimensionality.
60
62
 
61
- See also
63
+ See Also
62
64
  --------
63
- index_displacement
65
+ index_displacement : The same calculation, but using atom indices.
64
66
  """
65
67
  v1 = coord(atoms1)
66
68
  v2 = coord(atoms2)
@@ -189,7 +191,7 @@ def index_displacement(*args, **kwargs):
189
191
  copy is found for non-orthorhombic boxes; this is especially true
190
192
  for heavily skewed boxes.
191
193
 
192
- See also
194
+ See Also
193
195
  --------
194
196
  displacement
195
197
  """
@@ -222,9 +224,9 @@ def distance(atoms1, atoms2, box=None):
222
224
  The shape is equal to the shape of the input `atoms` with the
223
225
  highest dimensionality minus the last axis.
224
226
 
225
- See also
227
+ See Also
226
228
  --------
227
- index_distance
229
+ index_distance : The same calculation, but using atom indices.
228
230
  """
229
231
  diff = displacement(atoms1, atoms2, box)
230
232
  return np.sqrt(vector_dot(diff, diff))
@@ -280,7 +282,7 @@ def index_distance(*args, **kwargs):
280
282
  copy is found for non-orthorhombic boxes; this is especially true
281
283
  for heavily skewed boxes.
282
284
 
283
- See also
285
+ See Also
284
286
  --------
285
287
  distance
286
288
  """
@@ -310,9 +312,9 @@ def angle(atoms1, atoms2, atoms3, box=None):
310
312
  of the input `atoms` with the highest dimensionality minus the
311
313
  last axis.
312
314
 
313
- See also
315
+ See Also
314
316
  --------
315
- index_angle
317
+ index_angle : The same calculation, but using atom indices.
316
318
  """
317
319
  v1 = displacement(atoms1, atoms2, box)
318
320
  v2 = displacement(atoms3, atoms2, box)
@@ -369,7 +371,7 @@ def index_angle(*args, **kwargs):
369
371
  copy is found for non-orthorhombic boxes; this is especially true
370
372
  for heavily skewed boxes.
371
373
 
372
- See also
374
+ See Also
373
375
  --------
374
376
  angle
375
377
  """
@@ -402,8 +404,8 @@ def dihedral(atoms1, atoms2, atoms3, atoms4, box=None):
402
404
 
403
405
  See Also
404
406
  --------
405
- index_dihedral
406
- dihedral_backbone
407
+ index_dihedral : The same calculation, but using atom indices.
408
+ dihedral_backbone : Calculate the dihedral angle along a peptide backbone.
407
409
  """
408
410
  v1 = displacement(atoms1, atoms2, box)
409
411
  v2 = displacement(atoms2, atoms3, box)
@@ -470,7 +472,7 @@ def index_dihedral(*args, **kwargs):
470
472
  copy is found for non-orthorhombic boxes; this is especially true
471
473
  for heavily skewed boxes.
472
474
 
473
- See also
475
+ See Also
474
476
  --------
475
477
  dihedral
476
478
  dihedral_backbone
@@ -480,139 +482,84 @@ def index_dihedral(*args, **kwargs):
480
482
 
481
483
  def dihedral_backbone(atom_array):
482
484
  """
483
- Measure the characteristic backbone dihedral angles of a protein
484
- structure.
485
+ Measure the characteristic backbone dihedral angles of a chain.
485
486
 
486
487
  Parameters
487
488
  ----------
488
- atom_array: AtomArray or AtomArrayStack
489
- The protein structure. A complete backbone, without gaps,
490
- is required here.
491
- Chain transitions are allowed, the angles at the transition are
492
- `NaN`.
493
- The order of the backbone atoms for each residue must be
494
- (N, CA, C).
489
+ atom_array : AtomArray or AtomArrayStack
490
+ The protein structure to measure the dihedral angles for.
491
+ For missing backbone atoms the corresponding angles are `NaN`.
495
492
 
496
493
  Returns
497
494
  -------
498
495
  phi, psi, omega : ndarray
499
- An array containing the 3 backbone dihedral angles for every
500
- CA. 'phi' is not defined at the N-terminus, 'psi' and 'omega'
501
- are not defined at the C-terminus. In these places the arrays
502
- have *NaN* values. If an :class:`AtomArrayStack` is given, the
503
- output angles are 2-dimensional, the first dimension corresponds
504
- to the model number.
505
-
506
- Raises
507
- ------
508
- BadStructureError
509
- If the amount of backbone atoms is not equal to amount of
510
- residues times 3 (for N, CA and C).
511
-
512
- See Also
513
- --------
514
- dihedral
515
-
516
- Examples
517
- --------
518
-
519
- >>> phi, psi, omega = dihedral_backbone(atom_array)
520
- >>> print(np.stack([np.rad2deg(phi), np.rad2deg(psi)]).T)
521
- [[ nan -56.145]
522
- [ -43.980 -51.309]
523
- [ -66.466 -30.898]
524
- [ -65.219 -45.945]
525
- [ -64.747 -30.346]
526
- [ -73.136 -43.425]
527
- [ -64.882 -43.255]
528
- [ -59.509 -25.698]
529
- [ -77.989 -8.823]
530
- [ 110.784 8.079]
531
- [ 55.244 -124.371]
532
- [ -57.983 -28.766]
533
- [ -81.834 19.125]
534
- [-124.057 13.401]
535
- [ 67.931 25.218]
536
- [-143.952 131.297]
537
- [ -70.100 160.068]
538
- [ -69.484 145.669]
539
- [ -77.264 124.223]
540
- [ -78.100 nan]]
496
+ An array containing the 3 backbone dihedral angles for every CA atom.
497
+ `phi` is not defined at the N-terminus, `psi` and `omega` are not defined at the
498
+ C-terminus.
499
+ In these places the arrays have *NaN* values.
500
+ If an :class:`AtomArrayStack` is given, the output angles are 2-dimensional,
501
+ the first dimension corresponds to the model number.
541
502
  """
542
- bb_filter = filter_peptide_backbone(atom_array)
543
- backbone = atom_array[..., bb_filter]
544
-
545
- if (
546
- backbone.array_length() % 3 != 0
547
- or (backbone.atom_name[0::3] != "N").any()
548
- or (backbone.atom_name[1::3] != "CA").any()
549
- or (backbone.atom_name[2::3] != "C").any()
550
- ):
551
- raise BadStructureError(
552
- "The backbone is invalid, must be repeats of (N, CA, C), "
553
- "maybe a backbone atom is missing"
554
- )
555
- phis = []
556
- psis = []
557
- omegas = []
558
- for chain_bb in chain_iter(backbone):
559
- phi, psi, omega = _dihedral_backbone(chain_bb)
560
- phis.append(phi)
561
- psis.append(psi)
562
- omegas.append(omega)
563
- return (
564
- np.concatenate(phis, axis=-1),
565
- np.concatenate(psis, axis=-1),
566
- np.concatenate(omegas, axis=-1),
567
- )
503
+ amino_acid_mask = filter_amino_acids(atom_array)
568
504
 
505
+ # Coordinates for dihedral angle calculation
506
+ coord_n, coord_ca, coord_c = coord_for_atom_name_per_residue(
507
+ atom_array,
508
+ ("N", "CA", "C"),
509
+ amino_acid_mask,
510
+ )
511
+ n_residues = coord_n.shape[-2]
569
512
 
570
- def _dihedral_backbone(chain_bb):
571
- bb_coord = chain_bb.coord
572
513
  # Coordinates for dihedral angle calculation
573
514
  # Dim 0: Model index (only for atom array stacks)
574
515
  # Dim 1: Angle index
575
516
  # Dim 2: X, Y, Z coordinates
576
517
  # Dim 3: Atoms involved in dihedral angle
577
- if isinstance(chain_bb, AtomArray):
578
- angle_coord_shape = (len(bb_coord) // 3, 3, 4)
579
- elif isinstance(chain_bb, AtomArrayStack):
580
- angle_coord_shape = (bb_coord.shape[0], bb_coord.shape[1] // 3, 3, 4)
581
- phi_coord = np.full(angle_coord_shape, np.nan)
582
- psi_coord = np.full(angle_coord_shape, np.nan)
583
- omega_coord = np.full(angle_coord_shape, np.nan)
584
-
585
- # Indices for coordinates of CA atoms
586
- ca_i = np.arange(bb_coord.shape[-2] // 3) * 3 + 1
518
+ if isinstance(atom_array, AtomArray):
519
+ angle_coord_shape: tuple[int, ...] = (n_residues, 3, 4)
520
+ elif isinstance(atom_array, AtomArrayStack):
521
+ angle_coord_shape = (atom_array.stack_depth(), n_residues, 3, 4)
522
+ coord_for_phi = np.full(angle_coord_shape, np.nan, dtype=np.float32)
523
+ coord_for_psi = np.full(angle_coord_shape, np.nan, dtype=np.float32)
524
+ coord_for_omg = np.full(angle_coord_shape, np.nan, dtype=np.float32)
525
+
587
526
  # fmt: off
588
- phi_coord [..., 1:, :, 0] = bb_coord[..., ca_i[1: ]-2, :]
589
- phi_coord [..., 1:, :, 1] = bb_coord[..., ca_i[1: ]-1, :]
590
- phi_coord [..., 1:, :, 2] = bb_coord[..., ca_i[1: ], :]
591
- phi_coord [..., 1:, :, 3] = bb_coord[..., ca_i[1: ]+1, :]
592
- psi_coord [..., :-1, :, 0] = bb_coord[..., ca_i[:-1]-1, :]
593
- psi_coord [..., :-1, :, 1] = bb_coord[..., ca_i[:-1], :]
594
- psi_coord [..., :-1, :, 2] = bb_coord[..., ca_i[:-1]+1, :]
595
- psi_coord [..., :-1, :, 3] = bb_coord[..., ca_i[:-1]+2, :]
596
- omega_coord[..., :-1, :, 0] = bb_coord[..., ca_i[:-1], :]
597
- omega_coord[..., :-1, :, 1] = bb_coord[..., ca_i[:-1]+1, :]
598
- omega_coord[..., :-1, :, 2] = bb_coord[..., ca_i[:-1]+2, :]
599
- omega_coord[..., :-1, :, 3] = bb_coord[..., ca_i[:-1]+3, :]
527
+ coord_for_phi[..., 1:, :, 0] = coord_c[..., 0:-1, :]
528
+ coord_for_phi[..., 1:, :, 1] = coord_n[..., 1:, :]
529
+ coord_for_phi[..., 1:, :, 2] = coord_ca[..., 1:, :]
530
+ coord_for_phi[..., 1:, :, 3] = coord_c[..., 1:, :]
531
+
532
+ coord_for_psi[..., 0:-1, :, 0] = coord_n[..., 0:-1, :]
533
+ coord_for_psi[..., 0:-1, :, 1] = coord_ca[..., 0:-1, :]
534
+ coord_for_psi[..., 0:-1, :, 2] = coord_c[..., 0:-1, :]
535
+ coord_for_psi[..., 0:-1, :, 3] = coord_n[..., 1:, :]
536
+
537
+ coord_for_omg[..., 0:-1, :, 0] = coord_ca[..., 0:-1, :]
538
+ coord_for_omg[..., 0:-1, :, 1] = coord_c[..., 0:-1, :]
539
+ coord_for_omg[..., 0:-1, :, 2] = coord_n[..., 1:, :]
540
+ coord_for_omg[..., 0:-1, :, 3] = coord_ca[..., 1:, :]
600
541
  # fmt: on
601
542
 
602
543
  phi = dihedral(
603
- phi_coord[..., 0], phi_coord[..., 1], phi_coord[..., 2], phi_coord[..., 3]
544
+ coord_for_phi[..., 0],
545
+ coord_for_phi[..., 1],
546
+ coord_for_phi[..., 2],
547
+ coord_for_phi[..., 3],
604
548
  )
605
549
  psi = dihedral(
606
- psi_coord[..., 0], psi_coord[..., 1], psi_coord[..., 2], psi_coord[..., 3]
550
+ coord_for_psi[..., 0],
551
+ coord_for_psi[..., 1],
552
+ coord_for_psi[..., 2],
553
+ coord_for_psi[..., 3],
607
554
  )
608
- omega = dihedral(
609
- omega_coord[..., 0],
610
- omega_coord[..., 1],
611
- omega_coord[..., 2],
612
- omega_coord[..., 3],
555
+ omg = dihedral(
556
+ coord_for_omg[..., 0],
557
+ coord_for_omg[..., 1],
558
+ coord_for_omg[..., 2],
559
+ coord_for_omg[..., 3],
613
560
  )
614
561
 
615
- return phi, psi, omega
562
+ return phi, psi, omg
616
563
 
617
564
 
618
565
  def centroid(atoms):
@@ -621,7 +568,7 @@ def centroid(atoms):
621
568
 
622
569
  Parameters
623
570
  ----------
624
- atoms: ndarray or AtomArray or AtomArrayStack
571
+ atoms : ndarray or AtomArray or AtomArrayStack
625
572
  The structures to determine the centroid from.
626
573
  Alternatively an ndarray containing the coordinates can be
627
574
  provided.
@@ -656,7 +603,7 @@ def _call_non_index_function(
656
603
  box = atoms.box
657
604
  else:
658
605
  raise ValueError(
659
- "If `atoms` are coordinates, " "the box must be set explicitly"
606
+ "If `atoms` are coordinates, the box must be set explicitly"
660
607
  )
661
608
  else:
662
609
  box = None
@@ -43,30 +43,28 @@ def hbond(
43
43
  ----------
44
44
  atoms : AtomArray or AtomArrayStack
45
45
  The atoms to find hydrogen bonds in.
46
- selection1, selection2: ndarray or None
46
+ selection1, selection2 : ndarray, optional
47
47
  Boolean mask for atoms to limit the hydrogen bond search to
48
48
  specific sections of the model. The shape must match the
49
49
  shape of the `atoms` argument. If None is given, the whole atoms
50
- stack is used instead. (Default: None)
51
- selection1_type: {'acceptor', 'donor', 'both'}, optional (default: 'both')
50
+ stack is used instead.
51
+ selection1_type : {'acceptor', 'donor', 'both'}, optional
52
52
  Determines the type of `selection1`.
53
53
  The type of `selection2` is chosen accordingly
54
54
  ('both' or the opposite).
55
- (Default: 'both')
56
55
  cutoff_dist : float, optional
57
56
  The maximal distance between the hydrogen and acceptor to be
58
- considered a hydrogen bond. (Default: 2.5)
57
+ considered a hydrogen bond.
59
58
  cutoff_angle : float, optional
60
59
  The angle cutoff in degree between Donor-H..Acceptor to be
61
- considered a hydrogen bond (default: 120).
62
- donor_elements, acceptor_elements: tuple of str
60
+ considered a hydrogen bond.
61
+ donor_elements, acceptor_elements : tuple of str
63
62
  Elements to be considered as possible donors or acceptors
64
63
  (Default: O, N, S).
65
64
  periodic : bool, optional
66
65
  If true, hydrogen bonds can also be detected in periodic
67
66
  boundary conditions.
68
67
  The `box` attribute of `atoms` is required in this case.
69
- (Default: False).
70
68
 
71
69
  Returns
72
70
  -------
@@ -82,6 +80,10 @@ def hbond(
82
80
  `triplets` is present in the model *m* of the input `atoms`.
83
81
  Only returned if `atoms` is an :class:`AtomArrayStack`.
84
82
 
83
+ See Also
84
+ --------
85
+ hbond_frequency : Compute the frequency of each bond over the models.
86
+
85
87
  Notes
86
88
  -----
87
89
  The result of this function may include false positives:
@@ -92,6 +94,11 @@ def hbond(
92
94
  considered as acceptor atom by this method, although this does
93
95
  make sense from a chemical perspective.
94
96
 
97
+ References
98
+ ----------
99
+
100
+ .. footbibliography::
101
+
95
102
  Examples
96
103
  --------
97
104
  Calculate the total number of hydrogen bonds found in each model:
@@ -122,15 +129,6 @@ def hbond(
122
129
  A 15 GLY N N 8.320 -3.632 -0.318
123
130
  A 16 ARG N N 8.043 -1.206 -1.866
124
131
  A 6 TRP NE1 N 3.420 0.332 -0.121
125
-
126
- See Also
127
- --------
128
- hbond_frequency
129
-
130
- References
131
- ----------
132
-
133
- .. footbibliography::
134
132
  """
135
133
  if not (atoms.element == "H").any():
136
134
  warnings.warn(
@@ -400,7 +398,7 @@ def hbond_frequency(mask):
400
398
 
401
399
  Parameters
402
400
  ----------
403
- mask: ndarray, dtype=bool, shape=(m,n)
401
+ mask : ndarray, dtype=bool, shape=(m,n)
404
402
  Input mask obtained from `hbond` function.
405
403
 
406
404
  Returns
@@ -412,7 +410,7 @@ def hbond_frequency(mask):
412
410
 
413
411
  See Also
414
412
  --------
415
- hbond
413
+ hbond : Returns the mask that can be input into this function.
416
414
 
417
415
  Examples
418
416
  --------
@@ -16,6 +16,7 @@ __author__ = "Patrick Kunzmann, Tom David Müller"
16
16
 
17
17
  from .atoms import *
18
18
  from .bonds import *
19
+ from .ccd import *
19
20
  from .groups import *
20
21
  from .masses import *
21
22
  from .misc import *
@@ -18,7 +18,7 @@ NON_HETERO_RESIDUES = set([
18
18
  # fmt: on
19
19
 
20
20
 
21
- def residue(res_name):
21
+ def residue(res_name, allow_missing_coord=False):
22
22
  """
23
23
  Get an atom array, representing the residue with the given name.
24
24
 
@@ -30,6 +30,11 @@ def residue(res_name):
30
30
  ----------
31
31
  res_name : str
32
32
  The up to 3-letter name of the residue.
33
+ allow_missing_coord : bool, optional
34
+ Whether to allow missing coordinate values in the residue.
35
+ If ``True``, these will be represented as ``nan`` values.
36
+ If ``False``, a ``ValueError`` is raised when missing coordinates
37
+ are encountered.
33
38
 
34
39
  Returns
35
40
  -------
@@ -42,19 +47,19 @@ def residue(res_name):
42
47
  >>> alanine = residue("ALA")
43
48
  >>> # Atoms and geometry
44
49
  >>> print(alanine)
45
- 0 ALA N N -0.970 0.490 1.500
46
- 0 ALA CA C 0.260 0.420 0.690
47
- 0 ALA C C -0.090 0.020 -0.720
48
- 0 ALA O O -1.060 -0.680 -0.920
49
- 0 ALA CB C 1.200 -0.620 1.300
50
- 0 ALA OXT O 0.660 0.440 -1.740
51
- 0 ALA H H -1.380 -0.420 1.480
52
- 0 ALA H2 H -0.680 0.660 2.450
53
- 0 ALA HA H 0.750 1.390 0.680
54
- 0 ALA HB1 H 1.460 -0.330 2.320
55
- 0 ALA HB2 H 0.720 -1.590 1.310
56
- 0 ALA HB3 H 2.110 -0.680 0.700
57
- 0 ALA HXT H 0.440 0.180 -2.650
50
+ 0 ALA N N -0.966 0.493 1.500
51
+ 0 ALA CA C 0.257 0.418 0.692
52
+ 0 ALA C C -0.094 0.017 -0.716
53
+ 0 ALA O O -1.056 -0.682 -0.923
54
+ 0 ALA CB C 1.204 -0.620 1.296
55
+ 0 ALA OXT O 0.661 0.439 -1.742
56
+ 0 ALA H H -1.383 -0.425 1.482
57
+ 0 ALA H2 H -0.676 0.661 2.452
58
+ 0 ALA HA H 0.746 1.392 0.682
59
+ 0 ALA HB1 H 1.459 -0.330 2.316
60
+ 0 ALA HB2 H 0.715 -1.594 1.307
61
+ 0 ALA HB3 H 2.113 -0.676 0.697
62
+ 0 ALA HXT H 0.435 0.182 -2.647
58
63
  >>> # Bonds
59
64
  >>> print(alanine.atom_name[alanine.bonds.as_array()[:,:2]])
60
65
  [['N' 'CA']
@@ -74,7 +79,11 @@ def residue(res_name):
74
79
  from biotite.structure.io.pdbx import get_component
75
80
 
76
81
  try:
77
- component = get_component(get_ccd(), res_name=res_name)
82
+ component = get_component(
83
+ get_ccd(),
84
+ res_name=res_name,
85
+ allow_missing_coord=allow_missing_coord,
86
+ )
78
87
  except KeyError:
79
88
  raise KeyError(f"No atom information found for residue '{res_name}' in CCD")
80
89
  component.hetero[:] = res_name not in NON_HETERO_RESIDUES
@@ -6,6 +6,7 @@ __name__ = "biotite.structure.info"
6
6
  __author__ = "Patrick Kunzmann"
7
7
  __all__ = ["bond_type", "bonds_in_residue"]
8
8
 
9
+ import functools
9
10
  from biotite.structure.bonds import BondType
10
11
  from biotite.structure.info.ccd import get_from_ccd
11
12
 
@@ -69,6 +70,7 @@ def bond_type(res_name, atom_name1, atom_name2):
69
70
  return None
70
71
 
71
72
 
73
+ @functools.cache
72
74
  def bonds_in_residue(res_name):
73
75
  """
74
76
  Get a dictionary containing all atoms inside a given residue
@@ -94,6 +96,10 @@ def bonds_in_residue(res_name):
94
96
  In other functionalities throughout *Biotite* that uses this
95
97
  function.
96
98
 
99
+ Notes
100
+ -----
101
+ The returned values are cached for faster access in subsequent calls.
102
+
97
103
  Examples
98
104
  --------
99
105
  >>> bonds = bonds_in_residue("PHE")
@@ -126,16 +132,16 @@ def bonds_in_residue(res_name):
126
132
  """
127
133
  global _intra_bonds
128
134
  if res_name not in _intra_bonds:
129
- chem_comp_bond_dict = get_from_ccd("chem_comp_bond", res_name)
130
- if chem_comp_bond_dict is None:
135
+ chem_comp_bond = get_from_ccd("chem_comp_bond", res_name)
136
+ if chem_comp_bond is None:
131
137
  _intra_bonds[res_name] = {}
132
138
  else:
133
139
  bonds_for_residue = {}
134
140
  for atom1, atom2, order, aromatic_flag in zip(
135
- chem_comp_bond_dict["atom_id_1"],
136
- chem_comp_bond_dict["atom_id_2"],
137
- chem_comp_bond_dict["value_order"],
138
- chem_comp_bond_dict["pdbx_aromatic_flag"],
141
+ chem_comp_bond["atom_id_1"].as_array(),
142
+ chem_comp_bond["atom_id_2"].as_array(),
143
+ chem_comp_bond["value_order"].as_array(),
144
+ chem_comp_bond["pdbx_aromatic_flag"].as_array(),
139
145
  ):
140
146
  bond_type = BOND_TYPES[order, aromatic_flag]
141
147
  bonds_for_residue[atom1.item(), atom2.item()] = bond_type