Skip to content

Add ROI readback plotters#632

Merged
SimonHeybrock merged 5 commits intomainfrom
roi-readback-plotters
Jan 7, 2026
Merged

Add ROI readback plotters#632
SimonHeybrock merged 5 commits intomainfrom
roi-readback-plotters

Conversation

@SimonHeybrock
Copy link
Copy Markdown
Member

This is another (small) step towards replacing the complex and bespoke ROI plotter setup. In this change we add the ability the plot the "readback" ROI rectangles and polygons as their own layers.

We can thus now:

  • Plot image
  • Plot ROI readback overlay
  • Plot ROI spectra

What is missing for a fully modular setup is now just the "ROI request", based on a Holoviews stream. This is the most complex one.

As a secondary change in this PR we avoid depending on a particular name for detector the ROI type. As the title is now used for user display (output selection on plot creation, layer header) we needed something more informative instead of an internal identifier.

@SimonHeybrock SimonHeybrock marked this pull request as ready for review December 18, 2025 09:43
@nvaytet nvaytet self-assigned this Dec 18, 2025
Base automatically changed from static-geometry-overlay to main December 19, 2025 08:24
SimonHeybrock and others added 4 commits January 6, 2026 10:11
Add RectanglesReadbackPlotter and PolygonsReadbackPlotter for displaying
ROI shapes from workflow outputs in the new composable layer system.
Each shape is colored by its ROI index for stable visual identity.

Extend DataRequirements with:
- deny_coords: reject data containing specified coordinates
- required_dim_names: require specific dimension names

This enables the wizard to correctly filter plotters based on data
structure. LinePlotter now denies roi_index to avoid showing for ROI
data.

Prompt: We are in the process of converting the bespoke ROI plot setup
to the new approach of using composable layers in PlotOrchestrator/
PlotGridTabs. The next step would be to add a plotter that can plot
the "readback" rectangles or polygons. The end goal is that we want
to be able, in the PlotConfigModal, select a detector workflow, select
the "rectangles" output, get a Rectangles plotter on the wizard step,
and then plot this with different colors per rectangle based on index.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Decouple ROI type identification from the DataArray name attribute.
Previously, ROI.from_data_array() dispatched based on da.name, but
job_manager.py overwrites this with the field title, breaking parsing.

Now dispatch based on dimension name which is preserved through Kafka:
- 'bounds' -> RectangleROI
- 'vertex' -> PolygonROI
- 'ellipse' -> EllipseROI

This allows DetectorViewOutputs field titles to be user-friendly strings
like "Rectangle ROI (readback)" without breaking ROI deserialization.

Changes:
- ROI.from_data_array() dispatches on da.dims[0] instead of da.name
- EllipseROI uses 'ellipse' dimension instead of generic 'dim'
- Removed name-setting in to_data_array/to_concatenated_data_array
- Removed _get_plural_name/_get_singular_name helpers
- Updated tests to reflect dimension-based dispatch

Prompt: I need to change the title field in DetectorViewOutputs as shown
in the diff. But as the comment in the code emphasizes, this breaks
ROI.from_data_array. Can you think of a better solution? The title is
what the user sees, so it must not be relied upon.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
@SimonHeybrock SimonHeybrock force-pushed the roi-readback-plotters branch from 8fa326b to f554135 Compare January 6, 2026 10:11
The ROI type is encoded in the DataArray's name attribute, which maps to the
'label' field in da00 Variable for the signal.
The ROI type is encoded in the DataArray's dimension name: 'bounds' for
rectangles, 'vertex' for polygons, 'ellipse' for ellipses.
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

I find this mechanism difficult to follow/error prone.
Can we think of a different approach? Like make NewTypes for each case, where they would all be data arrays?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

The thing is that this gets serialized into da00 and the "other side" has to be able to tell what it is. We could add extra dummy coords or similar (minor message size/cost increase), but it is not really simpler I think?

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

ok gotcha

"""Plotters for ROI readback data from workflows.

These plotters display ROI shapes (rectangles, polygons) that come from
workflow outputs, with per-shape colors based on ROI index.
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Not sure I get what is meant by "that come from workflow outputs".
I thought the shapes were drawn by the user?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

See first line in what you quote: This is the "readback" - the detector view workflow that produces and output spectrum also returns the actual ROI that was used to make that spectrum.

sc.array(dims=['x'], values=[1.0, 2.0, 3.0]),
)
compatible = plotter_registry.get_compatible_plotters({'key': data})
assert 'lines' in compatible
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

I didn't really understand how the position or size of a rectangle or polygon gets updated from user interaction.
For my own understanding, can you describe quickly how that works?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

The backend detector view publishes the readback coords. This plotter plots this. There is no user interaction here.

The user interaction comes into play in the follow-up PR: Users draws/moves -> message to backend -> backend publishes readback (and updated ROI spectrum).

@SimonHeybrock SimonHeybrock merged commit be5cd7c into main Jan 7, 2026
4 checks passed
@SimonHeybrock SimonHeybrock deleted the roi-readback-plotters branch January 7, 2026 13:39
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.

2 participants