Подтвердить что ты не робот

Возможно ли связать свойство code-behind без установки DataContext?

Как указано, Я видел пары аналогичного вопроса this или this в формате SO, но я не вижу решения для него.

Я знаю, если мне нужно привязываться к коду, мне нужно установить Datacontext = this

Но моя проблема заключается в том, что мой datacontext уже привязан к моей ViewModel, но я хочу сделать некоторые манипуляции с пользовательским интерфейсом с помощью команды, которая определена в коде.

Возможно ли связать его в xaml? Если да, то как?

EDIT: я пробовал следующее:

<Window x:Class="WpfApplication3.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Window1" Height="300" Width="300" x:Name="_Root">
<Grid x:Name="hellogrid">
    <TextBlock x:Name="myTextBlock" Text="AAAA"/>
    <Button Margin="82,119,121,120" Name="button2" Content="{Binding Path=Text, ElementName=myTextBlock}"/>
    <Button Margin="82,72,121,0" Name="button3" Content="{Binding Path=MyText, ElementName=_Root}" Height="23" VerticalAlignment="Top" />
</Grid>

И код:

public partial class Window1 : Window
{
    public string MyText { get; set; }

    public Window1()
    {
        InitializeComponent();
        MyText = "ABC";
    }
}

Я мог видеть, что Button2 показывает AAAA, но Button3 ничего не показывает....

4b9b3361

Ответ 1

ИЗМЕНИТЬ

Лучшее решение IMO - это опубликовано by @Saad Imran в этом SO question...

С помощью этого решения все, что вам нужно сделать, это назвать ваше окно, и привязка к свойству в вашем XAML будет такой же простой, как этот {Binding ElementName=MyWindowName, Path=MyText}

Итак, что вы делаете с Content="{Binding Path=MyText, ElementName=_Root}" в точности, и свойство Button Content привязано к свойству MyText, но единственное, что вам не хватает, это уведомление об изменении (для этого нужно реализовать интерфейс INotifyPropertyChanged), поэтому, когда вы установите для свойства MyText значение ABC MyText = "ABC"; уведомление об изменении не отправлено...

Простой способ проверить это, установив свойство MyText явно как таковое:

private string myText = "ABC";
public string MyText
{
   get { return myText; }
   set { myText = value; }
}

или установка его в конструкторе до InitializeComponent():

MyText = "ABC";
InitializeComponent();

Если вы это сделаете, вы заметите, что ваша кнопка будет иметь ABC в качестве ее содержимого, но изменения в свойстве MyText не повлияют на содержимое кнопки, потому что уведомление об изменении отсутствует...

Ответ 2

Конечно,

Существует много типов привязок. Самый простой привязывает свойство к DataContext, которое обычно унаследовано от родительского объекта

<DataTemplate DataType="{x:Type MyModel}">
    <!-- DataContext is object of type MyModel -->
    <local:MyView />
</DataTemplate>

или

<Window x:Name="MyWindow">
    <!-- DataContext Inherited from Window -->
    <TextBlock Text="{Binding SomeProperty}" /> 
</Window>

где

var SomeObject = new SomeModel();
SomeObject.SomeProperty = "Test";
myWindow.DataContext = SomeObject;

Другие типы привязок включают ElementName, где вы можете указать целевой элемент пользовательского интерфейса для использования в качестве источника данных для привязки

<StackPanel>
    <CheckBox x:Name="SomeCheckBox" />
    <TextBlock Text="{Binding ElementName=SomeCheckBox, Path=IsChecked}" />
</StackPanel>

или

<local:MyUserControl x:Name="SomeUserControl">
    <Button Command="{Binding ElementName=SomeUserControl, Path=DataContext.SaveCommand}" />
</local:MyUserControl >

Или RelativeSource, который позволяет вам найти объект относительно текущего объекта для использования в качестве источника данных

<Window Title="Test">
    <TextBlock Text="{Binding RelativeSource={RelativeSource AncestorType={x:Type Window}}, Path=Title}" />
</Window>

или

<local:MyUserControl>
    <Button Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type local:MyUserControl}}, Path=DataContext.SaveCommand}" />
</local:MyUserControl >

И TemplateBinding, который связывает это ярлык привязки RelativeSource, которая привязывается к шаблонизированному объекту

<Button Content="Test">
    <Button.Template>
        <ControlTemplate TargetType="{x:Type Button}">
            <TextBlock Text="{TemplateBinding Content}" />
        </ControlTemplate>
    </Button.Template>
</Button>

Ответ 3

Конечно, вы можете использовать ElementName:

<Window Name="root"
        Class="..."
        ...>

    ...

    <TextBox Text="{Binding Path=Foo, ElementName=root}" />

Вы также можете сделать это с помощью RelativeSource, но синтаксис более уродливый...