Skip to article frontmatterSkip to article content
Site not loading correctly?

This may be due to an incorrect BASE_URL configuration. See the MyST Documentation for reference.

Bone Mineral Density Example

  • By: Michael T. Kuczynski, 2024

  • License: CC-BY

  • How to cite: Cite the ORMIR_XCT publication: Kuczynski et al., (2024). ORMIR_XCT: A Python package for high resolution peripheral quantitative computed tomography image processing. Journal of Open Source Software, 9(97), 6084, Kuczynski et al. (2024)


Aims


Step 1: Imports:

Import modules/packages and set the input image path.

import os
import SimpleITK as sitk

from ormir_xct.core.microarchitecture.bmd import bmd
from ormir_xct.core.microarchitecture.bmd_masked import bmd_masked
from ormir_xct.core.segmentation.autocontour import autocontour
joint_seg_path = os.path.join("images", "GRAY_JOINT.nii")

gray_img = sitk.ReadImage(joint_seg_path, sitk.sitkFloat32)

Step 2: Run the ORMIR_XCT Automatic Contour:

Run the ORMIR_XCT automatic periosteal contour script on the input grayscale joint image. This script will return the distal, proximal, and full joint mask.

When running the ORMIR_XCT automatic contour script, we need to provide the image units and parameters for unit conversion to get an accurate segmentation. Since we are using an AIM/ISQ image that has been converted to another file type using the ITKIOScanco module from ITK, the image units are Hounsfield Units (HU). For the sample image provided, the follow parameters taken from the AIM header are used:

  • mu_water = 0.24090

  • mu_scaling = 8192

  • resale_slope = 1603.51904

  • rescale_intercept = -391.209015

These values may vary depending on your scanner.

mu_water = 0.24090
mu_scaling = 8192
rescale_slope = 1603.51904
rescale_intercept = -391.209015

dst_mask, prx_mask, ormir_mask = autocontour(
    gray_img, mu_water, rescale_slope, rescale_intercept
)

Step 3: Compute vBMD:

Now computed vBMD. We will calculate the vBMD for each bone segment.

# First mask the image with the distal and proximal joint masks

# Unmasked bmd results
bmd_results = bmd(
    gray_img, 
    "hu", 
    mu_scaling,
    mu_water, 
    rescale_slope, 
    rescale_intercept
)

print("Unmasked vBMD: {:.2f} +/- {:.2f} mg HA/cm^3".format(bmd_results[0], bmd_results[1]))

# Distal vBMD
masked_gray_img = sitk.Mask(gray_img, dst_mask)
dst_bmd_masked = bmd_masked(
    masked_gray_img,
    dst_mask,
    "hu",
    mu_scaling,
    mu_water,
    rescale_slope,
    rescale_intercept,
)



print("Distal vBMD: {:.2f} +/- {:.2f} mg HA/cm^3".format(dst_bmd_masked[0], dst_bmd_masked[1]))

# Proximal vBMD
prx_gray_img = sitk.Mask(gray_img, prx_mask)
prx_bmd_masked = bmd_masked(
    masked_gray_img,
    prx_mask,
    "hu",
    mu_scaling,
    mu_water,
    rescale_slope,
    rescale_intercept,
)


print("Proximal vBMD: {:.2f} +/- {:.2f} mg HA/cm^3".format(prx_bmd_masked[0], prx_bmd_masked[1]))
Unmasked vBMD: -140.41 +/- 265.69 mg HA/cm^3
Distal vBMD: 193.18 +/- 205.73 mg HA/cm^3
Proximal vBMD: -4.92 +/- 0.00 mg HA/cm^3

Step 4: Compare Between IPL and ORMIR_XCT:

Now compare vBMD results between IPL and ORMIR_XCT.

The vBMD results from IPL have been pre-generated and are provided as:

  • Distal vBMD: 203.84 +/- 212.96 mg HA/cm^3

  • Proximal vBMD: 224.20 +/- 240.37 mg HA/cm^3


Notebook created using the template of the ORMIR community (version 1.0, 2023)

References
  1. Kuczynski, M. T., Neeteson, N. J., Stok, K. S., Burghardt, A. J., Hernandez, M. A. E., Vicory, J., Tse, J. J., Durongbhan, P., Bonaretti, S., Wong, A. K. O., Boyd, S. K., & Manske, S. L. (2024). ORMIR_XCT: A Python package for high resolution peripheral quantitative computed tomography image processing. Journal of Open Source Software, 9(97), 6084. 10.21105/joss.06084