diff --git a/PanTS-Demo/src/components/ScanReadout/ScanReadout.tsx b/PanTS-Demo/src/components/ScanReadout/ScanReadout.tsx new file mode 100644 index 0000000..c8b4c26 --- /dev/null +++ b/PanTS-Demo/src/components/ScanReadout/ScanReadout.tsx @@ -0,0 +1,62 @@ +import { organDescriptions } from "../../helpers/organInfo"; + +const pretty = (s: string) => s.replaceAll("_", " "); +const fmtVolume = (cm3: number) => (cm3 >= 1000 ? `${(cm3 / 1000).toFixed(1)} L` : `${Math.round(cm3)} cm³`); + +type ReadoutStat = { organ_name: string; volume_cm3: number; mean_hu: number }; + +type Props = { + stats: ReadoutStat[] | null; + loading: boolean; + error: boolean; + onLoad: () => void; +}; + +export default function ScanReadout({ stats, loading, error, onLoad }: Props) { + return ( +
+
+ Scan readout +
+
+ {loading ? ( +

Reading the scan…

+ ) : error ? ( +

Couldn't load measurements for this scan.

+ ) : !stats ? ( + <> +

+ A plain-language summary of this scan: each structure's measured size and density, explained. For learning, not diagnosis. +

+ + + ) : stats.length === 0 ? ( +

No measurable structures found in this scan.

+ ) : ( + <> +

+ Density is in Hounsfield Units (HU): water is 0, fat is negative, soft tissue is mildly positive, bone is high. Volumes are measured from the segmentation. For learning, not diagnosis. +

+ {stats.map((s) => ( +
+
+ {pretty(s.organ_name)} + — {fmtVolume(s.volume_cm3)} · {Math.round(s.mean_hu)} HU +
+

+ {organDescriptions[s.organ_name] ?? "A structure identified in this scan."} +

+
+ ))} + + )} +
+
+ ); +} diff --git a/PanTS-Demo/src/helpers/organInfo.ts b/PanTS-Demo/src/helpers/organInfo.ts new file mode 100644 index 0000000..8115976 --- /dev/null +++ b/PanTS-Demo/src/helpers/organInfo.ts @@ -0,0 +1,34 @@ +export const organDescriptions: Record = { + adrenal_gland_left: "A small hormone-making gland on top of the left kidney. It helps control stress response, blood pressure, and metabolism.", + adrenal_gland_right: "A small hormone-making gland on top of the right kidney. It helps control stress response, blood pressure, and metabolism.", + aorta: "The body's main artery, carrying oxygen-rich blood from the heart down through the chest and abdomen.", + bladder: "The hollow, stretchy organ that stores urine until you empty it.", + celiac_artery: "A short, major artery off the aorta that feeds the liver, stomach, and spleen.", + colon: "The large intestine, which pulls water back out of digested food and forms stool.", + common_bile_duct: "The tube carrying bile from the liver and gallbladder into the small intestine to help digest fat.", + duodenum: "The first stretch of the small intestine, right after the stomach.", + femur_left: "The thigh bone of the left leg, the longest, strongest bone in the body.", + femur_right: "The thigh bone of the right leg, the longest, strongest bone in the body.", + gall_bladder: "A small sac under the liver that stores bile and releases it into the gut to break down fats.", + kidney_left: "The left kidney, which filters waste out of the blood and makes urine.", + kidney_right: "The right kidney, which filters waste out of the blood and makes urine.", + liver: "A large organ that filters the blood, processes nutrients, and makes bile.", + lung_left: "The left lung, moving oxygen into the blood and carbon dioxide out.", + lung_right: "The right lung, moving oxygen into the blood and carbon dioxide out.", + pancreas: "An organ behind the stomach that makes digestive enzymes and insulin, which controls blood sugar.", + pancreas_body: "The middle section of the pancreas.", + pancreas_head: "The wide end of the pancreas, set into the curve of the duodenum.", + pancreas_tail: "The narrow end of the pancreas, reaching toward the spleen.", + pancreatic_duct: "The channel carrying digestive juices from the pancreas into the small intestine.", + pancreatic_lesion: "An abnormal spot in the pancreas that a doctor would want to look at closely.", + postcava: "The inferior vena cava, the large vein returning blood from the lower body to the heart.", + prostate: "A small gland below the bladder in men that adds fluid to semen.", + spleen: "An organ near the stomach that filters blood and helps fight infection.", + stomach: "The muscular pouch that mixes food with acid and starts breaking it down.", + superior_mesenteric_artery: "A major artery off the aorta that supplies most of the small intestine and part of the colon.", + veins: "Blood vessels that carry blood back toward the heart.", + intestine: "The long, coiled tube where most digestion and nutrient absorption happen.", + renal_vein_left: "The vein draining filtered blood from the left kidney back toward the heart.", + renal_vein_right: "The vein draining filtered blood from the right kidney back toward the heart.", + cbd_stent: "A small tube a doctor places to hold the bile duct open so bile can drain.", +}; diff --git a/PanTS-Demo/src/routes/VisualizationPage.tsx b/PanTS-Demo/src/routes/VisualizationPage.tsx index 5336ec6..e034e5f 100644 --- a/PanTS-Demo/src/routes/VisualizationPage.tsx +++ b/PanTS-Demo/src/routes/VisualizationPage.tsx @@ -24,6 +24,7 @@ import ReportScreen from "../components/ReportScreen/ReportScreen"; import SnakeGame from "../components/SnakeGame/SnakeGame"; import WindowingSlider from "../components/WindowingSlider/WindowingSlider"; import ZoomHandle from "../components/zoomHandle"; +import ScanReadout from "../components/ScanReadout/ScanReadout"; import { API_BASE, APP_CONSTANTS, @@ -805,6 +806,12 @@ function VisualizationPage() { setSubmitted={setZoomLevel} setZoomMode={setZoomMode} /> + {/* Report Download Zoom Buttons */}