Internalize shell command dispatch handling

This commit is contained in:
2026-04-07 11:44:16 +08:00
parent 864438c508
commit 35cd535b4c
4 changed files with 144 additions and 9 deletions

View File

@@ -39,6 +39,10 @@ struct UIEditorShellInteractionPalette {
Widgets::UIEditorMenuPopupPalette popupPalette = {};
};
struct UIEditorShellInteractionServices {
const UIEditorCommandDispatcher* commandDispatcher = nullptr;
};
struct UIEditorShellInteractionMenuButtonRequest {
std::string menuId = {};
std::string label = {};
@@ -84,10 +88,13 @@ struct UIEditorShellInteractionRequest {
struct UIEditorShellInteractionResult {
bool consumed = false;
bool menuModal = false;
bool workspaceInputSuppressed = false;
bool requestPointerCapture = false;
bool releasePointerCapture = false;
bool viewportInteractionChanged = false;
bool commandTriggered = false;
bool commandDispatched = false;
std::string menuId = {};
std::string popupId = {};
std::string itemId = {};
@@ -95,6 +102,7 @@ struct UIEditorShellInteractionResult {
std::string viewportPanelId = {};
UIEditorViewportInputBridgeFrame viewportInputFrame = {};
UIEditorMenuSessionMutationResult menuMutation = {};
UIEditorCommandDispatchResult commandDispatchResult = {};
UIEditorWorkspaceInteractionResult workspaceResult = {};
};
@@ -121,7 +129,8 @@ UIEditorShellInteractionRequest ResolveUIEditorShellInteractionRequest(
const UIEditorWorkspaceController& controller,
const UIEditorShellInteractionModel& model,
const UIEditorShellInteractionState& state = {},
const UIEditorShellInteractionMetrics& metrics = {});
const UIEditorShellInteractionMetrics& metrics = {},
const UIEditorShellInteractionServices& services = {});
UIEditorShellInteractionFrame UpdateUIEditorShellInteraction(
UIEditorShellInteractionState& state,
@@ -129,6 +138,7 @@ UIEditorShellInteractionFrame UpdateUIEditorShellInteraction(
const ::XCEngine::UI::UIRect& bounds,
const UIEditorShellInteractionModel& model,
const std::vector<::XCEngine::UI::UIInputEvent>& inputEvents,
const UIEditorShellInteractionServices& services = {},
const UIEditorShellInteractionMetrics& metrics = {});
void AppendUIEditorShellInteraction(

View File

@@ -220,6 +220,7 @@ bool HasMeaningfulInteractionResult(
result.requestPointerCapture ||
result.releasePointerCapture ||
result.commandTriggered ||
result.commandDispatched ||
result.menuMutation.changed ||
result.workspaceResult.consumed ||
!result.menuId.empty() ||
@@ -469,7 +470,9 @@ UIEditorShellInteractionRequest ResolveUIEditorShellInteractionRequest(
const UIEditorWorkspaceController& controller,
const UIEditorShellInteractionModel& model,
const UIEditorShellInteractionState& state,
const UIEditorShellInteractionMetrics& metrics) {
const UIEditorShellInteractionMetrics& metrics,
const UIEditorShellInteractionServices& services) {
(void)services;
return BuildRequest(
bounds,
controller,
@@ -484,6 +487,7 @@ UIEditorShellInteractionFrame UpdateUIEditorShellInteraction(
const UIRect& bounds,
const UIEditorShellInteractionModel& model,
const std::vector<UIInputEvent>& inputEvents,
const UIEditorShellInteractionServices& services,
const UIEditorShellInteractionMetrics& metrics) {
UIEditorShellInteractionResult interactionResult = {};
bool menuModalDuringFrame = state.menuSession.HasOpenMenu();
@@ -610,6 +614,13 @@ UIEditorShellInteractionFrame UpdateUIEditorShellInteraction(
} else if (hit.popupItem->enabled) {
eventResult.commandTriggered = true;
eventResult.commandId = hit.popupItem->commandId;
if (services.commandDispatcher != nullptr) {
eventResult.commandDispatchResult =
services.commandDispatcher->Dispatch(
eventResult.commandId,
controller);
eventResult.commandDispatched = true;
}
eventResult.menuMutation = state.menuSession.CloseAll();
} else {
eventResult.menuMutation =
@@ -700,6 +711,8 @@ UIEditorShellInteractionFrame UpdateUIEditorShellInteraction(
finalHit.popupItem != nullptr ? finalHit.popupItem->itemId : std::string();
frame.focused = state.focused || state.menuSession.HasOpenMenu();
interactionResult.workspaceResult = frame.workspaceInteractionFrame.result;
interactionResult.menuModal = state.menuSession.HasOpenMenu();
interactionResult.workspaceInputSuppressed = menuModalDuringFrame;
interactionResult.requestPointerCapture =
interactionResult.workspaceResult.requestPointerCapture;
interactionResult.releasePointerCapture =