Ответ 1
Прямой ответ на ваш вопрос: "да, вы можете определить привязку как ресурс". Проблема здесь в том, как вы тогда ее используете? Одна из возможностей - создать класс расширения, который вытащил бы привязку из ресурсов и применил бы его:
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}" />
Можно ли использовать это решение в 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
. Но, к счастью, есть быстрое решение - просто используйте StaticResourceExtension
вместо этого! Таким образом, это, будучи функционально эквивалентным во время выполнения, будет приниматься дизайнером:
<TextBlock>
<TextBlock.Text>
<MultiBinding StringFormat="First: {0}, Second: {1}">
<Binding Path="SomeProperty" />
<StaticResource ResourceKey="MyBinding" />
</MultiBinding>
</TextBlock.Text>
</TextBlock>