【问题标题】:How to delete dynamically created tree view items如何删除动态创建的树视图项
【发布时间】:2013-07-27 03:15:56
【问题描述】:

我有一个 WPF 应用程序,它允许用户在 treeview 中动态创建子项。这些子项是从一个单独的窗口中创建的,并添加到主窗口中。我还想实现一个删除方法,该方法将从单独的窗口中删除主窗口子项。

这些是我的想法以及一些代码:

//Okay button -- Delete sub-items in main window TreeView
private void button2_Click(object sender, RoutedEventArgs e)
{
    //Query for Window1
    var mainWindow = Application.Current.Windows
        .Cast<Window1>()
        .FirstOrDefault(window => window is Window1) as Window1;

    //Name of header that needs to be located
    string header = textBox1.Text;

    //While treeview from main window contains subitems
    while (!mainWindow.treeView.Items.IsEmpty)
    {
        //Find TreeView subitem with matching header
        //? - not sure on code

        //Delete TreeView subitem
        //I'm guessing it has something to do with
        //mainWindow.treeView.Items.Remove(At?)....
    }
}

我的 cmets 显示我不确定的内容。我已经正确查询了我的主窗口,并为我想要查找的标题设置了一个字符串值。我设置了一个循环来搜索我的treeview,但不知道完成工作的确切代码。请告诉我我应该使用的代码。

根据答案修改代码

我正在尽力理解您的回答。我已经解释了我想在我的 cmets 中做什么。我认为我在正确的轨道上,但是当我尝试使用RemoveAll 时遇到了一点编译器错误。我是否需要包含某种using resourceDictionary

代码修订

非常感谢您一直陪伴着我。编译器仍然为调用 RemoveAll 提供错误。

//Okay button -- Delete location and corrusponding block
    private void button2_Click(object sender, RoutedEventArgs e)
    {
        //Close Delete Window
        this.Close();

        //Query for Window1
        var mainWindow = Application.Current.Windows
            .Cast<Window1>()
            .FirstOrDefault(window => window is Window1) as Window1;

        //Name of header that needs to be located
        string header = textBox1.Text;

        //Treeview under operation from main window
        TreeViewItem items = mainWindow.treeViewItem;

        //Delete corresponding node
        RemoveAll(items, p => string.Equals(p.Header, header));
    }

    //REMOVE ALL METHOD - for use with button_click ^
    public void RemoveAll(ItemCollection items, Predicate<TreeViewItem> isValid)
    {
        for (int i = items.Count - 1; i >= 0; i--)
        {
            TreeViewItem vItem = (TreeViewItem)items[i];
            if (isValid(vItem))
            {
                items.RemoveAt(i);
            }
            else
            {
                RemoveAll(vItem.Items, isValid);
            }
        }
    }

生成错误

错误 1: '...(project)...' 的最佳重载方法匹配有一些无效参数。

错误 2:参数 '1':无法从 System.Windows.Controls.TreeViewitem 转换为 `System.Windows.Controls.ItemCollection'。

谢谢。

【问题讨论】:

    标签: c# wpf treeview treeviewitem


    【解决方案1】:
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
        }
    
        private void Button_Click_1(object sender, RoutedEventArgs e)
        {
            string header = txtRemove.Text; //name of Treeviewitem to delete
            TreeView view = trvView; //get from location
    
            RemoveAll(view.Items, p => string.Equals(p.Header, header));
        }
    
        public bool Remove(ItemCollection items, Predicate<TreeViewItem> isValid)
        {
            for (int i = items.Count - 1; i >= 0; i--)
            {
                TreeViewItem vItem = (TreeViewItem)items[i];
                if (isValid(vItem))
                {
                    items.RemoveAt(i);
                    return true;
                }
                else
                {
                    bool isDeleted = Remove(vItem.Items, isValid);
                    if (isDeleted)
                        return isDeleted;
                }
            }
            return false;
        }
    
        public void RemoveAll(ItemCollection items, Predicate<TreeViewItem> isValid)
        {
            for (int i = items.Count - 1; i >= 0; i--)
            {
                TreeViewItem vItem = (TreeViewItem)items[i];
                if (isValid(vItem))
                {
                    items.RemoveAt(i);
                }
                else
                {
                    RemoveAll(vItem.Items, isValid);
                }
            }
        }
    
    }
    

    ///Xaml

    <Window x:Class="TreeViewSample.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">
        <Grid>
            <TreeView x:Name="trvView" HorizontalAlignment="Left" Height="215" Margin="68,35,0,0" VerticalAlignment="Top" Width="221">
                <TreeView.Items>
                    <TreeViewItem Header="1">
                        <TreeViewItem Header="1/1"/>
                        <TreeViewItem Header="1/2"/>
                        <TreeViewItem Header="1/3"/>
                    </TreeViewItem>
                    <TreeViewItem Header="2">
                        <TreeViewItem Header="2/1"/>
                        <TreeViewItem Header="2/2"/>
                        <TreeViewItem Header="2/3"/>
                    </TreeViewItem>
                    <TreeViewItem Header="3">
                        <TreeViewItem Header="3/1"/>
                        <TreeViewItem Header="3/2"/>
                        <TreeViewItem Header="3/3"/>
                    </TreeViewItem>
                </TreeView.Items>
    
            </TreeView>
            <Button  Content="Button" HorizontalAlignment="Left" Margin="333,155,0,0" VerticalAlignment="Top" Width="75" Click="Button_Click_1"/>
            <TextBox x:Name="txtRemove" HorizontalAlignment="Left" Height="23" Margin="333,102,0,0" TextWrapping="Wrap" Text="TextBox" VerticalAlignment="Top" Width="120"/>
    
        </Grid>
    </Window>
    

    【讨论】:

    • 我用trycatch 解决了我的错误。该程序现在正在运行,但它摆脱了treeview 下的所有内容,而不是指定的子项。有没有一种方法可以演示如何隔离要删除的选定子项?
    • 关于这个答案的几个问题:我要从我的button_ClickeventHandler 调用这个方法吗?我需要实例化什么并将其传递给该方法(我猜我再次查询我的mainWindow,并传递我正在使用的TreeView)?
    • 您可以从您的“button_Click eventHandler”调用此方法,但编写代码时假设您正在维护一个“List”,即您的“toDelete”。 “项目”部分是 TreeView.Items 字段。您如何确定要删除哪些字段?要删除的 TreeViewItems 的存储列表,还是每个 treeviewitem 都有一个复选框?如果是后者,你也应该看看this
    • 我只是想根据header 删除它们。用户输入treeViewItemheader,然后程序删除对应header的项目。
    • 好的,我认为第一种方法对我来说是最清楚的。我只是不明白如何为我的toDelete 项目维护List&lt;TreeViewItem&gt;treeViewItems 没有复选框。抱歉,我是 WPF 新手,虽然我对自己所做的事情了解很多,但这个问题对我来说有点复杂。
    猜你喜欢
    • 2012-02-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-06-20
    • 1970-01-01
    • 2018-12-22
    • 2017-07-21
    相关资源
    最近更新 更多