如何在 UWP 中使用资源字典中的路径数据

How to use a path data from a resource dictionary in UWP

这是微不足道的事情,但它不起作用。

我有这样的东西(在它自己的文件夹里)

<ResourceDictionary>
    <Path x:Key="Test"
          Stroke="Black"
          Fill="Gray" 
          Data="M 10,100 C 10,300 300,-200 300,100" />
</ResourceDictionary>

现在我想用它

<Page>
    <Page.Resources>
        <ResourceDictionary>
            <ResourceDictionary.MergeDictionaries>
                <ResourceDictionary Source="MyFolder/MyResourceDictionary.xaml/>
            </ResourceDictionary.MergeDictionaries>
        </ResourceDictionary>
    </Page.Resources>
    <ContentPresenter Content="{StaticResource Test}"/>
<Page/>

这会抛出异常,但我不明白为什么。在 wpf 中完全相同的场景工作正常。

这个解决方案怎么样?

声明你的GeometryData

<x:String x:Key="TestPathGeomerty">M 10,100 C 10,300 300,-200 300,100</x:String>

并使用 Path,而不是 ContentPresenter

<Path Data="{StaticResource TestPathGeomerty}"
      Fill="Red"/>

在 WPF 中,您可以在多个控件中共享同一个实例。不幸的是,这在 UWP 中是不可能的。

保证在 UWP 中工作的唯一解决方案是在包含图标的资源中定义一个 DataTemplate。

使用PathIcon 代替Path 也更好。 PathIcon 使用将从您的父控件继承的前景 属性。

下面是一个示例,说明如何为自动缩放的图标共享数据路径(通过使用 Viewbox)。

<Page.Resources>
    <DataTemplate x:Key="MagnifyingGlassPathIconCT">
        <Viewbox Stretch="Uniform">
            <PathIcon Data="M44,12 C32,12 22,22 22,34 22,46 32,56 44,56 56,56 66,46 66,34 66,22 56,12 44,12z M44,0 C63,0 78,15 78,34 78,53 63,68 44,68 40,68 36.5,67.5 33,66 L32.5,66 14,90 0,79.5 18,55.5 17,55 C13,49 10,42 10,34 10,15 25,0 44,0z" />
        </Viewbox>
    </DataTemplate>
</Page.Resources>

<StackPanel Padding="40" HorizontalAlignment="Left">
    <!--  Plain icon  -->
    <ContentPresenter
        Width="40"
        Height="40"
        ContentTemplate="{StaticResource MagnifyingGlassPathIconCT}"
        Foreground="Purple" />
    <!--  Icon with a border  -->
    <Border
        Width="40" Padding="7"
        Height="40"
        BorderBrush="Black"
        BorderThickness="2">
        <ContentPresenter ContentTemplate="{StaticResource MagnifyingGlassPathIconCT}" Foreground="Red" />
    </Border>
    <!--  Icon in a normal Button  -->
    <Button
        Width="40"
        Height="40"
        ContentTemplate="{StaticResource MagnifyingGlassPathIconCT}"
        Foreground="RoyalBlue" />
    <!--  Icon in an AppBarButton  -->
    <AppBarButton
        Width="40"
        ContentTemplate="{StaticResource MagnifyingGlassPathIconCT}"
        Foreground="Black"
        Label="Search" />
</StackPanel>

对于允许您在样式中定义它的解决方案,请尝试像这样编写附加的 属性:

    public static string GetPathData(DependencyObject obj)
    {
        return (string)obj.GetValue(PathDataProperty);
    }

    public static void SetPathData(DependencyObject obj, string value)
    {
        obj.SetValue(PathDataProperty, value);
    }

    public static readonly DependencyProperty PathDataProperty =
        DependencyProperty.RegisterAttached("PathData", typeof(string), typeof(ElementExtensions), new PropertyMetadata(null, (d, e) =>
        {
            if (d is Path path)
            {
                Binding b = new Binding { Source = e.NewValue };
                path.SetBinding(Path.DataProperty, b);
            }
        }));

现在您可以像这样定义样式了:

<Style x:Key="BasePathStyle" TargetType="Path">
    <Setter Property="e:ElementExtensions.PathData" Value="M 10,100 C 10,300 300,-200 300,100" />
</Style>

然后像这样使用它:

<Path Style="{StaticResource BasePathStyle}" />

Path.Data 属性 是 Geometry 类型,因此将其定义为 Geometry 而不是 string

<Geometry x:Key="TestPathGeomerty">M 10,100 C 10,300 300,-200 300,100</Geometry>

<Path Data="{StaticResource TestPathGeomerty}"
      Fill="Red"/>