C# と VB.NET の質問掲示板

ASP.NET、C++/CLI、Java 何でもどうぞ

C# と VB.NET の入門サイト

Treeviewへのノードの追加について

[トピック内 5 記事 (1 - 5 表示)]  << 0 >>

■94710 / inTopicNo.1)  Treeviewへのノードの追加について
  
□投稿者/ マリ夫 (1回)-(2020/05/08(Fri) 19:43:59)

分類:[VB.NET/VB2005 以降] 

Visualstudio2019、VB.NETでFORMアプリケーションを作成しています。
Treeviewを使用してリストを作成したいのですが、狙った動きになってくれません。
Treeviewは初めて使うので、悪戦苦闘しています。


        TreeView1.Nodes.Clear()

        Dim TAIHI_NODE As String

        Dim WK_CODE1(4) As String
        WK_CODE1(0) = "TEST1"
        WK_CODE1(1) = "TEST1"
        WK_CODE1(2) = "TEST1"
        WK_CODE1(3) = "TEST1"
        WK_CODE1(4) = "TEST2"


        Dim WK_CODE2(4) As String
        WK_CODE2(0) = "TEST1-A"
        WK_CODE2(1) = "TEST1-B"
        WK_CODE2(2) = "TEST1-C"
        WK_CODE2(3) = "TEST1-D"
        WK_CODE2(4) = "TEST2-A"

        Dim WK_TEXT1(4) As String
        WK_TEXT1(0) = "LIST1-AA"
        WK_TEXT1(1) = "LIST1-BB"
        WK_TEXT1(2) = "LIST1-CC"
        WK_TEXT1(3) = "LIST1-DD"
        WK_TEXT1(4) = "LIST2-AA"

        Dim WK_TEXT2(4) As String
        WK_TEXT2(0) = "LIST1-AAA"
        WK_TEXT2(1) = "LIST1-BBB"
        WK_TEXT2(2) = "LIST1-CCC"
        WK_TEXT2(3) = "LIST1-DDD"
        WK_TEXT2(4) = "LIST2-AAA"


        Dim DO_COUNT As Integer = 5    '配列数

        For i = 0 To DO_COUNT
            Dim rootNode As New TreeNode
            If TAIHI_NODE <> WK_CODE1(i) Then
               rootNode.Text = WK_CODE1(i)
               TreeView1.Nodes.Add(rootNode)
            End If

            Dim rootNode1 As New TreeNode      '子ノード
            Dim rootNode2_1 As New TreeNode    '孫ノード1
            Dim rootNode2_2 As New TreeNode    '孫ノード2

            '子ノードの作成
            rootNode1.Text = WK_CODE2(i)
            '★★★子ノードを親ノードに追加★★★
            rootNode.Nodes.Add(rootNode1)

            '孫ノードの作成
            rootNode2_1.Text = WK_TEXT1(i)
            rootNode2_2.Text = WK_TEXT2(i)
            '★★★孫ノードを子ノードに追加★★★
            rootNode1.Nodes.Add(rootNode2_1)
            rootNode1.Nodes.Add(rootNode2_2)

            TAIHI_NODE = WK_CODE1(i)
        Next

上記のようなロジックで実行したのですが、以下のような結果になりました。


TEST1
┗TEST1-A
 ┗LIST1-AA
 ┗LIST1-AAA
TEST2
┗TEST2-A
 ┗LIST2-AA
 ┗LIST2-AAA

自分が目指している形としては、以下の通りです。
TEST1
┣TEST1-A
┃┗LIST1-AA
┃┗LIST1-AAA
┣TEST1-B
┃┗LIST1-BB
┃┗LIST1-BBB
┣TEST1-C
┃┗LIST1-CC
┃┗LIST1-CCC
┗TEST1-S
 ┗LIST1-DD
 ┗LIST1-DDD
TEST2
┗TEST2-A
 ┗LIST2-AA
 ┗LIST2-AAA


望んだ結果にできるやり方があれば教えていただけたらと思います。
よろしくお願いします。

引用返信 編集キー/
■94711 / inTopicNo.2)  Re[1]: Treeviewへのノードの追加について
□投稿者/ Hongliang (1024回)-(2020/05/08(Fri) 20:35:39)
構築方法が非常に難解なものになっている印象ですが。

>         For i = 0 To DO_COUNT
>             Dim rootNode As New TreeNode

問題となっている原因はここですね。
ループのたびにノードをNewしているので、iが1のときもrootNodeは新しいインスタンスが作られ、
その作られたノードに子ノード以降が追加され、そしてrootNode自体ははどこにも追加されず
そのままメモリの海に消えていくことになります。
TAIHIみたいなやり方ではなく、TreeView1.Nodes.Findで検索し、見つかればそれをrootNodeとし、
見つからなければNewしたTreeNodeをrootNodeとする、といった方法はどうでしょうか。

