Tutorial: 3D Structure Visualization#
version: 2.25.0
This tutorial covers the interactive 3D visualization functions in gunz_cm.visualizations.structures and the ParaView export functions. After working through it you will know how to:
Render a single 3D chromosome structure as an interactive HTML file (
plot_chromosome_3d).Compare multiple 3D structures side-by-side in a 4x4 grid (
plot_structure_grid).Add a PCA-derived bounding ellipsoid to indicate structural uncertainty (
plot_chromosome_3d_with_ellipsoid).Export 3D structures to ParaView-compatible formats (
write_vtp_polydata,write_vtk_points).
All examples use synthetic data only (fixed RNG seed for reproducibility).
import tempfile, pathlib
import numpy as np
rng = np.random.default_rng(42)
OUT = pathlib.Path(tempfile.mkdtemp())
print(f"Output directory: {OUT}")
# Build a synthetic 3D chromosome structure: a soft helix
n = 50
t = np.linspace(0, 4 * np.pi, n)
points = np.column_stack([
np.cos(t) + 0.05 * rng.standard_normal(n),
np.sin(t) + 0.05 * rng.standard_normal(n),
t / (2 * np.pi) + 0.05 * rng.standard_normal(n),
])
print(f"Synthetic chromosome: {points.shape}")
Output directory: /tmp/tmpsxy8yqfj
Synthetic chromosome: (50, 3)
1. plot_chromosome_3d: interactive 3D rendering#
Use this to render a single 3D structure as an interactive Plotly HTML file. The user can pan, zoom, and rotate the structure in their browser.
The node_colors parameter accepts several input types:
1D scalar array of length
n— per-bins color value (e.g. log-fold-change, A/B compartment)Array of
{-1, 0, 1}— discrete A/B compartment assignmentRGB triples (shape
(n, 3)) — per-bin colorArray of categorical strings — per-bin label
from gunz_cm.visualizations import plot_chromosome_3d
# Plain 3D rendering
out = OUT / "chromosome_3d.html"
plot_chromosome_3d(
points=points,
output_path=str(out),
marker_size=6,
line_width=3, # don't try to display in this headless env
)
print(f"Saved: {out} ({out.stat().st_size:,} bytes)")
# Verify the file is a valid HTML
html_content = out.read_text()
assert html_content.startswith('<!DOCTYPE html>') or '<html' in html_content, "Not a valid HTML file"
print(f"HTML verified: starts with valid doctype/html tag")
Saved: /tmp/tmpsxy8yqfj/chromosome_3d.html (4,848,506 bytes)
HTML verified: starts with valid doctype/html tag
# Render with per-bin scalar node_colors (e.g. log-fold-change vs average)
node_colors = np.sin(t) # some scalar value per bin
out = OUT / "chromosome_3d_colored.html"
plot_chromosome_3d(
points=points,
output_path=str(out),
node_colors=node_colors,
colorscale='RdBu',
)
print(f"Saved colored: {out} ({out.stat().st_size:,} bytes)")
Saved colored: /tmp/tmpsxy8yqfj/chromosome_3d_colored.html (4,849,096 bytes)
# Render with A/B compartment assignment ({-1, 0, 1} array)
ab_assignment = rng.choice([-1, 0, 1], size=n) # synthetic A/B
out = OUT / "chromosome_3d_ab.html"
plot_chromosome_3d(
points=points,
output_path=str(out),
node_colors=ab_assignment,
)
print(f"Saved A/B: {out} ({out.stat().st_size:,} bytes)")
Saved A/B: /tmp/tmpsxy8yqfj/chromosome_3d_ab.html (4,848,456 bytes)
2. plot_structure_grid: compare multiple structures#
Use this when you want to compare multiple reconstructed structures (e.g. from different methods, replicates, or time points) in a single 4x4 grid. The grid is rendered as a single interactive HTML page.
The grid_size parameter defaults to (4, 4) and accommodates up to 16 structures per page. For more, build multiple pages.
from gunz_cm.visualizations import plot_structure_grid
# Build 4 synthetic structures (each a perturbed copy of the helix)
structures = []
titles = []
for i, seed in enumerate([1, 2, 3, 4]):
r = np.random.default_rng(seed)
p = points + 0.1 * r.standard_normal(points.shape)
structures.append(p)
titles.append(f"Replicate {i+1}")
out = OUT / "structure_grid.html"
plot_structure_grid(
structures=structures,
titles=titles,
output_path=str(out),
main_title="4 Replicate Structures",
grid_size=(2, 2), # 2x2 instead of 4x4 for these 4 structures
use_cdn=True,
showscale=True,
)
print(f"Saved grid: {out} ({out.stat().st_size:,} bytes)")
print(f"Structures: {len(structures)}, titles: {titles}")
Saved grid: /tmp/tmpsxy8yqfj/structure_grid.html (19,470 bytes)
Structures: 4, titles: ['Replicate 1', 'Replicate 2', 'Replicate 3', 'Replicate 4']
3. plot_chromosome_3d_with_ellipsoid: PCA uncertainty#
Use this to show the structural uncertainty of a 3D structure by drawing a PCA-derived bounding ellipsoid around the points. This is useful when you have an ensemble of reconstructions and want to show the spread.
The confidence parameter controls the ellipsoid size:
confidence=1.0— 1σ (~68% of points)confidence=2.0(default) — 2σ (~95% of points)confidence=3.0— 3σ (~99.7% of points)
from gunz_cm.visualizations import plot_chromosome_3d_with_ellipsoid
out = OUT / "chromosome_3d_ellipsoid.html"
plot_chromosome_3d_with_ellipsoid(
points=points,
output_path=str(out),
ellipsoid_color="rgba(0, 200, 200, 0.2)",
confidence=2.0,
n_mesh=20,
use_cdn=True,
)
print(f"Saved with ellipsoid: {out} ({out.stat().st_size:,} bytes)")
Saved with ellipsoid: /tmp/tmpsxy8yqfj/chromosome_3d_ellipsoid.html (28,975 bytes)
# Try different confidence levels
for sigma in [1.0, 2.0, 3.0]:
out = OUT / f"chromosome_3d_ellipsoid_{sigma}sigma.html"
plot_chromosome_3d_with_ellipsoid(
points=points,
output_path=str(out),
confidence=sigma,
n_mesh=15, # coarser mesh = faster
)
size_kb = out.stat().st_size / 1024
print(f" {sigma}σ: {out.name} ({size_kb:.1f} KB)")
1.0σ: chromosome_3d_ellipsoid_1.0sigma.html (20.6 KB)
2.0σ: chromosome_3d_ellipsoid_2.0sigma.html (20.8 KB)
3.0σ: chromosome_3d_ellipsoid_3.0sigma.html (20.6 KB)
4. ParaView export: write_vtp_polydata and write_vtk_points#
ParaView is the standard tool for high-quality 3D visualization of scientific data. write_vtp_polydata writes a .vtp file (ParaView’s modern XML format) that renders each point as a sphere; write_vtk_points writes a .vtk legacy ASCII file.
Use write_vtp_polydata for new projects; write_vtk_points for legacy pipelines.
Summary#
Decision tree for choosing a 3D visualization function:
Use case |
Function |
Output format |
|---|---|---|
Render single 3D structure for browser viewing |
|
HTML (Plotly) |
Compare multiple reconstructions side-by-side |
|
HTML (Plotly) |
Show structural uncertainty via PCA ellipsoid |
|
HTML (Plotly) |
Export for high-quality rendering in ParaView |
|
|
Export for legacy pipelines |
|
|
All plot_* functions default to use_cdn=True (Plotly loaded from CDN, smaller file size) and produce a single self-contained HTML file. Set use_cdn=False for offline viewing (larger file size).
4. ParaView export (requires vtk extra)#
ParaView is the standard tool for high-quality 3D visualization. The functions write_vtp_polydata and write_vtk_points are available in gunz_cm.reconstructions.utils.vtk_writer and gunz_cm.visualizations.paraview_exporter respectively, but require the vtk Python package:
pip install vtk # or: pip install gunz-cm[3dr] (includes vtk)
After installing vtk, the function signatures are:
from gunz_cm.reconstructions.utils.vtk_writer import write_vtp_polydata
from gunz_cm.visualizations.paraview_exporter import write_vtk_points
write_vtp_polydata(
points=points, fpath="structure.vtp",
sphere_radius=0.05, # VTP renders each point as a sphere of this radius
add_index_based_color=True, # color by index for ParaView visualisation
)
write_vtk_points(points=points, filename="structure.vtk") # legacy ASCII
Use write_vtp_polydata for new projects; write_vtk_points for legacy pipelines.