无法解析样式、ResourceDictionary、UserControl

Cannot Resolve Style, ResourceDictionary, UserControl

这是迄今为止我在从事 WPF 工作的一年中遇到的最令人困惑的问题。对于使用 WPF 时间较长的人来说,问题的两个组成部分可能更能说明问题:

  1. UserControl 中,我的 ResourceDictionary 元素抱怨它需要 Key 属性。
  2. 当我定义 Key 属性并尝试在设计时从 XAML 访问样式时,Intellisense(和编译器)不知道我导入的 [=15= 中定义的样式].
  3. 我正在尝试将样式应用于 MenuItem
  4. 上的 .ItemTemplate

这是我的 UserControl XAML 资源声明,注意 x:Key 属性

<UserControl.Resources>
    <ResourceDictionary x:Key="HeaderViewStyles">
        <ResourceDictionary.MergedDictionaries>
            <ResourceDictionary Source="../../Styles/Controls/HeaderViewStyles.xaml"/>
        </ResourceDictionary.MergedDictionaries>
    </ResourceDictionary>
</UserControl.Resources>

这里是 ResourceDictionary 的部分实现,定义了我希望在 MenuItem 上使用的样式。

x:Class="Styles.Controls.HeaderViewStyles">

<Style x:Key="DarkMenuItem" TargetType="{x:Type MenuItem}">
    <Setter Property="Foreground" Value="{Binding Path=Foreground, RelativeSource={RelativeSource AncestorType={x:Type Menu}}}"/>
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type MenuItem}">

 <!---

以上样式本身可能有问题;但是,我感兴趣的是 为什么我无法在设计时访问样式

这是我应用样式的尝试(发布以获取完整信息):

     <Menu>
        <MenuItem ItemsSource="{Binding ContextMenuItemViewModels}">
            <MenuItem.Icon>
                <Image Source="../../Resources/menu.png"/>
            </MenuItem.Icon>
            <MenuItem.ItemTemplate>
                <DataTemplate DataType="{x:Type controlViewModels:ContextMenuItemViewModel}">
                    <MenuItem Style="{DynamicResource DarkMenuItem}"
                        Header="{Binding MenuHeaderText}"
                        Command="{Binding MenuItemClickedCommand}"/>
                </DataTemplate>
            </MenuItem.ItemTemplate>
        </MenuItem>
    </Menu>

我相信这是多种因素的结合;但是,我显然缺乏一些知识。我错过了什么或没有做什么?我尝试了各种组合,但仍然无法选择风格。

编辑

想要了解更多信息的朋友,这里是我的控件XAML:

<UserControl x:Class="Views.Controls.HeaderView"
         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
         xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
         xmlns:controlViewModels="clr-namespace:ViewModels.Controls"
         xmlns:controlViews="clr-namespace:Views.Controls"
         xmlns:converters="clr-namespace:Converters"
         VerticalContentAlignment="Stretch"
         Background="#4C4C4C">

<UserControl.Resources>
    <converters:SyncStateToVisibilityConverter x:Key="SyncStateToVisibilityConverter"/>
    <ResourceDictionary x:Key="HeaderViewStyles">
        <ResourceDictionary.MergedDictionaries>
            <ResourceDictionary Source="../../Styles/Controls/HeaderViewStyles.xaml"/>
        </ResourceDictionary.MergedDictionaries>
    </ResourceDictionary>
</UserControl.Resources>

<Grid>
    <Grid.RowDefinitions>
        <RowDefinition Height="*"/>
        <RowDefinition Height="6"/>
    </Grid.RowDefinitions>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="60"/>
        <ColumnDefinition Width="*"/>
        <ColumnDefinition Width="110"/>
    </Grid.ColumnDefinitions>

    <Button Background="#4C4C4C" Margin="20,0,0,0" 
            VerticalAlignment="Center" 
            Command="{Binding StatusButtonClickedCommand}">
        <Image >
            <Image.Style>
                <Style TargetType="{x:Type Image}">
                    <Style.Triggers>
                        <Trigger Property="IsMouseOver" Value="False">
                            <Setter Property="Source" Value="{Binding StatusIconLocation}"/>
                        </Trigger>
                        <Trigger Property="IsMouseOver" Value="True">
                            <Setter Property="Source" Value="{Binding StatusIconLocationHover}"/>
                        </Trigger>
                    </Style.Triggers>
                </Style>
            </Image.Style>
        </Image>
    </Button>

    <StackPanel Grid.Column="1" Grid.ColumnSpan="2" Orientation="Vertical">
        <TextBlock></TextBlock>
        <TextBlock></TextBlock>
    </StackPanel>

    <Menu>
        <MenuItem ItemsSource="{Binding ContextMenuItemViewModels}">
            <MenuItem.Icon>
                <Image Source="../../Resources/menu.png"/>
            </MenuItem.Icon>
            <MenuItem.ItemTemplate>
                <DataTemplate DataType="{x:Type controlViewModels:ContextMenuItemViewModel}">
                    <MenuItem Style="{DynamicResource DarkMenuItem}"
                        Header="{Binding MenuHeaderText}"
                        Command="{Binding MenuItemClickedCommand}"/>
                </DataTemplate>
            </MenuItem.ItemTemplate>
        </MenuItem>
    </Menu>

    <ProgressBar Grid.Row="1" 
                Grid.ColumnSpan="3" 
                Value="{Binding PercentageSynced}"
                Visibility="{Binding CurrentSyncSystemStatus, 
                            Converter={StaticResource SyncStateToVisibilityConverter}, 
                            ConverterParameter=Syncing, 
                            FallbackValue=Collapsed}"/>
</Grid>

您需要将转换器移到资源字典中,并删除 x:Key,如下所示:

<UserControl.Resources>
    <ResourceDictionary>
        <ResourceDictionary.MergedDictionaries>
            <ResourceDictionary Source="../../Styles/Controls/HeaderViewStyles.xaml"/>
        </ResourceDictionary.MergedDictionaries>
        <converters:SyncStateToVisibilityConverter x:Key="SyncStateToVisibilityConverter"/>
    </ResourceDictionary>
</UserControl.Resources>

如果您将没有键的 ResourceDictionary 作为 UserControl.Resources 的根 - 这意味着:

userControl.Resources = new ResourceDictionary();

所以你必须把所有其他资源放在那个字典里面,而不是放在外面。

你原来的xaml(加上x:Key)大致意思是:

userControl.Resources.Add("SyncStateToVisibilityConverter", new YourConverter());
userControl.Resources.Add("HeaderViewStyles", new ResourceDictionary(...));

所以,不是您所期望的那样。