Skip to content

FE-585: WIP petrinaut add hover + selected emphasis for nodes#8632

Open
alex-e-leon wants to merge 7 commits intomainfrom
FE-585-petrinaut-ux-improvements
Open

FE-585: WIP petrinaut add hover + selected emphasis for nodes#8632
alex-e-leon wants to merge 7 commits intomainfrom
FE-585-petrinaut-ux-improvements

Conversation

@alex-e-leon
Copy link
Copy Markdown
Contributor

🌟 What is the purpose of this PR?

WIP - not ready for review

Pre-Merge Checklist 🚀

🚢 Has this modified a publishable library?

This PR:

  • modifies an npm-publishable library and I have added a changeset file(s)

📜 Does this require a change to the docs?

The changes in this PR:

  • are internal and do not require a docs change

@vercel
Copy link
Copy Markdown

vercel bot commented Apr 15, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
hash Ready Ready Preview, Comment Apr 15, 2026 3:40pm
hashdotdesign Ready Ready Preview, Comment Apr 15, 2026 3:40pm
hashdotdesign-tokens Ready Ready Preview, Comment Apr 15, 2026 3:40pm
petrinaut Ready Ready Preview, Comment Apr 15, 2026 3:40pm

@cursor
Copy link
Copy Markdown

cursor bot commented Apr 15, 2026

PR Summary

Medium Risk
Touches shared EditorContext selection APIs and derives a new selectedConnections map from the Petri net definition on each render, which could affect selection behavior and performance across the editor. Visual-only changes otherwise, but regressions would be user-facing in the canvas selection UX.

Overview
Adds selection-neighbour awareness to the Petrinaut editor: a new getNodeConnections helper computes all places/transitions/arcs directly connected to the current selection, and EditorContext now exposes selectedConnections, isSelectedConnection, and isNotSelectedConnection.

Updates SDCPN canvas rendering to visually de-emphasize non-related items when anything is selected (background fade plus per-node/arc overlays), and adds styling variants so connected neighbours can be highlighted while unrelated nodes/arcs are lightened.

Reviewed by Cursor Bugbot for commit f1f6ff2. Bugbot is set up for automated code reviews on this repo. Configure here.

@github-actions github-actions bot added area/libs Relates to first-party libraries/crates/packages (area) type/eng > frontend Owned by the @frontend team labels Apr 15, 2026
@augmentcode
Copy link
Copy Markdown

augmentcode bot commented Apr 15, 2026

🤖 Augment PR Summary

Summary: This WIP PR adds “selection adjacency” awareness to Petrinaut so nodes/edges connected to the current selection can be visually emphasized while unrelated elements are de-emphasized.

Changes:

  • Added getNodeConnections() to compute places/transitions/arcs directly adjacent to selected items.
  • Extended EditorContext with selectedConnections, isSelectedConnection, and isNotSelectedConnection.
  • Computed the connection map in EditorProvider from petriNetDefinition.transitions and current selection IDs.
  • Updated place/transition/arc components to apply new “connected” vs “not connected” selection styling.
  • Added a global background fade overlay when a selection exists.
  • Introduced NOT_SELECTED_CONNECTION_OVERLAY_OPACITY and updated test editor context defaults.

Technical Notes: Arc IDs are derived via generateArcId(inputId, outputId) to match ReactFlow edge IDs; the connection map removes selected IDs so it represents neighbors only.

🤖 Was this summary useful? React with 👍 or 👎

Copy link
Copy Markdown

@augmentcode augmentcode bot left a comment

Choose a reason for hiding this comment

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

Review completed. 3 suggestions posted.

Fix All in Augment

Comment augment review to trigger a new review at any time.

/** Check whether a node/edge is connected to any selected item via an arc. */
isSelectedConnection: (id: string) => boolean;
/** Check whether a node/edge is connected to any selected item via an arc. */
isNotSelectedConnection: (id: string) => boolean;
Copy link
Copy Markdown

@augmentcode augmentcode bot Apr 15, 2026

Choose a reason for hiding this comment

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

libs/@hashintel/petrinaut/src/state/editor-context.ts:66 — The JSDoc for isNotSelectedConnection says “connected to any selected item”, but the implementation returns true for items that are neither selected nor connected. Consider adjusting the comment so callers don’t invert the meaning.

Severity: low

