Struggling to template a WPF MenuItem's Icon with control - c#

Following on from a previous question here, I'm struggling to style a MenuItem's Icon with a control I have that inserts icon images based upon a string dependency property.
Initially I started with:
<ContextMenu ItemsSource="{Binding MenuItems}">
<ContextMenu.Resources>
<Style TargetType="MenuItem">
...
<Setter Property="Icon">
<local:StringToIcon IconName="{Binding IconName}" />
</Setter>
</Style>
</ContextMenu.Resources>
</ContextMenu>
This had the predictable effect of only displaying one of the icons in the menu, usually the last one, as the instance was shared around.
I then tried the non-shared resource approach:
<ContextMenu ItemsSource="{Binding MenuItems}">
<ContextMenu.Resources>
<local:StringToIcon x:Key="MenuIcon" x:Shared="False" IconName="{Binding IconName}" />
<Style TargetType="MenuItem">
...
<Setter Property="Icon" Value="{StaticResource MenuIcon} />
</Style>
</ContextMenu.Resources>
</ContextMenu>
This had no effect. It didn't offer me x:Shared in Intellisense, so I wonder if that's an invalid property here.
Out of desperation, I threw the thing into a template:
<Setter Property="Icon">
<Setter.Value>
<ContentControl>
<ContentControl.Template>
<ControlTemplate>
<local:StringToIcon IconName="{Binding IconName}" />
</ControlTemplate>
</ContentControl.Template>
</ContentControl>
</Setter.Value>
</Setter>
Again, no effect. My StringToIcon looks like this at the moment, hard-coded with a single image to check the problem doesn't lie there. (Or does it?)
<UserControl x:Class="RAP.Admin3.Components.StringToIcon"
...
>
<Image DataContext="{Binding ElementName=StringIconControl}" Source="pack://application:,,,/Resources/Icons/lorry.png"/>
</UserControl>
How do I get this darn thing to template and allow multiple uses? It's probably something basic I'm overlooking.
I've looked at various similar questions, and most seem to have success with the non-shared resource method.
Edit: Let me add substantially more code as requested. I've come up with a minimal replication of the problem:
The context menu is part of a TreeView resource.
<UserControl x:Class="MyApp.ItemHierarchy"
...
Name="ItemHierarchyControl">
<Grid>
<TreeView ItemsSource="{Binding ElementName=ItemHierarchyControl, Path=Items}">
<TreeView.Resources>
<HierarchicalDataTemplate DataType="{x:Type local:HierarchyItem}" ItemsSource="{Binding Subitems}">
<StackPanel Orientation="Horizontal" Margin="0,1,4,1">
<TextBlock Text="My text" VerticalAlignment="Center" />
<StackPanel.ContextMenu>
<ContextMenu ItemsSource="{Binding MenuItems}">
<ContextMenu.Resources>
<local:StringToIcon x:Key="MenuIcon" x:Shared="False" IconName="{Binding IconName}" />
<Style TargetType="MenuItem">
<Setter Property="Header" Value="{Binding Path=Name}" />
<Setter Property="Icon" Value="{StaticResource MenuIcon}" />
</Style>
</ContextMenu.Resources>
</ContextMenu>
</StackPanel.ContextMenu>
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.Resources>
</TreeView>
</Grid>
</UserControl>
This is backed by a dependency property for the items.
public ObservableCollection<HierarchyItem> Items
{
get { return (ObservableCollection<HierarchyItem>)GetValue(ItemsProperty); }
set { SetValue(ItemsProperty, value); }
}
public static readonly DependencyProperty ItemsProperty = DependencyProperty.Register("Items", typeof(ObservableCollection<HierarchyItem>), typeof(ItemHierarchy), new PropertyMetadata(new ObservableCollection<HierarchyItem>()));
StringToIcon is also backed by a string dependency property for the icon name, which is summarily ignored because of the hard-coded image at the moment.
HierarchyItems are simple for the example:
public ObservableCollection<HierarchyItem> Subitems { get; set; }
public ObservableCollection<BindableMenuItem> MenuItems { get; set; }
Just to get this proof working, I attached the ItemHierarchy to some properties of the main window:
public ObservableCollection<BindableMenuItem> MenuItems { get; set; }
public ObservableCollection<HierarchyItem> IHItems { get; set; }
public MainWindow()
{
MenuItems = new ObservableCollection<BindableMenuItem>();
MenuItems.Add(new BindableMenuItem("Item", null));
MenuItems.Add(new BindableMenuItem("Item", null));
MenuItems.Add(new BindableMenuItem("Item", null));
MenuItems.Add(new BindableMenuItem("Item", null));
IHItems = new ObservableCollection<HierarchyItem>();
IHItems.Add(new HierarchyItem() { MenuItems = this.MenuItems });
InitializeComponent();
}
Edit 2: Here's BindableMenuItem also:
public class BindableMenuItem
{
public BindableMenuItem(string name, ICommand command)
{
this.Name = name;
this.Command = command;
}
public string Name { get; set; }
public ICommand Command { get; set; }
public string IconName { get; set; }
public ObservableCollection<BindableMenuItem> Children { get; set; }
}

