Можете ли вы иметь параметризованный стиль в WPF? - PullRequest
0 голосов
/ 24 мая 2018

Я пытаюсь найти решение для повторного использования кода в XAML для в WPF: у меня есть 3 кнопки, которые имеют очень похожие стили, с той лишь разницей, что BorderThickness.Все они имеют набор триггеров стилей, который, если пользователь наводит на них мышь, BorderThickness устанавливается на 1.

<Button Width="50" Height="50" BorderBrush="#66CCFF" >
  <Button.Style>
    <Style TargetType="{x:Type Button}">
      <Setter Property="BorderThickness" Value="0,0,0,1" />
      <Style.Triggers>
        <Trigger Property="IsMouseOver" Value="True">
          <Setter Property="BorderThickness" Value="1"/>
        </Trigger>
      </Style.Triggers>
      </Style>
  </Button.Style>
  <Image Margin="12" Source="picture1.png"/>
</Button>

<Button Width="50" Height="50" BorderBrush="#66CCFF">
  <Button.Style>
    <Style TargetType="{x:Type Button}">
      <Setter Property="BorderThickness" Value="0,1,0,1" />
      <Style.Triggers>
        <Trigger Property="IsMouseOver" Value="True">
          <Setter Property="BorderThickness" Value="1"/>
        </Trigger>
      </Style.Triggers>
      </Style>
  </Button.Style>
  <Image Margin="12" Source="picture2.png"/>
</Button>

<Button Width="50" Height="50"BorderBrush="#66CCFF">
  <Button.Style>
    <Style TargetType="{x:Type Button}">
      <Setter Property="BorderThickness" Value="1,0,1,1" />
      <Style.Triggers>
        <Trigger Property="IsMouseOver" Value="True">
          <Setter Property="BorderThickness" Value="1"/>
        </Trigger>
      </Style.Triggers>
    </Style>
  </Button.Style>
  <Image Margin="12" Source="picture3.png"/>
</Button>

Поскольку стили практически идентичны, кроме BorderThickness, который применяется, когда IsMouseOverfalse Я хотел бы удалить дубликаты кода и иметь какой-то стиль в ResourceDictionary, где я могу указать начальный BorderThickness в качестве параметра (или что-то в том же духе), а остальное - то же самое.

Я пытался переместить часть BorderThickness="p,q,r,s" в тег <Button ...>, но при наведении указателя мыши стиль не применяется (я предполагаю, что между ними есть иерархия).

Ответы [ 2 ]

0 голосов
/ 24 мая 2018

Вы можете использовать анимацию, поскольку она имеет более высокий приоритет, чем локальное значение: https://docs.microsoft.com/en-us/dotnet/framework/wpf/advanced/dependency-property-value-precedence

<Style TargetType="Button">
    <Style.Triggers>
        <Trigger Property="IsMouseOver" Value="True">
            <Trigger.EnterActions>
                <BeginStoryboard x:Name="BorderAnimation">
                    <Storyboard TargetProperty="BorderThickness">
                        <ThicknessAnimation To="1" Duration="0"/>
                    </Storyboard>
                </BeginStoryboard>
            </Trigger.EnterActions>
            <Trigger.ExitActions>
                <RemoveStoryboard BeginStoryboardName="BorderAnimation"/>
            </Trigger.ExitActions>
        </Trigger>
    </Style.Triggers>
</Style>

<UniformGrid Columns="2" Rows="2" Width="100" Height="100">
    <Button BorderThickness="1 1 0 0"/>
    <Button BorderThickness="0 1 1 0"/>
    <Button BorderThickness="1 0 0 1"/>
    <Button BorderThickness="0 0 1 1"/>
</UniformGrid>
0 голосов
/ 24 мая 2018

Не уверен, что это то, к чему вы стремитесь, но общий подход заключается в создании определения стиля в app.xaml и использовании этих стилей в шаблоне или на вашей странице, он использует общий повторно используемый базовый стиль, пригодный для повторного использованиятолщина (здесь они используются только один раз) и наследование:

<Application.Resources>
    <ResourceDictionary>
        <!-- not really parameters, more like static values. -->
        <!-- these could be bind dynamically and -->
        <!-- controlled from code if you like. -->
        <!-- ps: i used different values. -->
        <Thickness x:Key="topThickness">10,0,0,0</Thickness>
        <Thickness x:Key="middleThickness">0,10,0,0</Thickness>
        <Thickness x:Key="bottomThickness">0,0,10,0</Thickness>

        <Style x:Key="buttonBase" TargetType="{x:Type Button}">
            <Setter Property="Width" Value="50" />
            <Setter Property="Height" Value="50" />
            <Setter Property="BorderBrush" Value="#66CCFF" />
            <Style.Triggers>
                <Trigger Property="IsMouseOver" Value="True">
                    <Setter Property="BorderThickness" Value="1"/>
                </Trigger>
            </Style.Triggers>
        </Style>

        <Style x:Key="buttonTop" 
               BasedOn="{StaticResource buttonBase}" 
               TargetType="{x:Type Button}">
            <Setter Property="BorderThickness" 
                    Value="{StaticResource topThickness}" />
        </Style>

        <Style x:Key="buttonMiddle" 
               BasedOn="{StaticResource buttonBase}" 
               TargetType="{x:Type Button}">
            <Setter Property="BorderThickness" 
                    Value="{StaticResource middleThickness}" />
        </Style>

        <Style x:Key="buttonBottom" 
               BasedOn="{StaticResource buttonBase}" 
               TargetType="{x:Type Button}">
            <Setter Property="BorderThickness" 
                    Value="{StaticResource bottomThickness}" />
        </Style>
    </ResourceDictionary>
</Application.Resources>

И в вашем окне: обратите внимание, что фактическое оформление контролируется в словаре ресурсов

<Button Style="{StaticResource buttonTop}" >
    <Image Margin="12" Source="picture1.png"/>
</Button>
<Button Style="{StaticResource buttonMiddle}" >
   <Image Margin="12" Source="picture1.png"/>
</Button>
<Button Style="{StaticResource buttonBottom}" >
    <Image Margin="12" Source="picture1.png"/>
</Button>
...