QC Visualisation Workflow#

The thesis.workflows.qc package provides a self-registered QC workflow that generates ROI overlay figures, track density maps, and tractography statistics. Invoked via thesis run -w qc -p <patient_id>.

thesis.workflows.qc#

QC visualisation and statistics workflow.

Provides headless figure generation for ROI overlay inspection, track density map review, and tractography statistics collection. Registered as the qc workflow, invoked via thesis run -w qc -p <patient_id>.

Example

>>> from thesis.workflows.qc import (
...     generate_roi_overlays,
...     generate_track_density_figures,
...     collect_tractography_stats,
... )
thesis.workflows.qc.generate_roi_overlays(roi_paths, background_image, output_dir, display_mode='ortho')[source]

Generate QC overlay PNGs for each ROI mask on a background image.

Produces one PNG per ROI mask plus a combined figure showing all ROIs in different colours. Runs headlessly (Agg backend).

Parameters:
  • roi_paths (Mapping[str, Union[str, Path]]) – Mapping of ROI name to NIfTI mask path.

  • background_image (Union[str, Path]) – T1w (or FA) image used as the anatomical background.

  • output_dir (Union[str, Path]) – Directory to write PNGs into. Created if it does not exist.

  • display_mode (str) – nilearn display_mode parameter ("ortho", "x", "y", "z").

Return type:

List[Path]

Returns:

List of Path objects for every generated PNG.

Raises:

Example

>>> paths = generate_roi_overlays(
...     roi_paths={"seed": "seed.nii.gz"},
...     background_image="T1w.nii.gz",
...     output_dir="qc/roi_overlays",
... )
thesis.workflows.qc.generate_track_density_figures(fdt_paths, template_image, output_dir, thresholds=None, display_mode='ortho', prefix='track_density')[source]

Generate QC figures overlaying track density on a template image.

For every requested percentile threshold the track density map is thresholded at that percentile of non-zero voxels and overlaid on the template background. One PNG is produced per threshold.

Parameters:
  • fdt_paths (Union[str, Path]) – Path to fdt_paths.nii.gz (track density map).

  • template_image (Union[str, Path]) – Path to the background image (MNI template for template-space maps, T1w for subject-space maps).

  • output_dir (Union[str, Path]) – Directory to write PNGs into. Created if it does not exist.

  • thresholds (Optional[List[float]]) – Percentile thresholds (default [50, 90, 99]). Each value must be in the range (0, 100).

  • display_mode (str) – nilearn display_mode parameter.

  • prefix (str) – Filename prefix for the output PNGs.

Return type:

List[Path]

Returns:

List of Path objects for every generated PNG.

Raises:

Example

>>> figures = generate_track_density_figures(
...     "fdt_paths.nii.gz",
...     "MNI152_T1_2mm.nii.gz",
...     "qc/normtracks",
... )
thesis.workflows.qc.collect_tractography_stats(patient_output, patient_id=None, tractography_relpath='tractography/probtrackx2', tract_similarity_subdir='tract_similarity')[source]

Collect tractography statistics for a single subject.

Reads output files from a tractography run (ProbTrackX2 or MRtrix3) and returns a structured dictionary of statistics.

Parameters:
  • patient_output (Union[str, Path]) – Patient-level output directory (e.g. outputs/114823/).

  • patient_id (Optional[str]) – Optional patient identifier (included in the returned dict for convenience).

  • tractography_relpath (str) – Relative path under patient_output where the tractography run lives. Defaults to "tractography/probtrackx2". Use "tractography/mrtrix3" for the MRtrix3 backend.

  • tract_similarity_subdir (str) – Relative path under patient_output where the tract_similarity / tract_similarity_hcp_loo workflow wrote metrics.json. Read opportunistically and attached under result["tract_similarity"] when present.

Returns:

  • patient_id — subject identifier (or "unknown").

  • waytotal — total streamlines reaching all waypoints.

  • subject_space — fdt_paths statistics in subject space.

  • template_space — fdt_paths statistics in template space (empty dict if warped_streamlines not present).

  • roi_voxel_counts — non-zero voxel count per ROI mask.

  • tract_similarity — overlap / correlation / distance_mm / distribution / voxel_counts / thresholds blocks copied from <tract_similarity_subdir>/metrics.json (only present when that file exists).

Return type:

Dict[str, Any]

Raises:

FileNotFoundError – If patient_output does not exist.

Example

