modelcraft 5.0.2__tar.gz → 6.0.0__tar.gz

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.
Files changed (120) hide show
  1. modelcraft-6.0.0/PKG-INFO +76 -0
  2. modelcraft-6.0.0/README.md +55 -0
  3. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/__init__.py +16 -31
  4. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/__main__.py +0 -1
  5. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/arguments.py +35 -7
  6. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/combine.py +22 -41
  7. modelcraft-6.0.0/modelcraft/contents.py +347 -0
  8. modelcraft-6.0.0/modelcraft/environ.py +8 -0
  9. modelcraft-6.0.0/modelcraft/geometry.py +44 -0
  10. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/job.py +6 -5
  11. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/acedrg.py +2 -0
  12. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/buccaneer.py +22 -4
  13. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/comit.py +2 -0
  14. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/ctruncate.py +3 -1
  15. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/emda.py +2 -0
  16. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/findwaters.py +2 -0
  17. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/freerflag.py +2 -0
  18. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/libg.py +2 -0
  19. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/molrep.py +2 -0
  20. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/nautilus.py +28 -14
  21. modelcraft-6.0.0/modelcraft/jobs/nucleofind.py +88 -0
  22. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/parrot.py +13 -2
  23. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/phasematch.py +2 -1
  24. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/refmac.py +3 -1
  25. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/servalcat.py +38 -4
  26. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/sheetbend.py +2 -0
  27. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/modelcraftem.py +49 -6
  28. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/modelcraftxray.py +90 -42
  29. modelcraft-6.0.0/modelcraft/monlib.py +58 -0
  30. modelcraft-6.0.0/modelcraft/pdbe.py +54 -0
  31. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/pipeline.py +1 -1
  32. modelcraft-6.0.0/modelcraft/prune.py +69 -0
  33. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/reflections.py +11 -1
  34. modelcraft-6.0.0/modelcraft/scripts/contents.py +22 -0
  35. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/scripts/copies.py +26 -17
  36. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/scripts/modelcraft.py +1 -0
  37. modelcraft-6.0.0/modelcraft/scripts/sidechains.py +141 -0
  38. modelcraft-6.0.0/modelcraft/scripts/validate.py +81 -0
  39. modelcraft-6.0.0/modelcraft/sequence.py +106 -0
  40. modelcraft-6.0.0/modelcraft/solvent.py +116 -0
  41. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/structure.py +64 -41
  42. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/__init__.py +7 -11
  43. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_acedrg.py +2 -0
  44. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_arguments.py +3 -0
  45. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_buccaneer.py +3 -2
  46. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_cell.py +4 -1
  47. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_comit.py +2 -0
  48. modelcraft-6.0.0/modelcraft/tests/ccp4/test_contents.py +273 -0
  49. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_copies.py +1 -0
  50. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_ctruncate.py +2 -0
  51. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_findwaters.py +2 -0
  52. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_freerflag.py +2 -0
  53. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_libg.py +1 -0
  54. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_molrep.py +3 -0
  55. modelcraft-6.0.0/modelcraft/tests/ccp4/test_monlib.py +91 -0
  56. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_nautilus.py +5 -3
  57. modelcraft-6.0.0/modelcraft/tests/ccp4/test_nucleofind.py +62 -0
  58. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_parrot.py +3 -1
  59. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_phasematch.py +2 -0
  60. modelcraft-6.0.0/modelcraft/tests/ccp4/test_prune.py +17 -0
  61. {modelcraft-5.0.2/modelcraft/tests/unittests → modelcraft-6.0.0/modelcraft/tests/ccp4}/test_reflections.py +56 -4
  62. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_refmac.py +3 -0
  63. modelcraft-5.0.2/modelcraft/tests/unittests/test_contents.py → modelcraft-6.0.0/modelcraft/tests/ccp4/test_sequence.py +5 -12
  64. modelcraft-6.0.0/modelcraft/tests/ccp4/test_servalcat.py +52 -0
  65. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_sheetbend.py +4 -3
  66. modelcraft-6.0.0/modelcraft/tests/ccp4/test_sidechains.py +25 -0
  67. modelcraft-6.0.0/modelcraft/tests/ccp4/test_solvent.py +16 -0
  68. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_structure.py +1 -0
  69. modelcraft-6.0.0/modelcraft/tests/ccp4/test_validation.py +19 -0
  70. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccp4/test_xray.py +12 -6
  71. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccpem/test_em.py +3 -0
  72. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccpem/test_emda.py +2 -0
  73. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccpem/test_refmac.py +1 -0
  74. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccpem/test_servalcat.py +4 -3
  75. modelcraft-6.0.0/modelcraft/utils.py +18 -0
  76. modelcraft-6.0.0/modelcraft/validation.py +101 -0
  77. modelcraft-6.0.0/modelcraft.egg-info/PKG-INFO +76 -0
  78. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft.egg-info/SOURCES.txt +15 -19
  79. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft.egg-info/entry_points.txt +2 -0
  80. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft.egg-info/requires.txt +1 -0
  81. modelcraft-6.0.0/pyproject.toml +53 -0
  82. modelcraft-6.0.0/setup.cfg +4 -0
  83. modelcraft-5.0.2/LICENSE +0 -504
  84. modelcraft-5.0.2/MANIFEST.in +0 -4
  85. modelcraft-5.0.2/PKG-INFO +0 -48
  86. modelcraft-5.0.2/README.md +0 -14
  87. modelcraft-5.0.2/docs/css/custom.css +0 -23
  88. modelcraft-5.0.2/docs/css/milligram.min.css +0 -1
  89. modelcraft-5.0.2/docs/css/normalize.min.css +0 -2
  90. modelcraft-5.0.2/docs/img/modelcraft.png +0 -0
  91. modelcraft-5.0.2/docs/index.html +0 -283
  92. modelcraft-5.0.2/modelcraft/contents.py +0 -323
  93. modelcraft-5.0.2/modelcraft/coot/prune.py +0 -1085
  94. modelcraft-5.0.2/modelcraft/coot/sidechains.py +0 -68
  95. modelcraft-5.0.2/modelcraft/environ.py +0 -15
  96. modelcraft-5.0.2/modelcraft/geometry.py +0 -32
  97. modelcraft-5.0.2/modelcraft/jobs/acorn.py +0 -114
  98. modelcraft-5.0.2/modelcraft/jobs/coot.py +0 -104
  99. modelcraft-5.0.2/modelcraft/monlib.py +0 -55
  100. modelcraft-5.0.2/modelcraft/scripts/contents.py +0 -232
  101. modelcraft-5.0.2/modelcraft/solvent.py +0 -187
  102. modelcraft-5.0.2/modelcraft/tests/ccp4/test_contents.py +0 -191
  103. modelcraft-5.0.2/modelcraft/tests/ccp4/test_coot.py +0 -29
  104. modelcraft-5.0.2/modelcraft/tests/ccp4/test_geometry.py +0 -20
  105. modelcraft-5.0.2/modelcraft/tests/ccp4/test_monlib.py +0 -61
  106. modelcraft-5.0.2/modelcraft/tests/ccp4/test_reflections.py +0 -44
  107. modelcraft-5.0.2/modelcraft/tests/ccp4/test_solvent.py +0 -30
  108. modelcraft-5.0.2/modelcraft/tests/unittests/__init__.py +0 -0
  109. modelcraft-5.0.2/modelcraft/utils.py +0 -6
  110. modelcraft-5.0.2/modelcraft.egg-info/PKG-INFO +0 -48
  111. modelcraft-5.0.2/setup.cfg +0 -9
  112. modelcraft-5.0.2/setup.py +0 -42
  113. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/cell.py +0 -0
  114. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/jobs/__init__.py +0 -0
  115. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/maps.py +0 -0
  116. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/scripts/__init__.py +0 -0
  117. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/__init__.py +0 -0
  118. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft/tests/ccpem/__init__.py +0 -0
  119. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft.egg-info/dependency_links.txt +0 -0
  120. {modelcraft-5.0.2 → modelcraft-6.0.0}/modelcraft.egg-info/top_level.txt +0 -0
