diff --git a/build/Versions.props b/build/Versions.props
index 6e71cb77d..82484d8df 100644
--- a/build/Versions.props
+++ b/build/Versions.props
@@ -1,6 +1,6 @@
12.1.1
- 6.1.3
+ 6.1.4
diff --git a/docs/controls/desktop/navigation/combo-box/changelog.md b/docs/controls/desktop/navigation/combo-box/changelog.md
index b72b85b9a..5aa94a96f 100644
--- a/docs/controls/desktop/navigation/combo-box/changelog.md
+++ b/docs/controls/desktop/navigation/combo-box/changelog.md
@@ -2,6 +2,11 @@
本文档记录 ComboBox 控件级设计、API、主题契约、Token 和实现结构的变化。它不替代仓库根目录 `CHANGELOG.md`,也不作为正式版本发布说明。
+## 2026-08-18
+
+- Behavior
+ - Keep keyboard input on a non-editable ComboBox when reopening its popup so consecutive `Down` and `Enter` selections continue to update the selected item.
+
## 2026-07-05
- Behavior
diff --git a/src/AtomUI.Desktop.Controls/ComboBox/ComboBox.cs b/src/AtomUI.Desktop.Controls/ComboBox/ComboBox.cs
index 193b66e2b..97b196125 100644
--- a/src/AtomUI.Desktop.Controls/ComboBox/ComboBox.cs
+++ b/src/AtomUI.Desktop.Controls/ComboBox/ComboBox.cs
@@ -910,7 +910,16 @@ public class ComboBox : AvaloniaComboBox,
private void HandlePopupOpened(object? sender, EventArgs e)
{
RefreshFilteredItemVisibility();
- FocusEditableTextBox(NavigationMethod.Unspecified);
+
+ if (IsEditable)
+ {
+ FocusEditableTextBox(NavigationMethod.Unspecified);
+ }
+ else if (TopLevel.GetTopLevel(this)?.FocusManager.GetFocusedElement() is Visual focusedVisual &&
+ _popup?.IsInsidePopup(focusedVisual) == true)
+ {
+ Focus(NavigationMethod.Unspecified);
+ }
}
private void HandleEditableTextBoxTextInput(TextInputEventArgs e)
diff --git a/tests/AtomUI.Desktop.Controls.Tests/ComboBox/ComboBoxKeyboardNavigationTests.cs b/tests/AtomUI.Desktop.Controls.Tests/ComboBox/ComboBoxKeyboardNavigationTests.cs
new file mode 100644
index 000000000..80f86be4b
--- /dev/null
+++ b/tests/AtomUI.Desktop.Controls.Tests/ComboBox/ComboBoxKeyboardNavigationTests.cs
@@ -0,0 +1,128 @@
+using System.Reflection;
+using AtomUI.Controls;
+using AtomUI.Controls.Primitives;
+using Avalonia;
+using Avalonia.Controls;
+using Avalonia.Controls.Primitives;
+using Avalonia.Headless;
+using Avalonia.Input;
+using Avalonia.Threading;
+using Shouldly;
+using Xunit;
+using AvaloniaWindow = Avalonia.Controls.Window;
+using AtomUIComboBox = AtomUI.Desktop.Controls.ComboBox;
+
+namespace AtomUI.Desktop.Controls.Tests.ComboBox;
+
+public class ComboBoxKeyboardNavigationTests
+{
+ static ComboBoxKeyboardNavigationTests()
+ {
+ AvaloniaTestApp.EnsureInitialized();
+ }
+
+ [Fact]
+ public void NonEditable_ComboBox_Allows_Consecutive_Keyboard_Selections()
+ {
+ var comboBox = new AtomUIComboBox
+ {
+ Width = 240,
+ ItemsSource = new[] { "Alpha", "Beta", "Gamma" },
+ IsMotionEnabled = false
+ };
+
+ ShowInWindow(comboBox, window =>
+ {
+ comboBox.Focus(NavigationMethod.Tab).ShouldBeTrue();
+ Dispatcher.UIThread.RunJobs();
+
+ SelectNextItem(window, comboBox, 0);
+
+ comboBox.Focus(NavigationMethod.Tab).ShouldBeTrue();
+ comboBox.IsDropDownOpen = true;
+ Dispatcher.UIThread.RunJobs();
+
+ TopLevel.GetTopLevel(comboBox)?.FocusManager.GetFocusedElement()
+ .ShouldBeSameAs(comboBox);
+
+ PressKey(window, Key.Down, PhysicalKey.ArrowDown);
+ Dispatcher.UIThread.RunJobs();
+ PressKey(window, Key.Enter, PhysicalKey.Enter);
+ Dispatcher.UIThread.RunJobs();
+
+ comboBox.SelectedIndex.ShouldBe(1);
+ comboBox.IsDropDownOpen.ShouldBeFalse();
+ });
+ }
+
+ private static void SelectNextItem(AvaloniaWindow window, AtomUIComboBox comboBox, int expectedIndex)
+ {
+ comboBox.IsDropDownOpen = true;
+ Dispatcher.UIThread.RunJobs();
+
+ PressKey(window, Key.Down, PhysicalKey.ArrowDown);
+ Dispatcher.UIThread.RunJobs();
+ PressKey(window, Key.Enter, PhysicalKey.Enter);
+ Dispatcher.UIThread.RunJobs();
+
+ comboBox.SelectedIndex.ShouldBe(expectedIndex);
+ comboBox.IsDropDownOpen.ShouldBeFalse();
+ }
+
+ private static void PressKey(AvaloniaWindow window, Key key, PhysicalKey physicalKey)
+ {
+ window.KeyPress(key, RawInputModifiers.None, physicalKey, null);
+ }
+
+ private static void ShowInWindow(Control content, Action assertion)
+ {
+ var window = new AvaloniaWindow
+ {
+ Width = 360,
+ Height = 220,
+ Content = CreatePopupOverlayHost(content)
+ };
+
+ try
+ {
+ window.Show();
+ Dispatcher.UIThread.RunJobs();
+ content.ApplyTemplate();
+ content.Measure(Size.Infinity);
+ content.Arrange(new Rect(content.DesiredSize));
+ Dispatcher.UIThread.RunJobs();
+ assertion(window);
+ }
+ finally
+ {
+ window.Close();
+ }
+ }
+
+ private static VisualLayerManager CreatePopupOverlayHost(Control content)
+ {
+ var overlayPanel = new ScopeAwareOverlayLayerPanel
+ {
+ Width = 360,
+ Height = 220
+ };
+ overlayPanel.Children.Add(content);
+
+ var visualLayerManager = new VisualLayerManager
+ {
+ Child = overlayPanel
+ };
+ EnablePopupOverlayLayer(visualLayerManager);
+ return visualLayerManager;
+ }
+
+ private static void EnablePopupOverlayLayer(VisualLayerManager visualLayerManager)
+ {
+ var property = typeof(VisualLayerManager).GetProperty(
+ "EnablePopupOverlayLayer",
+ BindingFlags.Instance | BindingFlags.NonPublic);
+
+ property.ShouldNotBeNull();
+ property.SetValue(visualLayerManager, true);
+ }
+}