使用datatemplate时的wpf绑定

时间:2009-11-22 04:20:18

标签: wpf xaml binding datatemplate

好的,目前我有这段代码:

<TabItem Style="{DynamicResource MyStyle" x:Name="TabCustomers" Padding="0,1,4,1"
 Header={Binding Path=customersHeader}/>

现在我想在那里添加一个图标(通过删除上面的标题):

<TabItem.Header>
<StackPanel Orientation="Horizontal">
     <Image Stretch="UniformToFill" Source="{StaticResource customers}"/>
     <TextBlock x:Key="textblock" Margin="4,0,0,0" 
     Text="{Binding Path=customersHeader}"/>
</StackPanel>
</TabItem.Header>

到目前为止还可以。 我想使用datatemplate来概括它。我假设我必须在我的资源字典中执行此操作:

<DataTemplate x:Key="TabItemCustomersTemplate" DataType="{x:Type TabItem}">
<StackPanel Orientation="Horizontal">
     <Image Stretch="UniformToFill" Source="{StaticResource customers}"/>
     <TextBlock x:Key="textblock" Margin="4,0,0,0" 
     Text="{Binding Path=customersHeader}"/>
    </StackPanel>
</DataTemplate>

并在我的tabitem声明中更改此内容:

<TabItem ... HeaderTemplate="{StaticResource TabItemCustomersTemplate}".../>

所以我遇到了以下问题: 1)绑定不起作用,为什么? 2)如何从c#访问文本块? 3)我如何概括这一点,所以我不必为了不同的标签项(或其他控件)一遍又一遍地复制它,这样我每次都可以传递自己的文本和图像源?例如,您可以使用它来创建图像按钮,如果您有20个按钮,则代码会变得混乱。

有什么想法吗?

谢谢。

2 个答案:

答案 0 :(得分:0)

  1. 如果您在标题中模板 tabitem,你不需要设置 模板的数据类型。该 header是选项卡的属性 item,它实际上是一个属性 类型对象,你可以放任何东西 那里。

    尝试删除DataType="{x:Type TabItem}"并查看其是否有效。

  2. 你不应该访问 来自c#的textblock,你应该做 做绑定系统。放置一个 标题中的自定义对象。然后 将此对象绑定到您的文本块 然后调整对象,它会 操纵文本块。得到 如果它是一个元素总是很难 包含在数据模板中。您 不应该。如果你找到了 你自己走在视觉树上 找到你正在做的视觉元素 事情很艰难
  3. 您可以通过以下方式对此进行概括 建议2,使用自定义对象, 删除数据的x:键 模板并将其DataType设置为 是您的自定义对象的类型。 然后你的自定义对象 看来你会得到它的数据 模板化

答案 1 :(得分:0)

试试这个,这对我有用

<Window.Resources>
    <!-- <BitmapImage x:Key="customers" UriSource="einstein.jpg"/>--> 
    <DataTemplate x:Key="TabItemCustomersTemplate">
        <StackPanel Orientation="Horizontal">
            <Image Stretch="UniformToFill" Source="{Binding Path=Customers}"/>
            <TextBlock Margin="4,0,0,0" x:Name="txt" Text="{Binding Path=CustomersHeader}"/>
</StackPanel>
    </DataTemplate>
</Window.Resources>
    <Grid>
    <TabControl Name="mytabcontrol">
        <TabItem x:Name="TabCustomers" Padding="0,1,4,1" Header="{Binding}" HeaderTemplate="{StaticResource TabItemCustomersTemplate}">
            <Label Content="myContent" Background="Red"/>
        </TabItem>
    </TabControl>
</Grid>

中的代码

    public partial class Window1 : Window
{
    public Window1()
    {
        InitializeComponent();

        var lst = new List<People>();
        lst.Add(new People() { CustomersHeader = "My Customer" });
        this.DataContext = lst;
    }
}

public class People
{
    public string CustomersHeader { get; set; }
    public BitmapImage Customers { get; set; }
}

此外,您可以使用此

在代码中找到您的文本块
TabPanel tabPanel = GetVisualChild<TabPanel>(mytabcontrol);
if (tabPanel != null)
{
    foreach (UIElement element in tabPanel.Children)
    {
        TabItem tabItem = element as TabItem;
        var image = FindNameFromHeaderTemplate<TextBlock>(tabItem, "txt");
    }
}

    public static T FindNameFromHeaderTemplate<T>(TabItem tabItem, String name) where T : UIElement
    {
        if (tabItem == null)
        {
            throw new ArgumentNullException("container");
        }

        if (tabItem.HeaderTemplate == null)
        {
            return null;
        }

        ContentPresenter contentPresenter = GetVisualChild<ContentPresenter>(tabItem);
        if (contentPresenter == null)
        {
            return null;
        }

        T element = tabItem.HeaderTemplate.FindName(name, contentPresenter) as T;
        return element;
    }

    public static T GetVisualChild<T>(Visual referenceVisual) where T : Visual
    {
        Visual child = null;
        for (Int32 i = 0; i < VisualTreeHelper.GetChildrenCount(referenceVisual); i++)
        {
            child = VisualTreeHelper.GetChild(referenceVisual, i) as Visual;
            if (child != null && child.GetType() == typeof(T))
            {
                break;
            }
            else if (child != null)
            {
                child = GetVisualChild<T>(child);
                if (child != null && child.GetType() == typeof(T))
                {
                    break;
                }
            }
        }
        return child as T;
    }