Wpf 如何使用一个样式引用设置一组(嵌套)图元的样式

Wpf 如何使用一个样式引用设置一组(嵌套)图元的样式,wpf,xaml,Wpf,Xaml,我想知道是否有一种简单的(我相信每件事都有一个复杂的解决方法)方法来设置一组潜在嵌套元素的样式,同时在XAML/WPF中只引用父元素级别上的一种样式 在HTML/CSS中,可以执行以下操作: <div class="levels"><!--1st level; only reference to the style--> <div><!--2nd level--> <div></div><!--3rd le

我想知道是否有一种简单的(我相信每件事都有一个复杂的解决方法)方法来设置一组潜在嵌套元素的样式,同时在XAML/WPF中只引用父元素级别上的一种样式

在HTML/CSS中,可以执行以下操作:

<div class="levels"><!--1st level; only reference to the style-->
  <div><!--2nd level-->
    <div></div><!--3rd level-->
  </div>
  <div></div><!--2nd level-->
</div>
这使得在父元素上只引用一次样式“levels”成为可能,然后再也不用担心引用了,因此当稍后在父元素下添加新元素时(在xaml中或在代码中动态添加),您不需要记住也要将“class=levelx”添加到新元素中

在XAML/WPF中是否也可以这样做?BasedOn属性似乎不是我想要的,因为:a)我不是在寻找属性继承,b)除非新样式有一个已定义的x:Key,否则它将应用于给定TargetType的所有元素,如果有,那么您需要再次在给定元素上引用它(
style=“{static resource levelx}”
)<代码>很遗憾,它不起作用

那么,设计这样一组元素的正确方式是什么?在我看来,在每个嵌套元素上引用特定的样式似乎是不必要的混乱

这是一个元素结构的具体例子,但我认为这是许多不同情况的一个普遍问题:

<Grid Style="{StaticResource Levels}"><!--1st level-->
    <Grid><!--2nd level-->
        <Grid></Grid><!--3rd level-->
        <Image Source="/Resources/xxx.png"/><!--3rd level-->
    </Grid>
    <Grid><!--2nd level-->
        <Grid></Grid><!--3rd level-->
        <Image Source="/Resources/yyy.png" x:Name="yyy"/><!--3rd level-->
    </Grid>
    <Grid><!--2nd level-->
        <Image Source="/Resources/zzz.png"/><!--3rd level-->
    </Grid>
</Grid>


这可能是重复的,但我找不到答案。

你的意思是这样的吗

<Grid Margin="20">
  <Grid.Resources>
  <Style TargetType="Grid">
  <Setter Property="Background" Value="Blue"></Setter>
  </Style>
  </Grid.Resources>
  <Grid.RowDefinitions>
  <RowDefinition Height="Auto"/>
  <RowDefinition Height="Auto"/>
  <RowDefinition Height="Auto"/>
  </Grid.RowDefinitions>
    <Grid Margin="20" Height="20" Grid.Row="0">
    </Grid>
    <Grid Margin="20" Height="20" Grid.Row="1" Background="Yellow">
    </Grid>
    <Grid Margin="20" Height="20" Grid.Row="2">
    </Grid>
</Grid>

您想要的可能并不完全可能。尤其是氮水平。像这样的东西会在两个层次上给你想要的行为

内容

    <Grid Style="{StaticResource Levels}">
        <Grid VerticalAlignment="Top" Margin="20 20 0 0" Height="60">
            <Grid Height="40" VerticalAlignment="Center">
                <Grid Height="20" VerticalAlignment="Center"></Grid>
                <Label></Label>
            </Grid>
        </Grid>
        <Grid VerticalAlignment="Top" Margin="20 100 0 0" Height="60">
            <Grid Height="40" VerticalAlignment="Center">
                <Grid Height="20" VerticalAlignment="Center"></Grid>
            </Grid>
        </Grid>
        <Grid VerticalAlignment="Top" Margin="20 180 0 0" Height="60">
            <Grid Height="40" VerticalAlignment="Center">
                <Grid Height="20" VerticalAlignment="Center"></Grid>
            </Grid>
        </Grid>
    </Grid>       

