【问题标题】:wpf Treeview with three levels in具有三个级别的wpf Treeview
【发布时间】:2018-06-09 16:35:33
【问题描述】:

我是一名初学者,正在尝试创建我的第一个应用程序,该应用程序包含一个具有三个级别的 treeView
第一级显示进程名称
二级显示其模块和线程已修复
第三层包含子模块和子线程

 proc1      
    Module      
      subMod1     
   Thread      
      thread1                        
 proc2                                                                            
   Module
     submod1
   Thread
     subThread  

这是 xmal.cs 文件

public partial class MainWindow : Window
{


    public MainWindow()
    {


        InitializeComponent();

        for (int i = 0; i <= 3; i++)
        {
            Module mod = new Module
            {
                modulelist = new List<moduleList>() { new moduleList {           Name = "mod1" } ,
             new moduleList { Name = "mod1" } }
            };
            Thread th = new Thread
            {
                threadlist = new List<threadList>() { new threadList { Name = "thread1" } ,
             new threadList { Name = "thread1" } }
            };
            ProcName proc1 = new ProcName { Name = "proc" + i, mod = new Module(), th = new Thread() };
            tv.DataContext = proc1;
        }
    }

    public class ProcName
    {

        public string Name
        { get; set; }
        public Module mod = new Module();
        public Thread th = new Thread();

    }
    public class Module
    {
        public string Name = "Module";
        public List<moduleList> modulelist
        { get; set; }
    }
    public class moduleList
    {
        public string Name
        { get; set; }
    }
    public class Thread {
        public string Name = "Thread";
        public List<threadList> threadlist
        { get; set; }
    }
    public class threadList
    {
        public string Name
        { get; set; }
    }


}  

这是xmal文件

<TreeView Name="tv" ItemsSource="{Binding}">

    <TreeView.ItemTemplate>

        <HierarchicalDataTemplate ItemsSource="{Binding ProcName}">
            <TextBlock Margin="3" Text="{Binding Name}"/>
            <!-- child node will be a MasterAction -->
            <HierarchicalDataTemplate.ItemTemplate>
                <HierarchicalDataTemplate ItemsSource="{Binding Module}">
                    <TextBlock Text="{Binding Name}"/>
                    <!-- leaf will be a SlaveAction -->
                    <HierarchicalDataTemplate.ItemTemplate ItemSource ="{Binding moduleList} ">
                        <DataTemplate>
                            <TextBlock Text="{Binding Name}"/>
                        </DataTemplate>
                    </HierarchicalDataTemplate.ItemTemplate>
                </HierarchicalDataTemplate>
                <HierarchicalDataTemplate ItemsSource="{Binding Thread}">
                    <TextBlock Text="{Binding Name}"/>
                    <!-- leaf will be a SlaveAction -->
                    <HierarchicalDataTemplate.ItemTemplate ItemSource   ="{Binding threadList} ">
                        <DataTemplate>
                            <TextBlock Text="{Binding Name}"/>
                        </DataTemplate>
                    </HierarchicalDataTemplate.ItemTemplate>
                    </
            </HierarchicalDataTemplate.ItemTemplate>
        </HierarchicalDataTemplate>
    </TreeView.ItemTemplate>
</TreeView>
</Window>

我知道这不是正确的方法,但尝试这样做
如何正确使用?

【问题讨论】:

  • 您的数据类与您的树不匹配,这是第一个问题。一个进程可以有多个线程吗?多个模块?
  • 是的,一个进程有多个模块和线程

标签: c# wpf


【解决方案1】:

您可以使用Interface 来完成这项工作。

