Skip to content

fix: Use the image loader for dicom-seg to allow compressed images#2611

Open
wayfarer3130 wants to merge 85 commits into
mainfrom
fix/use-imageLoader-for-seg
Open

fix: Use the image loader for dicom-seg to allow compressed images#2611
wayfarer3130 wants to merge 85 commits into
mainfrom
fix/use-imageLoader-for-seg

Conversation

@wayfarer3130
Copy link
Copy Markdown
Collaborator

@wayfarer3130 wayfarer3130 commented Feb 10, 2026

Context

The previous version of the segmentation loader claimed to support labelmap, but didn't actually work for loading them. As well, both bitmap and labelmap supposedly had RLE support, but again it didn't quite work.
This change adds storing as either labelmap or bitmap, and allows storing in RLE. The RLE encoder is also fixed to support 1,8,16 bits, and actually does the RLE correctly instead of using a count of 1 for every pixel.

The result of this is far faster loading of seg images from standard back ends supporting the SEG frame retrieve rather than trying to retrieve the entire DICOM file. On storage, the store size is also significantly smaller as RLE compresses extremely well for segmentation images.

OHIF_REF: feat/load-seg-images

Changes & Results

Testing

Checklist

PR

  • [] My Pull Request title is descriptive, accurate and follows the
    semantic-release format and guidelines.

Code

  • [] My code has been well-documented (function documentation, inline comments,
    etc.)

Public Documentation Updates

  • [] The documentation page has been updated as necessary for any public API
    additions or removals.

Tested Environment

  • [] "OS:
  • [] "Node version:
  • [] "Browser:

wayfarer3130 and others added 30 commits February 10, 2026 14:30
* fix(security): Update lodash to 4.17.23 using a resolution to address CVE-2025-13465.

* Removed lodash from the dev dependencies since it is in the resolutions now.

* Update lodash to 4.17.23 in the docs package.

---------

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Joe Boccanfuso <joe.boccanfuso@radicalimaging.com>
* refactor: replace string literals with OrientationAxis enums for better type safety and clarity in BaseVolumeViewport and getCameraVectors

* feat(rendering): Add function to calculate acquisition plane reformat orientation based on image orientation patient values

* feat: enhance reformat orientation handling in VolumeViewport and BaseVolumeViewport, allowing for specific axial, sagittal, and coronal reformats while maintaining base orientation references

* feat: add buttons for setting viewport orientations to non-reformat, reformat, and acquisition types, enhancing user control over viewport display

* fix: suppress events during camera reset in VolumeViewport to prevent premature rendering

* fix(getCameraVectors): import OrientationVectors type

* fix(tests): update button text in MPR Reformat visual tests

* fix(tests): update MPR Reformat screenshots for Chromium and WebKit

---------

Co-authored-by: Bill Wallace <wayfarer3130@gmail.com>
---------

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Joe Boccanfuso <joe.boccanfuso@radicalimaging.com>
* refactor the solution given

* fix fetch color tables

* important refactors to optimize worker functionality

* refactor fetch palette data

* fix clearly wrong test values

* refactor as reviewer suggestions

* fix: Convert 16 bit declared as 8 palette color data

* fix: or condition on setting 16 bit palette data

---------

