From 85ebf53d52fe711e74c74d119173aae79b865589 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=A2=81=E5=85=B8=E5=85=B8?= Date: Wed, 15 Apr 2026 18:08:03 +0800 Subject: [PATCH 1/4] Expose Flutter debug toolbar extension group --- resources/META-INF/plugin.xml | 3 ++ src/io/flutter/run/FlutterDebugProcess.java | 1 + .../run/FlutterDebugProcessActions.java | 44 +++++++++++++++++++ .../run/bazelTest/BazelTestDebugProcess.java | 2 + src/io/flutter/run/test/TestDebugProcess.java | 2 + 5 files changed, 52 insertions(+) create mode 100644 src/io/flutter/run/FlutterDebugProcessActions.java diff --git a/resources/META-INF/plugin.xml b/resources/META-INF/plugin.xml index 3b4fa93e5e..fa1d77778f 100644 --- a/resources/META-INF/plugin.xml +++ b/resources/META-INF/plugin.xml @@ -76,6 +76,9 @@ + + + diff --git a/src/io/flutter/run/FlutterDebugProcess.java b/src/io/flutter/run/FlutterDebugProcess.java index 574eab06f7..7935d7c8dd 100644 --- a/src/io/flutter/run/FlutterDebugProcess.java +++ b/src/io/flutter/run/FlutterDebugProcess.java @@ -111,6 +111,7 @@ public void registerAdditionalActions(@NotNull final DefaultActionGroup leftTool topToolbar.addAction(new RestartFlutterApp(app, canReload)); topToolbar.addSeparator(); topToolbar.addAction(new OpenDevToolsAction(app, debugUrlAvailable)); + FlutterDebugProcessActions.addTopToolbarExtensionActions(topToolbar); settings.addAction(new ReloadAllFlutterApps(app, canReload)); settings.addAction(new RestartAllFlutterApps(app, canReload)); diff --git a/src/io/flutter/run/FlutterDebugProcessActions.java b/src/io/flutter/run/FlutterDebugProcessActions.java new file mode 100644 index 0000000000..4373e38396 --- /dev/null +++ b/src/io/flutter/run/FlutterDebugProcessActions.java @@ -0,0 +1,44 @@ +/* + * Copyright 2026 The Chromium Authors. All rights reserved. + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ +package io.flutter.run; + +import com.intellij.openapi.actionSystem.ActionGroup; +import com.intellij.openapi.actionSystem.ActionManager; +import com.intellij.openapi.actionSystem.AnAction; +import com.intellij.openapi.actionSystem.DefaultActionGroup; +import org.jetbrains.annotations.NotNull; + +/** + * Shared action groups for Flutter-specific run and debug toolbars. + */ +public final class FlutterDebugProcessActions { + /** + * Third-party plugins can contribute inline toolbar actions with: + * {@code }. + */ + public static final @NotNull String TOP_TOOLBAR_EXTENSION_GROUP_ID = "Flutter.DebugProcess.TopToolbar"; + + private FlutterDebugProcessActions() { + } + + public static void addTopToolbarExtensionActions(@NotNull DefaultActionGroup topToolbar) { + final AnAction action = ActionManager.getInstance().getAction(TOP_TOOLBAR_EXTENSION_GROUP_ID); + if (!(action instanceof ActionGroup actionGroup) || isEmpty(actionGroup)) { + return; + } + + topToolbar.addSeparator(); + topToolbar.addAction(action); + } + + private static boolean isEmpty(@NotNull ActionGroup actionGroup) { + if (actionGroup instanceof DefaultActionGroup defaultActionGroup) { + return defaultActionGroup.getChildActionsOrStubs().length == 0; + } + + return actionGroup.getChildren(null).length == 0; + } +} diff --git a/src/io/flutter/run/bazelTest/BazelTestDebugProcess.java b/src/io/flutter/run/bazelTest/BazelTestDebugProcess.java index 0f5b8636d0..2965b7f95b 100644 --- a/src/io/flutter/run/bazelTest/BazelTestDebugProcess.java +++ b/src/io/flutter/run/bazelTest/BazelTestDebugProcess.java @@ -11,6 +11,7 @@ import com.intellij.xdebugger.XDebugSession; import com.jetbrains.lang.dart.util.DartUrlResolver; import io.flutter.ObservatoryConnector; +import io.flutter.run.FlutterDebugProcessActions; import io.flutter.run.FlutterPopFrameAction; import io.flutter.run.OpenDevToolsAction; import io.flutter.vmService.DartVmServiceDebugProcess; @@ -40,6 +41,7 @@ public void registerAdditionalActions(@NotNull DefaultActionGroup leftToolbar, topToolbar.addSeparator(); topToolbar.addAction(new FlutterPopFrameAction()); topToolbar.addAction(new OpenDevToolsAction(connector, this::isActive)); + FlutterDebugProcessActions.addTopToolbarExtensionActions(topToolbar); } private boolean isActive() { diff --git a/src/io/flutter/run/test/TestDebugProcess.java b/src/io/flutter/run/test/TestDebugProcess.java index 5edcf22765..8ee3d24104 100644 --- a/src/io/flutter/run/test/TestDebugProcess.java +++ b/src/io/flutter/run/test/TestDebugProcess.java @@ -11,6 +11,7 @@ import com.intellij.xdebugger.XDebugSession; import com.jetbrains.lang.dart.util.DartUrlResolver; import io.flutter.ObservatoryConnector; +import io.flutter.run.FlutterDebugProcessActions; import io.flutter.run.FlutterPopFrameAction; import io.flutter.run.OpenDevToolsAction; import io.flutter.vmService.DartVmServiceDebugProcess; @@ -40,6 +41,7 @@ public void registerAdditionalActions(@NotNull DefaultActionGroup leftToolbar, topToolbar.addSeparator(); topToolbar.addAction(new FlutterPopFrameAction()); topToolbar.addAction(new OpenDevToolsAction(connector, this::isActive)); + FlutterDebugProcessActions.addTopToolbarExtensionActions(topToolbar); } private boolean isActive() { From 37f712dca3ac5a5f6900eaa36057ae5be6188ab1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=A2=81=E5=85=B8=E5=85=B8?= Date: Fri, 15 May 2026 09:28:36 +0800 Subject: [PATCH 2/4] Clarify debug toolbar extension actions --- src/io/flutter/run/FlutterDebugProcessActions.java | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/src/io/flutter/run/FlutterDebugProcessActions.java b/src/io/flutter/run/FlutterDebugProcessActions.java index 4373e38396..898c0c0c2e 100644 --- a/src/io/flutter/run/FlutterDebugProcessActions.java +++ b/src/io/flutter/run/FlutterDebugProcessActions.java @@ -24,14 +24,21 @@ public final class FlutterDebugProcessActions { private FlutterDebugProcessActions() { } + /** + * Appends toolbar actions contributed by downstream dependent plugins. + * + *

{@link ActionManager#getAction(String)} returns {@link AnAction} because action groups are + * actions too. The extension id resolves to an inline {@link ActionGroup}, which can contain + * multiple contributed child actions. + */ public static void addTopToolbarExtensionActions(@NotNull DefaultActionGroup topToolbar) { - final AnAction action = ActionManager.getInstance().getAction(TOP_TOOLBAR_EXTENSION_GROUP_ID); - if (!(action instanceof ActionGroup actionGroup) || isEmpty(actionGroup)) { + final AnAction extensionGroupAction = ActionManager.getInstance().getAction(TOP_TOOLBAR_EXTENSION_GROUP_ID); + if (!(extensionGroupAction instanceof ActionGroup actionGroup) || isEmpty(actionGroup)) { return; } topToolbar.addSeparator(); - topToolbar.addAction(action); + topToolbar.addAction(extensionGroupAction); } private static boolean isEmpty(@NotNull ActionGroup actionGroup) { From b80ea1cad5e48deafb496e4294b2ddc768f167f4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=A2=81=E5=85=B8=E5=85=B8?= Date: Tue, 19 May 2026 09:28:55 +0800 Subject: [PATCH 3/4] Avoid manual ActionGroup expansion --- src/io/flutter/run/FlutterDebugProcessActions.java | 13 +++---------- 1 file changed, 3 insertions(+), 10 deletions(-) diff --git a/src/io/flutter/run/FlutterDebugProcessActions.java b/src/io/flutter/run/FlutterDebugProcessActions.java index 898c0c0c2e..0a988e9503 100644 --- a/src/io/flutter/run/FlutterDebugProcessActions.java +++ b/src/io/flutter/run/FlutterDebugProcessActions.java @@ -5,7 +5,6 @@ */ package io.flutter.run; -import com.intellij.openapi.actionSystem.ActionGroup; import com.intellij.openapi.actionSystem.ActionManager; import com.intellij.openapi.actionSystem.AnAction; import com.intellij.openapi.actionSystem.DefaultActionGroup; @@ -33,19 +32,13 @@ private FlutterDebugProcessActions() { */ public static void addTopToolbarExtensionActions(@NotNull DefaultActionGroup topToolbar) { final AnAction extensionGroupAction = ActionManager.getInstance().getAction(TOP_TOOLBAR_EXTENSION_GROUP_ID); - if (!(extensionGroupAction instanceof ActionGroup actionGroup) || isEmpty(actionGroup)) { + if (!(extensionGroupAction instanceof DefaultActionGroup extensionGroup) || + extensionGroup.getChildActionsOrStubs().length == 0) { return; } topToolbar.addSeparator(); - topToolbar.addAction(extensionGroupAction); + topToolbar.addAction(extensionGroup); } - private static boolean isEmpty(@NotNull ActionGroup actionGroup) { - if (actionGroup instanceof DefaultActionGroup defaultActionGroup) { - return defaultActionGroup.getChildActionsOrStubs().length == 0; - } - - return actionGroup.getChildren(null).length == 0; - } } From 27e62b1bd25ca5bd44b1ecc9fc4d2f35851634ee Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=A2=81=E5=85=B8=E5=85=B8?= Date: Wed, 20 May 2026 09:41:06 +0800 Subject: [PATCH 4/4] Add author entry --- AUTHORS | 1 + 1 file changed, 1 insertion(+) diff --git a/AUTHORS b/AUTHORS index f6c6cfd638..3aec5903db 100644 --- a/AUTHORS +++ b/AUTHORS @@ -30,3 +30,4 @@ Kazuya Chikamatsu Dustin Feucht Nico Mexis Luke Memet +Diandian Liang