xaml.cs

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

        var subNodes = new List<ITreeNode>
        {
            new SubNode { Name = "Sub Node 1" },
            new SubNode { Name = "Sub Node 2" },
            new SubNode { Name = "Sub Node 3" },
            new SubNode { Name = "Sub Node 4" }
        };
        var nodes = new List<ITreeNode>
        {
            new Thread { Name = "Thread 1", ChildNodes = subNodes },
            new Thread { Name = "Thread 2", ChildNodes = subNodes },
            new Module { Name = "Module 1", ChildNodes = subNodes },
            new Module { Name = "Module 2", ChildNodes = subNodes }
        };
        var processes = new List<Process>
        {
            new Process{ Name = "Process1", ChildNodes = nodes },
            new Process{ Name = "Process2", ChildNodes = nodes }
        };
        TreeView.ItemsSource = processes;
    }
}
public interface ITreeNode
{
    string Name { get; set; }
    List<ITreeNode> ChildNodes { get; set; }
}
public class Process : ITreeNode
{
    public string Name { get; set; }
    public int ID { get; set; }
    public List<ITreeNode> ChildNodes { get; set; }
}
public class Module : ITreeNode
{
    public string Name { get; set; }
    public List<ITreeNode> ChildNodes { get; set; }
}
public class Thread : ITreeNode
{
    public string Name { get; set; }
    public int ID { get; set; }        
    public List<ITreeNode> ChildNodes { get; set; }
}
public class SubNode : ITreeNode
{
    public string Name { get; set; }
    public List<ITreeNode> ChildNodes { get => null; set => throw new System.NotImplementedException(); }
}

xaml

如果关卡不需要不同的模板,可以使用

<TreeView x:Name="TreeView">
    <TreeView.ItemTemplate>
        <HierarchicalDataTemplate ItemsSource="{Binding ChildNodes}">
            <TextBlock Margin="3" Text="{Binding Name}"/>
        </HierarchicalDataTemplate>
    </TreeView.ItemTemplate>            
</TreeView>

如果你需要不同的关卡模板,你可以使用这样的东西,

<TreeView x:Name="TreeView">
    <TreeView.Resources>
        <HierarchicalDataTemplate DataType="{x:Type local:Process}" ItemsSource="{Binding ChildNodes}">
            <StackPanel Orientation="Horizontal">
                <TextBlock Text="{Binding Path=Name, StringFormat='{}{0} '}" />
                <TextBlock Text="{Binding Path=ID, StringFormat=(ID: {0})}" />
            </StackPanel>
        </HierarchicalDataTemplate>
        <HierarchicalDataTemplate DataType="{x:Type local:Module}" ItemsSource="{Binding ChildNodes}">
            <TextBlock Text="{Binding Path=Name}" />
        </HierarchicalDataTemplate>
        <HierarchicalDataTemplate DataType="{x:Type local:Thread}" ItemsSource="{Binding ChildNodes}">
            <StackPanel Orientation="Horizontal">
                <TextBlock Text="{Binding Path=Name, StringFormat='{}{0} '}" />
                <TextBlock Text="{Binding Path=ID, StringFormat=(ID: {0})}" />
            </StackPanel>
        </HierarchicalDataTemplate>
        <HierarchicalDataTemplate DataType="{x:Type local:SubNode}" ItemsSource="{Binding ChildNodes}">
            <TextBlock Text="{Binding Path=Name}" />
        </HierarchicalDataTemplate>
    </TreeView.Resources>
</TreeView>

【讨论】:

  • 非常感谢它完美运行,但我有点困惑,因为在我的案例中,模块和线程不共享相同的子节点,原因是每个进程都有不同的线程和不同的模块跨度>
  • 您可以创建另一个SubNode 并像ModuleThread 类一样使用它。会是var subNodes = new List&lt;ITreeNode&gt; { new SubNode1 { Name = "Sub Node 1" }, new SubNode1 { Name = "Sub Node 2" }, new SubNode2 { Name = "Sub Node 3" }, new SubNode2 { Name = "Sub Node 4" } };
  • 我已经做了这样的事情,为模块公共类SubNode1 : ITreeNode { public string Name { get; set; } public List&lt;ITreeNode&gt; ChildNodes { get =&gt; null; set =&gt; throw new System.NotImplementedException(); } } then create its variable var subNodes1 = new List&lt;ITreeNode&gt; { new SubNode1 { Name = "Sub Node1 1" },} and then use it as new Module { Name = "Module 2", ChildNodes = subNodes1 }添加了一个子类,但效果不佳
  • subnode1 的输出是wpfexample.SubNode1
  • 我发现了错误。现在它已解决并完美运行,感谢您的帮助和努力
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-02-28
  • 2013-07-17
  • 2012-02-21
  • 1970-01-01
  • 2021-12-08
相关资源
最近更新 更多