I'm currently on the design of my application (WPF), and I'm trying to change the design of the IsSelected of DatagridRow.
The XAML :
<Style TargetType="DataGridRow" BasedOn="{StaticResource {x:Type DataGridRow}}">
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Foreground" Value="{StaticResource ForegroundSelectedRow}"/>
<Setter Property="Background" Value="{StaticResource BackgroundSelectedRow}"/>
</Trigger>
</Style.Triggers>
</Style>
This code is working when I've the focus on my application, but when I click out of the view with the DataGrid, I lose the Foreground (it takes another color) but the Background is still up with the same...
I don't understand how just one can work, but not the other... Someone knows why ?
EDIT 1 :
I don't have any DataGrid.Resources. I set all my style in the App.xaml with this :
<Style x:Key="DataGridStyle" TargetType="DataGrid" BasedOn="{StaticResource {x:Type DataGrid}}">
<Setter Property="AlternationCount" Value="2"/>
<Setter Property="AutoGenerateColumns" Value="False"/>
<Setter Property="IsReadOnly" Value="True"/>
<Setter Property="CanUserSortColumns" Value="True"/>
<Setter Property="CanUserAddRows" Value="False"/>
</Style>
And I bind it to my DataGrid
<DataGrid ItemsSource="{Binding Collects}" Style="{StaticResource DataGridStyle}" ColumnHeaderStyle="{StaticResource DGHeaderMargin}"/>
You can change TargedType to DataGridCell instead DataGridRow (WPF 4.0)
<DataGrid.Resources>
<Style TargetType="{x:Type dg:DataGridCell}">
<Style.Triggers>
<Trigger Property="dg:DataGridCell.IsSelected" Value="True">
<Setter Property="Foreground" Value="{StaticResource ForegroundSelectedRow}"/>
<Setter Property="Background" Value="{StaticResource BackgroundSelectedRow}"/>
</Trigger>
</Style.Triggers>
</Style>
solution 2
<DataGrid.Resources>
<Style TargetType="DataGridRow">
<Style.Resources>
<SolidColorBrush x:Key="{x:Static SystemColors.HighlightBrushKey}" Color="Red"/>
</Style.Resources>
</Style>
</DataGrid.Resources>
Thanks to M. Wiśnicki, I figured out !
If you want to have a properly design, you have to apply style on DataGridRow and DataGridCell, like this :
<Style TargetType="DataGridCell" BasedOn="{StaticResource {x:Type DataGridCell}}">
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Foreground" Value="{StaticResource ForegroundSelectedRow}"/>
</Trigger>
</Style.Triggers>
</Style>
<Style TargetType="DataGridRow" BasedOn="{StaticResource {x:Type DataGridRow}}">
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Background" Value="{StaticResource BackgroundSelectedRow}"/>
</Trigger>
</Style.Triggers>
</Style>
I hope it will help some others developers :)
Related
I am developing a WPF Application using Mahapps.Metro library.
There is a DataGrid where I want to use a ContextMenu on the added rows, for that I am defining this in datagrid resources
<DataGrid.Resources>
<ContextMenu x:Key="RowMenu"
DataContext="{Binding PlacementTarget.DataContext, RelativeSource={RelativeSource Self}}">
<MenuItem Header="Borrar detalle" Click="delete_Click" />
<MenuItem Header="Editar detalle" Click="edit_Click" />
</ContextMenu>
</DataGrid.Resources>
and adding that context menu in the rowstyle
<DataGrid.RowStyle>
<Style TargetType="DataGridRow" >
<Setter Property="ContextMenu" Value="{StaticResource RowMenu}" />
</Style>
</DataGrid.RowStyle>
The problem with this is that when user clicks on the row, it seems to disappear (the font color turns white).
I tried adding the following to the rowstyle but it does not seems to work.
<DataGrid.RowStyle>
<Style TargetType="DataGridRow" >
<Setter Property="ContextMenu" Value="{StaticResource RowMenu}" />
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="BorderBrush" Value="LightSkyBlue"/>
<Setter Property="Foreground" Value="Black"/>
<Setter Property="Background" Value="LightSkyBlue"/>
</Trigger>
<Trigger Property="IsMouseOver" Value="False">
<Setter Property="BorderBrush" Value="Transparent"/>
<Setter Property="Foreground" Value="Black"/>
<Setter Property="Background" Value="Transparent"/>
</Trigger>
<Trigger Property="IsSelected" Value="True">
<Setter Property="BorderBrush" Value="Transparent"/>
<Setter Property="Foreground" Value="Black"/>
<Setter Property="Background" Value="Transparent"/>
</Trigger>
</Style.Triggers>
</Style>
</DataGrid.RowStyle>
MY last option is to use the contextmenu in the grid instead rows, but I want to know if there is something I can do to make this work.
Hope you can help, thanks.
You should use based-on feature on your defined style:
<DataGrid.RowStyle>
<Style TargetType="DataGridRow" BasedOn="{StaticResource {x:Type DataGridRow}}">
<Setter Property="ContextMenu" Value="{StaticResource RowMenu}" />
</Style>
</DataGrid.RowStyle>
I have a TreeView bound to an ObservableCollection containing enum values:
public enum Categories
{
CatA, CatB, CatC, CatD
}
public ObservableCollection<Categories> CategoriesList = new ObservableCollection<Categories>();
foreach (Categories cat in (Categories[])Enum.GetValues(typeof(Categories)))
{
CategoriesList.Add(cat);
}
The TreeView is bound to CategoriesList:
tvCat.ItemsSource = CategoriesList;
The the XAML markup:
<TreeView x:Name="tvCat">
<TreeView.ItemContainerStyle>
<Style TargetType="{x:Type TreeViewItem}">
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="FontWeight" Value="Bold"/>
</Trigger>
</Style.Triggers>
</Style>
</TreeView.ItemContainerStyle>
</TreeView>
I am trying to figure out how to apply individual stying to TreeViewItem for each enum value, e.g. blue color for CatA, red color for CatB, may be an icon for CatC etc.
Thanks a lot for any help.
You can use DataTriggers to get the desired output.
<TreeView.ItemContainerStyle>
<Style TargetType="{x:Type TreeViewItem}">
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="FontWeight" Value="Bold"/>
</Trigger>
<DataTrigger Binding="{Binding}" Value="CatA">
<Setter Property="Foreground" Value="Blue" />
</DataTrigger>
<DataTrigger Binding="{Binding}" Value="CatB">
<Setter Property="Foreground" Value="Red" />
</DataTrigger>
</Style.Triggers>
</Style>
</TreeView.ItemContainerStyle>
EDIT
The above XAML is if you just want a different color for your Items. If you also want to have different content (e.g. an icon for CatC), then you'd have to set the ControlTemplate based on a DataTrigger.
Here is the XAML to achieve that.
<TreeView.Resources>
<ControlTemplate TargetType="TreeViewItem" x:Key="CatCTemplate">
<Image Source="icon.jpeg" Height="64" Width="64" />
</ControlTemplate>
</TreeView.Resources>
<TreeView.ItemContainerStyle>
<Style TargetType="{x:Type TreeViewItem}">
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="FontWeight" Value="Bold"/>
</Trigger>
<DataTrigger Binding="{Binding}" Value="CatA">
<Setter Property="Foreground" Value="Blue" />
</DataTrigger>
<DataTrigger Binding="{Binding}" Value="CatB">
<Setter Property="Foreground" Value="Red" />
</DataTrigger>
<DataTrigger Binding="{Binding}" Value="CatC">
<Setter Property="Template" Value="{StaticResource CatCTemplate}" />
</DataTrigger>
</Style.Triggers>
</Style>
</TreeView.ItemContainerStyle>
I am working in WPF with the MaterialDesign Toolkit and Dragablz.
I encountered a problem while trying to style a TabablzControl.
I already have style for the windows default TabControl and TabItem header, as shown in the picture:
http://i.imgur.com/2anl5rl.png
But when I change the default tabControl to TabablzControl, it turns into this:
http://i.imgur.com/bhaaMVy.png
Here are the window.resources:
<Style x:Key="mdTabControl" TargetType="TabControl">
<Setter Property="TextElement.Foreground" Value="{DynamicResource MaterialDesignBody}"/>
<Setter Property="Background" Value="{DynamicResource MaterialDesignPaper}"></Setter>
</Style>
<Style x:Key="mdTabHeader" TargetType="{x:Type TabItem}">
<Setter Property="Background" Value="{DynamicResource MaterialDesignPaper}"></Setter>
<Setter Property="Foreground" Value="{DynamicResource MaterialDesignBody}"></Setter>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type TabItem}">
<Grid>
<Border Name="Border" Margin="1,0,1,0" CornerRadius="3 3 0 0">
<ContentPresenter x:Name="ContentSite" VerticalAlignment="Center"
HorizontalAlignment="Center"
ContentSource="Header" Margin="10,2,10,2"
RecognizesAccessKey="True">
</ContentPresenter>
</Border>
</Grid>
<ControlTemplate.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Panel.ZIndex" Value="100" />
<Setter TargetName="Border" Property="Background" Value="{StaticResource SecondaryAccentBrush}" />
<Setter Property="Foreground" Value="{StaticResource SecondaryAccentForegroundBrush}"/>
</Trigger>
<Trigger Property="IsSelected" Value="False">
<Setter Property="Panel.ZIndex" Value="100" />
<Setter TargetName="Border" Property="Background" Value="{StaticResource PrimaryHueMidBrush}" />
<Setter Property="Foreground" Value="{StaticResource PrimaryHueMidForegroundBrush}"/>
</Trigger>
<Trigger Property="IsEnabled" Value="False">
<Setter TargetName="Border" Property="Background" Value="{StaticResource PrimaryHueDarkBrush}" />
<Setter Property="Foreground" Value="{StaticResource PrimaryHueDarkForegroundBrush}" />
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
The error appears when I change the mdTabControl style targetType to:
TargetType="dbz:TabablzControl"
I want to keep the style I set to the TabControl, but with the added functionality of the TabablzControl
Any help will be appreciated
First thing to note, which is a general WPF characteristic, you are not using style inheritance correctly.
As you are using Material Design with Dragablz, if you are restyling the tab control itself, you must inherit from the Material Design style in the Dragablz assembly using BasedOn:
<Style x:Key="mdTabControl" TargetType="TabControl" BasedOn="{StaticResource MaterialDesignTabablzControlStyle}">
<Setter Property="TextElement.Foreground" Value="{DynamicResource MaterialDesignBody}"/>
<Setter Property="Background" Value="{DynamicResource MaterialDesignPaper}"></Setter>
</Style>
Again, with the tab header itself, you need to inherit from the relevant style:
<Style x:Key="mdTabHeader" TargetType="{x:Type TabItem}" BasedOn="{StaticResource MaterialDesignDragableTabItemStyle}">
. . .
</Style>
Note, that (depending you your App.xaml setup) you probably need to make sure the correct resource dictionary is included in the same XAML file. For example a more complete XAML might be:
<Window.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="pack://application:,,,/Dragablz;component/Themes/materialdesign.xaml" />
</ResourceDictionary.MergedDictionaries>
<Style x:Key="NormalTabItemStyle" TargetType="{x:Type dragablz:DragablzItem}" BasedOn="{StaticResource MaterialDesignDragableTabItemStyle}">
<Setter Property="Width" Value="280" />
<Setter Property="Padding" Value="1" />
</Style>
. . .
</ResourceDictionary>
</Window.Resources>
Finally, as you are changing the TabItem style, you either need to the TabablzCOntrol style the correct style, or you could use it where you actually declare the TabablzControl itself:
<dragablz:TabablzControl ItemContainerStyle="{StaticResource mdTabHeader}" />
A good example of all this in action is in the SidePanels project in the demo solution at: https://github.com/ButchersBoy/DragablzSamplez
<Style TargetType="{x:Type dragablz:TabablzControl}" BasedOn="{StaticResource MaterialDesignTabablzControlStyle}"/>
I've tried to change style for mouseover event.
Here's my styles code:
<Window.Resources>
<Style x:Key="NavigationButton"
TargetType="{x:Type Button}">
<Setter Property="Background" Value="#295fa6"/>
<Setter Property="BorderBrush" Value="{x:Null}"/>
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="Background" Value="Red"/>
<Setter Property="BorderBrush" Value="{x:Null}"/>
</Trigger>
</Style.Triggers>
</Style>
</Window.Resources>
and I used it in that way:
<Button x:Name="test"
Grid.Column="0""
Style="{StaticResource NavigationButton}">
<Image Source="Assets/imaaa.png" />
</Button>
and mouseover still has default color
you need to modify the ControlTemplate. To remove the default behaviour on the Button.
<Style x:Key="NavigationButton"
TargetType="{x:Type Button}">
<Setter Property="Background" Value="#295fa6"/>
<Setter Property="BorderBrush" Value="{x:Null}"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type Button}">
<Border Background="#295fa6">
<ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="Background" Value="Red"/>
<Setter Property="BorderBrush" Value="{x:Null}"/>
</Trigger>
</Style.Triggers>
</Style>
I'm currently working with MVVM in WPF, I installed MahappsMetro in my project. I want to change the default DataGrid style, without losing all the properties of MetroDataGrid style (Style for DataGrid from MahappsMetro).
I simply want to change some Triggers as IsMouseOver and IsSelected, I tried doing this:
I defined this Style in App.xaml
<Style x:Key="TransparentDataGrid" TargetType="{x:Type DataGrid}" BasedOn="{StaticResource MetroDataGrid}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type DataGrid}">
<DataGrid>
<DataGrid.RowStyle>
<Style TargetType="{x:Type DataGridRow}">
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="Background" Value="Transparent" />
</Trigger>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Background" Value="Transparent" />
<Setter Property="Foreground" Value="Black" />
</Trigger>
</Style.Triggers>
</Style>
</DataGrid.RowStyle>
<DataGrid.CellStyle>
<Style TargetType="{x:Type DataGridCell}">
<Style.Triggers>
<Trigger Property="DataGridCell.IsSelected" Value="True">
<Setter Property="Background" Value="Transparent" />
<Setter Property="BorderBrush" Value="Transparent" />
<Setter Property="Foreground" Value="Black" />
</Trigger>
</Style.Triggers>
</Style>
</DataGrid.CellStyle>
</DataGrid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
And I bind this Style, where I need it
Style="{DynamicResource TransparentDataGrid}"
But I get the exception :
A first chance exception of type 'System.Windows.Markup.XamlParseException' occurred in PresentationFramework.dll
Also I tried :
I created the style in MainViewModel.xaml but I don't know how to bind this style to other views.
to derive from existing style for the controls you need to specify the type as the key in based on attribute
<Style x:Key="TransparentDataGrid" TargetType="{x:Type DataGrid}" BasedOn="{StaticResource {x:Type MetroDataGrid}}">
<Setter Property="Template">
<Setter.Value>
...
if above does not work then do prefix with correct namespace to MetroDataGrid eg mapp:MetroDataGrid where mapp points to MahappsMetro assembly
eg
<Application x:Class="CSharpWPF.App"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
StartupUri="MainWindow.xaml"
xmlns:mapp="clr-namespace:MahApps.Metro.Controls">
<Application.Resources>
<Style x:Key="TransparentDataGrid" TargetType="{x:Type DataGrid}" BasedOn="{StaticResource {x:Type mapp:MetroDataGrid}}">
<Setter Property="Template">
<Setter.Value>
...
</Application.Resources>
use the correct assembly above is just an example