Try to move the StringToIcon to <TreeView.Resources>:
<TreeView ItemsSource="{Binding ElementName=ItemHierarchyControl, Path=Items}">
<TreeView.Resources>
<local:StringToIcon x:Key="MenuIcon" x:Shared="False" IconName="{Binding IconName}" />
<HierarchicalDataTemplate DataType="{x:Type local:HierarchyItem}" ItemsSource="{Binding Subitems}">
<StackPanel Orientation="Horizontal" Margin="0,1,4,1">
<TextBlock Text="My text" VerticalAlignment="Center" />
<StackPanel.ContextMenu>
<ContextMenu ItemsSource="{Binding MenuItems}">
<ContextMenu.Resources>
<Style TargetType="MenuItem">
<Setter Property="Header" Value="{Binding Path=Name}" />
<Setter Property="Icon" Value="{StaticResource MenuIcon}" />
</Style>
</ContextMenu.Resources>
</ContextMenu>
</StackPanel.ContextMenu>
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.Resources>
</TreeView>

Related

RadioButtons in a ListView. SelectedItem not working [duplicate]

This question already has an answer here:
WPF ListView with group of RadioButtons and select default value
(1 answer)
Closed 4 months ago.
Have two properties in my viewmodel, INotifyPropertyChanged is implemented but not shown here. Both Properties are initiated in the constructor and values are set.
public ObservableCollection<Foo> Foos { get; init;}
public Foo SelectedFoo { get => _selectedFoo; set => _selectedFoo = value;}
the foo class:
public class Foo
{
public string NameOfFoo { get; set; }
public bool IsActive { get; set; }
}
in the corresponding View...
<ListView
ItemsSource="{Binding Foos}"
SelectedItem="{Binding SelectedFoo, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
Background="#FF063852"
BorderThickness="0">
<ListView.ItemTemplate>
<DataTemplate>
<RadioButton Content="{Binding NameOfFoo}"
GroupName="GroupSelector"
BorderThickness="0"
Style="{StaticResource RadioButtonStyle}"
IsChecked="{Binding IsActive}">
<i:Interaction.Triggers>
<i:EventTrigger EventName="Checked">
<i:InvokeCommandAction Command="{Binding Path=DataContext.SelectGroupCommand,
RelativeSource={RelativeSource AncestorType={x:Type UserControl}}}"
CommandParameter="{Binding}"/>
</i:EventTrigger>
</i:Interaction.Triggers>
</RadioButton>
</DataTemplate>
</ListView.ItemTemplate>
<ListView.ItemsPanel>
<ItemsPanelTemplate>
<StackPanel Orientation="Horizontal" Margin="5" />
</ItemsPanelTemplate>
</ListView.ItemsPanel>
<ListView.ItemContainerStyle>
<Style TargetType="{x:Type ListViewItem}">
<Setter Property="Background" Value="Transparent"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListViewItem}">
<ContentPresenter/>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</ListView.ItemContainerStyle>
</ListView>
ItemsSource of ListView is working fine.
The radioButton is not checked as expected after creating new instance from viewmodel.
The command for the event "checked" is ok.
The SETTER from the SelectedFoo propery is never called. Why??
What have I to do, to have the propper radiobutton checked in my view after creation?
Found a solution here: https://stackoverflow.com/a/24179089/14800168
Multibinding for IsChecked was the trick!

