Implement a more robust scoring mechanism for screw optimization and
add functionality to generate synthetic X-ray projections (AP and
lateral views) from CT data.
Key changes:
- core: add `generate_cylinder_butt_torch` to create a mask for the
screw entrance (0.25mm) to exempt it from bone-breaching penalties.
- core: update `cl_score_torch_xfr` to include a diameter preference
bonus and utilize the entrance mask.
- core: adjust optimizer bounds and scoring weights to favor larger
diameter screws and improve convergence.
- xfr_cbt_native: implement `render_xray_projections` to generate
synthetic AP and lateral X-ray images for visualization.
- visualization: enhance `render_bone_figure` with semi-transparent
spinous process rendering and improved depth sorting for screws.
- xfr_debug: improve level detection to support arbitrary lumbar
levels (L1-L9) and add safe volume-level cleanup for CBT writing.
- config: update allowed diameters and lengths constants.
Update the coordinate transformation pipeline to prioritize the affine
transformation chain recorded in `transform.json` (original_to_source)
instead of relying on re-calculated geometric parameters.
The previous method relied on re-estimating rotation, center, and
bounding boxes from the bone mask, which led to inaccuracies in screw
pillar mapping (e.g., dropping from 99% to 30-94% in-label accuracy).
The new approach uses the precise inverse affine mapping `o = M^-1 (s - t)`
from the transformation metadata.
A fallback mechanism is maintained for legacy volumes lacking
`transform.json`, which continues to use the re-calculation method.
- Implement `load_transform` and `original_to_source` integration
- Update documentation to reflect the new primary/fallback coordinate chains
- Improve precision of screw parameter mapping to native index space
Introduce a robust coordinate transformation system to manage the relationship
between original CT space and rotated/standardized segmentation spaces.
This includes a new directory hierarchy to separate unrotated crops from
rotated outputs and utility functions for geometric mapping.
Key changes:
- Implement `imaging/transforms.py` to handle bounding box metadata,
affine standardization, and coordinate mapping between spaces.
- Restructure dataset output: unrotated segmentation files (binary, SDF,
ROI, etc.) are now stored in a `<vol>/crop/` subdirectory to distinguish
them from `<vol>/rotated/` aligned versions.
- Add `level_file_path` utility to abstract file discovery across legacy
(top-level) and new (crop-based) directory structures.
- Enhance `seg_bone` to capture and export bounding box metadata
(`bbox2`, `nn_bbox`, `bbox_orig`) into `transform.json`.
- Implement `xfr_cbt_native.py` for mapping screw positions back to
original CT space.
- Update preprocessing and visualization scripts to support the new
directory layout and transformation metadata.
- Improve TinyDB metadata migration logic to prevent accidental corruption
of existing database structures.
Refactor the preprocessing and segmentation pipeline to handle AP orientation
variations and improve anatomical boundary detection.
Key changes include:
- Implement automated AP orientation detection in `process_single_image`
to handle prone scans by flipping CT and labels when necessary.
- Enhance `segment_spinous_process` using a gap-based approach to identify
the spinal canal, providing more stable thresholds for spinous process
and vertebral body segmentation.
- Improve optimization search space by using the vertebral body (VBODY)
projection for x/z bounding box calculation instead of the whole bone.
- Refactor `render_bone_figure` to unify 2D/3D visualization and support
detailed anatomical coloring (VBODY, spinous process).
- Update `cl_score_torch_xfr` with more robust penalty handling for
out-of-bone and null-voxel regions.
- Add `retry_robust` utility to handle transient NFS file system errors.
- Update `xfr_preprocess.py` to include anatomical segmentation coloring
in rotated level visualizations.
Introduces a new scoring component for vertebral body (VBODY) rewards
to improve optimization accuracy. The update includes:
- Added `vbody_tensor` to `OptimizationContext` and scoring functions
to reward screw placement within the vertebral body.
- Enhanced `segment_spinous_process` with diagnostic capabilities to
detect spinous process absence (e.g., post-laminectomy).
- Improved `resample_img` to prevent physical boundary clipping and
handle interpolation more robustly for CT and label data.
- Implemented a metadata cache using TinyDB in the preprocessing
pipeline to skip low-resolution or insufficient scans efficiently.
- Added robust error handling for NFS-based file operations and
directory creation.
- Added new visualization tools for bone figures and level plotting.
refactor(imaging): improve segmentation and resampling precision
- Refactored `seg_bone` to support original resolution binary masks and
Signed Maurer Distance Maps (SMD) for more accurate boundary handling.
- Updated `resample_img` to use `ceil` for output size calculation to
ensure full physical coverage.
- Optimized `process_single_image` to utilize metadata for skipping
processing of invalid or low-quality scans.
Refactor the optimization pipeline to eliminate module-level global variables,
improving thread safety and modularity. Introduced `OptimizationContext`
to explicitly manage shared state during cylinder evaluation.
Key changes:
- core: Replace global variables with `OptimizationContext` dataclass in
`objective.py`.
- core: Implement `refine_lateral_longer` in `optimizer.py` for deterministic
local refinement of screw placement.
- core: Update scoring logic in `scoring.py` to use higher penalties for
out-of-bone voxels.
- imaging: Add advanced symmetry detection including `best_symmetry_plane`
and `best_symmetry_axis_angle` in `orientation.py`.
- visualization: Enhance 3D plotting in `res_plot_3d.py` with volume
absorption rendering (Beer-Lambert law) for an X-ray-like appearance.
- xfr_debug: Implement a custom `_Tee` logger to support multi-process
logging with volume and level-specific tags.
- chore: Update `.gitignore` to include local logs and kilo directories.
Refactor the cylinder parameter selection and optimization process to
improve accuracy and robustness.
- Implement `snap_to_discrete_values_xfr` using a KDTree for efficient
mapping of continuous diameter and length values to a predefined
set of discrete points.
- Update `objective_function_xfr` to use the new snapping mechanism
and introduce a weighted loss component for diameter and length.
- Adjust PSO optimization bounds and search ranges in `run_pso_torch_xfr`
to better align with image dimensions and anatomical constraints.
- Refine scoring logic in `cl_score_torch_xfr` with updated penalty
weights for overlaps and out-of-bone voxels.
- Update `config/constant.py` with new allowed diameter and length
ranges.
- Improve `imaging/preprocessing.py` by making `PROGRESS_FILE` a
parameter to allow per-output-directory progress tracking.
- Update `xfr_debug.py` with improved error handling and directory
paths for batch processing.