>>> stats = collect_tractography_stats("outputs/114823")
>>> stats["waytotal"]
42351
thesis.workflows.qc.collect_batch_stats(output_base, patient_ids=None, tractography_relpath='tractography/probtrackx2', tract_similarity_subdir='tract_similarity')[source]

Collect tractography statistics for multiple subjects.

If patient_ids is None, discovers subject directories automatically by looking for subdirectories of output_base that contain <tractography_relpath>/.

Parameters:
  • output_base (Union[str, Path]) – Parent directory containing per-subject output directories (e.g. outputs/).

  • patient_ids (Optional[List[str]]) – Explicit list of subject IDs. If None, auto-discovers from output_base.

  • tractography_relpath (str) – Relative path under each patient directory where the tractography run lives. Defaults to "tractography/probtrackx2". Use "tractography/mrtrix3" for the MRtrix3 backend.

  • tract_similarity_subdir (str) – Relative path under each patient directory where tract_similarity / tract_similarity_hcp_loo wrote metrics.json. When present, that file’s content is attached under subject["tract_similarity"].

Return type:

List[Dict[str, Any]]

Returns:

List of per-subject statistics dictionaries (same format as collect_tractography_stats()).

Example

>>> all_stats = collect_batch_stats("outputs/")
>>> for s in all_stats:
...     print(s["patient_id"], s["waytotal"])
thesis.workflows.qc.format_stats_table(stats_list, include_roi_counts=False)[source]

Format tractography statistics as a human-readable text table.

Parameters:
  • stats_list (List[Dict[str, Any]]) – List of per-subject statistics dictionaries (from collect_tractography_stats() or collect_batch_stats()).

  • include_roi_counts (bool) – If True, append per-ROI voxel counts below the main table.

Return type:

str

Returns:

Formatted multi-line string suitable for terminal output.

Example

>>> print(format_stats_table(all_stats))
Patient    Waytotal   Nonzero Vox  Mean Dens  Max Dens  Vol Frac
-------    --------   -----------  ---------  --------  --------
114823       42351         12834      3.30       287    0.0128
thesis.workflows.qc.run_post_workflow_qc(cfg, ctx_obj)[source]

Generate QC overlays after workflow completion if configured.

This is a best-effort step — QC failures are logged as warnings but do not cause the pipeline run to fail.

Intended to be called by the CLI after a successful thesis run when qc.generate_overlays is True.

Parameters:
Return type:

None

thesis.workflows.qc.generate_connectivity_map_figures(tractography_dir, background_image, output_dir, thresholds=None, space='subject')[source]

Generate overlay figures for seeds_to_<target>.nii.gz maps.

Parameters:
  • tractography_dir (Union[str, Path]) – ProbTrackX2 output directory.

  • background_image (Union[str, Path]) – Anatomical background for the overlay.

  • output_dir (Union[str, Path]) – Directory to write PNGs into.

  • thresholds (Optional[List[float]]) – Percentile thresholds (default [50, 90]).

  • space (str) – Label for filenames ("subject" or "template").

Return type:

List[Path]

Returns:

List of generated PNG paths.

thesis.workflows.qc.collect_connectivity_map_stats(tractography_dir)[source]

Collect density statistics for each seeds_to_<target> map.

Parameters:

tractography_dir (Union[str, Path]) – ProbTrackX2 output directory.

Return type:

Dict[str, Dict[str, Any]]

Returns:

Mapping of target name to stats dict (nonzero_voxels, mean_density, max_density, total_streamlines).

thesis.workflows.qc.parse_synthseg_qc_csv(patient_output, threshold=0.6)[source]

Parse a SynthSeg _qc.csv file and flag low-quality subjects.

Parameters:
  • patient_output (Union[str, Path]) – Patient-level output directory.

  • threshold (float) – Minimum acceptable QC score (0–1).

Return type:

Dict[str, Any]

Returns:

Dict with path, scores (list of floats), mean_score, passed (bool), and threshold. Empty dict if file not found.

thesis.workflows.qc.parse_synthseg_volumes_csv(patient_output)[source]

Parse SynthSeg volumes CSV and flag anatomically unreasonable values.

Parameters:

patient_output (Union[str, Path]) – Patient-level output directory.

Return type:

Dict[str, Any]

Returns:

Dict with path, volumes (dict of structure -> volume), total_volume, warnings (list of issue strings).

