Есть TreeView содержащий данные двух типов. Каждый тип данных имеет своё контекстное меню. К меню привязаны команды, но почему-то они не выполняются.
<Window
x:Class="WpfApplication4.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:WpfApplication4"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:my="clr-namespace:BaseNS"
Title="MainWindow"
Width="525"
Height="350"
mc:Ignorable="d">
<Window.Resources>
<ContextMenu x:Key="GroupScreenContextMenu">
<MenuItem Command="{Binding DeleteGroupCommand}" Header="Удалить Группу" />
</ContextMenu>
<ContextMenu x:Key="ScreenContextMenu" DataContext="{Binding}">
<MenuItem Command="{Binding DeleteScreenCommand}" Header="Удалить экран" />
</ContextMenu>
</Window.Resources>
<Grid>
<TreeView>
<TreeView.Resources>
<DataTemplate DataType="{x:Type my:ScreenModel}">
<StackPanel ContextMenu="{StaticResource ScreenContextMenu}">
<Label Background="Aqua" Content="{Binding Name}" />
</StackPanel>
</DataTemplate>
<HierarchicalDataTemplate DataType="{x:Type my:GroupModel}" ItemsSource="{Binding Items}">
<StackPanel ContextMenu="{StaticResource GroupScreenContextMenu}">
<Label Background="Green" Content="{Binding Name}" />
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.Resources>
<TreeViewItem ItemsSource="{Binding Screens}">
<TreeViewItem.Header>
<StackPanel>
<Label>Screens</Label>
</StackPanel>
</TreeViewItem.Header>
</TreeViewItem>
</TreeView>
</Grid>
public class GroupModel : TreeItemBase
{
}
public class ScreenModel : TreeItemBase
{
}
public class TreeItemBase : INotifyPropertyChanged
{
private string _Name;
public string Name
{
get { return _Name; }
set
{
_Name = value; OnPropertyChanged("Name");
}
}
private ObservableCollection<TreeItemBase> _items;
public ObservableCollection<TreeItemBase> Items
{
get { return _items; }
set { _items = value; OnPropertyChanged("Items"); }
}
public class Command : ICommand
{
private Action _action;
public Command(Action p_action)
{
_action = p_action;
}
public bool CanExecute(object parameter)
{
return true;
}
public event EventHandler CanExecuteChanged;
public void Execute(object parameter)
{
if (_action != null)
{
_action();
}
}
}
public event PropertyChangedEventHandler PropertyChanged;
public void OnPropertyChanged([CallerMemberName]string prop = "")
{
if (PropertyChanged != null)
PropertyChanged(this, new PropertyChangedEventArgs(prop));
}
}
public partial class MainWindow : Window, INotifyPropertyChanged
{
private ObservableCollection<TreeItemBase> _screens;
public ObservableCollection<TreeItemBase> Screens
{
get { return _screens; }
set
{
_screens = value; OnPropertyChanged("Screens");
}
}
ICommand DeleteGroupCommand;
ICommand DeleteScreenCommand;
private void DeleteGroup()
{
Screens.RemoveAt(0);
}
private void DeleteScreen()
{
Screens.RemoveAt(3);
}
public event PropertyChangedEventHandler PropertyChanged;
public void OnPropertyChanged([CallerMemberName]string prop = "")
{
if (PropertyChanged != null)
PropertyChanged(this, new PropertyChangedEventArgs(prop));
}
public MainWindow()
{
InitializeComponent();
ScreenModel screen = new ScreenModel() { Name = "screen" };
Screens = new ObservableCollection<TreeItemBase>();
Screens.Add(screen);
GroupModel screen1 = new GroupModel() { Name = "fld1", Items = new ObservableCollection<TreeItemBase>() { new ScreenModel() { Name = "IP-54" }, new ScreenModel() { Name = "IP-86" } } };
Screens.Add(screen1);
GroupModel screen11 = new GroupModel() { Name = "fld2", Items = new ObservableCollection<TreeItemBase>() { new ScreenModel() { Name = "IP-10" }, new ScreenModel() { Name = "IP-38" } } };
Screens.Add(screen11);
GroupModel screen111 = new GroupModel() { Name = "fld3", Items = new ObservableCollection<TreeItemBase>() { new ScreenModel() { Name = "IP-92" }, new ScreenModel() { Name = "IP-99" }, new GroupModel() { Name = "fld6", Items = new ObservableCollection<TreeItemBase>() { new ScreenModel() { Name = "IP-55" } } } } };
Screens.Add(screen111);
DeleteScreenCommand = new Command(DeleteScreen);
DeleteGroupCommand = new Command(DeleteGroup);
this.DataContext = this;
}
}
Несколько часов пытался заставить это работать, но ничего не получилось.
Получилось, но пришлось выкручиваться задавая DataContext через Свойство Tag. Шаблоны изменил так:
<DataTemplate DataType="{x:Type my:ScreenModel}">
<StackPanel ContextMenu="{StaticResource ScreenContextMenu}" Tag="{Binding RelativeSource={RelativeSource Mode=FindAncestor,AncestorType={x:Type Window}}}">
<Label Background="Aqua" Content="{Binding Name}" />
</StackPanel>
</DataTemplate>
<HierarchicalDataTemplate DataType="{x:Type my:GroupModel}" ItemsSource="{Binding Items}" >
<StackPanel ContextMenu="{StaticResource GroupScreenContextMenu}" Tag="{Binding RelativeSource={RelativeSource Mode=FindAncestor,AncestorType={x:Type Window}}}">
<Label Background="Green" Content="{Binding Name}" />
</StackPanel>
</HierarchicalDataTemplate>
Сами меню так:
<ContextMenu x:Key="GroupScreenContextMenu" DataContext="{Binding RelativeSource={RelativeSource Self}, Path=PlacementTarget.Tag}">
<MenuItem Command="{Binding DeleteGroupCommand}" Header="Удалить Группу"/>
</ContextMenu>
<ContextMenu x:Key="ScreenContextMenu" DataContext="{Binding RelativeSource={RelativeSource Self}, Path=PlacementTarget.Tag}">
<MenuItem Command="{Binding DeleteScreenCommand}" Header="Удалить экран" />
</ContextMenu>
Кофе для программистов: как напиток влияет на продуктивность кодеров?
Рекламные вывески: как привлечь внимание и увеличить продажи
Стратегії та тренди в SMM - Технології, що формують майбутнє сьогодні
Выделенный сервер, что это, для чего нужен и какие характеристики важны?
Современные решения для бизнеса: как облачные и виртуальные технологии меняют рынок
Как в данную строку вместо f4 - на место 4 подставить переменную в которую будет попадать нужное количество знаков
Когда пытаюсь подключиться к базе данных - выводит ошибкуКогда я подключаюсь к базе данных из моего компьютера - все нормально, а когда к базе...
Проект AspNet MVC, который работает с базой данных MySQl с помощью EF 6
ЗдравствуйтеНашел на NuGet бета-версию библиотеки для kinopoisk