样式定义

  <Style x:Key="Levels" TargetType="Grid">
        <Setter Property="Background" Value="Blue"></Setter>
        <Setter Property="Width" Value="400"></Setter>
        <Style.Resources>
            <Style TargetType="Grid">
                <Setter Property="Grid.Background" Value="Purple"/>
                <Setter Property="Width" Value="200"></Setter>
                <Style.Resources>
                    <Style TargetType="Grid">
                        <Setter Property="Background" Value="Yellow"></Setter>
                        <Style.Resources>
                            <Style TargetType="Grid">
                                <Setter Property="Background" Value="Tomato"></Setter>
                            </Style>
                            <Style TargetType="Label">
                                <Setter Property="Height" Value="20"/>
                                <Setter Property="Width" Value="20"/>
                                <Setter Property="Background" Value="Azure"/>
                            </Style>
                        </Style.Resources>
                    </Style>
                </Style.Resources>
            </Style>
        </Style.Resources>
    </Style>


您希望在嵌套元素之间共享什么类型的属性?比如宽度、高度、边距等等?可能只有我一个人,但您的XAML示例并没有完全显示您希望避免的属性重复。你能详细说明一下你想缩小的范围吗?@MichaelThePotato是的,就是这样。例如,我希望父网格具有红色背景,而第二层上的任何嵌套网格具有绿色背景,第三层上的任何网格具有黄色背景或第三层上的任何图像(仅表示在第二层网格下)具有一定的高度/宽度等,而不必为这些元素中的每一个指定对样式的引用。就像示例中的CSS一样。您对“级别”的确切定义是什么?我假设父网格是第一层,您是说所有直接子网格都是第二层吗?或者你的意思是拥有XXX图像的是第二级,拥有YYY图像的是第三级,依此类推?@MichaelThePotato我在我的帖子中编辑了这个例子。包装网格是第一层,包含图像的网格是第二层,第二层网格包含的所有元素是第三层(现在添加了第三层网格)。刚刚看到您的编辑。感谢您的澄清,但我很遗憾地通知您,据我所知,XAML中不存在您希望的简单方式的相对样式应用程序。谢谢您的回答。我可能错了,但我不认为这是我要寻找的,因为:a)我想在父元素上引用一种样式;更重要的是b)这是否能让我对各种元素(网格、图像、按钮……)的第三/第四级进行风格设计?我不确定你所指的风格到底是什么意思。您可以在该级别拥有多个资源,每个元素类型对应一个资源。您还可以尝试使用一些引用的键x:Key来引用其中一个元素,稍后再引用它。通过“引用样式”,我的意思是指向它,例如:
style=“{Static resource MyStyle}”
——但这并不太重要,因为您的解决方案只是引用样式的内联等价物。这里真正的问题是,我相信,通过定义TargetType=“grid”,您可以设置网格中所有网格的属性以及网格本身,但我希望能够在每个级别上为网格设置不同的样式。就像CSS一样。你会如何为第三层/第四层的所有网格设置不同的高度/宽度?没有pm,所以:我不会接受你的回答,因为它似乎没有增加我目前的知识,似乎没有提供我正在寻找的实际解决方案,但随后的行为让我惊讶,感谢你,我想我能够找到一个解决方案(看起来像是黑客,但它是有效的)。我不想剥夺你的正确答案,所以如果你愿意根据以下内容修改你的答案:,我很乐意接受它作为正确答案。太好了;)这似乎正是我所寻找的,需要多少级别就有多少级别。非常感谢。
  <Style x:Key="Levels" TargetType="Grid">
        <Setter Property="Background" Value="Blue"></Setter>
        <Setter Property="Width" Value="400"></Setter>
        <Style.Resources>
            <Style TargetType="Grid">
                <Setter Property="Grid.Background" Value="Purple"/>
                <Setter Property="Width" Value="200"></Setter>
                <Style.Resources>
                    <Style TargetType="Grid">
                        <Setter Property="Background" Value="Yellow"></Setter>
                        <Style.Resources>
                            <Style TargetType="Grid">
                                <Setter Property="Background" Value="Tomato"></Setter>
                            </Style>
                            <Style TargetType="Label">
                                <Setter Property="Height" Value="20"/>
                                <Setter Property="Width" Value="20"/>
                                <Setter Property="Background" Value="Azure"/>
                            </Style>
                        </Style.Resources>
                    </Style>
                </Style.Resources>
            </Style>
        </Style.Resources>
    </Style>