0

Trying to learn a fair bit about s and I got stuck on a particular subject. I want my buttons edited in size and alignment using a pre made style I have. An example:

         <Button Style="{StaticResource ButtonFormat}">

        </Button>

The button has a style saved in App.Xaml the style is written like this:

 <Application.Resources>
    <Style TargetType="Button" x:Key="ButtonFormat">
        <Setter Property="Background" Value="#FF6E1400" />
        <Setter Property="Margin" Value="5,5,5,5" /> 
    </Style>
 <Application.Resources> 

Now, here is my dilemma:

I want to load another style that overwrites "ButtomFormat". I have been trying to experiment in VisualStatemanager to try and come up with the proper way of doing this but can't really find anything that explains enough for me on how to do it.

So in the visualstate such as below:

  <VisualState x:Name="BigView" >
                <VisualState.StateTriggers>
                    <AdaptiveTrigger MinWindowWidth="550" />
                </VisualState.StateTriggers>
                <VisualState.Setters>
                    <!--stuff goes here-->
                    <!--stuff goes here-->
                </VisualState.Setters>
            </VisualState>

I want to ooverwrite ButtonFormat with ButtonFormatBlue as such:

        <Style TargetType="Button" x:Key="ButtonFormatBlue ">
        <Setter Property="Background" Value="Blue" />
        <Setter Property="Margin" Value="5,5,5,5" />
    </Style>

I saw someone suggesting using C# instead of visualstatemanagers but I didn't properly understand that description, is it possible to load it from the visualstatetrigger as I want or am I looking at the wrong direction?

All aids are appreciated, thank you in advance!

Eilytres
  • 27
  • 3

2 Answers2

1

You cannot override a resource, but you can change the Button's style property.

You first have to give the button a name:

 <Button x:Name="MyButton" Style="{StaticResource ButtonFormat}">
 </Button>

And now you can use the VisualStateManager to change the Style property:

<VisualState x:Name="BigView">
    <VisualState.StateTriggers>
       <AdaptiveTrigger MinWindowWidth="550" />
    </VisualState.StateTriggers>
    <VisualState.Setters>
        <Setter Target="MyButton.Style" 
                Value="{StaticResource ButtonFormatBlue}" />
    </VisualState.Setters>
</VisualState>
Martin Zikmund
  • 38,440
  • 7
  • 70
  • 91
  • What if I have 5 buttons that I want to edit the same way? I mean if I have 5 buttons, and I want all of them to go blue when a certain width is reached, do I need to give each button a specific name and repeat this step 5 times? – Eilytres Jul 29 '16 at 06:20
  • I think this looks quite promising as a universal solution that will automatically replace the styles without you having to specify it manually :-) - http://dotnetbyexample.blogspot.cz/2016/01/using-style-replacing-behavior-for.html – Martin Zikmund Jul 29 '16 at 09:08
0

I saw someone suggesting using C# instead of visualstatemanagers but I didn't properly understand that description.

It means you can set a style to your Button manually in the code behind. For example, you can put your ButtonFormat and ButtonFormatBlue both in the App resource like this:

<Application.Resources>
    <Style TargetType="Button" x:Key="ButtonFormat">
        <Setter Property="Background" Value="#FF6E1400" />
        <Setter Property="Margin" Value="5,5,5,5" />
    </Style>
    <Style TargetType="Button" x:Key="ButtonFormatBlue">
        <Setter Property="Background" Value="Blue" />
        <Setter Property="Margin" Value="5,5,5,5" />
    </Style>
</Application.Resources>

Then your Button can be loaded with ButtonFormat style using StaticResource:

<Button x:Name="styleTestButton" Content="Style Sample" Style="{StaticResource ButtonFormat}"
        VerticalAlignment="Bottom" Click="styleTestButton_Click" />

In the Button click event for example, you can change your Button's style as follows:

private void styleTestButton_Click(object sender, RoutedEventArgs e)
{
    var ButtonFormatBlue = Application.Current.Resources.FirstOrDefault(r => r.Key.ToString() == "ButtonFormatBlue");
    styleTestButton.Style = ButtonFormatBlue.Value as Style;
}

Or you can totally define a new style in the code behind and set this style to Button using C# in the code behind:

private void styleTestButton_Click(object sender, RoutedEventArgs e)
{
    var dynamicStyle = new Style();
    dynamicStyle.TargetType = typeof(Button);
    dynamicStyle.Setters.Add(new Setter(BackgroundProperty, Colors.Blue));
    dynamicStyle.Setters.Add(new Setter(MarginProperty, new Thickness(5, 5, 5, 5)));
    styleTestButton.Style = dynamicStyle;
}

Need to know that as @MZetko said, we can't override a resource, this is why we created a new one.

is it possible to load it from the visualstatetrigger as I want or am I looking at the wrong direction?

Yes it's possible, but it's hard to tell whether you looked at the wrong direction, it depends on different scenarios. For example, if your UIElements are in the DataTemplate, then it doesn't work with StateTriggers, data binding is the best solution for this scenario. You can refer to the Remarks of VisualStateManager class, it shows perfect details of using VisualStateManager.

Grace Feng
  • 16,564
  • 2
  • 22
  • 45
  • What would be your recommendation if I have 10 buttons and they need resizing + color change at a certain width, just apply name to each and every one of them and go for it? – Eilytres Jul 29 '16 at 09:02
  • @Eilytres, using `VisualStateManager` with `AdaptiveTrigger`. – Grace Feng Jul 29 '16 at 09:05