2015-09-30 23 views
0

自定义控件已经自定义控件的内容定义如下:创建在WPF

<DockPanel> 
<ListView x:Name="TabControlMenu" DockPanel.Dock="Top" ScrollViewer.VerticalScrollBarVisibility="Disabled" 
      ItemsSource="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type UserControl}}, Path=Items}"> 
    <ListView.Resources> 
     <Style BasedOn="{StaticResource ListViewStyle}" TargetType="{x:Type ListView}" /> 
     <Style BasedOn="{StaticResource ListViewItemStyle}" TargetType="{x:Type ListViewItem}" /> 
    </ListView.Resources>    
    <ListView.ItemsPanel> 
     <ItemsPanelTemplate> 
      <StackPanel Orientation="Horizontal"></StackPanel> 
     </ItemsPanelTemplate> 
    </ListView.ItemsPanel> 
</ListView> 
<Border BorderBrush="Black" BorderThickness="1,0,0,0" DockPanel.Dock="Bottom"> 
    <ContentPresenter DataContext="{Binding SelectedItem}" Content="{Binding Body, ElementName=ThisControl}" /> 
</Border> 

public partial class MyTabControl : UserControl { 

    #region static properties 

    public static readonly DependencyProperty BodyProperty = DependencyProperty.Register(
     "Body", 
     typeof(object), 
     typeof(MyTabControl), 
     new UIPropertyMetadata(null)); 

    public static readonly DependencyProperty ItemsProperty = DependencyProperty.Register(
     "Items", 
     typeof(ObservableCollection<object>), 
     typeof(MyTabControl), 
     new UIPropertyMetadata(null)); 

    public static readonly DependencyProperty SelectedItemProperty = DependencyProperty.Register(
     "SelectedItem", 
     typeof(object), 
     typeof(MyTabControl), 
     new UIPropertyMetadata(null)); 

    #endregion 

    #region public properties 

    public object Body { 
     get { return GetValue(BodyProperty); } 
     set { SetValue(BodyProperty, value); } 
    } 

    public ObservableCollection<object> Items { 
     get { return (ObservableCollection<object>)GetValue(ItemsProperty); } 
     set { SetValue(ItemsProperty, value); } 
    } 

    public object SelectedItem { 
     get { return GetValue(SelectedItemProperty); } 
     set { SetValue(SelectedItemProperty, value); } 
    } 

    public ObservableCollection<ListViewItem> ListViewItems { get; set; } 

    #endregion 

    public MyTabControl() { 
     InitializeComponent(); 

     ListViewItems = new ObservableCollection<ListViewItem>(); 
    } 

} 

,并用它是这样的:

<Controls:MyTabControl Margin="5,0,0,0" Items="{Binding Items}"> 
    <Controls:MyTabControl.Body> 
     <ContentControl Content=" WHAT BINDING GOES HERE???? "> 
      <!--<ContentControl Content="{Binding}">--> 
      <ContentControl.Resources> 
       <DataTemplate DataType="{x:Type ViewModels:ProjectViewModel}"> 
        <Partials:ProjectView DataContext="{Binding Path=.}" /> 
       </DataTemplate> 
       <DataTemplate DataType="{x:Type ViewModels:TestSuiteViewModel}"> 
        <Partials:TestSuiteView DataContext="{Binding Path=.}" /> 
       </DataTemplate> 
       <DataTemplate DataType="{x:Type ViewModels:StepViewModel}"> 
        <Partials:StepView DataContext="{Binding Path=.}" /> 
       </DataTemplate> 
      </ContentControl.Resources> 
     </ContentControl> 
    </Controls:MyTabControl.Body> 
</Controls:MyTabControl> 

我怎样才能建立ContentControlContent绑定,以便它指向中定义的内容210?

也许有些人会问为什么我创建摆在首位的自定义选项卡控制 - 答案是:因为我必须做一些不规范 - 分组标签,着色等周围拖动......

编辑:

我在这里的目标是MyTabControl表现得像一个标准的WPF TabControl - 所以它的ItemsItemsSource应绑定到某个标签的一些收集和内容应该绑定到任何当前选择。为了实现这一点,我在我的控制代码后面绑定了ListViewItems集合,并试图将ContentPresenterDataContext绑定到当前选定的任何内容(它也在代码后面设置)。问题是,如果我在应用程序的某个地方使用MyTabControl.Body,我不知道如何绑定ContentControl.Content属性,以便它可以从我的自定义控件中获取它的数据。

回答

0

如果我理解正确,您需要将UserControl设为DataContext。问题是,您希望UserControl内的控件将UserControl视为DataContext,但您需要UserControl本身才能看到其他一些Datacontext。您可以通过设置根布局元素的DataContext来实现这一点,我认为这是DockPanel。像这样:

<UserControl 
    ... 
    x:Name="ThisControl 
    ... > 

    <DockPanel DataContext="{Binding ElementName=ThisControl}"> 

     ... 
    </ListView> 
    ... 
    </DockPanel> 
</UserControl> 

http://www.codeproject.com/Articles/325911/A-Simple-Pattern-for-Creating-Re-useable-UserContr是我想说的东西的正确解释。

编辑: 我想可能是这样的,你需要,以获得DataContextContentPresenter

<DockPanel DataContext="{Binding ElementName=ThisControl}"> 
... 
    <ListView ItemsSource="{Binding Items}" ... /> 

    <Border ... > 
    <ContentPresenter DataContext="{Binding SelectedItem}" ... /> 
    </Border> 

或者你有RelativeSource做了ContentPresenter,你已经为ItemsSourceListView

<DockPanel> 
<ListView ... 
    ItemsSource="{Binding RelativeSource= 
    {RelativeSource FindAncestor, AncestorType={x:Type UserControl}}, 
    Path=Items}"> 
    ... 
</ListView> 

<Border ...> 
    <ContentPresenter DataContext="{Binding RelativeSource= 
    {RelativeSource FindAncestor, AncestorType={x:Type UserControl}}, 
    Path=DataContext.SelectedItem}" 
    ... /> 
</Border> 

2日编辑:

看起来好像您正试图在XAML级别设置MyTabControl的属性,但我认为您应该设置DP,即XAML绑定的属性。喜欢这个? :

<Controls:MyTabControl 
    ... 
    Body="{Binding TheBody}" 
    Items="{Binding TheItems}"> 
    SelectedItem="{Binding TheSelectedItem}" /> 
+0

我不确定你是否正确理解我的意图。我更新了这个问题,以便它(希望)更具描述性。 –

+0

对于'ItemsSource',你将Source设置为指向MyTabControl,但对于ContentPresenter则不设置Source,所以我认为它正在寻找DataContext中的SelectedItem ''MyTabControl',它通过继承获得,并且是无论如何指向。您可以尝试 PScr

+0

好吧,但我仍然不知道如何绑定到外部的MyTabControl.DataContext,请看第二个代码片段,尤其是“什么是BINDING GOES HERE?” '字符串:) –