如何访问 TabControl.ContentTemplate 中的 ListBox? [英] How can I access a ListBox within a TabControl.ContentTemplate?

查看:19
本文介绍了如何访问 TabControl.ContentTemplate 中的 ListBox?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在我后面的代码中,我将 MessageBoxTabControl.ItemsSource 设置为 Observable 集合.

In my code behind I set the MessageBoxTabControl.ItemsSource to an Observable Collection.

<TabControl x:Name="MessageBoxTabControl">
    <TabControl.ContentTemplate>
        <DataTemplate>
            <ListBox x:Name="MessageListBox" />
                <!-- ^ I want a reference to this control -->
        </DataTemplate>
    </TabControl.ContentTemplate>
</TabControl>

假设我有相关的 tabcontrol 和 tabitem,我如何获得对我的 ListBox 的引用?

Assuming I have the relevant tabcontrol and tabitem, how can I get a reference to my ListBox?

推荐答案

你有没有想过用其他方式做你想做的事?通常,当您拥有 DataTemplate 时,您可能希望在该模板内的控件上设置的任何属性应该是静态的(所以为什么要访问它们)或取决于提供的数据,然后应该由 DataBinding 实现.

Have you thought about doing whatever you want to do some other way? Normally, when you have a DataTemplate, any properties you could want to set on the controls inside that template should either be static (so why access them) or depend upon the data supplied, which then should be implemented by a DataBinding.

您可以使用以下代码获取 ListBox.我仍然觉得最好重新考虑您的结构而不是使用此代码.

You can use the following code to get the ListBox. I still feel it would be better to rethink your structure instead of using this code.

XML:

<Window x:Class="WpfApplication1.MainWindow"
                    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
                    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
                    Title="MainWindow" Height="350" Width="525">

    <TabControl x:Name="MessageBoxTabControl">
        <TabControl.ContentTemplate>
            <DataTemplate >
                <ListBox x:Name="MessageListBox" >
                    <ListBoxItem Content="ListBoxItem 1" /> <!-- just for illustration -->
                </ListBox>
            </DataTemplate>
        </TabControl.ContentTemplate>
        <TabItem Header="Tab 1" />
        <TabItem Header="Tab 2" />
    </TabControl>
</Window>

背后的代码:

void MainWindow_Loaded(object sender, RoutedEventArgs e)
{
    ListBox lbx = FindVisualChildByName<ListBox>(this.MessageBoxTabControl, "MessageListBox");
    if (lbx != null)
    {
        // ... what exactly did you want to do ;)?
    }
}

private T FindVisualChildByName<T>(DependencyObject parent, string name) where T : FrameworkElement
{
    T child = default(T);
    for (int i = 0; i < VisualTreeHelper.GetChildrenCount(parent); i++)
    {
        var ch = VisualTreeHelper.GetChild(parent, i);
        child = ch as T;
        if (child != null && child.Name == name)
            break;
        else
            child = FindVisualChildByName<T>(ch, name);

        if (child != null) break;
    }
    return child;
}

还有第二种类似的方式,它实际上使用了模板,但仍然依赖于可视化树来访问 ContentPresenter(类似于上面的 FindVisualChild 实现):

There is also a second, similar way, that actually uses the template, but still depends on the visual tree to get to the ContentPresenter (FindVisualChild implementation analogous to above):

ContentPresenter cp = FindVisualChild<ContentPresenter>(this.MessageBoxTabControl);
ListBox lbx = cp.ContentTemplate.FindName("MessageListBox", cp) as ListBox;

请注意,由于对可视化树的这种依赖性,您将始终只能使用此方法找到所选选项卡的 ListBox.

Note that because of this dependency on the visual tree, you will always only find the ListBox of the selected tab with this method.

这篇关于如何访问 TabControl.ContentTemplate 中的 ListBox?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