Как переопределить или изменить наследование дочерних элементов, когда мой datacontext установлен на родительский элемент? - PullRequest
1 голос
/ 15 января 2012

Отказ от ответственности Мне кажется, это довольно простой вопрос, поэтому я должен повторить, что я искал ответ и ничего не мог найти!

Не уверен, правильно ли я задаю вопрос, но я скажу вам это. Я работаю над тем, чтобы лучше познакомиться с MVVM, поэтому я возился с смехотворно простым проектом, состоящим из двух стековых панелей, десяти текстовых полей и некоторого простого связывания. Теперь все работает, так как у меня есть две панели, которые разделяют мои блоки и позволяют мне установить два datacontext.

Мой вопрос такой:

a) можно ли установить текст данных для родительского элемента (Stackpanel), и половина моих дочерних элементов (текстовых полей) использует этот контекст через наследование, а затем дает другой половине элементов РАЗНЫЙ контекст данных?

и

б) если это возможно, то как ??

Спасибо, люди умнее меня

Вот код, который так старается, но на самом деле не делает ничего, что я хочу, чтобы он делал:

1019 * XAML *

   <Grid>
    <StackPanel>
    <StackPanel HorizontalAlignment="Left" Margin="8,8,0,75" Width="224" DataContext="{Binding Path=Customer}">
        <TextBox Text="{Binding Path=FirstName}"  Height="28" Name="label1"/>
        <TextBox Text="{Binding Path=MiddleName}"  Height="28" Name="l2"/>
        <TextBox Text="{Binding Path=LastName}"  Height="28" Name="l3"/>
        <TextBox Text="{Binding Path=CompanyName}"  Height="28" Name="l4"/>
        <TextBox Text="{Binding Path=EmailAddress}"  Height="28" Name="l5"/>

        <!--I want the next five TextBox elements to bind to a different datacontext-->

        <TextBox Text="{Binding Path=FirstName}"  Height="28" Name="label11"/>
        <TextBox Text="{Binding Path=MiddleName}"  Height="28" Name="l21"/>
        <TextBox   Text="{Binding Path=LastName}"  Height="28" Name="l1lgh3"/>
        <TextBox Text="{Binding Path=CompanyName}"  Height="28" Name="l1hj4"/>
        <TextBox Text="{Binding Path=EmailAddress}" Height="28"/>
   </StackPanel>
   </StackPanel>
</Grid>

Код позади C #

   public partial class MainWindow : Window
{
    public MainWindow()
    {
        InitializeComponent();
    }

    private void Window_Loaded(object sender, RoutedEventArgs e)
    {
        this.DataContext = new MainViewModel();
    }
}

Просмотр модели

   public class MainViewModel : INotifyPropertyChanged
{
    public MainViewModel()
    {
        PopulateCustomerInfo();
    }

    private Customer customer;
    public Customer Customer
    {
        get { return customer; }
        set
        {
            customer = value;
            OnPropertyChanged("Customer");
        }
    }

    private Customer customer2;
    public Customer Customer2
    {
        get { return customer2; }
        set
        {
            customer2 = value;
            OnPropertyChanged("Customer");
        }
    }


    private void PopulateCustomerInfo()
    {
        AdventureWorksLTE ctx = new AdventureWorksLTE();
        this.Customer = (from c in ctx.Customers
                   select c).FirstOrDefault();
        this.Customer2 = (from c in ctx.Customers
                          orderby c.FirstName descending
                          select c).FirstOrDefault();

    }

    public event PropertyChangedEventHandler PropertyChanged;
    protected virtual void OnPropertyChanged(string propertyName)
    {
        var handle = PropertyChanged;
        if (handle != null)
        {
            var e = new PropertyChangedEventArgs(propertyName);
            handle(this, e);
        }
    }

}

Ответы [ 2 ]

1 голос
/ 15 января 2012

Самый простой способ состоит в том, чтобы иметь две StackPanels внутри первой, группируя 5 на 5 ваших текстовых полей, первое из которых имеет customer как datacontext, второе - customer2.даже может быть определен как DataTemplate (не имеющий ключа или имени, а скорее DataType = {x: Type local: Customer} (где local - ваше пространство имен clr)), и вы просто используете 2 ContentPresenters, имеющих привязку контента к Customer / Customer 2,это автоматически отобразит то, что вы хотите.

1 голос
/ 15 января 2012

Ну, вы можете делать разные вещи, например, локально менять DataContext на все эти нижние TextBoxes:

<TextBox Text="{Binding Path=FirstName}" DataContext="..."/>

Вопрос на самом деле: чего вы хотите достичь?Имеет ли смысл даже устанавливать DataContext на StackPanel?

Может быть, вам не следует использовать вместо этого более длинный путь:

<TextBox Text="{Binding Path=Customer.FirstName}"  Height="28" Name="label1"/>

Все зависит от того, какие свойства будут использоватьсяв дочерних элементах управления, если большинство или все они находятся в Customer, обязательно установите его так, чтобы привязки были короткими.Если вам нужна модель основного вида в некоторых местах, вы можете использовать RelativeSource, чтобы перейти к элементу управления с правильным контекстом данных и соответствующим образом изменить путь.(DataContext.*, контекст данных появляется в пути, поскольку указан другой источник)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...