1

To Change a Wpf-Material checkbox border color, it is needed to override it's resource as follow:

<Style TargetType="Checkbox" BasedOn="{StaticResource MaterialDesignCheckBox}">
    <Style.Resources>
        <SolidColorBrush x:Key="MaterialDesignCheckBoxOff" Color="Red" />
    </Style.Resources>
</Style>

This works and checkbox borders turn red. With Material Checkboxes this: <Setter Property="BorderBrush" Value="Red" /> does not work.

Problem is that I'm trying to apply this border property dynamically. So I created a custom component for checkbox where i added a boolean DependencyProperty called IsDirty. If IsDirty == true and the checkbox IsChecked, then i change the background (this works well). If the IsDirty == true and the checkbox is not IsChecked, then I would like to change the border color (as the background is transparent) in this case. I tried something as follow:

<Style TargetType="{x:Type local:CustomCheckbox}" x:Key="dirtyCustomCheckbox" BasedOn="{StaticResource MaterialDesignCheckBox}">
    <Style.Resources>
        <SolidColorBrush x:Key="MaterialDesignCheckBoxOff" Color="Red" />
    </Style.Resources>
</Style>

<Style TargetType="{x:Type local:CustomCheckbox}" BasedOn="{StaticResource MaterialDesignCheckBox}">
    <Style.Triggers>
        <MultiDataTrigger>
            <MultiDataTrigger.Conditions>
                <Condition Binding="{Binding IsDirty, RelativeSource={RelativeSource Self}}" Value="True" />
                <Condition Binding="{Binding IsChecked, RelativeSource={RelativeSource Self}}" Value="True" />
            </MultiDataTrigger.Conditions>
            <MultiDataTrigger.Setters>
                <Setter Property="Background" Value="Red" />
            </MultiDataTrigger.Setters>
        </MultiDataTrigger>
        <MultiDataTrigger>
            <MultiDataTrigger.Conditions>
                <Condition Binding="{Binding IsDirty, RelativeSource={RelativeSource Self}}" Value="True" />
                <Condition Binding="{Binding IsChecked, RelativeSource={RelativeSource Self}}" Value="False" />
            </MultiDataTrigger.Conditions>
            <MultiDataTrigger.Setters>
                <Setter Property="Style" Value="{StaticResource dirtyCustomCheckbox}" />
            </MultiDataTrigger.Setters>
        </MultiDataTrigger>
    </Style.Triggers>
</Style>

But i get this Exception: ArgumentException: Style object is not allowed to affect the Style property of the object to which it applies.

Any other idea on how I can achieve this?

nomadev
  • 162
  • 1
  • 12

1 Answers1

1

Any other idea on how I can achieve this?

You could add a resource that binds to the Tag property in the constructor of your custom control:

public CustomCheckbox()
{
    var brush = new SolidColorBrush();
    BindingOperations.SetBinding(brush, SolidColorBrush.ColorProperty, new Binding(nameof(Tag)) { Source = this, Mode = BindingMode.TwoWay });
    Resources.Add("MaterialDesignCheckBoxOff", brush);
}

Then you simply set the Tag property in the Style:

<Style TargetType="{x:Type local:CustomCheckbox}"
       BasedOn="{StaticResource MaterialDesignCheckBox}">
    <Style.Triggers>
        <MultiDataTrigger>
            <MultiDataTrigger.Conditions>
                <Condition Binding="{Binding IsDirty, RelativeSource={RelativeSource Self}}" Value="True" />
                <Condition Binding="{Binding IsChecked, RelativeSource={RelativeSource Self}}" Value="True" />
            </MultiDataTrigger.Conditions>
            <MultiDataTrigger.Setters>
                <Setter Property="Background" Value="Red" />
            </MultiDataTrigger.Setters>
        </MultiDataTrigger>
        <MultiDataTrigger>
            <MultiDataTrigger.Conditions>
                <Condition Binding="{Binding IsDirty, RelativeSource={RelativeSource Self}}" Value="True" />
                <Condition Binding="{Binding IsChecked, RelativeSource={RelativeSource Self}}" Value="False" />
            </MultiDataTrigger.Conditions>
            <MultiDataTrigger.Setters>
                <Setter Property="Tag" Value="Red" />
            </MultiDataTrigger.Setters>
        </MultiDataTrigger>
    </Style.Triggers>
</Style>
mm8
  • 163,881
  • 10
  • 57
  • 88
  • Thank you very much mm8! it works very well. Just a little fix: you need also to set the Tag property with a default value, otherwise you see the checkbox with no borders when not entering in the trigger. So after the – nomadev Apr 07 '20 at 14:15