今提示されているツリーを作成するのなら、私であれば
WK_CODE1はTEST1とTEST2の2要素にして、
WK_CODE2をDictionary(Of Stirng, String())にするかなぁ。

引用返信 編集キー/
■94713 / inTopicNo.3)  Re[2]: Treeviewへのノードの追加について
□投稿者/ マリ夫 (2回)-(2020/05/08(Fri) 21:11:44)
No94711 (Hongliang さん) に返信
> 構築方法が非常に難解なものになっている印象ですが。
>
>> For i = 0 To DO_COUNT
>> Dim rootNode As New TreeNode
>
> 問題となっている原因はここですね。
> ループのたびにノードをNewしているので、iが1のときもrootNodeは新しいインスタンスが作られ、
> その作られたノードに子ノード以降が追加され、そしてrootNode自体ははどこにも追加されず
> そのままメモリの海に消えていくことになります。
> TAIHIみたいなやり方ではなく、TreeView1.Nodes.Findで検索し、見つかればそれをrootNodeとし、
> 見つからなければNewしたTreeNodeをrootNodeとする、といった方法はどうでしょうか。
>
> 今提示されているツリーを作成するのなら、私であれば
> WK_CODE1はTEST1とTEST2の2要素にして、
> WK_CODE2をDictionary(Of Stirng, String())にするかなぁ。

TreeView1.Nodes.Findで検索を行ってみたのですが、常にfalseが返ってくる状態です。

Dim Anser As Boolean
TreeView1.Nodes.Find(WK_KEY_CODE1(i).TrimEnd, Anser)

1週目:WK_CODE1(0) = TEST1 結果:False
2週目:WK_CODE1(1) = TEST1 結果:False

このような状態で、検索がうまくいってないようです。
TreeView1.Nodes.Find() で「searchAllChildren」とあったのですが、WK_CODE1は親のノードですが、検索できるのでしょうか
無知で大変申し訳ないです。



引用返信 編集キー/
■94714 / inTopicNo.4)  Re[3]: Treeviewへのノードの追加について
□投稿者/ Hongliang (1025回)-(2020/05/08(Fri) 21:27:44)
https://docs.microsoft.com/ja-jp/dotnet/api/system.windows.forms.treenodecollection.find?view=netcore-3.1#System_Windows_Forms_TreeNodeCollection_Find_System_String_System_Boolean_
Findメソッドの第2引数は、子孫ノードすべてを検索するか直接の子ノードのみを検索するかを指定するパラメータであって、見つかったかどうかを返してくるパラメータではありません(ByRefではないですよね)。
返値として見つかったノードの配列が返されるので(同じ名前を持ったノードが複数存在できるので配列になります)、その長さが0なら存在しない、そうでないなら存在する、と判定できます。

ああ、ただFindメソッドはTreeNodeのTextではなくてNameを検索するメソッドでした。
Findメソッドを有効に使うには、TreeNodeをNewしたときについでにNameプロパティにも同じ文字列を設定しておく必要がありますね。

Find以外の手段としては、For EachなどでNodesプロパティの中のTreeNodeを順次調べて対応するTextを持ったTreeNodeを探すというのもあります。
引用返信 編集キー/
■94715 / inTopicNo.5)  Re[4]: Treeviewへのノードの追加について
□投稿者/ マリ夫 (4回)-(2020/05/09(Sat) 10:11:14)
No94714 (Hongliang さん) に返信
> https://docs.microsoft.com/ja-jp/dotnet/api/system.windows.forms.treenodecollection.find?view=netcore-3.1#System_Windows_Forms_TreeNodeCollection_Find_System_String_System_Boolean_
> Findメソッドの第2引数は、子孫ノードすべてを検索するか直接の子ノードのみを検索するかを指定するパラメータであって、見つかったかどうかを返してくるパラメータではありません(ByRefではないですよね)。
> 返値として見つかったノードの配列が返されるので(同じ名前を持ったノードが複数存在できるので配列になります)、その長さが0なら存在しない、そうでないなら存在する、と判定できます。
>
> ああ、ただFindメソッドはTreeNodeのTextではなくてNameを検索するメソッドでした。
> Findメソッドを有効に使うには、TreeNodeをNewしたときについでにNameプロパティにも同じ文字列を設定しておく必要がありますね。
>
> Find以外の手段としては、For EachなどでNodesプロパティの中のTreeNodeを順次調べて対応するTextを持ったTreeNodeを探すというのもあります。
Findメソッドを使用して判別する方法を取り、処理を見直した結果、望んでいた結果が得られました。
ありがとうございました。
解決済み
引用返信 編集キー/

このトピックをツリーで一括表示


トピック内ページ移動 / << 0 >>

このトピックに書きこむ