如何知道动态创建的TabItem的索引

本文关键字:TabItem 索引 创建 何知道 动态 | 更新日期: 2023-09-27 18:20:35

我在xaml中有这样的:

<controls:TabControl Grid.Row="0" BorderThickness="0" Background="White" 
                         ItemsSource="{Binding TabList, Mode=TwoWay, Converter={StaticResource TabConverter}}"                        
                         SelectedItem="{Binding CurrentItem, Mode=TwoWay}"/>

在视图模型中我有:

 private TabItem currentItem;
    public TabItem CurrentItem
    {
        get { return currentItem; }
        set 
        {
            //currentItem.Content               
            currentItem = value;
          int index = currentItem.TabIndex;  //IT GIVES STRANgE INDEX ON DEBUGGING ob Tab click (like 22255788586)                   
            OnPropertyChanged("CurrentItem");
        }
    }

但是这个TabList(在xaml中)是这样动态生成的:

public void AddVersion(ProgramVersion pv) //it creates the TabList
        {
            if (pv != null)
            {               
                if (index == -1)
                {                      
                    TabList.Add(new ProgramVersionItemViewModel(pv));                    
                    OnPropertyChanged("TabList");                
                }                
            }
        }

每次按下一个按钮,我调用函数AddVersion(版本);并将其添加到TabList中。

问题是,当我点击CurrentItem(动态创建的TabItems(TabList)数量)时,它会给出非常大的奇怪地址(比如222557456)。

我获取当前项目索引的方法是错误的吗?(int index=currentItem.TabIndex;)?

如何知道动态创建的TabItem的索引

7年后,仍然没有令人满意的答案。。

这里有一个快速的伪修复,只要您使用TabItem实例来填充父TabControl,并且不要干扰复杂的转换器。

将下面的代码放入实用程序静态(内部)类中。添加适当的引用,如using System.Windows.Controls(或者直接在System.Windows.Controls命名空间下创建静态类)

/// <summary>
/// Gets the current index of the Tab under a TabControl.
/// </summary>
/// <param name="tabItem">This TabItem.</param>
/// <param name="defaultReturn">A default value to return if no index could be retrieved.</param>
/// <returns>The sequential index of the tab.</returns>
public static Int32 GetIndex(this TabItem tabItem, Int32 defaultReturn = 0) 
{
    if (tabItem == null) 
        throw new ArgumentNullException("tabItem", "TabItem is null.");
    if (tabItem.Parent is TabControl) 
    {
        TabControl parent = (TabControl)tabItem.Parent;
        int i = 0;
        foreach (var tab in parent.Items) 
        {
            if (ReferenceEquals(tab, tabItem)) 
                return i;
            i = i + 1;
        }
    }
    return defaultReturn;
}

然后你可以使用它:

// Select the latest created tab...
Dispatcher.BeginInvoke((Action)(() => TheTabControl.SelectedIndex = CurrentItem.GetIndex(0)));

您可以在相同的基础上创建其他扩展方法,如TabControl.GetLastTab()或TabItem.SetIndex(0),但这超出了主题的范围。

老实说,这是一种方法

    private void Button1_Click(object sender, RoutedEventArgs e)
    {
        TabControl1.Items.Add(new TabItem() { TabIndex = 0, Header = "Tab 0" });
        TabControl1.Items.Add(new TabItem() { TabIndex = 1, Header = "Tab 1" });
        TabControl1.Items.Add(new TabItem() { TabIndex = 2, Header = "Tab 2" });
        TabControl1.Items.Add(new TabItem() { TabIndex = 3, Header = "Tab 3" });
    }

请注意,我们正在添加new TabItem(),并为其提供选项卡索引和标头。使用这种方法要动态得多,也要可靠得多。

所以,在你的例子中,你可能会做这样的事情:

        if (pv != null)
        {
            if (index == -1)
            {
                TabList.Add(new TabItem() { TabIndex = <EnumeratedValue>, Header = "Tab " + <EnumeratedValue>.ToString()});
            }
        }