Fix This in Augment

🤖 Was this useful? React with 👍 or 👎, or 🚀 if it prevented an incident/outage.


const isSelectedConnection = (id: string) => selectedConnections.has(id);
const isNotSelectedConnection = (id: string) =>
selection.size > 0 && !isSelected(id) && !selectedConnections.has(id);
Copy link
Copy Markdown

@augmentcode augmentcode bot Apr 15, 2026

Choose a reason for hiding this comment

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

libs/@hashintel/petrinaut/src/state/editor-provider.tsx:239 — isNotSelectedConnection becomes true for all unselected IDs whenever selection.size > 0, even if the selection is a non-canvas item (e.g. parameter/type), which could unexpectedly dim the whole net. Consider gating this behavior to selections that include places/transitions/arcs (or when selectedConnections is non-empty).

Severity: medium

Other Locations
  • libs/@hashintel/petrinaut/src/views/SDCPN/sdcpn-view.tsx:400

Fix This in Augment

🤖 Was this useful? React with 👍 or 👎, or 🚀 if it prevented an incident/outage.

* An item is included if it shares an arc with a selected item:
* - A selected place includes its connected transitions and arcs.
* - A selected transition includes its connected places and arcs.
* - A selected arc includes its source place and target transition.
Copy link
Copy Markdown

@augmentcode augmentcode bot Apr 15, 2026

Choose a reason for hiding this comment

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

libs/@hashintel/petrinaut/src/lib/get-connections.ts:13 — The docs say a selected arc includes its “source place and target transition”, but output arcs are transition→place as well. Consider rewording to “source and target nodes” to avoid confusion.

Severity: low

Fix This in Augment

🤖 Was this useful? React with 👍 or 👎, or 🚀 if it prevented an incident/outage.

Copy link
Copy Markdown

@cursor cursor bot left a comment

Choose a reason for hiding this comment

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

Cursor Bugbot has reviewed your changes and found 3 potential issues.

Fix All in Cursor

❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.

Reviewed by Cursor Bugbot for commit f1f6ff2. Configure here.


const isSelectedConnection = (id: string) => selectedConnections.has(id);
const isNotSelectedConnection = (id: string) =>
selection.size > 0 && !isSelected(id) && !selectedConnections.has(id);
Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Non-graph item selection fades entire graph unexpectedly

Medium Severity

When a non-graph item (type, parameter, or differential equation) is selected from the sidebar, getNodeConnections returns an empty map because it only traverses transitions/arcs. Combined with hasSelection being true, this causes: (1) the global fadeBgStyle overlay to render over the entire canvas, and (2) isNotSelectedConnection to return true for every graph item, applying the dimmed/faded visual to all nodes and the brightness(1.5) filter to all arcs. The entire Petri net appears heavily washed out when selecting a non-graph item.

Additional Locations (1)
Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit f1f6ff2. Configure here.

const selectedConnections = getNodeConnections(
petriNetDefinition.transitions,
new Set(selection.keys()),
);
Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Expensive computation runs on every unrelated render

Medium Severity

getNodeConnections is called in the render body of EditorProvider without useMemo, so it recomputes on every state change — sidebar resizes, panel toggles, dragging state updates — even when selection and petriNetDefinition.transitions haven't changed. For large Petri nets with many transitions and arcs, this O(n) computation runs unnecessarily on unrelated interactions.

Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit f1f6ff2. Configure here.

: notSelectedConnection
? {
filter: `brightness(${1 + NOT_SELECTED_CONNECTION_OVERLAY_OPACITY})`,
}
Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Arc brightness filter makes strokes completely invisible

Medium Severity

The NOT_SELECTED_CONNECTION_OVERLAY_OPACITY (0.5) was designed as a white overlay opacity for nodes (rgba(255,255,255, 0.5)), but for arcs it's reused as a brightness additive: brightness(1 + 0.5) = brightness(1.5). The default arc stroke #b1b1b7 has channel values ~177; multiplied by 1.5 they clip to 255, producing pure white. Unconnected arcs become completely invisible instead of subtly faded like nodes.

Additional Locations (1)
Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit f1f6ff2. Configure here.

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

Labels

area/libs Relates to first-party libraries/crates/packages (area) type/eng > frontend Owned by the @frontend team

Development

Successfully merging this pull request may close these issues.

1 participant