By default implementing a ExpanderView in an application the UI renders and the expanderView control has this left margin applied to it, some sort of indentation. It's rather stupid really that it's like that by default.
Is there some way to get rid of that margin and just that the control float completely to the left?
Also, how does one add some text to the expanders rectangle? No such property available.
You just need to edit the Control Template for the Expander. If you have Expression Blend it makes it quick and easy. You would just right-click your Expander on the artboard, choose "Edit Template" and then choose to either edit the current one, or a copy you could make and maybe put in a separate resource dictionary. Here's an example template. Notice the 11,0,0,0 Margin on the itemsCanvas towards the bottom? You can use this same method for editing just about any controls template. :)
<Style x:Key="ExpanderViewStyle1" TargetType="toolkit:ExpanderView">
<Setter Property="HorizontalAlignment" Value="Stretch"/>
<Setter Property="HorizontalContentAlignment" Value="Stretch"/>
<Setter Property="ItemsPanel">
<Setter.Value>
<ItemsPanelTemplate>
<StackPanel/>
</ItemsPanelTemplate>
</Setter.Value>
</Setter>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="toolkit:ExpanderView">
<Grid>
<Grid.Resources>
<QuadraticEase x:Key="QuadraticEaseOut" EasingMode="EaseOut"/>
<QuadraticEase x:Key="QuadraticEaseInOut" EasingMode="EaseInOut"/>
</Grid.Resources>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="41"/>
<ColumnDefinition Width="*"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="ExpansionStates">
<VisualStateGroup.Transitions>
<VisualTransition From="Collapsed" GeneratedDuration="0:0:0.15" To="Expanded">
<Storyboard>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(FrameworkElement.Height)" Storyboard.TargetName="ItemsCanvas">
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseOut}" KeyTime="0:0:0.00" Value="0"/>
<EasingDoubleKeyFrame x:Name="CollapsedToExpandedKeyFrame" EasingFunction="{StaticResource QuadraticEaseOut}" KeyTime="0:0:0.15" Value="1"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimation Duration="0" To="1.0" Storyboard.TargetProperty="(UIElement.Opacity)" Storyboard.TargetName="ItemsCanvas"/>
</Storyboard>
</VisualTransition>
<VisualTransition From="Expanded" GeneratedDuration="0:0:0.15" To="Collapsed">
<Storyboard>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(FrameworkElement.Height)" Storyboard.TargetName="ItemsCanvas">
<EasingDoubleKeyFrame x:Name="ExpandedToCollapsedKeyFrame" EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.00" Value="1"/>
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.15" Value="0"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Opacity)" Storyboard.TargetName="ItemsCanvas">
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.00" Value="1.0"/>
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.15" Value="0.0"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.TranslateY)" Storyboard.TargetName="ItemsCanvas">
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.00" Value="0.0"/>
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.15" Value="-35"/>
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</VisualTransition>
</VisualStateGroup.Transitions>
<VisualState x:Name="Collapsed"/>
<VisualState x:Name="Expanded">
<Storyboard>
<DoubleAnimation Duration="0" Storyboard.TargetProperty="(FrameworkElement.Height)" Storyboard.TargetName="ItemsCanvas"/>
<DoubleAnimation Duration="0" To="1.0" Storyboard.TargetProperty="(UIElement.Opacity)" Storyboard.TargetName="ItemsCanvas"/>
</Storyboard>
</VisualState>
</VisualStateGroup>
<VisualStateGroup x:Name="ExpandabilityStates">
<VisualState x:Name="Expandable"/>
<VisualState x:Name="NonExpandable">
<Storyboard>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Visibility)" Storyboard.TargetName="ExpandableContent">
<DiscreteObjectKeyFrame KeyTime="0:0:0.0" Value="Collapsed"/>
</ObjectAnimationUsingKeyFrames>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Visibility)" Storyboard.TargetName="Line">
<DiscreteObjectKeyFrame KeyTime="0:0:0.0" Value="Collapsed"/>
</ObjectAnimationUsingKeyFrames>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Visibility)" Storyboard.TargetName="NonExpandableContent">
<DiscreteObjectKeyFrame KeyTime="0:0:0.0" Value="Visible"/>
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<ListBoxItem x:Name="ExpandableContent" Grid.ColumnSpan="2" Grid.Column="0" toolkit:TiltEffect.IsTiltEnabled="True" Grid.Row="0" Grid.RowSpan="2">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="41"/>
<ColumnDefinition Width="*"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<ContentControl x:Name="Header" Grid.ColumnSpan="2" ContentTemplate="{TemplateBinding HeaderTemplate}" Content="{TemplateBinding Header}" Grid.Column="0" HorizontalAlignment="Stretch" HorizontalContentAlignment="Stretch" Grid.Row="0"/>
<ContentControl x:Name="Expander" ContentTemplate="{TemplateBinding ExpanderTemplate}" Content="{TemplateBinding Expander}" Grid.Column="1" HorizontalAlignment="Stretch" HorizontalContentAlignment="Stretch" Margin="11,0,0,0" Grid.Row="1"/>
<Grid x:Name="ExpanderPanel" Background="Transparent" Grid.ColumnSpan="2" Grid.Column="0" Grid.Row="0" Grid.RowSpan="2"/>
</Grid>
</ListBoxItem>
<Line x:Name="Line" Grid.Column="1" HorizontalAlignment="Left" Grid.Row="1" Grid.RowSpan="2" Stretch="Fill" Stroke="{StaticResource PhoneSubtleBrush}" StrokeThickness="3" X1="0" X2="0" Y1="0" Y2="1"/>
<ContentControl x:Name="NonExpandableContent" Grid.ColumnSpan="2" ContentTemplate="{TemplateBinding NonExpandableHeaderTemplate}" Content="{TemplateBinding NonExpandableHeader}" Grid.Column="0" HorizontalAlignment="Stretch" HorizontalContentAlignment="Stretch" Grid.Row="0" Grid.RowSpan="2" Visibility="Collapsed"/>
<Canvas x:Name="ItemsCanvas" Grid.Column="1" Margin="11,0,0,0" Opacity="0.0" Grid.Row="2">
<Canvas.RenderTransform>
<CompositeTransform TranslateY="0.0"/>
</Canvas.RenderTransform>
<ItemsPresenter x:Name="Presenter"/>
</Canvas>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
Either way, once you find the control template its quick and painless. Hope this helps!
It's late but maybe it will help somebody. I remove that margin in this style. I deleted columns from default grid. Moreover I create it as Wrap panel. It can be modified in ItemsPanelTemplate.
<Style x:Key="ExpanderViewStyle" TargetType="toolkit:ExpanderView">
<Setter Property="HorizontalAlignment" Value="Stretch"/>
<Setter Property="HorizontalContentAlignment" Value="Stretch"/>
<Setter Property="ItemsPanel">
<Setter.Value>
<ItemsPanelTemplate>
<toolkit:WrapPanel/>
</ItemsPanelTemplate>
</Setter.Value>
</Setter>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="toolkit:ExpanderView">
<Grid>
<Grid.Resources>
<QuadraticEase x:Key="QuadraticEaseOut" EasingMode="EaseOut"/>
<QuadraticEase x:Key="QuadraticEaseInOut" EasingMode="EaseInOut"/>
</Grid.Resources>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="ExpansionStates">
<VisualStateGroup.Transitions>
<VisualTransition From="Collapsed" GeneratedDuration="0:0:0.15" To="Expanded">
<Storyboard>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(FrameworkElement.Height)" Storyboard.TargetName="ItemsCanvas">
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseOut}" KeyTime="0:0:0.00" Value="0"/>
<EasingDoubleKeyFrame x:Name="CollapsedToExpandedKeyFrame" EasingFunction="{StaticResource QuadraticEaseOut}" KeyTime="0:0:0.15" Value="1"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimation Duration="0" To="1.0" Storyboard.TargetProperty="(UIElement.Opacity)" Storyboard.TargetName="ItemsCanvas"/>
</Storyboard>
</VisualTransition>
<VisualTransition From="Expanded" GeneratedDuration="0:0:0.15" To="Collapsed">
<Storyboard>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(FrameworkElement.Height)" Storyboard.TargetName="ItemsCanvas">
<EasingDoubleKeyFrame x:Name="ExpandedToCollapsedKeyFrame" EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.00" Value="1"/>
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.15" Value="0"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Opacity)" Storyboard.TargetName="ItemsCanvas">
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.00" Value="1.0"/>
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.15" Value="0.0"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.TranslateY)" Storyboard.TargetName="ItemsCanvas">
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.00" Value="0.0"/>
<EasingDoubleKeyFrame EasingFunction="{StaticResource QuadraticEaseInOut}" KeyTime="0:0:0.15" Value="-35"/>
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</VisualTransition>
</VisualStateGroup.Transitions>
<VisualState x:Name="Collapsed">
<Storyboard>
<DoubleAnimation Duration="0" To="0" Storyboard.TargetProperty="(FrameworkElement.Height)" Storyboard.TargetName="ItemsCanvas"/>
<DoubleAnimation Duration="0" To="0.0" Storyboard.TargetProperty="(UIElement.Opacity)" Storyboard.TargetName="ItemsCanvas"/>
</Storyboard>
</VisualState>
<VisualState x:Name="Expanded">
<Storyboard>
<DoubleAnimation Duration="0" Storyboard.TargetProperty="(FrameworkElement.Height)" Storyboard.TargetName="ItemsCanvas"/>
<DoubleAnimation Duration="0" To="1.0" Storyboard.TargetProperty="(UIElement.Opacity)" Storyboard.TargetName="ItemsCanvas"/>
</Storyboard>
</VisualState>
</VisualStateGroup>
<VisualStateGroup x:Name="ExpandabilityStates">
<VisualState x:Name="Expandable"/>
<VisualState x:Name="NonExpandable">
<Storyboard>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Visibility)" Storyboard.TargetName="ExpandableContent">
<DiscreteObjectKeyFrame KeyTime="0:0:0.0" Value="Collapsed"/>
</ObjectAnimationUsingKeyFrames>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Visibility)" Storyboard.TargetName="NonExpandableContent">
<DiscreteObjectKeyFrame KeyTime="0:0:0.0" Value="Visible"/>
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<ListBoxItem x:Name="ExpandableContent" toolkit:TiltEffect.IsTiltEnabled="True" Grid.Row="0" Grid.RowSpan="2">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<ContentControl x:Name="Header" ContentTemplate="{TemplateBinding HeaderTemplate}" Content="{TemplateBinding Header}" HorizontalAlignment="Stretch" HorizontalContentAlignment="Stretch" Grid.Row="0"/>
<ContentControl x:Name="Expander" ContentTemplate="{TemplateBinding ExpanderTemplate}" Content="{TemplateBinding Expander}" HorizontalAlignment="Stretch" HorizontalContentAlignment="Stretch" Grid.Row="1"/>
<Grid x:Name="ExpanderPanel" Background="Transparent" Grid.Row="0" Grid.RowSpan="2"/>
</Grid>
</ListBoxItem>
<ContentControl x:Name="NonExpandableContent" ContentTemplate="{TemplateBinding NonExpandableHeaderTemplate}" Content="{TemplateBinding NonExpandableHeader}" HorizontalAlignment="Stretch" HorizontalContentAlignment="Stretch" Grid.Row="0" Grid.RowSpan="2" Visibility="Collapsed"/>
<Canvas x:Name="ItemsCanvas" Opacity="0.0" Grid.Row="2">
<Canvas.RenderTransform>
<CompositeTransform TranslateY="0.0"/>
</Canvas.RenderTransform>
<ItemsPresenter x:Name="Presenter"/>
</Canvas>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
Related
I am new to WPF and am struggling to put the pieces of information together. I am trying to create a two level vertical menu like the one here. I have achieved my desired look by overriding the control template of tree view items.
Here is my code.
<BooleanToVisibilityConverter x:Key="BooleanToVisibility" />
<Style x:Key="MenuText" TargetType="TextBlock" BasedOn="{StaticResource BaseTextBlockStyle}">
<Setter Property="Foreground" Value="#FFA7B1C2"/>
<Setter Property="VerticalAlignment" Value="Center"/>
</Style>
<Style x:Key="MenuIcon" TargetType="TextBlock" BasedOn="{StaticResource BaseIconTextBlockStyle}">
<Setter Property="Foreground" Value="#FFA7B1C2"/>
<Setter Property="VerticalAlignment" Value="Center"/>
</Style>
<Style x:Key="MenuToggleButton" TargetType="ToggleButton">
<Setter Property="Background" Value="Transparent"/>
<Setter Property="Height" Value="46"/>
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="Cursor" Value="Hand"/>
</Trigger>
</Style.Triggers>
</Style>
<ControlTemplate x:Key="MenuItemNormal" TargetType="{x:Type TreeViewItem}">
<Grid>
<Grid.RowDefinitions>
<RowDefinition/>
<RowDefinition/>
</Grid.RowDefinitions>
<ToggleButton Grid.Row="0" Tag="{TemplateBinding Tag}" Content="{TemplateBinding Header}" Style="{StaticResource MenuToggleButton}" >
<ToggleButton.Template>
<ControlTemplate TargetType="ToggleButton">
<Border x:Name="Border" BorderBrush="Transparent" >
<StackPanel Orientation="Horizontal" Background="{TemplateBinding Background}" Margin="25,0" >
<TextBlock x:Name="Icon" Style="{StaticResource MenuIcon}" Text="{TemplateBinding Tag}"/>
<TextBlock x:Name="MenuText" Style="{StaticResource MenuText}" Text="{TemplateBinding Content}" Margin="6,0,0,0"/>
</StackPanel>
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CommonStates">
<VisualState x:Name="MouseOver">
<Storyboard>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(Panel.Background)" Storyboard.TargetName="Border">
<DiscreteObjectKeyFrame KeyTime="0">
<DiscreteObjectKeyFrame.Value>
<SolidColorBrush Color="#FF293846"/>
</DiscreteObjectKeyFrame.Value>
</DiscreteObjectKeyFrame>
</ObjectAnimationUsingKeyFrames>
<ColorAnimationUsingKeyFrames Storyboard.TargetProperty="(TextElement.Foreground).(SolidColorBrush.Color)" Storyboard.TargetName="Icon">
<EasingColorKeyFrame KeyTime="0" Value="White"/>
</ColorAnimationUsingKeyFrames>
<ColorAnimationUsingKeyFrames Storyboard.TargetProperty="(TextElement.Foreground).(SolidColorBrush.Color)" Storyboard.TargetName="MenuText">
<EasingColorKeyFrame KeyTime="0" Value="White"/>
</ColorAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="Normal"/>
</VisualStateGroup>
<VisualStateGroup x:Name="CheckStates">
<VisualState x:Name="Checked">
<Storyboard>
<ThicknessAnimationUsingKeyFrames Storyboard.TargetProperty="(Border.BorderThickness)" Storyboard.TargetName="Border">
<EasingThicknessKeyFrame KeyTime="0" Value="4,0,0,0"/>
</ThicknessAnimationUsingKeyFrames>
<ColorAnimationUsingKeyFrames Storyboard.TargetProperty="(Border.BorderBrush).(SolidColorBrush.Color)" Storyboard.TargetName="Border">
<EasingColorKeyFrame KeyTime="0" Value="#FF19AA8D"/>
</ColorAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="Unchecked"/>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
</Border>
</ControlTemplate>
</ToggleButton.Template>
</ToggleButton>
<StackPanel Grid.Row="1" Visibility="Visible">
<ItemsPresenter />
</StackPanel>
</Grid>
</ControlTemplate>
<ControlTemplate x:Key="MenuItemParent" TargetType="{x:Type TreeViewItem}">
<Grid>
<Grid.RowDefinitions>
<RowDefinition/>
<RowDefinition/>
</Grid.RowDefinitions>
<ToggleButton x:Name="MenuButton" Grid.Row="0" Tag="{TemplateBinding Tag}" Content="{TemplateBinding Header}" Style="{StaticResource MenuToggleButton}" >
<ToggleButton.Template>
<ControlTemplate TargetType="ToggleButton">
<Border x:Name="Border" BorderBrush="Transparent" >
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="Auto"/>
</Grid.ColumnDefinitions>
<StackPanel Grid.Column="0" Orientation="Horizontal" Background="{TemplateBinding Background}" Margin="25,0" >
<TextBlock x:Name="Icon" Style="{StaticResource MenuIcon}" Text="{TemplateBinding Tag}"/>
<TextBlock x:Name="MenuText" Style="{StaticResource MenuText}" Text="{TemplateBinding Content}" Margin="6,0,0,0"/>
</StackPanel>
<TextBlock x:Name="Chevron" Grid.Column="1" Style="{StaticResource MenuIcon}" Text="" Margin="0,0,20,0"/>
</Grid>
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CommonStates">
<VisualState x:Name="MouseOver">
<Storyboard>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(Panel.Background)" Storyboard.TargetName="Border">
<DiscreteObjectKeyFrame KeyTime="0">
<DiscreteObjectKeyFrame.Value>
<SolidColorBrush Color="#FF293846"/>
</DiscreteObjectKeyFrame.Value>
</DiscreteObjectKeyFrame>
</ObjectAnimationUsingKeyFrames>
<ColorAnimationUsingKeyFrames Storyboard.TargetProperty="(TextElement.Foreground).(SolidColorBrush.Color)" Storyboard.TargetName="Icon">
<EasingColorKeyFrame KeyTime="0" Value="White"/>
</ColorAnimationUsingKeyFrames>
<ColorAnimationUsingKeyFrames Storyboard.TargetProperty="(TextElement.Foreground).(SolidColorBrush.Color)" Storyboard.TargetName="MenuText">
<EasingColorKeyFrame KeyTime="0" Value="White"/>
</ColorAnimationUsingKeyFrames>
<ColorAnimationUsingKeyFrames Storyboard.TargetProperty="(TextElement.Foreground).(SolidColorBrush.Color)" Storyboard.TargetName="Chevron">
<EasingColorKeyFrame KeyTime="0" Value="White"/>
</ColorAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="Normal"/>
</VisualStateGroup>
<VisualStateGroup x:Name="CheckStates">
<VisualState x:Name="Checked">
<Storyboard>
<ThicknessAnimationUsingKeyFrames Storyboard.TargetProperty="(Border.BorderThickness)" Storyboard.TargetName="Border">
<EasingThicknessKeyFrame KeyTime="0" Value="4,0,0,0"/>
</ThicknessAnimationUsingKeyFrames>
<ColorAnimationUsingKeyFrames Storyboard.TargetProperty="(Border.BorderBrush).(SolidColorBrush.Color)" Storyboard.TargetName="Border">
<EasingColorKeyFrame KeyTime="0" Value="#FF19AA8D"/>
</ColorAnimationUsingKeyFrames>
<StringAnimationUsingKeyFrames Storyboard.TargetProperty="(TextBlock.Text)" Storyboard.TargetName="Chevron">
<DiscreteStringKeyFrame KeyTime="0" Value=""/>
</StringAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="Unchecked"/>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
</Border>
</ControlTemplate>
</ToggleButton.Template>
<ToggleButton.Triggers>
<EventTrigger RoutedEvent="ToggleButton.Checked">
<BeginStoryboard>
<Storyboard >
<DoubleAnimation Storyboard.TargetName="ChildContainer" Storyboard.TargetProperty="RenderTransform.ScaleY" From="0" To="1" Duration="0:00:.500"/>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
<EventTrigger RoutedEvent="ToggleButton.Unchecked">
<BeginStoryboard>
<Storyboard >
<DoubleAnimation Storyboard.TargetName="ChildContainer" Storyboard.TargetProperty="RenderTransform.ScaleY" From="1" To="0" Duration="0:00:.500"/>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
</ToggleButton.Triggers>
</ToggleButton>
<StackPanel x:Name="ChildContainer" Grid.Row="1" Visibility="{Binding IsChecked, ElementName=MenuButton, Converter={StaticResource BooleanToVisibility}}">
<StackPanel.RenderTransform>
<ScaleTransform ScaleY="0"></ScaleTransform>
</StackPanel.RenderTransform>
<ItemsPresenter />
</StackPanel>
</Grid>
</ControlTemplate>
<ControlTemplate x:Key="MenuItemChild" TargetType="{x:Type TreeViewItem}">
<Grid>
<Grid.RowDefinitions>
<RowDefinition/>
<RowDefinition/>
</Grid.RowDefinitions>
<ToggleButton Grid.Row="0" Tag="{TemplateBinding Tag}" Content="{TemplateBinding Header}" Style="{StaticResource MenuToggleButton}" >
<ToggleButton.Template>
<ControlTemplate TargetType="ToggleButton">
<Border x:Name="Border" BorderBrush="Transparent" Background="#FF293846">
<StackPanel Grid.Column="0" Orientation="Horizontal" Background="{TemplateBinding Background}" Margin="25,0" >
<TextBlock x:Name="Icon" Style="{StaticResource MenuIcon}" Text=""/>
<TextBlock x:Name="MenuText" Style="{StaticResource MenuText}" Text="{TemplateBinding Content}" Margin="6,0,0,0"/>
</StackPanel>
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CommonStates">
<VisualState x:Name="MouseOver">
<Storyboard>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(Panel.Background)" Storyboard.TargetName="Border">
<DiscreteObjectKeyFrame KeyTime="0">
<DiscreteObjectKeyFrame.Value>
<SolidColorBrush Color="#FF293846"/>
</DiscreteObjectKeyFrame.Value>
</DiscreteObjectKeyFrame>
</ObjectAnimationUsingKeyFrames>
<ColorAnimationUsingKeyFrames Storyboard.TargetProperty="(TextElement.Foreground).(SolidColorBrush.Color)" Storyboard.TargetName="Icon">
<EasingColorKeyFrame KeyTime="0" Value="White"/>
</ColorAnimationUsingKeyFrames>
<ColorAnimationUsingKeyFrames Storyboard.TargetProperty="(TextElement.Foreground).(SolidColorBrush.Color)" Storyboard.TargetName="MenuText">
<EasingColorKeyFrame KeyTime="0" Value="White"/>
</ColorAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="Normal"/>
</VisualStateGroup>
<VisualStateGroup x:Name="CheckStates">
<VisualState x:Name="Checked">
<Storyboard>
<ThicknessAnimationUsingKeyFrames Storyboard.TargetProperty="(Border.BorderThickness)" Storyboard.TargetName="Border">
<EasingThicknessKeyFrame KeyTime="0" Value="4,0,0,0"/>
</ThicknessAnimationUsingKeyFrames>
<ColorAnimationUsingKeyFrames Storyboard.TargetProperty="(Border.BorderBrush).(SolidColorBrush.Color)" Storyboard.TargetName="Border">
<EasingColorKeyFrame KeyTime="0" Value="#FF19AA8D"/>
</ColorAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="Unchecked"/>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
</Border>
</ControlTemplate>
</ToggleButton.Template>
</ToggleButton>
<StackPanel Grid.Row="1" Visibility="Visible">
<ItemsPresenter />
</StackPanel>
</Grid>
</ControlTemplate>
And in my Window I declare Treeview like this.
<TreeView x:Name="Menu" Background="Transparent" BorderThickness="0">
<TreeViewItem Tag="" Header="Dashboard" Template="{StaticResource MenuItemNormal}" />
<TreeViewItem Tag="" Header="Home" Template="{StaticResource MenuItemNormal}" />
<TreeViewItem Tag="" Header="Reporting" Template="{StaticResource MenuItemNormal}" />
<TreeViewItem Tag="" Header="Sell" Template="{StaticResource MenuItemNormal}" />
<TreeViewItem Tag="" Header="Products" Template="{StaticResource MenuItemParent}" >
<TreeViewItem Header="Item 2.1" Template="{StaticResource MenuItemChild}" />
<TreeViewItem Header="Item 2.2" Template="{StaticResource MenuItemChild}" />
</TreeViewItem>
<TreeViewItem Tag="" Header="Sales Ledger" Template="{StaticResource MenuItemNormal}" />
<TreeViewItem Tag="" Header="Customers" Template="{StaticResource MenuItemNormal}" />
<TreeViewItem Tag="" Header="Setup" Template="{StaticResource MenuItemNormal}" />
</TreeView>
The problem is that now I realize I should have probably overridden the data
template of the tree view item because I want to bind the tree view to a property on my view model. I cannot figure out if I use data template how do I remove the default ugly expander icon that comes with tree view items
Specifically I have 3 questions
Is overriding control template the right way to achieve what I am
trying to do?
How do I bind my tree view to a view model property
instead of hard coding the items?
How do I track the selected item in my view model?
Thank you in advance!
I have a Style defined for a RadioButton which includes a ControlTemplate made up of BulletDecorator, VisualStateManager and Triggers. I currently have my GroupName defined on the RadioButton in the XAML code.
The selection of a radio button when running the code is not mutually exclusive.
I have read other posts saying that the problem is a second RadioButton defined in the ControlTemplate. I do not have a second RadioButton defined.
Here is a picture of buttons selected which should be mutually exclusive:
Here is my style:
<Style x:Key="RadioButtonStyle" TargetType="RadioButton">
<Setter Property="SnapsToDevicePixels" Value="true"/>
<Setter Property="OverridesDefaultStyle" Value="true"/>
<Setter Property="BorderThickness" Value="1"/>
<Setter Property="Height" Value="15"/>
<Setter Property="Margin" Value="5"/>
<Setter Property="FocusVisualStyle" Value="{x:Null}"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="RadioButton">
<BulletDecorator>
<BulletDecorator.Bullet>
<Grid Height="{TemplateBinding Height}" Width="{Binding RelativeSource={RelativeSource Self}, Path=Height, UpdateSourceTrigger=PropertyChanged}" MinHeight="15" MinWidth="15">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="1*"/>
<ColumnDefinition Width="3*"/>
<ColumnDefinition Width="1*"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="1*"/>
<RowDefinition Height="3*"/>
<RowDefinition Height="1*"/>
</Grid.RowDefinitions>
<Ellipse Name="EllipseMain"
Grid.Column="0" Grid.ColumnSpan="3"
Grid.Row="0" Grid.RowSpan="3"
Fill="Transparent"
StrokeThickness="{TemplateBinding BorderThickness}"
Stroke="DimGray"/>
<Ellipse Name="CheckMark"
Grid.Column="1"
Grid.Row="1"
Opacity="0"
Fill="#029cc7"/>
</Grid>
</BulletDecorator.Bullet>
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CommonStates">
<VisualState x:Name="Disabled">
<Storyboard>
<ColorAnimation Storyboard.TargetName="CheckMark" Storyboard.TargetProperty="(Ellipse.Fill).(SolidColorBrush.Color)" To="LightGray" Duration="0:0:0.3"/>
<ColorAnimation Storyboard.TargetName="CheckMain" Storyboard.TargetProperty="(Ellipse.Stroke).(SolidColorBrush.Color)" To="LightGray" Duration="0:0:0.3"/>
</Storyboard>
</VisualState>
</VisualStateGroup>
<VisualStateGroup x:Name="CheckStates">
<VisualState x:Name="Checked">
<Storyboard>
<DoubleAnimation Storyboard.TargetName="CheckMark" Storyboard.TargetProperty="Opacity" To="1" Duration="0:0:0.3"/>
</Storyboard>
</VisualState>
<VisualState x:Name="UnChecked">
<Storyboard>
<DoubleAnimation Storyboard.TargetName="CheckMark" Storyboard.TargetProperty="Opacity" To="0" Duration="0:0:0.3"/>
</Storyboard>
</VisualState>
<VisualState x:Name="Indeterminate">
<Storyboard>
<DoubleAnimation Storyboard.TargetName="CheckMark" Storyboard.TargetProperty="Opacity" To="1" Duration="0:0:0.3"/>
<ColorAnimation Storyboard.TargetName="CheckMain" Storyboard.TargetProperty="(Ellipse.Fill).(SolidColorBrush.Color)" To="Gray" Duration="0:0:0.3"/>
</Storyboard>
</VisualState>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<ContentPresenter Margin="4,0,0,0" HorizontalAlignment="Left" VerticalAlignment="Center" RecognizesAccessKey="True"/>
</BulletDecorator>
<ControlTemplate.Triggers>
<Trigger Property="IsPressed" Value="True">
<Setter TargetName="EllipseMain" Property="Fill" Value="#55029cc7"/>
</Trigger>
<Trigger Property="IsFocused" Value="True">
<Setter TargetName="EllipseMain" Property="Stroke" Value="#88029cc7"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
Here is the XAML:
<RadioButton Grid.Row="0" Grid.Column="0" Content="Normal" Foreground="WhiteSmoke" Style="{StaticResource RadioButtonStyle}" GroupName="gpHeadingMode" Margin="0,0,0,0"/>
<RadioButton Grid.Row="1" Grid.Column="0" Content="Weather Vane" Foreground="WhiteSmoke" Style="{StaticResource RadioButtonStyle}" GroupName="gpHeadingMode" Margin="0,0,0,0"/>
Tried this as a work around (in XAML):
<RadioButton Grid.Row="0" Grid.Column="0" x:Name="Normal" Content="Normal" Foreground="WhiteSmoke" GroupName="gpHeadingMode1"
Style="{StaticResource RadioButtonStyle}"
IsChecked="{Binding HeadingModeChecked, ElementName=HeadingDialog, Converter={StaticResource RbCheckedConverter}, ConverterParameter=Normal, FallbackValue=False}"
Click="RbHeadingMode_Click"/>
<RadioButton Grid.Row="1" Grid.Column="0" x:Name="WeatherVane" Content="Weather Vane" Foreground="WhiteSmoke" GroupName="gpHeadingMode2"
Style="{StaticResource RadioButtonStyle}"
IsChecked="{Binding HeadingModeChecked, ElementName=HeadingDialog, Converter={StaticResource RbCheckedConverter}, ConverterParameter=WeatherVane, FallbackValue=False}"
Click="RbHeadingMode_Click"/>
In RbHeadingMode_Click, the dependency object HeadingModeChecked is set with the value of RadioButton.Name. If I remove the "Style" the converter fires and does the job of toggling the IsClicked value.
Unfortunately, with the Style, the converter does not fire.
Now the question becomes, how can I bind the IsChecked property in XAML to the Style?
Note: Actually, the converter does fire with Style specified but the change to IsChecked in XAML has no effect on the RadioButton.
Had to remove the following code from the Style and it works:
<VisualStateGroup x:Name="CheckStates">
<VisualState x:Name="Checked">
<Storyboard>
<DoubleAnimation Storyboard.TargetName="CheckMark" Storyboard.TargetProperty="Opacity" To="1" Duration="0:0:0.3"/>
</Storyboard>
</VisualState>
<VisualState x:Name="UnChecked">
<Storyboard>
<DoubleAnimation Storyboard.TargetName="CheckMark" Storyboard.TargetProperty="Opacity" To="0" Duration="0:0:0.3"/>
</Storyboard>
</VisualState>
<VisualState x:Name="Indeterminate">
<Storyboard>
<DoubleAnimation Storyboard.TargetName="CheckMark" Storyboard.TargetProperty="Opacity" To="1" Duration="0:0:0.3"/>
<ColorAnimation Storyboard.TargetName="CheckMain" Storyboard.TargetProperty="(Ellipse.Fill).(SolidColorBrush.Color)" To="Gray" Duration="0:0:0.3"/>
</Storyboard>
</VisualState>
</VisualStateGroup>
Note: Not only does the converter work on the IsChecked property but now I can remove that converter and just use Groupname to achieve mutual exclusion on the radiobuttons!
I have a ListView where the SelectionMode is set to Multiple. That adds checkboxes in front of every ListViewItem. Is it possible to change the layout so that I can change the color and position of the checkboxes?
U can see my code here of the ListView:
<ListView x:Name="lstCategories" Grid.Row="2" Margin="20,10,20,0" ItemsSource="{Binding Categories}" SelectionMode="Multiple">
<ListView.ItemContainerStyle>
<Style TargetType="ListViewItem">
<Setter Property="HorizontalContentAlignment" Value="Stretch"></Setter>
</Style>
</ListView.ItemContainerStyle>
<ListView.ItemTemplate>
<DataTemplate>
<StackPanel>
<TextBlock Text="{Binding}" Style="{StaticResource TextBlockStyle}" />
<Rectangle Style="{StaticResource DividerStyle}"/>
</StackPanel>
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
What I get as result when running this XAML is: http://i.stack.imgur.com/WYvUN.png,
but I need something like this: http://i.stack.imgur.com/vmtaQ.png
I know you can adjust templates to change individual controls but I dont know how to change it when it's in a ListViewItem.
<Style TargetType="ListViewItem">
<Setter Property="FontFamily" Value="{ThemeResource ContentControlThemeFontFamily}" />
<Setter Property="FontSize" Value="{ThemeResource ControlContentThemeFontSize}" />
<Setter Property="Background" Value="Transparent" />
<Setter Property="TabNavigation" Value="Local" />
<Setter Property="IsHoldingEnabled" Value="False" />
<Setter Property="Margin" Value="{ThemeResource ListViewItemMargin}" />
<Setter Property="HorizontalContentAlignment" Value="Left" />
<Setter Property="VerticalContentAlignment" Value="Top" />
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="ListViewItem">
<Border x:Name="OuterContainer" RenderTransformOrigin="0.5,0.5">
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CommonStates">
<VisualState x:Name="Normal" />
<VisualState x:Name="Pressed">
<Storyboard>
<PointerDownThemeAnimation Storyboard.TargetName="TiltContainer" />
</Storyboard>
</VisualState>
<VisualState x:Name="CheckboxPressed">
<Storyboard>
<PointerDownThemeAnimation Storyboard.TargetName="CheckboxTiltContainer" />
<ObjectAnimationUsingKeyFrames Storyboard.TargetName="NormalRectangle" Storyboard.TargetProperty="Fill">
<DiscreteObjectKeyFrame KeyTime="0" Value="{ThemeResource CheckBoxPressedBackgroundThemeBrush}" />
</ObjectAnimationUsingKeyFrames>
<ObjectAnimationUsingKeyFrames Storyboard.TargetName="CheckGlyph" Storyboard.TargetProperty="Fill">
<DiscreteObjectKeyFrame KeyTime="0" Value="{ThemeResource CheckBoxPressedForegroundThemeBrush}" />
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="Disabled">
<Storyboard>
<DoubleAnimation Duration="0"
Storyboard.TargetName="contentPresenter"
Storyboard.TargetProperty="Opacity"
To="{ThemeResource ListViewItemDisabledThemeOpacity}" />
<ObjectAnimationUsingKeyFrames Duration="0"
Storyboard.TargetName="NormalRectangle"
Storyboard.TargetProperty="Stroke">
<DiscreteObjectKeyFrame KeyTime="0" Value="{ThemeResource CheckBoxDisabledBorderThemeBrush}" />
</ObjectAnimationUsingKeyFrames>
<ObjectAnimationUsingKeyFrames Duration="0"
Storyboard.TargetName="CheckGlyph"
Storyboard.TargetProperty="Fill">
<DiscreteObjectKeyFrame KeyTime="0" Value="{ThemeResource CheckBoxDisabledForegroundThemeBrush}" />
</ObjectAnimationUsingKeyFrames>
<ObjectAnimationUsingKeyFrames Duration="0"
Storyboard.TargetName="SelectedBorder"
Storyboard.TargetProperty="BorderBrush">
<DiscreteObjectKeyFrame KeyTime="0" Value="Transparent" />
</ObjectAnimationUsingKeyFrames>
<ObjectAnimationUsingKeyFrames Duration="0"
Storyboard.TargetName="SelectedEarmark"
Storyboard.TargetProperty="Fill">
<DiscreteObjectKeyFrame KeyTime="0" Value="Transparent" />
</ObjectAnimationUsingKeyFrames>
<ObjectAnimationUsingKeyFrames Duration="0"
Storyboard.TargetName="SelectedGlyph"
Storyboard.TargetProperty="Fill">
<DiscreteObjectKeyFrame KeyTime="0" Value="Transparent" />
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualStateGroup.Transitions>
<VisualTransition From="Pressed" To="Normal">
<Storyboard>
<PointerUpThemeAnimation Storyboard.TargetName="TiltContainer" />
</Storyboard>
</VisualTransition>
</VisualStateGroup.Transitions>
</VisualStateGroup>
<VisualStateGroup x:Name="SelectionStates">
<VisualState x:Name="Unselected" />
<VisualState x:Name="Selected">
<Storyboard>
<DoubleAnimation Duration="0"
Storyboard.TargetName="CheckGlyph"
Storyboard.TargetProperty="Opacity"
To="1" />
<DoubleAnimation Duration="0"
Storyboard.TargetName="SelectedCheckMark"
Storyboard.TargetProperty="Opacity"
To="1" />
</Storyboard>
</VisualState>
<VisualState x:Name="SelectedUnfocused">
<Storyboard>
<DoubleAnimation Duration="0"
Storyboard.TargetName="CheckGlyph"
Storyboard.TargetProperty="Opacity"
To="1" />
<DoubleAnimation Duration="0"
Storyboard.TargetName="SelectedCheckMark"
Storyboard.TargetProperty="Opacity"
To="1" />
</Storyboard>
</VisualState>
</VisualStateGroup>
<VisualStateGroup x:Name="DataVirtualizationStates">
<VisualState x:Name="DataAvailable" />
<VisualState x:Name="DataPlaceholder">
<Storyboard>
<ObjectAnimationUsingKeyFrames Duration="0"
Storyboard.TargetName="PlaceholderTextBlock"
Storyboard.TargetProperty="Visibility">
<DiscreteObjectKeyFrame KeyTime="0" Value="Visible" />
</ObjectAnimationUsingKeyFrames>
<ObjectAnimationUsingKeyFrames Duration="0"
Storyboard.TargetName="PlaceholderRect"
Storyboard.TargetProperty="Visibility">
<DiscreteObjectKeyFrame KeyTime="0" Value="Visible" />
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
</VisualStateGroup>
<VisualStateGroup x:Name="MultiSelectStates">
<VisualState x:Name="NoMultiSelect" />
<VisualState x:Name="ListMultiSelect">
<Storyboard>
<DoubleAnimation Duration="0"
Storyboard.TargetName="CheckboxContainerTranslateTransform"
Storyboard.TargetProperty="X"
To="0" />
<DoubleAnimation Duration="0"
Storyboard.TargetName="ContentBorderTranslateTransform"
Storyboard.TargetProperty="X"
To="{ThemeResource ListViewItemContentTranslateX}" />
</Storyboard>
</VisualState>
<VisualState x:Name="GridMultiSelect">
<Storyboard>
<DoubleAnimation Duration="0"
Storyboard.TargetName="SelectedBorder"
Storyboard.TargetProperty="Opacity"
To="1" />
</Storyboard>
</VisualState>
<VisualStateGroup.Transitions>
<VisualTransition From="ListMultiSelect"
GeneratedDuration="0:0:0.15"
To="NoMultiSelect" />
<VisualTransition From="NoMultiSelect"
GeneratedDuration="0:0:0.15"
To="ListMultiSelect" />
</VisualStateGroup.Transitions>
</VisualStateGroup>
<VisualStateGroup x:Name="ReorderModeStates">
<VisualState x:Name="ReorderEnabled">
<Storyboard>
<DropTargetItemThemeAnimation Storyboard.TargetName="OuterContainer" />
</Storyboard>
</VisualState>
<VisualState x:Name="Reorderable">
<Storyboard>
<DoubleAnimationUsingKeyFrames Storyboard.TargetName="ContentScaleTransform" Storyboard.TargetProperty="ScaleX">
<LinearDoubleKeyFrame KeyTime="00:00:00.075" Value="1.05" />
<LinearDoubleKeyFrame KeyTime="00:00:00.2" Value="1.0" />
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames Storyboard.TargetName="ContentScaleTransform" Storyboard.TargetProperty="ScaleY">
<LinearDoubleKeyFrame KeyTime="00:00:00.075" Value="1.05" />
<LinearDoubleKeyFrame KeyTime="00:00:00.2" Value="1.0" />
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="ReorderDisabled" />
<VisualStateGroup.Transitions>
<VisualTransition From="ReorderEnabled"
GeneratedDuration="00:00:00.2"
To="ReorderDisabled" />
</VisualStateGroup.Transitions>
</VisualStateGroup>
<VisualStateGroup x:Name="ReorderHintStates">
<VisualState x:Name="NoReorderHint" />
<VisualState x:Name="BottomReorderHint">
<Storyboard>
<DragOverThemeAnimation Direction="Bottom"
Storyboard.TargetName="ReorderHintContent"
ToOffset="{ThemeResource ListViewItemReorderHintThemeOffset}" />
</Storyboard>
</VisualState>
<VisualState x:Name="RightReorderHint">
<Storyboard>
<DragOverThemeAnimation Direction="Right"
Storyboard.TargetName="ReorderHintContent"
ToOffset="{ThemeResource ListViewItemReorderHintThemeOffset}" />
</Storyboard>
</VisualState>
<VisualState x:Name="TopReorderHint">
<Storyboard>
<DragOverThemeAnimation Direction="Top"
Storyboard.TargetName="ReorderHintContent"
ToOffset="0" />
</Storyboard>
</VisualState>
<VisualState x:Name="LeftReorderHint">
<Storyboard>
<DragOverThemeAnimation Direction="Left"
Storyboard.TargetName="ReorderHintContent"
ToOffset="0" />
</Storyboard>
</VisualState>
<VisualStateGroup.Transitions>
<VisualTransition GeneratedDuration="0:0:0.2" To="NoReorderHint" />
</VisualStateGroup.Transitions>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<Border.RenderTransform>
<ScaleTransform x:Name="ContentScaleTransform" />
</Border.RenderTransform>
<Grid x:Name="ReorderHintContent" Background="Transparent">
<Border x:Name="CheckboxTiltContainer"
Margin="{ThemeResource ListViewItemMultiselectCheckBoxMargin}"
HorizontalAlignment="Left"
VerticalAlignment="Top">
<Border x:Name="CheckboxOuterContainer">
<Border.Clip>
<RectangleGeometry Rect="0,0,25.5,25.5" />
</Border.Clip>
<Grid x:Name="CheckboxContainer">
<Grid.RenderTransform>
<TranslateTransform x:Name="CheckboxContainerTranslateTransform" X="{ThemeResource ListViewItemContentOffsetX}" />
</Grid.RenderTransform>
<Rectangle x:Name="NormalRectangle"
Width="25.5"
Height="25.5"
Fill="{ThemeResource CheckBoxBackgroundThemeBrush}"
Stroke="{ThemeResource CheckBoxBorderThemeBrush}"
StrokeThickness="{ThemeResource CheckBoxBorderThemeThickness}" />
<Path x:Name="CheckGlyph"
Width="18.5"
Height="17"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Data="M0,123 L39,93 L124,164 L256,18 L295,49 L124,240 z"
Fill="{ThemeResource CheckBoxForegroundThemeBrush}"
FlowDirection="LeftToRight"
IsHitTestVisible="False"
Opacity="0"
Stretch="Fill"
StrokeLineJoin="Round"
StrokeThickness="2.5" />
</Grid>
</Border>
</Border>
<Border x:Name="ContentContainer">
<Border x:Name="TiltContainer">
<Border x:Name="ContentBorder"
Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}">
<Border.RenderTransform>
<TranslateTransform x:Name="ContentBorderTranslateTransform" />
</Border.RenderTransform>
<Grid>
<ContentPresenter x:Name="contentPresenter"
Margin="{TemplateBinding Padding}"
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
Content="{TemplateBinding Content}"
ContentTemplate="{TemplateBinding ContentTemplate}"
ContentTransitions="{TemplateBinding ContentTransitions}" />
<TextBlock x:Name="PlaceholderTextBlock"
Margin="{TemplateBinding Padding}"
AutomationProperties.AccessibilityView="Raw"
Foreground="{x:Null}"
IsHitTestVisible="False"
Opacity="0"
Text="Xg" />
<Rectangle x:Name="PlaceholderRect"
Fill="{ThemeResource ListViewItemPlaceholderBackgroundThemeBrush}"
IsHitTestVisible="False"
Visibility="Collapsed" />
</Grid>
</Border>
</Border>
</Border>
<Border x:Name="SelectedBorder"
BorderBrush="{ThemeResource ListViewItemSelectedBackgroundThemeBrush}"
BorderThickness="{ThemeResource GridViewItemMultiselectBorderThickness}"
IsHitTestVisible="False"
Opacity="0">
<Grid x:Name="SelectedCheckMark"
Width="34"
Height="34"
HorizontalAlignment="Right"
VerticalAlignment="Top"
Opacity="0">
<Path x:Name="SelectedEarmark"
Data="M0,0 L40,0 L40,40 z"
Fill="{ThemeResource ListViewItemSelectedBackgroundThemeBrush}"
Stretch="Fill" />
<Path x:Name="SelectedGlyph"
Width="17"
Height="14.5"
Margin="0,1,1,0"
HorizontalAlignment="Right"
VerticalAlignment="Top"
Data="M0,123 L39,93 L124,164 L256,18 L295,49 L124,240 z"
Fill="{ThemeResource ListViewItemCheckThemeBrush}"
FlowDirection="LeftToRight"
Stretch="Fill" />
</Grid>
</Border>
</Grid>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
I've been messing around trying to change this red border around the LoopingSelector in code, and in Blend. I just can't figure out how to do it. Here's a picture so you have an idea of what I'm talking about.
<Grid Grid.Row="1" Margin="12,0,12,0" toolkit:TurnstileFeatherEffect.FeatheringIndex="1">
<Grid.Resources>
<DataTemplate x:Key="KiloTemplate">
<Grid Background="DarkBlue">
<TextBlock Text="{Binding}" FontSize="54" FontFamily="{StaticResource PhoneFontFamilySemiBold}" HorizontalAlignment="Center" VerticalAlignment="Center" />
<TextBlock Text="kg" FontSize="24" HorizontalAlignment="Right" VerticalAlignment="Bottom" />
</Grid>
</DataTemplate>
</Grid.Resources>
<toolkitPrimitives:LoopingSelector x:Name="loopingSelectorStarost" Margin="12" Width="128" ItemSize="128,128" ItemTemplate="{StaticResource StarostTemplate}" ManipulationStarted="loopingSelector_ManipulationStarted">
<toolkitPrimitives:LoopingSelector.DataSource>
<local:NumberDataSource Privzeti="18" Minimum="13" Maximum="99" />
</toolkitPrimitives:LoopingSelector.DataSource>
</toolkitPrimitives:LoopingSelector>
</Grid>
EDIT: Here's the soulution, thanks to Chris. W. I copied the style from the Generic.xaml file in the Phone Toolkit samples. I changed the <DiscreteObjectKeyFrame KeyTime="0" Value="Transparent" /> in the Selected Visual State. Here's the code:
<Style TargetType="toolkitPrimitives:LoopingSelectorItem">
<Setter Property="Foreground" Value="{StaticResource PhoneSubtleBrush}"/>
<Setter Property="Padding" Value="6"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate>
<Border x:Name="root" CacheMode="BitmapCache" Background="Transparent" Padding="{TemplateBinding Padding}">
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CommonStates">
<VisualStateGroup.Transitions>
<VisualTransition From="Normal" To="Expanded" GeneratedDuration="0:0:0.33" />
<VisualTransition From="Expanded" To="Normal" GeneratedDuration="0:0:0.33" />
</VisualStateGroup.Transitions>
<VisualState x:Name="Normal" />
<VisualState x:Name="Expanded">
<Storyboard>
<DoubleAnimation Storyboard.TargetName="border" Storyboard.TargetProperty="Opacity" To="0.8" Duration="0"/>
</Storyboard>
</VisualState>
<VisualState x:Name="Selected">
<Storyboard>
<DoubleAnimation Storyboard.TargetName="background" Storyboard.TargetProperty="Opacity" To="1" Duration="0"/>
<DoubleAnimation Storyboard.TargetName="border" Storyboard.TargetProperty="Opacity" To="1" Duration="0"/>
<ObjectAnimationUsingKeyFrames Storyboard.TargetName="border" Storyboard.TargetProperty="BorderBrush" Duration="0">
<ObjectAnimationUsingKeyFrames.KeyFrames>
<DiscreteObjectKeyFrame KeyTime="0" Value="DarkGray" />
</ObjectAnimationUsingKeyFrames.KeyFrames>
</ObjectAnimationUsingKeyFrames>
<ObjectAnimationUsingKeyFrames Storyboard.TargetName="contentControl" Storyboard.TargetProperty="Foreground" Duration="0">
<ObjectAnimationUsingKeyFrames.KeyFrames>
<DiscreteObjectKeyFrame KeyTime="0" Value="White" />
</ObjectAnimationUsingKeyFrames.KeyFrames>
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<Border.RenderTransform>
<TranslateTransform x:Name="Transform"/>
</Border.RenderTransform>
<Grid>
<Rectangle x:Name="background" Margin="0" Opacity="0" Fill="{StaticResource PhoneAccentBrush}" CacheMode="BitmapCache"/>
<Border x:Name="border" Opacity="0" BorderThickness="3" BorderBrush="{StaticResource PhoneSubtleBrush}">
<ContentControl x:Name="contentControl" HorizontalAlignment="Stretch" HorizontalContentAlignment="Stretch" VerticalAlignment="Stretch" VerticalContentAlignment="Stretch">
<ContentPresenter x:Name="contentPresenter" CacheMode="BitmapCache"/>
</ContentControl>
</Border>
</Grid>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
Start by finding the template for it, a quick solution search for TargetType="primitives:LoopingSelectorItem" should expose it pretty quick or you could likely get to it in Blend.
Once you have the template you'll just locate the Border or Rectangle object in the template that's causing that border.
However that may not even be necessary if the property is bound to the template already. Can you set something like BorderBrush directly to it? I'd have to load something up to look so I'm just guessing at this point.
Hope this helps.
I am designing an application in Silverlight with C# and MVVM. On one of the pages I have an image (as in a visual, not the type Image) which is composed of several Path's. In this case they form a face and I would like the user to be able to select several parts (eyes, nose, ears...). Each of these is a separate Path.
The idea is that the user can select one of these vectors and work with it. I'd like the selected one to change color.
I can write a converted of bool to the selected color, that's not a problem. The problem is adding selection logic.
My idea was wrapping it in a ListBox, editing the ItemTemplate to include the Path but this position edthe paths incorrectly. Even after applying margins and the like I couldn't get it properly.
Does anyone have any experience or guidance on this?
Thanks in advance!
ANSWER:
1) Change the ItemsPanel template to your container:
<ListBox.ItemsPanel>
<ItemsPanelTemplate>
<Canvas Width="208"
Height="391" />
</ItemsPanelTemplate>
</ListBox.ItemsPanel>
2) Set the ItemsSource:
The trick here is that positioning/attached attributes only work on the direct children of the ListBox. In this case I am using Canvas.Top and Canvas.Left. The solution is to wrap each Item in an additional ListBoxItem and apply those attributes on the ListBoxItem. (This will happen by default if you dont anyway).
<ListBox>
<ListBoxItem Canvas.Left="10" Canvas.Top="5">
<Path Data="..." Height="200" Width="200" Fill="Black" />
</ListBoxItem>
</ListBox>
Try setting a MouseLeftButtonDown event handler on the Path's that binds to an command on the ViewModel. Should be able to use the sender parameter in the handler to determine which Path to modify.
For the ListBox approach, did you try modifying the ItemsPanel and using a Canvas?
If I understand correctly you could add a VisualStateGroup for FocusStates with a VisualStateManager like you would see on a standard button to apply a different Fill or Border to the path selected. Essentially you'd be making each path behave as a button control would showing a different visual state based on its focus.
(Changed this example to default checkbox template as an example) I can make an example if you need one.
<Style TargetType="CheckBox" x:Key="DefaultCheckBoxStyle">
<Setter Property="FontFamily" Value="{StaticResource ContentFontFamily}"/>
<Setter Property="FontSize" Value="{StaticResource ContentFontSize}"/>
<Setter Property="Background" Value="{StaticResource NormalBrush}"/>
<Setter Property="Foreground" Value="{StaticResource TextContentBrush}"/>
<Setter Property="HorizontalContentAlignment" Value="Left"/>
<Setter Property="VerticalContentAlignment" Value="Top"/>
<Setter Property="Padding" Value="4,1,0,0"/>
<Setter Property="BorderThickness" Value="1"/>
<Setter Value="{StaticResource NormalBorderBrush}" Property="BorderBrush"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="CheckBox">
<Grid x:Name="grid" RenderTransformOrigin="0.5,0.5">
<Grid.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform/>
<TranslateTransform/>
</TransformGroup>
</Grid.RenderTransform>
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CommonStates">
<VisualStateGroup.Transitions>
<VisualTransition From="Normal" GeneratedDuration="0:0:0.01" To="MouseOver">
<VisualTransition.GeneratedEasingFunction>
<ExponentialEase EasingMode="EaseIn" Exponent="7"/>
</VisualTransition.GeneratedEasingFunction>
</VisualTransition>
<VisualTransition From="MouseOver" GeneratedDuration="0:0:0.1" To="Normal">
<VisualTransition.GeneratedEasingFunction>
<CircleEase EasingMode="EaseIn"/>
</VisualTransition.GeneratedEasingFunction>
</VisualTransition>
</VisualStateGroup.Transitions>
<VisualState x:Name="Normal"/>
<VisualState x:Name="MouseOver">
<Storyboard>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="MouseOverRectangleFill" Storyboard.TargetProperty="(UIElement.Opacity)">
<SplineDoubleKeyFrame KeyTime="00:00:00.1000000" Value="1.0"/>
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="Pressed">
<Storyboard>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="PressedBorder" Storyboard.TargetProperty="(UIElement.Opacity)">
<SplineDoubleKeyFrame KeyTime="00:00:00.1000000" Value="1.0"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[0].(ScaleTransform.ScaleX)" Storyboard.TargetName="grid">
<EasingDoubleKeyFrame KeyTime="0:0:0.1" Value="1.05"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[0].(ScaleTransform.ScaleY)" Storyboard.TargetName="grid">
<EasingDoubleKeyFrame KeyTime="0:0:0.1" Value="1.05"/>
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="Disabled">
<Storyboard>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="contentPresenter" Storyboard.TargetProperty="(UIElement.Opacity)">
<SplineDoubleKeyFrame KeyTime="00:00:00.1000000" Value="0.3"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="DisabledVisualElement" Storyboard.TargetProperty="(UIElement.Opacity)">
<SplineDoubleKeyFrame KeyTime="00:00:00.1000000" Value="1.0"/>
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
</VisualStateGroup>
<VisualStateGroup x:Name="CheckStates">
<VisualState x:Name="Checked">
<Storyboard>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Opacity)" Storyboard.TargetName="CheckIcon">
<SplineDoubleKeyFrame KeyTime="0" Value="1"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="CheckedRectangle" Storyboard.TargetProperty="(UIElement.Opacity)">
<SplineDoubleKeyFrame KeyTime="00:00:00.1000000" Value="0.6"/>
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="Unchecked"/>
<VisualState x:Name="Indeterminate">
<Storyboard>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Opacity)" Storyboard.TargetName="IndeterminateIcon">
<SplineDoubleKeyFrame KeyTime="0" Value="1"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="IndeterminateRectangle" Storyboard.TargetProperty="(UIElement.Opacity)">
<SplineDoubleKeyFrame KeyTime="00:00:00.1000000" Value="0.6"/>
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
</VisualStateGroup>
<VisualStateGroup x:Name="FocusStates">
<VisualState x:Name="Focused">
<Storyboard>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="Opacity" Storyboard.TargetName="ContentFocusVisualElement">
<SplineDoubleKeyFrame KeyTime="0" Value="1"/>
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="Unfocused"/>
</VisualStateGroup>
<VisualStateGroup x:Name="ValidationStates">
<VisualState x:Name="Valid"/>
<VisualState x:Name="InvalidUnfocused">
<Storyboard>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="Visibility" Storyboard.TargetName="ValidationErrorElement">
<DiscreteObjectKeyFrame KeyTime="0">
<DiscreteObjectKeyFrame.Value>
<Visibility>Visible</Visibility>
</DiscreteObjectKeyFrame.Value>
</DiscreteObjectKeyFrame>
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="InvalidFocused">
<Storyboard>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="Visibility" Storyboard.TargetName="ValidationErrorElement">
<DiscreteObjectKeyFrame KeyTime="0">
<DiscreteObjectKeyFrame.Value>
<Visibility>Visible</Visibility>
</DiscreteObjectKeyFrame.Value>
</DiscreteObjectKeyFrame>
</ObjectAnimationUsingKeyFrames>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="IsOpen" Storyboard.TargetName="validationTooltip">
<DiscreteObjectKeyFrame KeyTime="0">
<DiscreteObjectKeyFrame.Value>
<System:Boolean>True</System:Boolean>
</DiscreteObjectKeyFrame.Value>
</DiscreteObjectKeyFrame>
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="21"/>
</Grid.ColumnDefinitions>
<Grid HorizontalAlignment="Right" VerticalAlignment="Top" Grid.Column="1" Margin="5,0,0,0">
<Grid Width="16" Height="16">
<Rectangle x:Name="Background" Fill="{StaticResource BlankBackgroundBrush}" StrokeThickness="{TemplateBinding BorderThickness}" Stroke="{StaticResource BaseBrush7}" />
<Rectangle x:Name="BackgroundInner" Fill="{TemplateBinding Background}" Margin="1" StrokeThickness="{TemplateBinding BorderThickness}" Stroke="{TemplateBinding BorderBrush}"/>
<Rectangle x:Name="MouseOverRectangleFill" Fill="{StaticResource MouseOverBrush}" StrokeThickness="2" Opacity="0" Margin="3"/>
<Rectangle x:Name="MouseOverRectangle" StrokeThickness="2" Stroke="{StaticResource MouseOverBrush}" Opacity="0"/>
<Border x:Name="PressedBorder" BorderThickness="1" BorderBrush="{StaticResource MouseOverBrush}" Opacity="0" />
<Rectangle x:Name="ContentFocusVisualElement" StrokeThickness="1" IsHitTestVisible="false" Opacity="0" Stroke="{StaticResource FocusedBrush}" />
<Rectangle x:Name="DisabledVisualElement" Fill="{StaticResource DisabledBackgroundBrush}" Stroke="{StaticResource DisabledBackgroundBrush}" Opacity="0" RadiusY="1" RadiusX="1" />
<Rectangle x:Name="CheckedRectangle" StrokeThickness="0.5" Stroke="{StaticResource BaseBrush4}" Opacity="0" RadiusX="0.5" RadiusY="0.5"/>
<Path x:Name="CheckIcon" Data="M335.69366,107.11728 L339,111.375 347.09859,99.975309" HorizontalAlignment="Center" Stretch="Fill" Stroke="{StaticResource BaseBrush4}" UseLayoutRounding="False" VerticalAlignment="Center" StrokeThickness="2" StrokeStartLineCap="Round" StrokeEndLineCap="Round" Margin="3.5" Opacity="0"/>
<Rectangle x:Name="IndeterminateRectangle" StrokeThickness="2" Stroke="{StaticResource BaseBrush4}" Opacity="0"/>
<Rectangle x:Name="IndeterminateIcon" Fill="{StaticResource BaseBrush3}" Height="2" Opacity="0" Width="6"/>
<Border x:Name="ValidationErrorElement" BorderBrush="{StaticResource ControlsValidationBrush}" BorderThickness="1" CornerRadius="1" Margin="1" ToolTipService.PlacementTarget="{Binding RelativeSource={RelativeSource TemplatedParent}}" Visibility="Collapsed">
<ToolTipService.ToolTip>
<ToolTip x:Name="validationTooltip" DataContext="{Binding RelativeSource={RelativeSource TemplatedParent}}" Placement="Right" PlacementTarget="{Binding RelativeSource={RelativeSource TemplatedParent}}" Template="{StaticResource ValidationToolTipTemplate}">
<ToolTip.Triggers>
<EventTrigger RoutedEvent="Canvas.Loaded">
<BeginStoryboard>
<Storyboard>
<ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="IsHitTestVisible" Storyboard.TargetName="validationTooltip">
<DiscreteObjectKeyFrame KeyTime="0">
<DiscreteObjectKeyFrame.Value>
<System:Boolean>true</System:Boolean>
</DiscreteObjectKeyFrame.Value>
</DiscreteObjectKeyFrame>
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
</ToolTip.Triggers>
</ToolTip>
</ToolTipService.ToolTip>
<Grid Background="Transparent" HorizontalAlignment="Right" Height="10" Margin="0,-4,-4,0" VerticalAlignment="Top" Width="10">
<Path Data="M 1,0 L5,0 A 2,2 90 0 1 7,2 L7,6 z" Fill="{StaticResource ValidationBrush5}" Margin="0,3,0,0"/>
<Path Data="M 0,0 L2,0 L 7,5 L7,7" Fill="{StaticResource BlankBackgroundBrush}" Margin="0,3,0,0"/>
</Grid>
</Border>
</Grid>
</Grid>
<ContentPresenter x:Name="contentPresenter" ContentTemplate="{TemplateBinding ContentTemplate}" Content="{TemplateBinding Content}" HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" Margin="{TemplateBinding Padding}" VerticalAlignment="{TemplateBinding VerticalContentAlignment}"/>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
Updated my question with the solution, posting again so I can mark it as answered:
ANSWER:
1) Change the ItemsPanel template to your container:
<ListBox.ItemsPanel>
<ItemsPanelTemplate>
<Canvas Width="208"
Height="391" />
</ItemsPanelTemplate>
</ListBox.ItemsPanel>
2) Set the ItemsSource:
The trick here is that positioning/attached attributes only work on the direct children of the ListBox. In this case I am using Canvas.Top and Canvas.Left. The solution is to wrap each Item in an additional ListBoxItem and apply those attributes on the ListBoxItem. (This will happen by default if you dont anyway).
<ListBox>
<ListBoxItem Canvas.Left="10" Canvas.Top="5">
<Path Data="..." Height="200" Width="200" Fill="Black" />
</ListBoxItem>
</ListBox>