tmquick 1.0.0__py3-none-any.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.
tmq/__init__.py ADDED
@@ -0,0 +1,14 @@
1
+ __version__ = "1.0"
2
+ from .core.traj2pdb import traj2pdb
3
+ from .core.pdb2csv import pdb2csv
4
+ from .core.trajmap import trajmap
5
+ from .core.csv2shift import shift
6
+ from .core.shift2graph import shift2graph
7
+ from .core.hotspot import detect_shifts
8
+ from .core.hotspot import create_submatrices
9
+ from .core.hotspot import plot_shift_regions
10
+ from .core.hotspot import slice_shifts
11
+ from .core.hotspot import plot_slice_regions
12
+ from .core.hotspot import plot_hotspot_regions
13
+ from .core.diff2graph import diff_map
14
+ from .core.average_trajmap import avg_trajmap
tmq/cli.py ADDED
@@ -0,0 +1,250 @@
1
+ """Main CLI launcher
2
+ """
3
+
4
+ import argparse
5
+ import time
6
+ from .commands.traj2pdb_cli import traj2pdb_cli
7
+ from .commands.pdb2csv_cli import pdb2csv_cli
8
+ from .commands.trajmap_cli import trajmap_cli
9
+ from .commands.csv2shift_cli import shift_cli
10
+ from .commands.shift2graph_cli import shift2graph_cli
11
+ from .commands.hotspot_cli import detect_shift_cli
12
+ from .commands.hotspot_cli import create_submatrices_cli
13
+ from .commands.hotspot_cli import slice_shifts_cli
14
+ from .commands.hotspot_cli import run_hotspot_cli
15
+ from .commands.diff2graph_cli import diff_map_cli
16
+ from .commands.average_trajmap_cli import avg_trajmap_cli
17
+ from colorama import init, Fore, Style
18
+ init(convert=False)
19
+
20
+
21
+ """Time counter"""
22
+ def print_final_message(total):
23
+ print(
24
+ Fore.GREEN +
25
+ "\nTrajMapQuick analysis complete. \n" +
26
+ Fore.CYAN +
27
+ "\nAll tasks completed successfully.\n"+
28
+ Style.RESET_ALL
29
+ )
30
+ print(f"Total computation time: {total:.2f} seconds \n" +
31
+ Fore.MAGENTA +
32
+ "\nThank you for using TrajMapQuick 1.0 — ResLaR Labs, Afe Babalola University, Ado-Ekiti Nigeria.\n" +
33
+ Style.RESET_ALL)
34
+
35
+
36
+ """Display logo"""
37
+ def main():
38
+ start_time = time.perf_counter()
39
+ init()
40
+ print(Fore.GREEN + r"""
41
+
42
+ _______ _ __ __ ____
43
+ |__ __| (_) \/ | / __ \
44
+ | |_ __ __ _ _| \ / | __ _ _ __ | | | |
45
+ | | '__/ _` | | |\/| |/ _` | '_ \| | | |
46
+ | | | | (_| | | | | | (_| | |_) | |__| |
47
+ |_|_| \__,_| |_| |_|\__,_| .__/ \___\_\
48
+ _/ | | |
49
+ |__/ |_|
50
+
51
+
52
+ """ + Style.RESET_ALL)
53
+ print("========== Welcome to TrajMapQuick 1.0 ==========")
54
+ print("")
55
+ print("Authors : " + Fore.BLUE + "Wande M. Oluyemi, Adeniyi T. Adewumi, Shadrach C. Eze & Stephen C. Nnemolisa @ ResLaR Labs, Afe Babalola University, Ado-Ekiti Nigeria" + Style.RESET_ALL)
56
+ print("")
57
+ print("")
58
+
59
+ parser = argparse.ArgumentParser(
60
+ prog="tmq",
61
+ add_help=False,
62
+ formatter_class=argparse.RawTextHelpFormatter,
63
+ description="""
64
+ A command-line toolkit for MD trajectory map analysis:
65
+ • matrix extraction
66
+ • shift computation
67
+ • visualization
68
+
69
+ Built on the original work of Kožić & Bertoša, 2024,
70
+ Trajectory maps: molecular dynamics visualization and analysis,
71
+ https://doi.org/10.1093/nargab/lqad114
72
+
73
+ TrajMapQuick is faster, improves batch processing, and allows
74
+ automatic shift detection from trajectory maps.
75
+ """
76
+ )
77
+
78
+ parser.add_argument(
79
+ "-h", "--help",
80
+ action="help",
81
+ help="Show usage information")
82
+
83
+ subparsers = parser.add_subparsers(
84
+ title="Available subcommands",
85
+ dest="command",
86
+ metavar=""
87
+ )
88
+
89
+ """SHIFT SUBCOMMAND"""
90
+ shift_parser = subparsers.add_parser(
91
+ "shift",
92
+ help="Extract matrices, compute residue-residue shifts and make plots: For more, use tmq shift --help",
93
+ description=(
94
+ "Converts your trajectory into pdb multimodel form and then to a CSV file, "
95
+ "extracts a distance matrix from the CSV file and computes "
96
+ "a shift value between a residue range over a specified frame.\n\n"
97
+ "Example:\n"
98
+ " tmq shift --traj traj.pdb --top top.parmtop --str 1 --resr 1-300 --resrs 110-125 --cent backbone --plot --out shift_output\n\n"
99
+ "This will compute the shift of the backbone atoms, for residues 110-125, across the trajectory of a protein with residues 1-300, and will generate plots automatically."),
100
+ formatter_class=argparse.RawTextHelpFormatter
101
+ )
102
+
103
+ shift_parser.add_argument("-tr", "--traj", required=True,
104
+ help="Input trajectory, accepts pdb, nc, xtc xtr")
105
+ shift_parser.add_argument("-to", "--top", required=True,
106
+ help="Topology file, accepts parmtop, pdb, gro")
107
+ shift_parser.add_argument("-st", "--str", type=int, default=1,
108
+ help="Stride of the trajectory, (default: 1)")
109
+ shift_parser.add_argument("-rr", "--resr", type=str, required=True,
110
+ help="Residue range of your protein in the form start-end (e.g., 1-300")
111
+ shift_parser.add_argument("-rs", "--resrs", type=str, required=True,
112
+ help="Residue range for shift calculation, in the form start-end (e.g., 110-125")
113
+ shift_parser.add_argument("-ce", "--cent", type=str, default="backbone", required=True,
114
+ help="Centre of calculations, either the backbone " \
115
+ "atoms or the ca atoms, (default: backbone)")
116
+ shift_parser.add_argument("-ma", "--max", type=int, default=5, required=False,
117
+ help="Max shift value for color scaling, (default: 5)")
118
+ shift_parser.add_argument("-o", "--out", type=str, required=True,
119
+ help="Basename for all outputs")
120
+
121
+
122
+ """HOTSPOT SUBCOMMAND"""
123
+ dehot_parser = subparsers.add_parser(
124
+ "hotspot",
125
+ help="Detect hotspots in residue shifts and create plots: For more, use tmq hotspot --help",
126
+ description=(
127
+ "Detect hotspots in residue shifts and creates publication-ready plot with trajectory map"
128
+ "and hotspot regions annotated, and also generates shift graphs for detected hotspot regions.\n\n"
129
+ "Example:\n"
130
+ " tmq hotspot --traj traj.pdb --top top.parmtop --str 1 --resr 1-300 --cent backbone --out hotspot_output\n\n"
131
+ ),
132
+ formatter_class=argparse.RawTextHelpFormatter
133
+ )
134
+
135
+ dehot_parser.add_argument("-tr", "--traj", required=True,
136
+ help="Input trajectory, accepts Pdb, nc, xtc xtr")
137
+ dehot_parser.add_argument("-to", "--top", required=True,
138
+ help="Topology file, accepts .parmtop, pdb, gro")
139
+ dehot_parser.add_argument("-st", "--str", type=int, default=1,
140
+ help="Stride of the trajectory, (default: 1)")
141
+ dehot_parser.add_argument("-rr", "--resr", type=str, required=True,
142
+ help="Residue range of your protein in the form start-end (e.g., 1-300")
143
+ dehot_parser.add_argument("-ce", "--cent", type=str, default="backbone", required=True,
144
+ help="Centre of calculations, either the backbone " \
145
+ "atoms or the ca atoms, (default: backbone)")
146
+ dehot_parser.add_argument("-win", "--window", type=int, default=5, required=False,
147
+ help="Rolling window size for smoothing, (default: 5) (Not Required)")
148
+ dehot_parser.add_argument("-md", "--mindist", type=int, default=3, required=False,
149
+ help="Minimum distance between peaks, (default: 3) (Not Required)")
150
+ dehot_parser.add_argument("-hs", "--hot", type=int, default=10, required=False,
151
+ help="Number of top peaks to extract, (default: 10) (Not Required)")
152
+ dehot_parser.add_argument("-ma", "--max", type=int, default=5, required=False,
153
+ help="Max shift value for color scaling, (default: 5) (Not Required)")
154
+ dehot_parser.add_argument("-o", "--out", type=str, required=True,
155
+ help="Basename for outputs")
156
+
157
+
158
+ """DIFFERENCE SUBCOMMAND"""
159
+ dehot_parser = subparsers.add_parser(
160
+ "diff",
161
+ help="Computes difference between two matrices and creates the difference map: For more, use tmq diff --help",
162
+ description=(
163
+ "Computes difference between two matrices and creates publication-ready plot with difference map.\n\n"
164
+ "The input matrices must be supplied by the names of the output of previous 'Shift' runs.\n\n"
165
+ "A subsequent downstream processing after 'Shift' runs; thus, matrices must have equal lengths.\n\n"
166
+ "Example:\n"
167
+ " tmq diff --mat1 apo --mat2 holo --resr 1-300 --max 8 --out my_diff\n\n"
168
+ ),
169
+ formatter_class=argparse.RawTextHelpFormatter
170
+ )
171
+
172
+ dehot_parser.add_argument("-m1", "--mat1", required=True,
173
+ help="First matrix, accepts only the name without extension")
174
+ dehot_parser.add_argument("-m2", "--mat2", required=True,
175
+ help="Second matrix, accepts only the name without extension")
176
+ dehot_parser.add_argument("-rr", "--resr", type=str, required=True,
177
+ help="Residue range of your protein in the form start-end (e.g., 1-300")
178
+ dehot_parser.add_argument("-ma", "--max", type=int, default=5, required=True,
179
+ help="Max shift value for color scaling, (default: 5)")
180
+ dehot_parser.add_argument("-o", "--out", type=str, required=True,
181
+ help="Basename for outputs")
182
+
183
+
184
+
185
+ """DIFFERENCE SUBCOMMAND"""
186
+ dehot_parser = subparsers.add_parser(
187
+ "average",
188
+ help="Computes average of n matrices and creates the average map: For more, use tmq average --help",
189
+ description=(
190
+ "Computes average of n matrices and creates publication-ready plot with average map. \n\n"
191
+ "The input matrices must be supplied by the names of the output of previous 'Shift' runs as comma separated values.\n\n"
192
+ "A subsequent downstream processing after 'Shift' runs; thus, matrices must have equal lengths.\n\n"
193
+ "Example:\n"
194
+ " tmq average --mat apo,holo,bound --resr 1-300 --max 8 --out my_avg\n\n"
195
+ ),
196
+ formatter_class=argparse.RawTextHelpFormatter
197
+ )
198
+
199
+ dehot_parser.add_argument("-m", "--mat", required=True, type=str,
200
+ help="Comma-separated list of matrix names, accepts only the name without extension")
201
+ dehot_parser.add_argument("-rr", "--resr", type=str, required=True,
202
+ help="Residue range of your protein in the form start-end (e.g., 1-300")
203
+ dehot_parser.add_argument("-ma", "--max", type=int, default=5, required=True,
204
+ help="Max shift value for color scaling, (default: 5)")
205
+ dehot_parser.add_argument("-o", "--out", type=str, required=True,
206
+ help="Basename for outputs")
207
+
208
+
209
+ print("")
210
+ args = parser.parse_args()
211
+
212
+ if args.command == "shift":
213
+ traj2pdb_cli(args)
214
+ pdb2csv_cli(args)
215
+ shift_cli(args)
216
+ trajmap_cli(args)
217
+ shift2graph_cli(args)
218
+ end_time = time.perf_counter()
219
+ total = end_time - start_time
220
+ print_final_message(total)
221
+ elif args.command == "hotspot":
222
+ traj2pdb_cli(args)
223
+ pdb2csv_cli(args)
224
+ trajmap_cli(args)
225
+ detect_shift_cli(args)
226
+ create_submatrices_cli(args)
227
+ run_hotspot_cli(args)
228
+ slice_shifts_cli(args)
229
+ run_hotspot_cli(args)
230
+ end_time = time.perf_counter()
231
+ total = end_time - start_time
232
+ print_final_message(total)
233
+
234
+ elif args.command == "diff":
235
+ diff_map_cli(args)
236
+ end_time = time.perf_counter()
237
+ total = end_time - start_time
238
+ print_final_message(total)
239
+
240
+ elif args.command == "average":
241
+ avg_trajmap_cli(args)
242
+ end_time = time.perf_counter()
243
+ total = end_time - start_time
244
+ print_final_message(total)
245
+
246
+ else:
247
+ parser.print_help()
248
+ print("")
249
+ print("Cite this as: " + Fore.BLUE + "SHEDOOMTC. (2026). TrajMapQuick: Towards Fast Trajectory Map Analysis and Visualization (v1.0). Zenodo. https://doi.org/10.5281/zenodo.20681061" + Style.RESET_ALL)
250
+ print("")
@@ -0,0 +1,2 @@
1
+ __version__ = "1.0"
2
+
@@ -0,0 +1,36 @@
1
+ """Parse input matrices, compute their element-wise average,
2
+ and save an averaged trajectory map PNG.
3
+ """
4
+
5
+ import time
6
+ from ..core.average_trajmap import avg_trajmap
7
+ import matplotlib
8
+ matplotlib.use("Agg")
9
+ import matplotlib.pyplot as plt
10
+ from ..utils.utils import ensure_csv_extension, ensure_png_extension, parse_range, load_matrix_4_diff_map, csv2matrix
11
+
12
+
13
+ def avg_trajmap_cli(args):
14
+ start_time = time.perf_counter()
15
+ print("")
16
+ print("Plotting Average map...")
17
+
18
+ """split the matrix argument to get list of matrices
19
+ """
20
+ matrix_names = args.mat.split(",")
21
+ prefix = "_pdb2csv_"
22
+ matrices = [csv2matrix(ensure_csv_extension(name + prefix)) for name in matrix_names]
23
+
24
+ residue_start, residue_end = parse_range(args.resr)
25
+
26
+ """pass the matrices to the core function
27
+ """
28
+ fig = avg_trajmap(residue_start, residue_end, args.max, *matrices)
29
+
30
+ prefix1 = "_average_map_"
31
+ savename = ensure_png_extension(args.out + prefix1)
32
+ fig.savefig(savename, dpi=800, bbox_inches='tight')
33
+ print(f"Difference map saved to {savename}")
34
+ plt.close(fig)
35
+ total = time.perf_counter() - start_time
36
+ print(f"Time taken to plot Difference map: {total:.2f} seconds")
@@ -0,0 +1,27 @@
1
+ """Load a distance matrix, compute residue-range shifts across frames, and write a shift CSV.
2
+ """
3
+
4
+ import time
5
+ from ..core.csv2shift import shift
6
+ from ..utils.utils import csv2matrix, ensure_csv_extension, parse_range
7
+
8
+
9
+ def shift_cli(args):
10
+ start_time = time.perf_counter()
11
+ print("")
12
+ prefix = "_pdb2csv_"
13
+ file = ensure_csv_extension(args.out + prefix)
14
+ matrix = csv2matrix(file)
15
+ residue_start, residue_end = parse_range(args.resrs)
16
+ n_frames = matrix.shape[1]
17
+ print(f"Calculating shift for residues {residue_start} to {residue_end} "
18
+ f"across frames 0 to {n_frames - 1}...")
19
+
20
+ shifta = shift(matrix, residue_start, residue_end)
21
+
22
+ prefix2 = "_shift_"
23
+ savename = ensure_csv_extension(args.out + prefix2)
24
+ shifta.to_csv(savename, index=False)
25
+ print(f"Shift saved to {savename}")
26
+ total = time.perf_counter() - start_time
27
+ print(f"Time taken to calculate shift: {total:.2f} seconds")
@@ -0,0 +1,35 @@
1
+ """Load two matrices, render their difference heatmap (A−B), and save the figure PNG.
2
+ """
3
+
4
+ import time
5
+ from ..core.diff2graph import diff_map
6
+ import matplotlib
7
+ matplotlib.use("Agg")
8
+ import matplotlib.pyplot as plt
9
+ from ..utils.utils import ensure_csv_extension, ensure_png_extension, parse_range, load_matrix_4_diff_map
10
+
11
+
12
+
13
+ def diff_map_cli(args):
14
+ start_time = time.perf_counter()
15
+ print("")
16
+ print("Plotting Difference map...")
17
+
18
+ prefix = "_pdb2csv_"
19
+ file1 = ensure_csv_extension(args.mat1 + prefix)
20
+ file2 = ensure_csv_extension(args.mat2 + prefix)
21
+
22
+ A = load_matrix_4_diff_map(file1)
23
+ B = load_matrix_4_diff_map(file2)
24
+
25
+ residue_start, residue_end = parse_range(args.resr)
26
+
27
+ fig = diff_map(A, B, args.max, residue_start, residue_end)
28
+
29
+ prefix1 = "_diff_map_"
30
+ savename = ensure_png_extension(args.out + prefix1)
31
+ fig.savefig(savename, dpi=800, bbox_inches='tight')
32
+ print(f"Difference map saved to {savename}")
33
+ plt.close(fig)
34
+ total = time.perf_counter() - start_time
35
+ print(f"Time taken to plot Difference map: {total:.2f} seconds")
@@ -0,0 +1,89 @@
1
+ """Run hotspot detection and save a summary hotspot-region plot PNG.
2
+ """
3
+
4
+ import time
5
+ import matplotlib
6
+ matplotlib.use("Agg")
7
+ import matplotlib.pyplot as plt
8
+ from matplotlib.ticker import MultipleLocator
9
+ from ..core.hotspot import create_submatrices, detect_shifts, plot_hotspot_regions, plot_shift_regions, plot_slice_regions, slice_shifts
10
+ from ..utils.utils import csv2matrix, ensure_csv_extension, ensure_png_extension, parse_range, shift_to_dataframe
11
+
12
+
13
+ def detect_shift_cli(args):
14
+ print("")
15
+ print("Detecting shift regions...")
16
+ prefix = "_pdb2csv_"
17
+ file = ensure_csv_extension(args.out + prefix)
18
+ matrix = csv2matrix(file)
19
+ mean_shift, smooth, regions = detect_shifts(
20
+ matrix=matrix,
21
+ window=args.window,
22
+ mindist=args.mindist,
23
+ hotspot=args.hot,)
24
+ return mean_shift, smooth, regions
25
+
26
+
27
+ def create_submatrices_cli(args):
28
+ print("")
29
+ print("Extracting region submatrices...")
30
+ prefix = "_pdb2csv_"
31
+ file = ensure_csv_extension(args.out + prefix)
32
+ matrix = csv2matrix(file)
33
+ prefix1 = "_matrix_"
34
+ savematrix = ensure_csv_extension(args.out + prefix1)
35
+ matrix.to_csv(savematrix, index=False)
36
+
37
+ """Call backend"""
38
+ submatrices, regions, mean_shift, smooth = create_submatrices(
39
+ matrix=matrix,
40
+ window=args.window,
41
+ mindist=args.mindist,
42
+ hotspot=args.hot)
43
+ return submatrices
44
+
45
+
46
+ def slice_shifts_cli(args):
47
+ start_time = time.perf_counter()
48
+ print("")
49
+ print("Searching for hotspot regions and plotting individual shift graphs...")
50
+ prefix = "_pdb2csv_"
51
+ file = ensure_csv_extension(args.out + prefix)
52
+ matrix = csv2matrix(file)
53
+
54
+ """Backend: detect"""
55
+ results = slice_shifts(
56
+ matrix=matrix,
57
+ window=args.window,
58
+ mindist=args.mindist,
59
+ hotspot=args.hot)
60
+
61
+ for start, end, shift_data in results:
62
+ fig = plot_slice_regions(shift_data, start, end)
63
+ savename = f"{args.out}_shift_{start}_{end}.png"
64
+ fig.savefig(savename, dpi=800, bbox_inches='tight')
65
+ plt.close(fig)
66
+ print(f"Hotspot region shift graph saved to {savename}")
67
+ total = time.perf_counter() - start_time
68
+ print(f"Time taken to search for hotspot regions: {total:.2f} seconds")
69
+
70
+
71
+ """Hotspot region detection and plotting
72
+ """
73
+ def run_hotspot_cli(args):
74
+ start_time = time.perf_counter()
75
+ print("")
76
+ print("Detecting hotspot regions based on mean shift and plotting...")
77
+ mean_shift, smooth, regions = detect_shift_cli(args)
78
+
79
+ fig = plot_hotspot_regions(
80
+ mean_shift,
81
+ smooth,
82
+ regions,
83
+ title="Residue Shift Hotspots")
84
+ savename = f"{args.out}_shift_hotspots.png"
85
+ fig.savefig(savename, dpi=800, bbox_inches='tight')
86
+ plt.close(fig)
87
+ print(f"Hotspot region plot saved to {savename}")
88
+ total = time.perf_counter() - start_time
89
+ print(f"Time taken to detect hotspot regions: {total:.2f} seconds")
@@ -0,0 +1,29 @@
1
+ """Convert a multi-model PDB (produced from trajectories) into a residue×frame distance CSV.
2
+ """
3
+
4
+ import time
5
+ from ..utils.utils import parse_range, ensure_csv_extension
6
+ from ..core.pdb2csv import pdb2csv
7
+
8
+
9
+ def pdb2csv_cli(args):
10
+ start_time = time.perf_counter()
11
+ prefix = "_pdb2csv_"
12
+ prefix2 = "_traj2pdb_"
13
+ savename = ensure_csv_extension(args.out + prefix)
14
+ pdb_file = args.out + prefix2 + ".pdb"
15
+ start, end = parse_range(args.resr)
16
+ mode = args.cent
17
+ print("")
18
+ print("Converting PDB to CSV distance matrix...")
19
+
20
+ matrix= pdb2csv(
21
+ pdb_file=pdb_file,
22
+ residue_start=start,
23
+ residue_end=end,
24
+ mode=mode)
25
+
26
+ matrix.to_csv(savename)
27
+ print(f"Distance matrix saved to {savename}")
28
+ total = time.perf_counter() - start_time
29
+ print(f"Time taken to convert PDB to CSV: {total:.2f} seconds")
@@ -0,0 +1,29 @@
1
+ """Load a shift CSV, plot the time-series with rolling-average, and save a PNG graph.
2
+ """
3
+
4
+ import time
5
+ import matplotlib
6
+ matplotlib.use("Agg")
7
+ import matplotlib.pyplot as plt
8
+ from ..core.shift2graph import shift2graph
9
+ from ..utils.utils import ensure_csv_extension, ensure_png_extension, shift_to_dataframe
10
+
11
+
12
+ def shift2graph_cli(args):
13
+ start_time = time.perf_counter()
14
+ print("")
15
+ print("Plotting shift graph...")
16
+ prefix = "_shift_"
17
+ file = ensure_csv_extension(args.out + prefix)
18
+ prefix1 = "_shift_graph_"
19
+ savename = ensure_png_extension(args.out + prefix1)
20
+ df = shift_to_dataframe(file)
21
+
22
+ fig = shift2graph(df, args.resrs)
23
+
24
+ fig.savefig(savename, dpi=800, bbox_inches='tight')
25
+ print(f"Shift graph saved to {savename}")
26
+ plt.close(fig)
27
+ total = time.perf_counter() - start_time
28
+ print(f"Time taken to plot shift graph: {total:.2f} seconds")
29
+
@@ -0,0 +1,21 @@
1
+ """Load a residue×frame matrix, render a trajectory heatmap, and save the PNG figure.
2
+ """
3
+
4
+ import time
5
+ from ..core.traj2pdb import traj2pdb
6
+ from ..utils.utils import ensure_pdb_extension
7
+
8
+
9
+ def traj2pdb_cli(args):
10
+ start_time = time.perf_counter()
11
+ prefix = "_traj2pdb_"
12
+ savename = ensure_pdb_extension(args.out + prefix)
13
+ print("Loading trajectory...")
14
+ traj = traj2pdb(args.top, args.traj, args.str)
15
+ print("Selecting backbone...")
16
+ print("Aligning...")
17
+ print("Saving trajectory to", savename)
18
+ traj.save_pdb(savename)
19
+ end_time = time.perf_counter()
20
+ total = end_time - start_time
21
+ print(f"Time taken to convert trajectory to PDB: {total:.2f} seconds")
@@ -0,0 +1,29 @@
1
+ """Load a residue×frame matrix, render a trajectory heatmap, and save the PNG figure.
2
+ """
3
+
4
+ import time
5
+ import matplotlib
6
+ matplotlib.use("Agg")
7
+ import matplotlib.pyplot as plt
8
+ from ..core.trajmap import trajmap
9
+ from ..utils.utils import csv2matrix, ensure_csv_extension, ensure_png_extension, parse_range
10
+
11
+
12
+ def trajmap_cli(args):
13
+ start_time = time.perf_counter()
14
+ print("")
15
+ print("Plotting trajectory map...")
16
+ prefix = "_pdb2csv_"
17
+ file = ensure_csv_extension(args.out + prefix)
18
+ matrix = csv2matrix(file)
19
+ residue_start, residue_end = parse_range(args.resr)
20
+ prefix1 = "_trajmap_"
21
+ savename = ensure_png_extension(args.out + prefix1)
22
+
23
+ fig = trajmap(matrix, residue_start, residue_end, args.max)
24
+
25
+ fig.savefig(savename, dpi=800, bbox_inches='tight')
26
+ print(f"Trajectory map saved to {savename}")
27
+ plt.close(fig)
28
+ total = time.perf_counter() - start_time
29
+ print(f"Time taken to plot trajectory map: {total:.2f} seconds")
tmq/core/__init__.py ADDED
@@ -0,0 +1,2 @@
1
+ __version__ = "1.0"
2
+
@@ -0,0 +1,35 @@
1
+ """ Compute an element-wise average of input matrices
2
+ and render a trajectory map figure
3
+
4
+ """
5
+
6
+ import pandas as pd
7
+ import numpy as np
8
+ import matplotlib
9
+ matplotlib.use("Agg")
10
+ from ..core.trajmap import trajmap
11
+
12
+
13
+
14
+ def avg_trajmap(residue_start, residue_end, vmax, *matrices):
15
+ """
16
+ Take the element-wise average of two or more matrices.
17
+ All matrices must have the same shape.
18
+ """
19
+
20
+ mats = [np.asarray(m) for m in matrices]
21
+ print("Loaded shapes:", [m.shape for m in mats])
22
+
23
+ shapes = {m.shape for m in mats}
24
+ if len(shapes) != 1:
25
+ raise ValueError(f"All matrices must have the same shape, got: {shapes}")
26
+
27
+
28
+ avg_array = np.nanmean(mats, axis=0)
29
+ avg_array = np.nan_to_num(avg_array, nan=0.0)
30
+
31
+ matrix = pd.DataFrame(avg_array)
32
+
33
+
34
+ fig = trajmap(matrix, residue_start, residue_end, vmax)
35
+ return fig
tmq/core/csv2shift.py ADDED
@@ -0,0 +1,17 @@
1
+ """ This computes shift in Armstrongs for
2
+ a given loop region of the protein
3
+
4
+ """
5
+
6
+ import numpy as np
7
+ import pandas as pd
8
+ from ..utils.utils import matrix2shift
9
+
10
+
11
+ def shift(matrix, residue_start, residue_end):
12
+ n_frames = matrix.shape[1]
13
+ start_frame = 0
14
+ end_frame = n_frames - 1
15
+ params = [residue_start, residue_end, start_frame, end_frame]
16
+ shift = matrix2shift(matrix, params)
17
+ return shift