I know how to extend a style in XAML, i.e. for a TextBlock:
BasedOn="{StaticResource {x:Type TextBlock}}"
But if the control has a prefix, it throws an exception:
BasedOn="{StaticResource {x:Type Foo:MyControl}}"
What is the right syntax?
I found the reason for the error in the Style itself.
Related
In a UserControl XAML file, I want to define a ListView based on the predefined style. So I write the following lines:
<ListView Grid.Column="2" SelectionMode="Single">
<ListView.ItemContainerStyle>
<Style
TargetType="{x:Type ListViewItem}"
BasedOn="{StaticResource {x:Type ListViewItem}}">
Though, for the BasedOn attribute, I get the error: The resource "{x:Type ListViewItem}" could not be resolved..
If I replace the ListViewItem word with ListBoxItem or TreeViewItem the compilation is successful, but at runtime it raises a System.InvalidOperationException exception, specifying that the BasedOn attribute needs a ListBoxItem.
If I remove that attribute, it works, but it has a weird look.
If you are using MahApps.Metro, you should base your Style on the MetroListViewItem resource:
<Style TargetType="{x:Type ListViewItem}"
BasedOn="{StaticResource MetroListViewItem}">
...
BasedOn is used for Style inheritance, so it should be pointing to another ListViewItem Style that you've previously defined, not a type.
<Style TargetType="{x:Type ListViewItem}"
BasedOn="{StaticResource MyListViewItemBaseStyle}">
I've got the following scenario
custom control library
<Style TargetType="{x:Type local:CustomControl}" x:Key="Default"> ... </Style>
<Style TargetType="{x:Type local:CustomControl}" BasedOn="{StaticResource Default}"> ... </Style>
application which references custom control library
<Style TargetType="{x:Type local:CustomControl}" BasedOn="{StaticResource Default}"> ... </Style>
for some reason the styles i am specifying in my app.xaml seem to have no effect. Could it be that the App.xaml is loaded prior to foreign generic.xaml contents? And if so - How does one fix that so global style overrides do work.
I know I'm a pervert, but I am very curious, is there a way to make custom controls to seek for it's base class style first, and then it's own.
Why I'm asking: I have some TreeView derived controls with custom item templates. I apply those templates, then I have a base style. Later I might apply some color palette. At the last step I have a problem. I need to apply 2 styles. PVStructuralTree is derived from TreeView it has some DependencyProperty DataTemplates that get inserted into resources in code.
PVStructuralTreeView
EmploeeTemplate
... more templates
Default style for PVStructuralTreeView:
<Style x:Key="DefaultPVStructuralTreeView" TargetType="{x:Type c:PVStructuralTreeView}" BasedOn="{StaticResource DefaultTreeView}">
<Setter Property="EmploeeTemplate"><!-- This get inserted inro Resources in code -->
<Setter.Value>
<DataTemplate DataType="{x:Type s:Emploee}">
...
</DataTemplate>
</Setter.Value>
</Setter>
... Lots of them here
</Style>
<Style TargetType="{x:Type c:PVStructuralTreeView}" BasedOn="{StaticResource DefaultPVStructuralTreeView}"/>
Default style for a TreeView (it's pretty big, so I won't post it here):
<Style TargetType="{x:Type TreeView}" BasedOn="{StaticResource DefaultTreeView}"/>
In color template.xaml file I'd like to have this + some magic to apply both styles at the same time (from Generic.xaml and themed one):
<Style x:Key="ThemedTreeView" TargetType="{x:Type TreeView}" BasedOn="{StaticResource DefaultTreeView}">
...
</Style>
<Style TargetType="{x:Type c:PVStructuralTreeView}" BasedOn="{StaticResource ThemedTreeView}"/>
But it just overwrites generic.xaml styles. I want it to add to it.
Now I'm doing this way:
<Style x:Key="ThemedPVStructuralTreeView" TargetType="{x:Type c:PVStructuralTreeView}" BasedOn="{StaticResource DefaultPVStructuralTreeView}">
... CopyPaste from ThemedTreeView ...
</Style>
<Style TargetType="{x:Type c:PVStructuralTreeView}" BasedOn="{StaticResource ThemedPVStructuralTreeView}"/>
Does anyone knows the way how to reuse the ThemedTreeView style here?
You can base a Style on Another (one only!) Style using the BasedOn property and override specific properties, but you cannot base a DataTemplate or a ControlTemplate on another template. This is not supported. A template must be defined as a whole:
WPF: Is there a way to override part of a ControlTemplate without redefining the whole style?
From here it seems possible to create a custom implicit style for WpfToolkit IntegerUpDown control.
<Style TargetType="xctk:IntegerUpDown"
BasedOn="{StaticResource {x:Type xctk:IntegerUpDown}}">
I cannot seem to create a custom implicit style for WpfToolkit WatermarkTextBox though. I have tried this but it does not compile:
<ResourceDictionary xmlns:xctk="http://schemas.xceed.com/wpf/xaml/toolkit" ...>
<Style TargetType="xctk:WatermarkTextBox"
BasedOn="{StaticResource {x:Type xctk:WatermarkTextBox}}">...</Style>
Produces error:
Failed to create a 'TargetType' from the text 'xctk:WatermarkTextBox'
Also tried:
<Style TargetType="{x:Type Control}" BasedOn="{StaticResource BaseStyle}" x:Key="WatermarkBaseStyle">
<Setter Property="FontSize" Value="24" />
</Style>
<Style TargetType="{x:Type xctk:WatermarkTextBox}" BasedOn="{StaticResource WatermarkBaseStyle}"/>
Produces error:
'Failed to create a 'Type' from the text 'xctk:WatermarkTextBox'.'
The following works for me:
<Style TargetType="{x:Type xctk:WatermarkTextBox}"
BasedOn="{StaticResource {x:Type xctk:WatermarkTextBox}}">
Try using the x:Type markup extension in both the TargetType and BasedOn properties.
I have some locally defined styles within Window.Resources. I have some styles for a TextBlock, TextBox, CheckBox and RadioButton. These are supposed to be applied to all controls in the window, so I haven't provided a value for x:Key. I would like them to inherit from a style targeting FrameworkElement. So I have something like:
<Style TargetType="{x:Type RadioButton}">
...
</Style>
<Style TargetType="{x:Type TextBlock}">
...
</Style>
<Style TargetType="{x:Type TextBox}">
...
</Style>
<Style TargetType="{x:Type CheckBox}">
...
</Style>
<Style x:Key="TriggerBase" TargetType="{x:Type FrameworkElement}">
<Style.Triggers>
<Trigger Property="UIElement.IsMouseOver" Value="True">
...
</Trigger>
</Style.Triggers>
</Style>
My problem is that I am unable to set the BasedOn property to inherit from my TriggerBase style. After looking at similar questions, such as this and this, I still cannot get it working. These answers suggest you need to specify the TargetType on your base style, which I have done.
I thought maybe the Styles have to target the exact same type, but after digging around on MSDN I found that wasn't the problem:
If you create a style with a TargetType property and base it on another style that also defines a TargetType property, the target type of the derived style must be the same as or be derived from the type of the base style.
If I set BasedOn like BasedOn="{DynamicResource TriggerBase}", it can find my TriggerBase, but I get an error stating:
A 'DynamicResourceExtension' cannot be set on the 'BasedOn' property
of type 'Style'. A 'DynamicResourceExtension' can only be set on a
DependencyProperty of a DependencyObject.
If I try BasedOn="{StaticResource TriggerBase}", I get an error that it cannot find TriggerBase. One of the linked answers above showed using StaticResource like BasedOn="{StaticResource {x:Type FrameworkElement}, but it still cannot resolve the style.
How can I inherit from the TriggerBase style? I'm targeting .NET 4.5.
You are correct and you can base your styles on FrameworkElement style just need to move
<Style x:Key="TriggerBase" TargetType="{x:Type FrameworkElement}">
</Style>
to the top and then
<Style TargetType="{x:Type RadioButton}" BasedOn="{StaticResource TriggerBase}">
will work