thesis.workflows.qc.generate_synthseg_overlay(patient_output, background_image, output_dir)[source]

Generate a colour-coded SynthSeg label overlay on T1w.

Parameters:
  • patient_output (Union[str, Path]) – Patient-level output directory.

  • background_image (Union[str, Path]) – T1w anatomical background.

  • output_dir (Union[str, Path]) – Directory for output PNGs.

Return type:

List[Path]

Returns:

List of generated PNG paths.

thesis.workflows.qc.generate_roi_transform_comparison(tractography_dir, background_image, output_dir)[source]

Compare original and transformed ROI masks.

Generates overlay figures and computes volume change and centroid shift for each ROI that has both an original and transformed version.

Parameters:
  • tractography_dir (Union[str, Path]) – ProbTrackX2 output directory (parent of rois/ and rois_transformed/).

  • background_image (Union[str, Path]) – Anatomical background.

  • output_dir (Union[str, Path]) – Directory for output PNGs.

Return type:

Tuple[List[Path], List[Dict[str, Any]]]

Returns:

Tuple of (list of PNG paths, list of comparison dicts).

thesis.workflows.qc.validate_waypoints_file(tractography_dir, reference_image=None)[source]

Validate waypoints text files.

Checks that every path listed in waypoints files exists and (if a reference image is provided) has compatible dimensions.

Parameters:
  • tractography_dir (Union[str, Path]) – ProbTrackX2 output directory.

  • reference_image (Union[str, Path, None]) – Optional reference NIfTI (e.g. brain mask) to check dimension compatibility.

Return type:

Dict[str, Any]

Returns:

Dict with files_checked, total_paths, missing, dimension_mismatches, valid.

thesis.workflows.qc.generate_brain_mask_overlay(brain_mask, background_image, output_dir)[source]

Generate an overlay of the brain mask on an anatomical image.

Parameters:
  • brain_mask (Union[str, Path]) – Path to the brain mask NIfTI.

  • background_image (Union[str, Path]) – Anatomical background (T1w or DWI b0).

  • output_dir (Union[str, Path]) – Directory for output PNGs.

Return type:

List[Path]

Returns:

List of generated PNG paths.

thesis.workflows.qc.compute_jacobian_stats(warp_field, output_dir=None)[source]

Compute Jacobian determinant statistics from a warp field.

Parameters:
  • warp_field (Union[str, Path]) – Path to a 4D or 5D warp field NIfTI (e.g. from ANTs).

  • output_dir (Union[str, Path, None]) – If provided, save a Jacobian determinant volume as NIfTI.

Return type:

Dict[str, Any]

Returns:

Dict with negative_voxels, negative_fraction, min_jacobian, max_jacobian, mean_jacobian. Empty dict if warp field cannot be loaded.

thesis.workflows.qc.generate_bedpostx_overlay(bedpostx_dir, background_image, output_dir)[source]

Generate an overlay of f1 (primary fibre fraction) and report stats.

Parameters:
  • bedpostx_dir (Union[str, Path]) – BedpostX output directory containing mean_f1samples.nii.gz.

  • background_image (Union[str, Path]) – Anatomical background.

  • output_dir (Union[str, Path]) – Directory for output PNGs.

Return type:

Tuple[List[Path], Dict[str, Any]]

Returns:

Tuple of (list of PNG paths, stats dict with mean_f1, etc.).

thesis.workflows.qc.generate_waytotal_overlay(tractography_dir, template_image, output_dir)[source]

Generate overlay for template-space waytotal.nii.gz.

Parameters:
  • tractography_dir (Union[str, Path]) – ProbTrackX2 output directory.

  • template_image (Union[str, Path]) – Template background image.

  • output_dir (Union[str, Path]) – Directory for output PNGs.

Return type:

List[Path]

Returns:

List of generated PNG paths.

thesis.workflows.qc.detect_batch_outliers(stats_list, sd_threshold=2.0)[source]

Flag subjects whose metrics are outliers relative to the batch.

Parameters:
  • stats_list (List[Dict[str, Any]]) – Batch statistics from collect_batch_stats().

  • sd_threshold (float) – Number of standard deviations to flag.

Return type:

List[Dict[str, Any]]

Returns:

List of dicts, each with patient_id, metric, value, mean, std, z_score.

thesis.workflows.qc.workflow#

QC visualisation and statistics workflow.

Produces ROI overlay PNGs, track density figures, and tractography statistics for a patient whose HCP workflow has already completed.

