diff --git a/src/Avalonia.Controls/MenuItem.cs b/src/Avalonia.Controls/MenuItem.cs index 03a43b5164..055d49fb0b 100644 --- a/src/Avalonia.Controls/MenuItem.cs +++ b/src/Avalonia.Controls/MenuItem.cs @@ -99,13 +99,13 @@ namespace Avalonia.Controls SelectableMixin.Attach(IsSelectedProperty); CommandProperty.Changed.Subscribe(CommandChanged); FocusableProperty.OverrideDefaultValue(true); + HeaderProperty.Changed.AddClassHandler(x => x.HeaderChanged); IconProperty.Changed.AddClassHandler(x => x.IconChanged); IsSelectedProperty.Changed.AddClassHandler(x => x.IsSelectedChanged); ItemsPanelProperty.OverrideDefaultValue(DefaultPanel); ClickEvent.AddClassHandler(x => x.OnClick); SubmenuOpenedEvent.AddClassHandler(x => x.OnSubmenuOpened); IsSubMenuOpenProperty.Changed.AddClassHandler(x => x.SubMenuOpenChanged); - PseudoClass(HeaderProperty, x => x as string == "-", ":separator"); } public MenuItem() @@ -420,6 +420,24 @@ namespace Avalonia.Controls IsEnabled = Command == null || Command.CanExecute(CommandParameter); } + /// + /// Called when the property changes. + /// + /// The property change event. + private void HeaderChanged(AvaloniaPropertyChangedEventArgs e) + { + if (e.NewValue is string newValue && newValue == "-") + { + PseudoClasses.Add(":separator"); + Focusable = false; + } + else if (e.OldValue is string oldValue && oldValue == "-") + { + PseudoClasses.Remove(":separator"); + Focusable = true; + } + } + /// /// Called when the property changes. /// diff --git a/tests/Avalonia.Base.UnitTests/AvaloniaObjectTests_Binding.cs b/tests/Avalonia.Base.UnitTests/AvaloniaObjectTests_Binding.cs index 4638aa84a5..23984a7c8d 100644 --- a/tests/Avalonia.Base.UnitTests/AvaloniaObjectTests_Binding.cs +++ b/tests/Avalonia.Base.UnitTests/AvaloniaObjectTests_Binding.cs @@ -479,6 +479,18 @@ namespace Avalonia.Base.UnitTests Assert.False(source.SetterCalled); } + [Fact] + public void Disposing_Completed_Binding_Does_Not_Throw() + { + var target = new Class1(); + var source = new Subject(); + var subscription = target.Bind(Class1.FooProperty, source); + + source.OnCompleted(); + + subscription.Dispose(); + } + /// /// Returns an observable that returns a single value but does not complete. /// @@ -595,4 +607,4 @@ namespace Avalonia.Base.UnitTests public bool SetterCalled { get; private set; } } } -} \ No newline at end of file +} diff --git a/tests/Avalonia.Controls.UnitTests/MenuItemTests.cs b/tests/Avalonia.Controls.UnitTests/MenuItemTests.cs new file mode 100644 index 0000000000..e7352af23e --- /dev/null +++ b/tests/Avalonia.Controls.UnitTests/MenuItemTests.cs @@ -0,0 +1,26 @@ +using System; +using System.Collections.Generic; +using System.Text; +using Xunit; + +namespace Avalonia.Controls.UnitTests +{ + public class MenuItemTests + { + [Fact] + public void Header_Of_Minus_Should_Apply_Separator_Pseudoclass() + { + var target = new MenuItem { Header = "-" }; + + Assert.True(target.Classes.Contains(":separator")); + } + + [Fact] + public void Separator_Item_Should_Set_Focusable_False() + { + var target = new MenuItem { Header = "-" }; + + Assert.False(target.Focusable); + } + } +}