Reputation: 61
I'm trying to create something like expandable button - button with context menu above, which will open by left mouse button click. Only thing I still can't finishing up is items property, which could be setting up in WPF XAML designer like for ContextMenu
control. So, as far as I can understand, that means I need to use ItemCollection
type for my property. Ok. Let's take a look on my component:
public partial class MenuButton : Button
{
private readonly ContextMenu Menu;
public static readonly DependencyProperty MenuItemsProperty =
DependencyProperty.Register("MenuItems", typeof(ItemCollection), typeof(ContextMenu), new PropertyMetadata(default(ItemCollection), new PropertyChangedCallback(OnSomeMenuItemsPropertyChanged)));
public ItemCollection MenuItems
{
get => (ItemCollection)GetValue(MenuItemsProperty);
set => SetValue(MenuItemsProperty, value);
}
public MenuButton()
{
MenuItems = new DataGrid().Items; // I really need to do it - otherwise I'll get an error
Menu = new ContextMenu
{
HasDropShadow = false,
PlacementTarget = this,
Placement = PlacementMode.Top,
};
InitializeComponent();
}
protected override void OnMouseLeftButtonDown(MouseButtonEventArgs e)
{
base.OnMouseLeftButtonDown(e);
Menu.Width = ActualWidth;
Menu.IsOpen = true;
}
private static void OnSomeMenuItemsPropertyChanged(DependencyObject target, DependencyPropertyChangedEventArgs e)
{
if (target is ContextMenu menu)
{
menu.ItemsSource = (ItemCollection)e.NewValue;
}
}
}
But I can't 'catch' the OnSomeMenuItemsPropertyChanged
- breakpoint does not work here. So, that means this mechanism is wrong.
How can I fix that? Should I use OnItemsChanged
and OnItemsCollectionChanged
events instead (like for ObservableCollection
) to handle the changes of the property? Or maybe something else?
Upvotes: -1
Views: 498
Reputation: 61
So, finally I found the solution. I don't claim that this is the best practice, but maybe it will be useful for someone:
public partial class MenuButton : Button
{
private readonly ContextMenu Menu;
public static readonly DependencyProperty MenuItemsProperty =
DependencyProperty.Register("MenuItems", typeof(ItemCollection), typeof(MenuButton), new PropertyMetadata(default(ItemCollection), new PropertyChangedCallback(OnSomeMenuItemsPropertyChanged)));
public ItemCollection MenuItems
{
get => (ItemCollection)GetValue(MenuItemsProperty);
set => SetValue(MenuItemsProperty, value);
}
public MenuButton()
{
Menu = new ContextMenu
{
HasDropShadow = false,
PlacementTarget = this,
Placement = PlacementMode.Top,
};
MenuItems = new DataGrid().Items;
InitializeComponent();
}
protected override void OnMouseLeftButtonDown(MouseButtonEventArgs e)
{
base.OnMouseLeftButtonDown(e);
Menu.Width = ActualWidth;
Menu.IsOpen = true;
}
private static void OnSomeMenuItemsPropertyChanged(DependencyObject target, DependencyPropertyChangedEventArgs e)
{
var menuButton = target as MenuButton;
menuButton.Menu.ItemsSource = (ItemCollection)e.NewValue;
}
}
Upvotes: 0