@@ -0,0 +1,76 @@
1
+ Metadata-Version: 2.4
2
+ Name: modelcraft
3
+ Version: 6.0.0
4
+ Summary: Automated model-building pipeline for X-ray crystallography and cryo-EM
5
+ Author-email: Paul Bond <paul.bond@york.ac.uk>
6
+ Maintainer-email: Paul Bond <paul.bond@york.ac.uk>
7
+ Project-URL: Source, https://github.com/paulsbond/modelcraft
8
+ Project-URL: Issues, https://github.com/paulsbond/modelcraft/issues
9
+ Classifier: Development Status :: 5 - Production/Stable
10
+ Classifier: License :: OSI Approved :: GNU Lesser General Public License v2 or later (LGPLv2+)
11
+ Classifier: Operating System :: OS Independent
12
+ Classifier: Programming Language :: Python :: 3
13
+ Requires-Python: >=3.9
14
+ Description-Content-Type: text/markdown
15
+ Requires-Dist: gemmi>=0.5.5
16
+ Requires-Dist: numpy
17
+ Requires-Dist: pandas
18
+ Requires-Dist: requests
19
+ Requires-Dist: scipy
20
+ Requires-Dist: tabulate
21
+
22
+ ![](https://github.com/paulsbond/modelcraft/blob/691b8a0d72dbf48b8d8a431bdb193298a397e1bb/modelcraft.png)
23
+
24
+ # ModelCraft
25
+
26
+ ModelCraft is an automated model-building pipeline
27
+ that builds proteins and nucleic acids
28
+ into X-ray crystallography and cryo-EM maps.
29
+ It combines the previous Buccaneer and Nautilus pipelines and adds new steps
30
+ for density modification, refinement, validation and pruning.
31
+
32
+ ## Installation
33
+
34
+ ModelCraft is distributed with CCP4.
35
+ Please obtain the latest version from the
36
+ [CCP4 download page](https://www.ccp4.ac.uk/download).
37
+
38
+ ## Graphical interfaces
39
+
40
+ For X-ray crystallography, ModelCraft can be used through
41
+ [CCP4i2](https://ccp4i2.gitlab.io/rstdocs/tasks/modelcraft/index.html) or
42
+ [CCP4 Cloud](https://cloud.ccp4.ac.uk/manuals/html-taskref/doc.task.ModelCraft.html).
43
+ For cryo-EM, it is available in
44
+ [CCP-EM Doppio](https://www.ccpem.ac.uk/docs/doppio/user_guide.html).
45
+
46
+ ## Command-line interface
47
+
48
+ The first argument must be either
49
+ `xray` for X-ray crystallography or `em` for cryo-EM SPA.
50
+ The command line documentation has detailed information on individual arguments.
51
+
52
+ ```bash
53
+ modelcraft xray --help
54
+ ```
55
+
56
+ ```bash
57
+ modelcraft em --help
58
+ ```
59
+
60
+ ## Links
61
+
62
+ - [Source (latest)](https://github.com/paulsbond/modelcraft)
63
+ - [Source (releases)](https://github.com/paulsbond/modelcraft/releases)
64
+ - [Issues (e.g. bugs and feature requests)](https://github.com/paulsbond/modelcraft/issues)
65
+ - [PyPI (Python Package Index)](https://pypi.org/project/modelcraft)
66
+
67
+ ## Citations
68
+
69
+ - [ModelCraft](https://doi.org/10.1107/S2059798322007732)
70
+ - [Buccaneer](https://doi.org/10.1107/S0907444906022116)
71
+ - [EMDA](https://doi.org/10.1016/j.jsb.2021.107826)
72
+ - [Nautilus](https://doi.org/10.1107/S2052252514019290)
73
+ - [Parrot](https://doi.org/10.1107/S090744490903947X)
74
+ - [Refmac](https://doi.org/10.1107/S2059798318000979)
75
+ - [Servalcat](https://doi.org/10.1107/S2059798321009475)
76
+ - [Sheetbend](https://doi.org/10.1107/S2059798320013170)
@@ -0,0 +1,55 @@
1
+ ![](https://github.com/paulsbond/modelcraft/blob/691b8a0d72dbf48b8d8a431bdb193298a397e1bb/modelcraft.png)
2
+
3
+ # ModelCraft
4
+
5
+ ModelCraft is an automated model-building pipeline
6
+ that builds proteins and nucleic acids
7
+ into X-ray crystallography and cryo-EM maps.
8
+ It combines the previous Buccaneer and Nautilus pipelines and adds new steps
9
+ for density modification, refinement, validation and pruning.
10
+
11
+ ## Installation
12
+
13
+ ModelCraft is distributed with CCP4.
14
+ Please obtain the latest version from the
15
+ [CCP4 download page](https://www.ccp4.ac.uk/download).
16
+
17
+ ## Graphical interfaces
18
+
19
+ For X-ray crystallography, ModelCraft can be used through
20
+ [CCP4i2](https://ccp4i2.gitlab.io/rstdocs/tasks/modelcraft/index.html) or
21
+ [CCP4 Cloud](https://cloud.ccp4.ac.uk/manuals/html-taskref/doc.task.ModelCraft.html).
22
+ For cryo-EM, it is available in
23
+ [CCP-EM Doppio](https://www.ccpem.ac.uk/docs/doppio/user_guide.html).
24
+
25
+ ## Command-line interface
26
+
27
+ The first argument must be either
28
+ `xray` for X-ray crystallography or `em` for cryo-EM SPA.
29
+ The command line documentation has detailed information on individual arguments.
30
+
31
+ ```bash
32
+ modelcraft xray --help
33
+ ```
34
+
35
+ ```bash
36
+ modelcraft em --help
37
+ ```
38
+
39
+ ## Links
40
+
41
+ - [Source (latest)](https://github.com/paulsbond/modelcraft)
42
+ - [Source (releases)](https://github.com/paulsbond/modelcraft/releases)
43
+ - [Issues (e.g. bugs and feature requests)](https://github.com/paulsbond/modelcraft/issues)
44
+ - [PyPI (Python Package Index)](https://pypi.org/project/modelcraft)
45
+
46
+ ## Citations
47
+
48
+ - [ModelCraft](https://doi.org/10.1107/S2059798322007732)
49
+ - [Buccaneer](https://doi.org/10.1107/S0907444906022116)
50
+ - [EMDA](https://doi.org/10.1016/j.jsb.2021.107826)
51
+ - [Nautilus](https://doi.org/10.1107/S2052252514019290)
52
+ - [Parrot](https://doi.org/10.1107/S090744490903947X)
53
+ - [Refmac](https://doi.org/10.1107/S2059798318000979)
54
+ - [Servalcat](https://doi.org/10.1107/S2059798321009475)
55
+ - [Sheetbend](https://doi.org/10.1107/S2059798320013170)
@@ -1,16 +1,11 @@
1
- __version__ = "5.0.2"
1
+ __version__ = "6.0.0"
2
2
 
3
3
  from .cell import max_distortion as max_cell_distortion
4
- from .cell import remove_scale
5
- from .cell import update_cell
6
- from .contents import AsuContents
7
- from .contents import PolymerType
8
- from .geometry import rmsz
4
+ from .cell import remove_scale, update_cell
5
+ from .contents import AsuContents, PolymerType
9
6
  from .jobs.acedrg import Acedrg
10
7
  from .jobs.buccaneer import Buccaneer
11
8
  from .jobs.comit import Comit
12
- from .jobs.coot import FixSideChains
13
- from .jobs.coot import Prune
14
9
  from .jobs.ctruncate import CTruncate
15
10
  from .jobs.emda import EmdaMapMask
16
11
  from .jobs.findwaters import FindWaters
@@ -19,26 +14,21 @@ from .jobs.molrep import Molrep
19
14
  from .jobs.nautilus import Nautilus
20
15
  from .jobs.parrot import Parrot
21
16
  from .jobs.phasematch import PhaseMatch
22
- from .jobs.refmac import Refmac
23
- from .jobs.refmac import RefmacMapToMtz
24
- from .jobs.servalcat import ServalcatNemap
25
- from .jobs.servalcat import ServalcatRefine
26
- from .jobs.servalcat import ServalcatTrim
17
+ from .jobs.refmac import Refmac, RefmacMapToMtz
18
+ from .jobs.servalcat import ServalcatNemap, ServalcatRefine, ServalcatTrim
27
19
  from .jobs.sheetbend import Sheetbend
20
+ from .monlib import MonLib
28
21
  from .pipeline import Pipeline
29
- from .reflections import DataItem
30
- from .reflections import write_mtz
31
- from .scripts.contents import _entry_contents as entry_contents
22
+ from .reflections import DataItem, write_mtz
32
23
  from .scripts.modelcraft import main as run
33
- from .solvent import solvent_fraction
34
- from .structure import contains_residue
35
- from .structure import ModelStats
36
- from .structure import read_structure
37
- from .structure import remove_non_library_atoms
38
- from .structure import remove_non_protein
39
- from .structure import remove_residues
40
- from .structure import write_mmcif
41
-
24
+ from .structure import (
25
+ ModelStats,
26
+ contains_residue,
27
+ read_structure,
28
+ remove_non_protein,
29
+ remove_residues,
30
+ write_mmcif,
31
+ )
42
32
 
43
33
  __all__ = [
44
34
  "Acedrg",
@@ -49,33 +39,28 @@ __all__ = [
49
39
  "CTruncate",
50
40
  "DataItem",
51
41
  "EmdaMapMask",
52
- "entry_contents",
53
42
  "FindWaters",
54
- "FixSideChains",
55
43
  "FreeRFlag",
56
44
  "max_cell_distortion",
57
45
  "ModelStats",
58
46
  "Molrep",
47
+ "MonLib",
59
48
  "Nautilus",
60
49
  "Parrot",
61
50
  "PhaseMatch",
62
51
  "Pipeline",
63
52
  "PolymerType",
64
- "Prune",
65
53
  "read_structure",
66
54
  "Refmac",
67
55
  "RefmacMapToMtz",
68
- "remove_non_library_atoms",
69
56
  "remove_non_protein",
70
57
  "remove_residues",
71
58
  "remove_scale",
72
- "rmsz",
73
59
  "run",
74
60
  "ServalcatNemap",
75
61
  "ServalcatRefine",
76
62
  "ServalcatTrim",
77
63
  "Sheetbend",
78
- "solvent_fraction",
79
64
  "update_cell",
80
65
  "write_mmcif",
81
66
  "write_mtz",
@@ -1,5 +1,4 @@
1
1
  from .scripts.modelcraft import main
2
2
 
3
-
4
3
  if __name__ == "__main__":
5
4
  main()
@@ -1,15 +1,16 @@
1
- from typing import List, Optional
2
1
  import argparse
3
2
  import os
4
3
  import sys
4
+ from typing import List, Optional
5
+
5
6
  import gemmi
6
7
  import numpy as np
8
+
7
9
  from . import __version__
8
10
  from .contents import AsuContents
9
11
  from .reflections import DataItem
10
12
  from .structure import read_structure
11
13
 
12
-
13
14
  _PROG = None
14
15
  if os.path.basename(sys.argv[0]) == "__main__.py":
15
16
  _PROG = f"{sys.executable} -m modelcraft"
@@ -23,12 +24,16 @@ _GROUP.add_argument(
23
24
  required=True,
24
25
  metavar="X",
25
26
  help=(
26
- "A file with a description of the assymetric unit contents, "
27
+ "A file with a description of the full asymmetric unit contents, "
27
28
  "either as a sequence file (in FASTA or PIR format) "
28
29
  "with both protein and nucleic acid sequences, "
29
30
  "or a more detailed contents file in JSON format. "
30
31
  "Example JSON files for existing PDB entries "
31
- "can be created using the modelcraft-contents script."
32
+ "can be created using the modelcraft-contents script. "
33
+ "Currently, the only advantage of using the JSON format "
34
+ "is a more accurate calculation of the solvent fraction "
35
+ "for Parrot density modification in the X-ray pipeline. "
36
+ "Otherwise, the solvent fraction will be calculated using Matthews probability."
32
37
  ),
33
38
  )
34
39
  _GROUP = _PARENT.add_argument_group("optional arguments (shared)")
@@ -181,6 +186,16 @@ _GROUP.add_argument(
181
186
  "This is not required if the MTZ only contains one free-R flag."
182
187
  ),
183
188
  )
189
+ _GROUP.add_argument(
190
+ "--freerflag-value",
191
+ type=int,
192
+ metavar="X",
193
+ help=(
194
+ "Value of the free-R flag to identify reflections as free. "
195
+ "It defaults to the lowest flag with <50% of reflections. "
196
+ "If the chosen flag is not 0 it will changed to match the CCP4 convention."
197
+ ),
198
+ )
184
199
  _GROUP.add_argument(
185
200
  "--unbiased",
186
201
  action="store_true",
@@ -387,9 +402,22 @@ def _parse_freerflag(args: argparse.Namespace, mtz: gemmi.Mtz):
387
402
  else:
388
403
  args.freer = _item_from_label(mtz, args.freerflag_label, ["I"])
389
404
  values = list(args.freer.columns[-1])
390
- percentage = values.count(0) / len(values) * 100
391
- if percentage == 0 or percentage > 50:
392
- _PARSER.error(f"{percentage}% of the reflections are in the free set (flag 0)")
405
+ if args.freerflag_value is None:
406
+ for value in sorted(set(values)):
407
+ fraction = values.count(value) / len(values)
408
+ if fraction < 0.5:
409
+ args.freerflag_value = value
410
+ break
411
+ else:
412
+ _PARSER.error("No suitable value found for the free-R flag")
413
+ else:
414
+ percentage = values.count(args.freerflag_value) / len(values) * 100
415
+ if percentage == 0 or percentage > 50:
416
+ _PARSER.error(f"{percentage}% of the reflections are in the free set")
417
+ if args.freerflag_value != 0:
418
+ print("Changing the free-R flag to match CCP4 convention", flush=True)
419
+ values = [0 if v == args.freerflag_value else 1 for v in values]
420
+ args.freer.array[:, -1] = values
393
421
 
394
422
 
395
423
  def _parse_phases(args: argparse.Namespace, mtz: gemmi.Mtz):
@@ -1,23 +1,29 @@
1
1
  import gemmi
2
+
2
3
  from .jobs.refmac import RefmacResult
3
- from .monlib import is_protein, is_nucleic
4
+ from .monlib import MonLib
5
+ from .structure import remove_isolated_fragments
4
6
 
5
7
 
6
- def combine_results(buccaneer: RefmacResult, nautilus: RefmacResult) -> gemmi.Structure:
8
+ def combine_results(
9
+ buccaneer: RefmacResult, nautilus: RefmacResult, monlib: MonLib
10
+ ) -> gemmi.Structure:
7
11
  structure = buccaneer.structure.clone()
8
12
  for i, chain in reversed(list(enumerate(structure[0]))):
9
- if _is_nucleic_chain(chain):
13
+ if _is_nucleic_chain(chain, monlib):
10
14
  del structure[0][i]
11
- chains_to_add, clashing_to_remove = _resolve_clashes(structure, buccaneer, nautilus)
15
+ chains_to_add, clashing_to_remove = _resolve_clashes(
16
+ structure, buccaneer, nautilus, monlib
17
+ )
12
18
  for chain in structure[0]:
13
- protein = _is_protein_chain(chain)
19
+ protein = _is_protein_chain(chain, monlib)
14
20
  any_removed = False
15
21
  for i, residue in reversed(list(enumerate(chain))):
16
22
  if _key(chain, residue) in clashing_to_remove:
17
23
  del chain[i]
18
24
  any_removed = True
19
25
  if protein and any_removed:
20
- _remove_isolated_fragments(chain, _are_joined_protein, min_length=6)
26
+ remove_isolated_fragments(chain, monlib, max_length=5)
21
27
  structure.remove_empty_chains()
22
28
  for chain in chains_to_add:
23
29
  structure[0].add_chain(chain, unique_name=True)
@@ -25,7 +31,10 @@ def combine_results(buccaneer: RefmacResult, nautilus: RefmacResult) -> gemmi.St
25
31
 
26
32
 
27
33
  def _resolve_clashes(
28
- structure: gemmi.Structure, buccaneer: RefmacResult, nautilus: RefmacResult
34
+ structure: gemmi.Structure,
35
+ buccaneer: RefmacResult,
36
+ nautilus: RefmacResult,
37
+ monlib: MonLib,
29
38
  ) -> tuple:
30
39
  chains_to_add = []
31
40
  clashing_to_remove = set()
@@ -33,7 +42,7 @@ def _resolve_clashes(
33
42
  naut_scores = _scores(nautilus)
34
43
  search = gemmi.NeighborSearch(structure, max_radius=1).populate()
35
44
  for chain in nautilus.structure[0]:
36
- if _is_nucleic_chain(chain):
45
+ if _is_nucleic_chain(chain, monlib):
37
46
  residues_to_remove = set()
38
47
  for keys, clashing in _clashing_zones(chain, search, structure):
39
48
  if _mean_score(keys, naut_scores) < _mean_score(clashing, bucc_scores):
@@ -44,7 +53,7 @@ def _resolve_clashes(
44
53
  for i, residue in reversed(list(enumerate(chain))):
45
54
  if _key(chain, residue) in residues_to_remove:
46
55
  del chain[i]
47
- _remove_isolated_fragments(chain, _are_joined_nucleic, min_length=2)
56
+ remove_isolated_fragments(chain, monlib, max_length=1)
48
57
  if len(chain) > 0:
49
58
  chains_to_add.append(chain)
50
59
  return chains_to_add, clashing_to_remove
@@ -74,12 +83,12 @@ def _key(chain: gemmi.Chain, residue: gemmi.Residue) -> tuple:
74
83
  return (chain.name, residue.seqid.num, residue.seqid.icode)
75
84
 
76
85
 
77
- def _is_nucleic_chain(chain: gemmi.Chain) -> bool:
78
- return len(chain) > 1 and all(is_nucleic(res.name) for res in chain)
86
+ def _is_nucleic_chain(chain: gemmi.Chain, monlib: MonLib) -> bool:
87
+ return len(chain) > 1 and all(monlib.is_nucleic(res.name) for res in chain)
79
88
 
80
89
 
81
- def _is_protein_chain(chain: gemmi.Chain) -> bool:
82
- return len(chain) > 1 and all(is_protein(res.name) for res in chain)
90
+ def _is_protein_chain(chain: gemmi.Chain, monlib: MonLib) -> bool:
91
+ return len(chain) > 1 and all(monlib.is_protein(res.name) for res in chain)
83
92
 
84
93
 
85
94
  def _clashing_zones(
@@ -106,31 +115,3 @@ def _clashing_zones(
106
115
 
107
116
  def _mean_score(keys: set, scores: dict) -> float:
108
117
  return sum(scores[key] for key in keys) / len(keys)
109
-
110
-
111
- def _remove_isolated_fragments(chain: gemmi.Chain, are_joined, min_length: int):
112
- to_remove = []
113
- fragment = []
114
- for i, residue in enumerate(chain):
115
- if i > 0 and are_joined(chain[i - 1], residue):
116
- fragment.append(i)
117
- else:
118
- if len(fragment) < min_length:
119
- to_remove.extend(fragment)
120
- fragment = [i]
121
- if len(fragment) < min_length:
122
- to_remove.extend(fragment)
123
- for i in reversed(to_remove):
124
- del chain[i]
125
-
126
-
127
- def _are_joined_protein(res1: gemmi.Residue, res2: gemmi.Residue) -> bool:
128
- return "C" in res1 and "N" in res2 and res1["C"][0].pos.dist(res2["N"][0].pos) < 2.5
129
-
130
-
131
- def _are_joined_nucleic(res1: gemmi.Residue, res2: gemmi.Residue) -> bool:
132
- return (
133
- "O3'" in res1
134
- and "P" in res2
135
- and res1["O3'"][0].pos.dist(res2["P"][0].pos) < 2.5
136
- )