Skip to content

Commit 6599d13

Browse files
committed
add visualization functions and dependencies
1 parent 8a9fb08 commit 6599d13

5 files changed

Lines changed: 442 additions & 7 deletions

File tree

CHANGELOG.md

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,33 @@ All notable changes to this project will be documented in this file.
44

55
The format follows [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
66

7+
## [Unreleased]
8+
9+
### Added
10+
- `seq_tools/visualization.py` — matplotlib-based plotting utilities requiring no grelu or genome files:
11+
- `plot_ism_heatmap` — ISM log2FC result as a diverging-colormap heatmap (ACGT rows)
12+
- `plot_prediction_track` — 1D bin-level model prediction as a filled area chart
13+
- `plot_gene_model` — exon/intron track from a soft-label DataFrame, colored by p_exon
14+
- `plot_attribution` — per-position saliency bar chart or tangermeme logo (falls back gracefully)
15+
- `multi_track_figure` — stacked, shared-x-axis multi-panel figure layout
16+
- All five visualization functions exposed in `seq_tools.__init__.__all__`
17+
- `examples/04_interpretation_workflow.ipynb` — end-to-end interpretation notebook:
18+
- ISM with `seq_tools.variant` (no grelu required)
19+
- API tour of `interpret.ism`, `interpret.attribution`, `interpret.modisco`
20+
- Synthetic attribution and gene model visualization
21+
- Composite multi-track figure combining all tracks
22+
- `tests/test_labels.py` — comprehensive tests for the splicing label generation pipeline:
23+
- `_disjoint_labels_with_priority`: priority ordering, exon/intron segmentation, PSI override, multi-chrom
24+
- `collapse_exon_coords_weighted`: read-weighted PSI aggregation vs. naive average
25+
- `generate_soft_labels`: schema, exon/intron assignment, rMATS PSI integration (pyranges-gated)
26+
- `tests/test_dataset.py` — tests for `GenomicWindowDataset` and `rasterize_window`:
27+
- Shard loading, caching behavior, transform support, DataLoader compatibility
28+
- Bin boundary alignment, partial overlap weighting, NaN handling
29+
30+
### Changed
31+
- `training/multitask_head.py` — module docstring now includes a design note explaining the output-collapse problem and how per-task `BatchNorm1d` in `SplitHead` prevents it
32+
- `pyproject.toml` — added `matplotlib >= 3.5` as a core dependency
33+
734
## [0.1.0] — 2025-01-01
835

936
### Added

README.md

Lines changed: 26 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ Built around [gReLU](https://github.com/Genentech/gReLU) and designed for Borzoi
1212
- **Genomic intervals** — chromosome tiling, window centering, output bin mapping
1313
- **Splicing label generation** — hard/soft PSI labels from rMATS + StringTie, with priority-based disjoint segmentation
1414
- **Variant construction** — SNV generation and scoring for in silico mutagenesis
15+
- **Visualization** — ISM heatmaps, prediction tracks, gene model and attribution plots (matplotlib, no grelu required)
1516
- **Custom losses** — PSI-aware, Bhattacharyya, masked MSE/Poisson for multitask training
1617
- **Multitask heads** — nonlinear, split-head, and cell-type conditional architectures
1718
- **LoRA fine-tuning** — lightweight low-rank adaptation for Conv1d and Linear layers with weight merging
@@ -37,7 +38,8 @@ seq_tools/ Core sequence utilities
3738
├── intervals.py Genomic interval generation, centering, bin conversion
3839
├── fasta.py FASTA reading, windowed iteration
3940
├── labels.py Splicing label generation (rMATS + StringTie)
40-
└── variant.py SNV generation and variant scoring
41+
├── variant.py SNV generation and variant scoring
42+
└── visualization.py ISM heatmaps, prediction tracks, gene model and attribution plots
4143
4244
training/ Model training infrastructure
4345
├── losses.py PSI, Bhattacharyya, masked MSE/Poisson losses
@@ -100,6 +102,28 @@ cond_head = ConditionalHead(in_channels=1920, n_celltypes=5, out_channels=1)
100102
pred = cond_head(trunk_features, cell_type_id=torch.tensor([2]))
101103
```
102104

105+
### Visualize ISM results and model predictions
106+
107+
```python
108+
from seq_tools.visualization import (
109+
plot_ism_heatmap,
110+
plot_prediction_track,
111+
plot_gene_model,
112+
multi_track_figure,
113+
)
114+
import matplotlib.pyplot as plt
115+
116+
# ISM heatmap from score_variants output — shape (4, L), ACGT rows
117+
fig, ax = plt.subplots(figsize=(15, 2))
118+
plot_ism_heatmap(ism_matrix, genome_start=10_500_000, ax=ax, title="log2FC")
119+
120+
# Stacked multi-track figure with shared x-axis
121+
fig, axes = multi_track_figure(3, height_ratios=[2, 1.5, 1])
122+
plot_prediction_track(predictions, ax=axes[0], ylabel="PSI")
123+
plot_ism_heatmap(ism_matrix, ax=axes[1])
124+
plot_gene_model(soft_label_df, ax=axes[2])
125+
```
126+
103127
### Generate splicing labels
104128

105129
```python
@@ -124,7 +148,7 @@ This toolkit extends [gReLU](https://github.com/Genentech/gReLU) rather than rep
124148

125149
- Python ≥ 3.10
126150
- PyTorch ≥ 2.0
127-
- NumPy, Pandas
151+
- NumPy, Pandas, Matplotlib
128152

129153
Optional:
130154
- [gReLU](https://github.com/Genentech/gReLU) — model loading, attribution, ISM

pyproject.toml

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -22,17 +22,17 @@ classifiers = [
2222
"Programming Language :: Python :: 3.11",
2323
"Programming Language :: Python :: 3.12",
2424
]
25-
26-
[project.urls]
27-
Repository = "https://github.com/jsdearbo/sequence_to_function_model_tools"
28-
"Bug Tracker" = "https://github.com/jsdearbo/sequence_to_function_model_tools/issues"
29-
3025
dependencies = [
3126
"numpy>=1.24",
3227
"pandas>=2.0",
3328
"torch>=2.0",
29+
"matplotlib>=3.5",
3430
]
3531

32+
[project.urls]
33+
Repository = "https://github.com/jsdearbo/sequence_to_function_model_tools"
34+
"Bug Tracker" = "https://github.com/jsdearbo/sequence_to_function_model_tools/issues"
35+
3636
[project.optional-dependencies]
3737
full = [
3838
"grelu",

seq_tools/__init__.py

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,13 @@
66
from seq_tools.encoding import one_hot_encode, decode_one_hot, reverse_complement, normalize_chrom
77
from seq_tools.intervals import generate_intervals, make_input_interval, genome_to_output_bins
88
from seq_tools.variant import generate_snvs, generate_window_variants, score_variants
9+
from seq_tools.visualization import (
10+
plot_ism_heatmap,
11+
plot_prediction_track,
12+
plot_gene_model,
13+
plot_attribution,
14+
multi_track_figure,
15+
)
916

1017
__all__ = [
1118
"one_hot_encode",
@@ -18,4 +25,9 @@
1825
"generate_snvs",
1926
"generate_window_variants",
2027
"score_variants",
28+
"plot_ism_heatmap",
29+
"plot_prediction_track",
30+
"plot_gene_model",
31+
"plot_attribution",
32+
"multi_track_figure",
2133
]

0 commit comments

Comments
 (0)