Co-authored-by: Bill Wallace <wayfarer3130@gmail.com>
…eehandROI open U-shape contours (#2615)

* feat(tools): implement orthogonalT and lineSegment modes for PlanarFreehandROI open U-shape contours

Add two new rendering modes for the open U-shaped contour T-overlay:

- 'orthogonalT': computes the T-line endpoint as the perpendicular
  ray-contour intersection from the chord midpoint, instead of the
  farthest point. Useful for LA cardiac workflows where the T must be
  perpendicular to the chord.

- 'lineSegment': draws only the dashed chord connecting endpoints
  without any T-line, closing the contour visually.

Also adds optional shaded fill for the enclosed region (contour + chord)
when fillOpacity > 0, and centralizes variant dispatch into a single
resolveVectorToPeak function to eliminate duplicated branching across
drawLoop, openContourEditLoop, and renderMethods.

* fix(tools): address PR review for PlanarFreehandROI U-shape modes

- Use vec2.sub instead of create+set for chord vector
- Replace double-loop ray intersection with single-pass dot-product
  approach for orthogonalT peak finding
- Return null with console.warn instead of falling back to farthestT
  when no orthogonal intersection is found
- Add 'none' option to U-shape dropdown to remove U-shape rendering
- Auto-apply U-shape mode on dropdown change, remove separate button
- Apply configured U-shape mode to newly drawn open contours
- Add fill opacity dropdown using tool configuration
- Read fillOpacity from tool config in renderMethods

* refactor(tools): use vec2.dot for orthogonal T dot product calculation

* Move open u shaped to utils helper

---------

Co-authored-by: Bill Wallace <wayfarer3130@gmail.com>
* fix(security): Various dependency updates as a result of CVE-2026-26996.
Ultimately the vulnerability was ignored because it is only exposed in itk-wasm via CLI and it is limited to build/dev environments.
* refactor: update getTextBoxCoordsCanvas function to accept element and textLines parameters for improved textbox placement across multiple annotation tools

* fix: correct bounding box calculations in _drawTextGroup function to accurately reflect text box position and size

* feat: implement text box overlap management with registry for improved placement accuracy

- Added a text box overlap registry to track rendered text box positions.
- Integrated overlap avoidance logic in getTextBoxCoordsCanvas to prevent occlusion of existing text boxes.
- Updated draw and drawTextBox functions to clear and register text boxes during rendering.

* refactor: enhance overlap detection in getTextBoxCoordsCanvas using AABB intersection

- Replaced the previous rectangle overlap logic with a more accurate AABB intersection method.
- Introduced a new utility function to convert text box rectangles to AABB format, allowing for better handling of overlap checks.
- Updated the overlap detection functions to utilize the new intersection logic for improved accuracy in text box placement.

* test: add unit tests for getTextBoxCoordsCanvas to validate positioning logic

- Introduced a new test suite for getTextBoxCoordsCanvas to ensure correct coordinate calculations for text boxes.
- Added tests for default positioning, overlap handling, and fallback mechanisms when space is limited.
- Utilized a mock viewport element to simulate various scenarios for accurate testing.

* style: format getTextBoxCoordsCanvas test cases for improved readability

- Reformatted the test cases in getTextBoxCoordsCanvas.spec.ts to enhance code clarity.
- Adjusted the indentation and line breaks for better visual structure without altering functionality.

* refactor: update type assertions in getTextBoxCoordsCanvas tests for better type safety

- Changed type assertions from any to unknown in getTextBoxCoordsCanvas test cases to enhance type safety and maintain code quality.
- Ensured consistency in type handling across the test suite without altering existing functionality.

* refactor: remove unnecessary type assertions in getTextBoxCoordsCanvas tests

- Updated test cases in getTextBoxCoordsCanvas.spec.ts to eliminate type assertions from unknown to the actual type for annotationPoints and related variables.
- Improved code clarity and type safety without changing the existing functionality of the tests.

* chore: update tsconfig.json to exclude test files from compilation

- Added an "exclude" property to tsconfig.json to prevent test files from being included in the TypeScript compilation process.
- This change helps streamline the build process by omitting unnecessary test files.

* refactor: integrate getTextBoxCoordsCanvas into ArrowAnnotateTool for improved text box positioning

- Replaced direct canvas coordinate assignment with a call to getTextBoxCoordsCanvas to enhance the accuracy of text box placement.
- This change ensures that text box coordinates are calculated based on the current canvas state and element, improving overall annotation functionality.

* refactor: streamline text box rendering across annotation tools

- Replaced direct text box rendering logic with a unified renderLinkedTextBoxAnnotation method in multiple annotation tools.
- This change enhances code maintainability and consistency in text box visibility and positioning logic.
- Improved handling of text box state and coordinates, ensuring better integration with existing annotation functionalities.

---------

Co-authored-by: Bill Wallace <wayfarer3130@gmail.com>
* fix: Continuous flicker on viewer redraw

* fix: Comment on size 0
…kfile changes. (#2629)

Disabled all dependabot pull requests for bun and npm version updates.
@wayfarer3130 wayfarer3130 changed the title [WIP] fix: Use the image loader for dicom-seg to allow compressed images fix: Use the image loader for dicom-seg to allow compressed images Apr 16, 2026
@jbocce jbocce self-requested a review May 19, 2026 01:47
Comment thread bun.lock
@@ -1,5 +1,6 @@
{
"lockfileVersion": 1,
"configVersion": 0,
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You might consider using the version of bun that CI uses. That said, I'm sure we should look at upgrading considering I suspect you are experiencing no problems with it?

Comment thread bun.lock
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think should be able to revert the changes in this file as you have no dependency changes and cornerstone is now at a later version. I suppose just update your branch.

@@ -0,0 +1,210 @@
const RLE_LOSSLESS_TRANSFER_SYNTAX_UID = '1.2.840.10008.1.2.5';
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does it make sense to have these declared as constants in some central location?

@jbocce
Copy link
Copy Markdown
Collaborator

jbocce commented May 19, 2026

Here are a list of things Claude considered must fixes...

  • maxBytesPerChunk default lost → main-thread regression at labelmapImagesFromBuffer.ts:213. Previously defaulted to 199_000_000. Now destructured without a default, so chunkPixelData falls back to Number.POSITIVE_INFINITY and chunking never happens. Large SEGs will block the main thread / blow memory expectations on small devices. Restore the 199000000 default (or wire a sensible per-OS default).
  • Breaking API change with no deprecation at generateToolState.ts:50. createFromDICOMSegBuffer's 2nd arg changed from arrayBuffer to segImageId. Same name, same position, completely different contract — downstream OHIF/integrators will silently pass an ArrayBuffer and get metadataProvider.get('instance', ). Either rename the function (createFromDICOMSegImage) or detect the legacy shape and warn. At minimum, call this out in the PR body and changelog.
  • getReferencedSourceImageSequenceItem regex is too narrow at generateSegmentation.ts:175. /[?&]frame=(\d+)/ won't match the wadors form (wadors:.../frames/N) or imageId:multiframe?N shapes used elsewhere in this repo. Multi-frame source references will silently lose ReferencedFrameNumber. Reuse an existing helper (e.g. whatever derives frame index from imageId in the loader) instead of a one-off regex.
  • Uint16Array(uint8Array) value-copy vs. byte-reinterpret at generateSegmentation.ts:141. For 16-bit input where pixelData is a Uint8Array, new Uint16Array(pixelData) copies values (length stays the same), not reinterpret bytes. Likely dead path for SEG today (SEGs are 1-bit or 8-bit), but it's a latent landmine if a 16-bit bitmap SEG ever flows through.

@jbocce
Copy link
Copy Markdown
Collaborator

jbocce commented May 19, 2026

@claude review

Copy link
Copy Markdown
Collaborator

@jbocce jbocce left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See the comments I have left thus far.

Copy link
Copy Markdown

@claude claude Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Code review skipped — your organization's overage spend limit has been reached.

Code review is billed via overage credits. To resume reviews, an organization admin can raise the monthly limit at claude.ai/admin-settings/claude-code.

Once credits are available, reopen this pull request to trigger a review.

Copy link
Copy Markdown

@claude claude Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Code review skipped — your organization's overage spend limit has been reached.

Code review is billed via overage credits. To resume reviews, an organization admin can raise the monthly limit at claude.ai/admin-settings/claude-code.

Once credits are available, reopen this pull request to trigger a review.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

7 participants