Usage:

thesis run -w qc -p 114823 -c default
thesis.workflows.qc.workflow.verify_requirements(config, context)[source]#

Verify the patient has tractography output from a prior backend run.

Parameters:
Return type:

List[str]

thesis.workflows.qc.workflow.build_workflow(*, qc_dir, config, context)[source]#

Build a single-Function-node QC workflow.

The Function node deserialises the config, builds a fresh context, and delegates to run_qc_for_patient which has its own path-discovery fallbacks for T1 and tractography outputs.

Parameters:
Return type:

Workflow

thesis.workflows.qc.operations#

QC workflow operations and helpers.

Contains the post-workflow QC hook, ROI discovery logic, and background image resolution that support both the thesis run -w qc workflow and the automatic post-HCP QC generation.

thesis.workflows.qc.operations.discover_roi_files(tractography_dir)[source]#

Discover ROI NIfTI masks from patient tractography output.

Searches rois_merged/, rois_transformed/, and rois/ (in that order), returning the first non-empty set found. Descends one level into per-atlas-source subdirectories (e.g. rois/main/) so naming-convention runs with atlas_sources[].name != "atlas" are picked up.

Parameters:

tractography_dir (Union[str, Path]) – The <output_dir>/tractography/probtrackx2/ directory.

Return type:

Dict[str, Path]

Returns:

Mapping of ROI name (derived from filename, prefixed with source subdir when present) to Path.

thesis.workflows.qc.operations.resolve_background_image(config, context)[source]#

Resolve the T1w background image for a patient.

Uses the same resolution logic as the HCP workflow (resolve_t1_path) so paths that work for thesis run also work for QC.

Parameters:
Return type:

Optional[Path]

Returns:

Path to the T1w image, or None if it cannot be resolved.

thesis.workflows.qc.operations.run_post_workflow_qc(cfg, ctx_obj)[source]#

Generate QC overlays after workflow completion if configured.

This is a best-effort step — QC failures are logged as warnings but do not cause the pipeline run to fail.

Intended to be called by the CLI after a successful thesis run when qc.generate_overlays is True.

Parameters:
Return type:

None

thesis.workflows.qc.operations.run_qc_for_patient(config, context, background=None, track_density=True, stats=True)[source]#

Run full QC suite for a single patient.

This is the core logic used by both the qc workflow’s Nipype Function node and any future CLI invocation.

Parameters:
  • config (PipelineConfig) – Loaded pipeline configuration.

  • context (ProcessingContext) – Processing context.

  • background (Optional[Path]) – Override background image. If None, resolved from config.

  • track_density (bool) – Generate track density overlay figures.

  • stats (bool) – Print tractography statistics.

Return type:

List[str]

Returns:

List of output file paths (PNGs) generated.

thesis.workflows.qc.roi_overlay#

Generate QC overlay figures for ROI masks on anatomical backgrounds.

All plotting is performed with the Agg backend so the module works in headless environments (e.g. compute nodes without an X server).

Example

>>> from thesis.workflows.qc.roi_overlay import generate_roi_overlays
>>> paths = generate_roi_overlays(
...     roi_paths={"seed": Path("seed.nii.gz"), "waypoint": Path("wp.nii.gz")},
...     background_image=Path("T1w.nii.gz"),
...     output_dir=Path("qc/roi_overlays"),
... )
thesis.workflows.qc.roi_overlay.generate_roi_overlays(roi_paths, background_image, output_dir, display_mode='ortho')[source]#

Generate QC overlay PNGs for each ROI mask on a background image.

Produces one PNG per ROI mask plus a combined figure showing all ROIs in different colours. Runs headlessly (Agg backend).

Parameters:
  • roi_paths (Mapping[str, Union[str, Path]]) – Mapping of ROI name to NIfTI mask path.

  • background_image (Union[str, Path]) – T1w (or FA) image used as the anatomical background.

  • output_dir (Union[str, Path]) – Directory to write PNGs into. Created if it does not exist.

  • display_mode (str) – nilearn display_mode parameter ("ortho", "x", "y", "z").

Return type:

List[Path]

Returns:

List of Path objects for every generated PNG.

Raises:

Example

>>> paths = generate_roi_overlays(
...     roi_paths={"seed": "seed.nii.gz"},
...     background_image="T1w.nii.gz",
...     output_dir="qc/roi_overlays",
... )

