Skip to content

CmdPal: Fix first-open top-level context menus for slow providers#46626

Open
jiripolasek wants to merge 1 commit intomainfrom
dev/jpolasek/b/46625-cmdpal-context-menu-first-click-wont-open
Open

CmdPal: Fix first-open top-level context menus for slow providers#46626
jiripolasek wants to merge 1 commit intomainfrom
dev/jpolasek/b/46625-cmdpal-context-menu-first-click-wont-open

Conversation

@jiripolasek
Copy link
Copy Markdown
Collaborator

Summary of the Pull Request

This PR fixes opening of the list item context menu through right-click, which affected mainly 3rd party out-of-process extensions.

  • Keeps the first context-menu request alive when a top-level item is selected but its out-of-proc MoreCommands are still hydrating.
  • Short-circuits CanOpenContextMenu when a valid synthetic primary command is already available, so items with a usable primary action can open immediately without waiting for late menu hydration.

PR Checklist

  • Communication: I've discussed this with core contributors already. If the work hasn't been agreed, this work might be rejected
  • Tests: Added/updated and all pass
  • Localization: All end-user-facing strings can be localized
  • Dev docs: Added/updated
  • New binaries: Added on the required places
  • Documentation updated: If checked, please file a pull request on our docs repo and link it here: #xxx

Detailed Description of the Pull Request / Additional comments

Validation Steps Performed

- Keeps the first context-menu request alive when a top-level item is selected
but its out-of-proc MoreCommands are still hydrating.
- Short-circuits CanOpenContextMenu when a valid synthetic primary command
is already available, so items with a usable primary action can open
immediately without waiting for late menu hydration.
@jiripolasek jiripolasek self-assigned this Mar 29, 2026
@jiripolasek jiripolasek added Product-Command Palette Refers to the Command Palette utility Needs-Review This Pull Request awaits the review of a maintainer. labels Mar 29, 2026
@michaeljolley michaeljolley requested a review from Copilot March 30, 2026 17:09
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

Fixes CmdPal’s first-attempt context menu opening for slow / out-of-proc providers by keeping the initial open request alive until the selected item becomes context-openable, and by making a usable synthetic primary command available earlier in item initialization.

Changes:

  • Add “pending context menu open” tracking in ListPage to retry opening once the selected item’s context menu becomes available.
  • Update CommandItemViewModel to allow CanOpenContextMenu to succeed immediately when a visible synthetic primary command exists (even if MoreCommands hydration is still in progress).
  • Add a unit test validating that fast init creates the synthetic primary context item.

Reviewed changes

Copilot reviewed 3 out of 3 changed files in this pull request and generated 3 comments.

File Description
src/modules/cmdpal/Tests/Microsoft.CmdPal.UI.ViewModels.UnitTests/CommandItemViewModelTests.cs Adds coverage for fast-init creation of the synthetic primary context item.
src/modules/cmdpal/Microsoft.CmdPal.UI/ExtViews/ListPage.xaml.cs Keeps first context-menu open request pending and opens once the selected item becomes context-openable.
src/modules/cmdpal/Microsoft.CmdPal.UI.ViewModels/CommandItemViewModel.cs Enables context menu opening via a visible synthetic primary command before MoreCommands hydration completes.

Comment on lines +1274 to +1279
private void CancelPendingContextMenuOpen()
{
Interlocked.Increment(ref _pendingContextMenuOpenRequestId);
_cancelPendingContextMenuOpen?.Invoke();
_cancelPendingContextMenuOpen = null;
}
Copy link

Copilot AI Mar 30, 2026

Choose a reason for hiding this comment

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

CancelPendingContextMenuOpen is only invoked on navigation, explicit context-cancel, or a new context-menu request. If the user changes selection while an open request is pending (e.g., slow provider never hydrates, or selection changes due to list updates), the PropertyChanged handler remains attached to the old item indefinitely. Consider canceling pending requests on selection changes (and/or when the selected item no longer matches) so the handler is detached promptly and doesn’t keep doing work for stale requests.

Copilot uses AI. Check for mistakes.
Comment on lines +1011 to 1013
ViewModel?.UpdateSelectedItemCommand.Execute(item);
RequestContextMenuOpen(item, element, pos);
e.Handled = true;
Copy link

Copilot AI Mar 30, 2026

Choose a reason for hiding this comment

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

Both Items_RightTapped and Items_OnContextRequested are wired up in XAML and each calls UpdateSelectedItemCommand.Execute(item) and RequestContextMenuOpen(...). If these two events can fire for the same mouse right-click, this will run selection updates twice and can cancel/restart the background slow-init work in ListViewModel.SetSelectedItem, potentially delaying menu hydration. Consider consolidating to a single code path or adding a guard to ensure the selection/open logic runs only once per user action.

Copilot uses AI. Check for mistakes.
Comment on lines +447 to 456
// We only synthesize the primary entry when the command is already
// usable; a null/empty primary must still fall back to late
// MoreCommands-based opening.
if (string.IsNullOrEmpty(Command.Name) || commandModel is null)
{
return;
}

_defaultCommandContextItemViewModel = new CommandContextItemViewModel(new CommandContextItem(model.Command!), PageContext)
_defaultCommandContextItemViewModel = new CommandContextItemViewModel(new CommandContextItem(commandModel), PageContext)
{
Copy link

Copilot AI Mar 30, 2026

Choose a reason for hiding this comment

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

Creating _defaultCommandContextItemViewModel here changes the computed CanOpenContextMenu value, but this method doesn’t raise a CanOpenContextMenu notification when the synthetic primary gets created. In the fast-init path this can leave listeners that react specifically to CanOpenContextMenu (e.g., CommandBarViewModel.SelectedItemPropertyChanged) out of date. Consider raising CanOpenContextMenu alongside AllCommands when the synthetic primary is first created.

Copilot uses AI. Check for mistakes.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Needs-Review This Pull Request awaits the review of a maintainer. Product-Command Palette Refers to the Command Palette utility

Projects

Status: No status

Development

Successfully merging this pull request may close these issues.

CmdPal: First click doesn't open context menu on 3rd party items

2 participants