Data Binding to menu using multiple data types and being able to set the icon

Before you mark as duplicate, I have read the other SO entries, none seem to apply
I have two classes, one for menu item groups which will comprise my root menu items, and one for the sub items as such
public class RootItem
{
public string name {get;set;}
public image icon {get;set;}
public List<SubItem> subItems {get;set;}
}
public class SubItem
{
public string name {get;set;}
public image icon {get;set;}
}
The rest of what I am trying to do is probibly obvious but ill outline it anyway:
<MenuItem ItemsSource="{Binding Path=RootItems}" Header="Menu">
<MenuItem.Resources>
<DataTemplate DataType="{x:Type root:RootItem}">
<DataTemplate.Resources>
<Style TargetType="{x:Type MenuItem}">
<Setter Property="Header" Value="{Binding name}"/>
<Setter Property="ItemsSource" Value="{Binding subItems}"/>
<Setter Property="Icon" Value="{Binding icon}"/>
</Style>
</DataTemplate.Resources>
</DataTemplate>
<DataTemplate DataType="{x:Type root:SubItem}">
<DataTemplate.Resources>
<Style TargetType="{x:Type MenuItem}">
<Setter Property="Header" Value="{Binding name}"/>
<Setter Property="Icon" Value="{Binding icon}"/>
</Style>
</DataTemplate.Resources>
</DataTemplate>
</MenuItem.Resources>
</MenuItem>
This is just one of the methods I tried, in this one it doesn't seem like the style is used at all as only the root items show but they are blank, no icon or name.
I must be able to use 2 separate classes and the icon must be set-able and there must be 2 data templates or styles to handle/show the 2 classes differently.
I have also tried this, which while a mess, gets me 90% of the way, I just have issues where the icon is only visible on the last menu item.
<MenuItem ItemsSource="{Binding Path=RootItems}" Header="Menu">
<MenuItem.Resources>
<imico:InputMapperIcon x:Key="ico" Icon="{Binding icon}" x:Shared="false"/>
<HierarchicalDataTemplate DataType="{x:Type root:RootItem}" x:Shared="false" ItemsSource="{Binding subItems}">
<HierarchicalDataTemplate.ItemContainerStyle>
<Style>
<Setter Property="MenuItem.Header" Value="{Binding name}"/>
<Setter Property="MenuItem.Icon" Value="{StaticResource ico}"/>
<Setter Property="MenuItem.Tag" Value="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Menu}}, Path=DataContext}"/>
<EventSetter Event="MenuItem.Click" Handler="BtnAddCommand_Click"/>
</Style>
</HierarchicalDataTemplate.ItemContainerStyle>
</HierarchicalDataTemplate>
</MenuItem.Resources>
<MenuItem.ItemContainerStyle>
<Style>
<Setter Property="MenuItem.Header" Value="{Binding name}"/>
<Setter Property="MenuItem.Icon" Value="{StaticResource ico}"/>
</Style>
</MenuItem.ItemContainerStyle>
</MenuItem>
here is a working example, copied from your second xaml snippet:
.xaml
<Grid Background="Transparent">
<Grid.ContextMenu>
<ContextMenu>
<MenuItem ItemsSource="{Binding Path=RootItems}" Header="Menu">
<MenuItem.Resources>
<HierarchicalDataTemplate DataType="{x:Type root:RootItem}" x:Shared="false" ItemsSource="{Binding subItems}">
<HierarchicalDataTemplate.ItemContainerStyle>
<Style>
<Setter Property="MenuItem.Header" Value="{Binding name}"/>
<Setter Property="MenuItem.Icon" Value="{Binding icon}"/>
</Style>
</HierarchicalDataTemplate.ItemContainerStyle>
</HierarchicalDataTemplate>
</MenuItem.Resources>
<MenuItem.ItemContainerStyle>
<Style>
<Setter Property="MenuItem.Header" Value="{Binding name}"/>
<Setter Property="MenuItem.Icon" Value="{Binding icon}"/>
</Style>
</MenuItem.ItemContainerStyle>
</MenuItem>
</ContextMenu>
</Grid.ContextMenu>
</Grid>
.cs
public partial class MainWindow : Window
{
public ObservableCollection<RootItem> RootItems { get; set; }
public MainWindow()
{
InitializeComponent();
RootItems = new ObservableCollection<RootItem>();
var rootitem = new RootItem() { name = "rootitem" };
rootitem.subItems = new List<SubItem>();
var subitem = new SubItem() { name = "subitem" };
subitem.icon = new Image();
subitem.icon.Source = new BitmapImage(new Uri(#"C:\Users\username\source\repos\WpfApp3\WpfApp3\New Bitmap Image.bmp"));
var subitem2 = new SubItem() { name = "subitem2" };
subitem2.icon = new Image();
subitem2.icon.Source = new BitmapImage(new Uri(#"C:\Users\username\source\repos\WpfApp3\WpfApp3\New Bitmap Image.bmp"));
rootitem.subItems.Add(subitem);
rootitem.subItems.Add(subitem2);
RootItems.Add(rootitem);
this.DataContext = this;
}
}
public class RootItem
{
public string name { get; set; }
public Image icon { get; set; }
public List<SubItem> subItems { get; set; }
}
public class SubItem
{
public string name { get; set; }
public Image icon { get; set; }
}
so the mistake i imagine must be in how you assign image to your SubItem(which i removed in my example, i use a staticresource instead), or in your InputMapperIcon

Refresh DataGrid data on TreeViewItem selection change

I was able to implement Tree View using the link
Now I have attached the below Data Grid to it for displaying the city details like Area, Population, TimeZone etc.I was able to receive the event IsSelected upon selecting the City name from the treeview using example. But how do I bind the data of City model (Area, Population, TimeZone ) to a datagrid in the .xaml ? I tried using the CityViewModel directly but it never populates the data.CityViewModel has an observableCollection of "CityTown"( with props like Area, Population, TimeZone etc) property called "CityTowns" which I am populating when IsSelected is fired.My Tree View only has Region -> State -> City hierarchy. City towns should be displayed in grid not in tree.
//DemoWindow.xaml content:
<TabControl>
<TabItem Header="Load Towns">
<StackPanel Orientation="Horizontal">
<advanced: LoadOnDemandControl/>
<DataGrid ItemsSource="{Binding Path=local.CityViewModel.CityTowns}"
AutoGenerateColumns="False" IsReadOnly="True"
>
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding Path=Popluation}" Header="Popluation"/>
<DataGridTextColumn Binding="{Binding Path=Revenue}" Header="Revenue"/>
<DataGridTextColumn Binding="{Binding Path=TimeZone}" Header="TimeZone"/>
<DataGridTextColumn Binding="{Binding Path=Area}" Header="Area"/>
</DataGrid.Columns>
</DataGrid>
</StackPanel>
</TabItem>
</TabControl>
//LoadOnDemandCcontrol.xaml:
<TreeView ItemsSource="{Binding Regions}">
<TreeView.ItemContainerStyle>
<!--
This Style binds a TreeViewItem to a TreeViewItemViewModel.
-->
<Style TargetType="{x:Type TreeViewItem}">
<Setter Property="IsExpanded" Value="{Binding IsExpanded, Mode=TwoWay}" />
<Setter Property="IsSelected" Value="{Binding IsSelected, Mode=TwoWay}" />
<Setter Property="FontWeight" Value="Normal" />
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="FontWeight" Value="Bold" />
</Trigger>
</Style.Triggers>
</Style>
</TreeView.ItemContainerStyle>
<TreeView.Resources>
<HierarchicalDataTemplate
DataType="{x:Type local:RegionViewModel}"
ItemsSource="{Binding Children}"
>
<StackPanel Orientation="Horizontal">
<Image Width="16" Height="16" Margin="3,0" Source="Images\Region.png" />
<TextBlock Text="{Binding RegionName}" />
</StackPanel>
</HierarchicalDataTemplate>
<HierarchicalDataTemplate
DataType="{x:Type local:StateViewModel}"
ItemsSource="{Binding Children}"
>
<StackPanel Orientation="Horizontal">
<Image Width="16" Height="16" Margin="3,0" Source="Images\State.png" />
<TextBlock Text="{Binding StateName}" />
</StackPanel>
</HierarchicalDataTemplate>
<DataTemplate DataType="{x:Type local:CityViewModel}">
<StackPanel Orientation="Horizontal">
<Image Width="16" Height="16" Margin="3,0" Source="Images\City.png" />
<TextBlock Text="{Binding CityName}" />
</StackPanel>
</DataTemplate>
</TreeView.Resources>
</TreeView>
//CityTown.cs content:
public class CityTown
{
public int Area { get; set; }
public int Population { get; set; }
public string TimeZone { get; set; }
public int Revenue { get; set; }
public virtual City City { get; set; }
}
//CityViewModel.cs cocntent
public class CityViewModel : TreeViewItemViewModel
{
readonly City _city;
public CityViewModel(City city, StateViewModel parentState)
: base(parentState, false)
{
_city = city;
}
public string CityName
{
get { return _city.CityName; }
}
private ObservableCollection<CityTown> _CityTowns;
public ObservableCollection<CityTown> CityTowns
{
get { return Database.GetTowns(CityName); }
set { _CityTowns = value; }
}
}
//LoadOnDemandDemoControl.xaml.cs content:
public partial class LoadOnDemandDemoControl : UserControl
{
public LoadOnDemandDemoControl()
{
InitializeComponent();
Region[] regions = Database.GetRegions();
CountryViewModel viewModel = new CountryViewModel(regions);
base.DataContext = viewModel;
}
}
I solved it by defining the SelectedValuePath property for TreeView xaml element class and used the same in DataGrid element -> ItemsSoruce property -> Path -> SelectedItem.ViewModelDataCollection.

Why does my context menu look different when generated dynamically

I am trying to dynamically bind context menus from my base view model. I've managed to functionally do what i'd like to do, but I'm stuck with how my dynamic context menu looks compared to my static one. There seems to be an extra level of menu items. My View Model looks like this.
public ObservableCollection<ContextMenuItem> ContextMenuItems { get; protected set; }
protected Constructor
{
ContextMenuItems = new ObservableCollection<ContextMenuItem>()
{
new ContextMenuItem() {Caption = "Add/Replace Supporting Data", Command = AddReplaceSupportingCommand},
new ContextMenuItem() {Caption = "Display SupportingData", Command = DisplaySupportingDataCommand}
};
}
the xaml for the 1st context menu us generated like this.
<StackPanel Orientation="Vertical" Margin="0,20">
<StackPanel.ContextMenu >
<ContextMenu ItemsSource="{Binding ContextMenuItems}">
<ContextMenu.ItemTemplate>
<DataTemplate>
<MenuItem Command="{Binding Command}" Header="{Binding Caption}"/>
</DataTemplate>
</ContextMenu.ItemTemplate>
</ContextMenu>
</StackPanel.ContextMenu>
...
</StackPanel>
The xaml for the second context menu looks like this
<StackPanel >
<StackPanel.ContextMenu>
<ContextMenu>
<MenuItem Command="{Binding AddReplaceSupportingCommand}" Header="Add or Replace Supporting Data"/>
<MenuItem Command="{Binding DisplaySupportingDataCommand}" Header="Display Supporting Data"/>
</ContextMenu>
</StackPanel.ContextMenu>
...
</StackPanel>
(for completeness, here's the ContextMenuItem class)
public class ContextMenuItem : ReactiveObject
{
private string _Caption;
public string Caption
{
get { return _Caption; }
set { this.RaiseAndSetIfChanged(ref _Caption, value); }
}
public ReactiveCommand Command { get; set; }
}
It looks different because ContextMenu, MenuBase to be specific, uses MenuItem as ItemContainerStyle so you're effectively wrapping MenuItem within MenuItem. Try this instead:
<StackPanel Orientation="Vertical" Margin="0,20">
<StackPanel.ContextMenu>
<ContextMenu ItemsSource="{Binding ContextMenuItems}">
<ContextMenu.ItemContainerStyle>
<Style TargetType="{x:Type MenuItem}">
<Setter Property="Header" Value="{Binding Caption}"/>
<Setter Property="Command" Value="{Binding Command}"/>
</Style>
</ContextMenu.ItemContainerStyle>
</ContextMenu>
</StackPanel.ContextMenu>
<!-- ... -->
</StackPanel>
you can use ItemTemplate if you want but use something like TextBox instead
<StackPanel Orientation="Vertical" Margin="0,20">
<StackPanel.ContextMenu >
<ContextMenu ItemsSource="{Binding ContextMenuItems}">
<ContextMenu.ItemContainerStyle>
<Style TargetType="{x:Type MenuItem}">
<Setter Property="Command" Value="{Binding Command}"/>
</Style>
</ContextMenu.ItemContainerStyle>
<ContextMenu.ItemTemplate>
<DataTemplate>
<TextBlock Text="{Binding Caption}"/>
</DataTemplate>
</ContextMenu.ItemTemplate>
</ContextMenu>
</StackPanel.ContextMenu>
<!-- ... -->
</StackPanel>

Bind to index in ItemsControl from DataTemplate

I have a simple class which creates a list of objects:
namespace TestWPF2
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
public ObservableCollection<TestObj> SomeList { get; set; }
public string WindowTitle { get; set; }
public MainWindow()
{
this.DataContext = this;
WindowTitle = "People";
SomeList = new ObservableCollection<TestObj>();
SomeList.Add(new TestObj("Bob"));
SomeList.Add(new TestObj("Jane"));
SomeList.Add(new TestObj("Mike"));
InitializeComponent();
}
}
}
The TestObj class is as follows:
namespace TestWPF2
{
public class TestObj
{
public string FirstName { get; set; }
public TestObj(string firstName)
{
this.FirstName = firstName;
}
}
}
I then attempt to display each item in the list with the following:
<Window x:Class="TestWPF2.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:TestWPF2"
Title="MainWindow" Height="350" Width="525">
<Window.Resources>
<DataTemplate DataType="{x:Type local:TestObj}">
<StackPanel Orientation="Vertical">
<StackPanel Orientation="Horizontal">
<TextBlock Text="Pos: "/>
<TextBlock x:Name="posText"/>
</StackPanel>
<StackPanel Orientation="Horizontal">
<TextBlock Text="Name: "/>
<TextBlock Text="{Binding FirstName}"/>
</StackPanel>
</StackPanel>
<!-- THESE TRIGGERS DONT WORK -->
<DataTemplate.Triggers>
<Trigger Property="ItemsControl.AlternationIndex" Value="0">
<Setter Property="Text" Value="First" TargetName="posText"/>
</Trigger>
<Trigger Property="ItemsControl.AlternationIndex" Value="1">
<Setter Property="Text" Value="Second" TargetName="posText"/>
</Trigger>
<Trigger Property="ItemsControl.AlternationIndex" Value="3">
<Setter Property="Text" Value="Third" TargetName="posText"/>
</Trigger>
</DataTemplate.Triggers>
</DataTemplate>
</Window.Resources>
<StackPanel>
<TextBlock Text="{Binding Title}"/>
<ItemsControl HorizontalAlignment="Stretch"
ItemsSource="{Binding SomeList}">
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<StackPanel Orientation="Vertical" />
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
</ItemsControl>
</StackPanel>
</Window>
What I would like to display is something like:
Pos: First
Name: Bob
Pos: Second
Name: Jane
etc.
It's pretty straight-forward to bind to the FirstName property of each item in the list, but I would also like bind to the index in the list. I know I can do this from inside an ItemsControl using ItemsControl.AlternationIndex, but how do I link to the AlternationIndex from within in DataTemplate?
You need to understand that your context is TestObj and with your trigger, you are basicly checking the value of a property named ItemsControl which should have a property AlternationIndex.
You should changed the context of your triggers with a RelativeSource binding to the control that hold your object, named the ContentPresenter:
<DataTemplate.Triggers>
<DataTrigger Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type ContentPresenter}}, Path=(ItemsControl.AlternationIndex)" Value="0">
<Setter Property="Text" Value="First" TargetName="posText"/>
</Trigger>
<!--- here be the other triggers -->
</DataTemplate.Triggers>
Hope this helps..

Categories