thesis.workflows.qc.track_density#

Generate QC figures for track density maps on template backgrounds.

Overlays fdt_paths.nii.gz on a template (or subject) image at configurable percentile thresholds. All plotting uses the Agg backend so the module works in headless environments.

Example

>>> from thesis.workflows.qc.track_density import generate_track_density_figures
>>> paths = generate_track_density_figures(
...     fdt_paths=Path("fdt_paths.nii.gz"),
...     template_image=Path("MNI152_T1_2mm.nii.gz"),
...     output_dir=Path("qc/normtracks"),
...     thresholds=[50.0, 90.0, 99.0],
... )
thesis.workflows.qc.track_density.generate_track_density_figures(fdt_paths, template_image, output_dir, thresholds=None, display_mode='ortho', prefix='track_density')[source]#

Generate QC figures overlaying track density on a template image.

For every requested percentile threshold the track density map is thresholded at that percentile of non-zero voxels and overlaid on the template background. One PNG is produced per threshold.

Parameters:
  • fdt_paths (Union[str, Path]) – Path to fdt_paths.nii.gz (track density map).

  • template_image (Union[str, Path]) – Path to the background image (MNI template for template-space maps, T1w for subject-space maps).

  • output_dir (Union[str, Path]) – Directory to write PNGs into. Created if it does not exist.

  • thresholds (Optional[List[float]]) – Percentile thresholds (default [50, 90, 99]). Each value must be in the range (0, 100).

  • display_mode (str) – nilearn display_mode parameter.

  • prefix (str) – Filename prefix for the output PNGs.

Return type:

List[Path]

Returns:

List of Path objects for every generated PNG.

Raises:

Example

>>> figures = generate_track_density_figures(
...     "fdt_paths.nii.gz",
...     "MNI152_T1_2mm.nii.gz",
...     "qc/normtracks",
... )

thesis.workflows.qc.statistics#

Collect tractography statistics from per-patient output directories.

Reads waytotal, fdt_paths.nii.gz, and ROI mask files to produce a structured summary of tractography results for one or more subjects. Works with both ProbTrackX2 (tractography/probtrackx2, the default) and MRtrix3 (tractography/mrtrix3) layouts via the tractography_relpath parameter.

For cross-method comparison the collector also emits a unified Normalized Connection Strength (NCS) per subject and per hemisphere:

  • ProbTrackX2: NCS = target_total_streamlines / (n_samples × |seed_voxels|) — per-sample arrival probability in [0, 1].

  • MRtrix3: NCS = mu × target_total_streamlines — Fibre Bundle Capacity (units of fibre cross-sectional area). The target sum is already SIFT2-weighted (the per-target TDI uses -tck_weights_in), so multiplying by mu from sift2_mu.txt gives the FBC value.

The two values are different physical quantities; cross-method comparison should use Spearman rank / z-scored profiles, not absolute equality.

Example

>>> from thesis.workflows.qc.statistics import collect_tractography_stats
>>> stats = collect_tractography_stats(Path("outputs/114823"))
>>> print(stats["waytotal"])
42351
thesis.workflows.qc.statistics.collect_tractography_stats(patient_output, patient_id=None, tractography_relpath='tractography/probtrackx2', tract_similarity_subdir='tract_similarity')[source]#

Collect tractography statistics for a single subject.

Reads output files from a tractography run (ProbTrackX2 or MRtrix3) and returns a structured dictionary of statistics.

Parameters:
  • patient_output (Union[str, Path]) – Patient-level output directory (e.g. outputs/114823/).

  • patient_id (Optional[str]) – Optional patient identifier (included in the returned dict for convenience).

  • tractography_relpath (str) – Relative path under patient_output where the tractography run lives. Defaults to "tractography/probtrackx2". Use "tractography/mrtrix3" for the MRtrix3 backend.

  • tract_similarity_subdir (str) – Relative path under patient_output where the tract_similarity / tract_similarity_hcp_loo workflow wrote metrics.json. Read opportunistically and attached under result["tract_similarity"] when present.

Returns:

  • patient_id — subject identifier (or "unknown").

  • waytotal — total streamlines reaching all waypoints.

  • subject_space — fdt_paths statistics in subject space.

  • template_space — fdt_paths statistics in template space (empty dict if warped_streamlines not present).

  • roi_voxel_counts — non-zero voxel count per ROI mask.

  • tract_similarity — overlap / correlation / distance_mm / distribution / voxel_counts / thresholds blocks copied from <tract_similarity_subdir>/metrics.json (only present when that file exists).

