绑定为资源

时间:2016-04-28 10:40:30

标签: wpf xaml wpf-controls resourcedictionary

我可以将Binding定义为Resource,然后将其重复使用不同的Controls属性吗?

示例:

绑定:

<Window.Resources>        
    <Binding x:Key="MyBinding" Path="MyProperty" Mode="TwoWay" />
</Window.Resources>

在XAML中重复使用:

<TextBox Text="{StaticResource MyBinding}" />

在声明Binding之后,我收到了错误:

  

&#34;名称&#39; InitializeComponent&#39;在当前不存在   上下文&#34;

有没有办法在不同的上下文中重用相同的Binding

2 个答案:

答案 0 :(得分:14)

直接回答您的问题是“是的,您可以将绑定定义为资源”。这里的问题是你如何使用它?一种可能性是创建一个扩展类,它将从资源中提取绑定并应用它:

public class BindingResourceExtension : StaticResourceExtension
{
    public BindingResourceExtension() : base() { }

    public BindingResourceExtension(object resourceKey) : base(resourceKey) { }

    public override object ProvideValue(IServiceProvider serviceProvider)
    {
        var binding = base.ProvideValue(serviceProvider) as BindingBase;
        if (binding != null)
            return binding.ProvideValue(serviceProvider);
        else
            return null; //or throw an exception
    }
}

用法示例:

<Window.Resources>
    <ResourceDictionary>
        <Binding x:Key="MyBinding" Path="MyProperty" Mode="TwoWay" />
    </ResourceDictionary>
</Window.Resources>

(...)

<TextBox Text="{ns:BindingResource MyBinding}" />

此解决方案是否可以用于<{strong> MultiBinding

是的,它可以:

<TextBlock>
    <TextBlock.Text>
        <MultiBinding StringFormat="First: {0}, Second: {1}">
            <Binding Path="SomeProperty" />
            <ns:BindingResource ResourceKey="MyBinding" />
        </MultiBinding>
    </TextBlock.Text>
</TextBlock>

但是有一个缺点 - 尽管一切都可以在运行时使用, XAML Designer 会抱怨BindingResourceExtension的类型不合适MultiBinding.Bindings 1}}集合。但是,幸运的是,有一个快速的解决方案 - 只需使用StaticResourceExtension代替!因此,在运行时功能相同的情况下,设计师将接受这一点:

<TextBlock>
    <TextBlock.Text>
        <MultiBinding StringFormat="First: {0}, Second: {1}">
            <Binding Path="SomeProperty" />
            <StaticResource ResourceKey="MyBinding" />
        </MultiBinding>
    </TextBlock.Text>
</TextBlock>

答案 1 :(得分:4)

以下两种方法可能无法完全满足您的需求:

<强> 1。使用自定义标记扩展

删除所有nullchecks等以保持简短。

if second_do.lower() == "market":

    print "You are now inside of the market place. It appears to be abandoned. The shelves are almost empty, however, you to manage find some salvagable goods, including peanut butter, beans, and crackers."
    goods = raw_input(">>> ")

    if goods.lower() == "collect":
        print "You have collected the food items. These will help you later on."
    if goods.lower() == "get":
        print "You have collected the food items. These will help you later on."
    if goods.lower() == "collect food":
        print "You have collected the food items. These will help you later on."
    if goods.lower() == "collect goods":
        print "You have collected the food items. These will help you later on."
    if goods.lower() == "get food":
        print "You have collected the food items. These will help you later on."
    if goods.lower() == "get goods":
        print "You have collected the food items. These will help you later on."

    after_market = raw_input("What's next?")

    if "mansion" in after_market:
        second_do = "mansion"
        # After this, the control drops to the next if-statement

if second_do.lower() == "mansion":
    print "You are now inside of the mansion."
using System;
using System.Windows;
using System.Windows.Data;
using System.Windows.Markup;

public class BindingDefinition
{
    public PropertyPath Path { get; set; }

    public BindingMode Mode { get; set; }
}

[MarkupExtensionReturnType(typeof(BindingExpression))]
public class ApplyBindingDefinition : MarkupExtension
{
    public BindingDefinition Definition { get; set; }

    public override object ProvideValue(IServiceProvider serviceProvider)
    {
        var binding = new Binding
        {
            Path = this.Definition.Path,
            Mode = this.Definition.Mode
        };
        return binding.ProvideValue(serviceProvider);
    }
}

<强> 2。使PropertyPath成为资源

可能或可能不足以满足您的需求。

<Window.Resources>
    <local:BindingDefinition x:Key="MyProperty"
                             Mode="TwoWay"
                             Path="MyProperty" />
</Window.Resources>
<TextBox>
    <TextBox.Text>
        <!--  using element style here as the parser chokes on parsing nested markupextensions  -->
        <local:ApplyBindingDefinition Definition="{StaticResource MyProperty}" />
    </TextBox.Text>
</TextBox>