Skip to content

fix(desktop): cron edit button unclickable in sidebar (#66854) - #66919

Closed
kyssta-exe wants to merge 1 commit into
NousResearch:mainfrom
kyssta-exe:auto-fix/issue-66854
Closed

fix(desktop): cron edit button unclickable in sidebar (#66854)#66919
kyssta-exe wants to merge 1 commit into
NousResearch:mainfrom
kyssta-exe:auto-fix/issue-66854

Conversation

@kyssta-exe

Copy link
Copy Markdown
Contributor

Summary

Fixes #66854 - The cron edit button in the desktop sidebar was unclickable in v0.18.2.

Root Cause

The previous fix for stuck tooltips (commit 7f69494) used event.preventDefault() on focus events to suppress tooltip opens for mouse-driven focus. However, in Electron/Chromium, calling preventDefault() on a focus event prevents subsequent click events from firing on the same element, breaking interactive elements wrapped in <Tip> components.

Fix

Instead of preventDefault(), use a context-based approach:

  1. The TooltipTrigger sets a ref flag when focus is mouse-driven (not keyboard-visible)
  2. The Tooltip Root's onOpenChange handler checks this flag before opening
  3. If the flag is set, suppress the open and clear the flag
  4. This preserves the original fix for stuck tooltips while allowing clicks to work

Changes

  • apps/desktop/src/components/ui/tooltip.tsx: Replace suppressNonKeyboardFocusOpen with context-based suppression
  • apps/desktop/src/components/ui/tooltip.test.tsx: Update tests to cover the new logic

Testing

All 5 tests pass:

  • Mouse focus suppression works correctly
  • Keyboard focus (Tab) still shows tooltips (a11y preserved)
  • Fails open when :focus-visible is unsupported
  • onOpenChange suppresses open when flag is set
  • onOpenChange allows open when flag is not set

Verification

Tested in the desktop app: cron edit button now responds to clicks, and tooltips no longer get stuck after menu interactions.

…6854)

The suppressNonKeyboardFocusOpen function called event.preventDefault() on
focus events, which in Electron/Chromium prevented subsequent click events
from firing on the same element. This broke the cron edit button in the
sidebar.

Instead of preventDefault(), use a context-based approach: the trigger sets
a ref flag when focus is mouse-driven, and the Tooltip Root's onOpenChange
handler checks it before opening. This preserves the original fix for
stuck tooltips while allowing clicks to work.

Fixes NousResearch#66854
@alt-glitch alt-glitch added type/bug Something isn't working comp/desktop Electron desktop app (apps/desktop/*) P3 Low — cosmetic, nice to have labels Jul 18, 2026
@alt-glitch

Copy link
Copy Markdown
Collaborator

This was generated by AI during triage.

Fixes open report #66854 and is related to merged #66737: it repairs the Electron click regression caused by that tooltip focus-suppression change.

@teknium1 teknium1 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Thanks for tracing this to the shared tooltip wrapper; current main still has the affected Tip-wrapped cron manage button at apps/desktop/src/app/chat/sidebar/cron-jobs-section.tsx:250.

Problems

  • apps/desktop/src/components/ui/tooltip.tsx:60 uses onOpenChange as a cancellation hook, but Radix has already committed an uncontrolled state change before notifying that callback. Its useControllableState calls setUncontrolledProp first (node_modules/@radix-ui/react-use-controllable-state/dist/index.js:76-78) and invokes the callback later (:94-99), so returning at tooltip.tsx:50 does not keep the tooltip closed.
  • apps/desktop/src/components/ui/tooltip.test.tsx:28 and :80 reimplement the proposed branches rather than render Tip/Tooltip; they cannot catch that Radix lifecycle behavior.

Suggested changes

  • Intercept the state request before Radix commits it, for example by owning controlled open state in the wrapper, then forward accepted transitions to any caller callback.
  • Add a rendered interaction test covering non-keyboard focus, click delivery, suppressed tooltip open, and keyboard-focus accessibility.

Automated hermes-sweeper review.

}
return (
<suppressMouseFocusOpenContext.Provider value={{ suppressNextOpen: suppressNextOpenRef }}>
<TooltipPrimitive.Root data-slot="tooltip" onOpenChange={handleOpenChange} {...props} />

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

onOpenChange is a post-transition notification for uncontrolled Radix Tooltip state, not a cancellation hook: setUncontrolledProp(nextValue) runs before its onChange effect. Returning from handleOpenChange therefore suppresses only a consumer callback; it does not prevent the tooltip from opening. Please intercept the request before Radix commits state (for example with controlled open state).

const suppressNextOpen = { current: true }
const onOpenChange = vi.fn()

// Simulate the Tooltip Root onOpenChange handler logic

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

This test reimplements handleOpenChange instead of exercising TooltipPrimitive.Root, so it cannot verify the proposed cancellation mechanism. Render Tip around a button and assert both that mouse-focus/click is delivered and that the tooltip does not open; retain a keyboard-focus case.

@teknium1 teknium1 added sweeper:risk-compatibility Sweeper risk: may break existing users, config, migrations, defaults, or upgrades sweeper:risk-platform-windows Sweeper risk: may break or behave differently on native Windows sweeper:blast-moderate Sweeper blast radius: moderate — a subsystem or single platform labels Jul 19, 2026
@kyssta-exe

Copy link
Copy Markdown
Contributor Author

Closing due to merge conflicts. This PR has a CONFLICTING merge status (DIRTY), meaning it cannot be merged without manual conflict resolution. Please rebase on the latest main and resolve conflicts before re-submitting.

@kyssta-exe kyssta-exe closed this Jul 28, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

comp/desktop Electron desktop app (apps/desktop/*) P3 Low — cosmetic, nice to have sweeper:blast-moderate Sweeper blast radius: moderate — a subsystem or single platform sweeper:risk-compatibility Sweeper risk: may break existing users, config, migrations, defaults, or upgrades sweeper:risk-platform-windows Sweeper risk: may break or behave differently on native Windows type/bug Something isn't working

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Desktop] Scheduled task edit button unclickable in sidebar (v0.18.2)

3 participants