Return type:

Dict[str, Any]

Raises:

FileNotFoundError – If patient_output does not exist.

Example

>>> stats = collect_tractography_stats("outputs/114823")
>>> stats["waytotal"]
42351
thesis.workflows.qc.statistics.collect_batch_stats(output_base, patient_ids=None, tractography_relpath='tractography/probtrackx2', tract_similarity_subdir='tract_similarity')[source]#

Collect tractography statistics for multiple subjects.

If patient_ids is None, discovers subject directories automatically by looking for subdirectories of output_base that contain <tractography_relpath>/.

Parameters:
  • output_base (Union[str, Path]) – Parent directory containing per-subject output directories (e.g. outputs/).

  • patient_ids (Optional[List[str]]) – Explicit list of subject IDs. If None, auto-discovers from output_base.

  • tractography_relpath (str) – Relative path under each patient directory where the tractography run lives. Defaults to "tractography/probtrackx2". Use "tractography/mrtrix3" for the MRtrix3 backend.

  • tract_similarity_subdir (str) – Relative path under each patient directory where tract_similarity / tract_similarity_hcp_loo wrote metrics.json. When present, that file’s content is attached under subject["tract_similarity"].

Return type:

List[Dict[str, Any]]

Returns:

List of per-subject statistics dictionaries (same format as collect_tractography_stats()).

Example

>>> all_stats = collect_batch_stats("outputs/")
>>> for s in all_stats:
...     print(s["patient_id"], s["waytotal"])
thesis.workflows.qc.statistics.format_stats_table(stats_list, include_roi_counts=False)[source]#

Format tractography statistics as a human-readable text table.

Parameters:
Return type:

str

Returns:

Formatted multi-line string suitable for terminal output.

Example

>>> print(format_stats_table(all_stats))
Patient    Waytotal   Nonzero Vox  Mean Dens  Max Dens  Vol Frac
-------    --------   -----------  ---------  --------  --------
114823       42351         12834      3.30       287    0.0128

thesis.workflows.qc.checks#

Extended QC checks for pipeline outputs.

Covers per-target connectivity maps, SynthSeg quality, ROI transform comparison, waypoints validation, brain mask overlay, warp field Jacobian analysis, BedpostX fibre quality, and cross-subject outlier detection.

All plotting uses the Agg backend for headless rendering.

thesis.workflows.qc.checks.generate_connectivity_map_figures(tractography_dir, background_image, output_dir, thresholds=None, space='subject')[source]#

Generate overlay figures for seeds_to_<target>.nii.gz maps.

Parameters:
  • tractography_dir (Union[str, Path]) – ProbTrackX2 output directory.

  • background_image (Union[str, Path]) – Anatomical background for the overlay.

  • output_dir (Union[str, Path]) – Directory to write PNGs into.

  • thresholds (Optional[List[float]]) – Percentile thresholds (default [50, 90]).

  • space (str) – Label for filenames ("subject" or "template").

Return type:

List[Path]

Returns:

List of generated PNG paths.

thesis.workflows.qc.checks.collect_connectivity_map_stats(tractography_dir)[source]#

Collect density statistics for each seeds_to_<target> map.

Parameters:

tractography_dir (Union[str, Path]) – ProbTrackX2 output directory.

Return type:

Dict[str, Dict[str, Any]]

Returns:

Mapping of target name to stats dict (nonzero_voxels, mean_density, max_density, total_streamlines).

thesis.workflows.qc.checks.parse_synthseg_qc_csv(patient_output, threshold=0.6)[source]#

Parse a SynthSeg _qc.csv file and flag low-quality subjects.

Parameters:
  • patient_output (Union[str, Path]) – Patient-level output directory.

  • threshold (float) – Minimum acceptable QC score (0–1).

Return type:

Dict[str, Any]

Returns:

Dict with path, scores (list of floats), mean_score, passed (bool), and threshold. Empty dict if file not found.

thesis.workflows.qc.checks.parse_synthseg_volumes_csv(patient_output)[source]#

Parse SynthSeg volumes CSV and flag anatomically unreasonable values.

Parameters:

patient_output (Union[str, Path]) – Patient-level output directory.

Return type:

Dict[str, Any]

Returns:

Dict with path, volumes (dict of structure -> volume), total_volume, warnings (list of issue strings).

thesis.workflows.qc.checks.generate_synthseg_overlay(patient_output, background_image, output_dir)[source]#

Generate a colour-coded SynthSeg label overlay on T1w.

Parameters:
  • patient_output (Union[str, Path]) – Patient-level output directory.

  • background_image (Union[str, Path]) – T1w anatomical background.

  • output_dir (Union[str, Path]) – Directory for output PNGs.

Return type:

List[Path]

Returns:

List of generated PNG paths.

thesis.workflows.qc.checks.generate_roi_transform_comparison(tractography_dir, background_image, output_dir)[source]#

Compare original and transformed ROI masks.

Generates overlay figures and computes volume change and centroid shift for each ROI that has both an original and transformed version.

Parameters:
  • tractography_dir (Union[str, Path]) – ProbTrackX2 output directory (parent of rois/ and rois_transformed/).

  • background_image (Union[str, Path]) – Anatomical background.

  • output_dir (Union[str, Path]) – Directory for output PNGs.

Return type:

Tuple[List[Path], List[Dict[str, Any]]]

Returns:

Tuple of (list of PNG paths, list of comparison dicts).

thesis.workflows.qc.checks.validate_waypoints_file(tractography_dir, reference_image=None)[source]#

Validate waypoints text files.

Checks that every path listed in waypoints files exists and (if a reference image is provided) has compatible dimensions.

Parameters:
  • tractography_dir (Union[str, Path]) – ProbTrackX2 output directory.

  • reference_image (Union[str, Path, None]) – Optional reference NIfTI (e.g. brain mask) to check dimension compatibility.

Return type:

Dict[str, Any]

Returns:

Dict with files_checked, total_paths, missing, dimension_mismatches, valid.

thesis.workflows.qc.checks.generate_brain_mask_overlay(brain_mask, background_image, output_dir)[source]#

Generate an overlay of the brain mask on an anatomical image.

Parameters:
  • brain_mask (Union[str, Path]) – Path to the brain mask NIfTI.

  • background_image (Union[str, Path]) – Anatomical background (T1w or DWI b0).

  • output_dir (Union[str, Path]) – Directory for output PNGs.

Return type:

List[Path]

Returns:

List of generated PNG paths.

thesis.workflows.qc.checks.compute_jacobian_stats(warp_field, output_dir=None)[source]#

Compute Jacobian determinant statistics from a warp field.

Parameters:
  • warp_field (Union[str, Path]) – Path to a 4D or 5D warp field NIfTI (e.g. from ANTs).

  • output_dir (Union[str, Path, None]) – If provided, save a Jacobian determinant volume as NIfTI.

Return type:

Dict[str, Any]

Returns:

Dict with negative_voxels, negative_fraction, min_jacobian, max_jacobian, mean_jacobian. Empty dict if warp field cannot be loaded.

thesis.workflows.qc.checks.generate_bedpostx_overlay(bedpostx_dir, background_image, output_dir)[source]#

Generate an overlay of f1 (primary fibre fraction) and report stats.

Parameters:
  • bedpostx_dir (Union[str, Path]) – BedpostX output directory containing mean_f1samples.nii.gz.

  • background_image (Union[str, Path]) – Anatomical background.

  • output_dir (Union[str, Path]) – Directory for output PNGs.

Return type:

Tuple[List[Path], Dict[str, Any]]

Returns:

Tuple of (list of PNG paths, stats dict with mean_f1, etc.).

thesis.workflows.qc.checks.generate_waytotal_overlay(tractography_dir, template_image, output_dir)[source]#

Generate overlay for template-space waytotal.nii.gz.

Parameters:
  • tractography_dir (Union[str, Path]) – ProbTrackX2 output directory.

  • template_image (Union[str, Path]) – Template background image.

  • output_dir (Union[str, Path]) – Directory for output PNGs.

Return type:

List[Path]

Returns:

List of generated PNG paths.

thesis.workflows.qc.checks.detect_batch_outliers(stats_list, sd_threshold=2.0)[source]#

Flag subjects whose metrics are outliers relative to the batch.

Parameters:
  • stats_list (List[Dict[str, Any]]) – Batch statistics from collect_batch_stats().

  • sd_threshold (float) – Number of standard deviations to flag.

Return type:

List[Dict[str, Any]]

Returns:

List of dicts, each with patient_id, metric, value, mean, std, z_score.