🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Article View: borland.public.jbuilder.java.swing
Article #1528

Re: displaying child nodes on demand

#1528
From: Alan Shiers
Date: Mon, 27 Oct 2003 00:14
287 lines
10629 bytes
Hi there,

Ok, I've done a little more digging.  I finally realized that subclassing
DefaultTreeModel is what would give me access to the
fireTreeStructureChanged() method.  So I did exactly that.  Below you'll
find my entire class.  The ReceiveChildrenFromServer( ) method is the one
I'm having a challenge with.

In the class that contains the JTree I listen for tree expansion events, so
in the treeWillExpand( ) method I set a boolean flag in MyTreeModel and the
path to the node that was expanded, like so:

public void treeWillExpand(javax.swing.event.TreeExpansionEvent tee) throws
javax.swing.tree.ExpandVetoException
  {
      System.out.println("Node Expanding.");
      model.setNodeExpanding(true);
      model.setParentNodesPath(tee.getPath());
      expandingNode = (DefaultTreeNode)tee.getPath().getLastPathComponent();
  }

Everytime the getChildCount() method in MyTreeModel is called it sends a
request to the server for the childCount, also if the flag NodeExpanding is
set to true (which it would be from the treeWillExpand( ) method), then we
call RequestChildrenFromServer( ) method which in turn calls
ReceiveChildrenFromServer( ) method.

The ReceiveChildrenFromServer( ) method is definitely collecting the names
of each node as it is being transmitted by the server, however, where I've
inserted the line:

this.fireTreeStructureChanged(parent, path, childIndecies, children);

this compiles fine but I'm still not displaying the child nodes in the
JTree. Any ideas as to why?

Please advise,

Alan

import java.io.*;
import javax.swing.tree.*;
import javax.swing.event.*;
import java.awt.Cursor;
import java.util.*;

public class MyTreeModel extends DefaultTreeModel
{
    DataOutputStream output;
    Response ref;
    int RequestedChildCount;
    private boolean ReceivedChildCount;
    private boolean NodeExpanding;
    RefreshTimer timer = null;
    TreePath ParentNodesPath;


    public MyTreeModel(TreeNode node)
    {
      super(node);
    }

    public MyTreeModel(TreeNode node, boolean asksAllowsChildren)
    {
      super(node, asksAllowsChildren);
    }

    public Object getRoot(){return root;}

    public void setResponseReference(Response reference)
    {
         ref = reference;
    }

    public void setOutputStream(DataOutputStream out)
    {
      output = out;
    }

    public void insertNodeInto(DefaultTreeNode child, DefaultTreeNode
parent, int param)
    {
        parent.insert(child, param);
    }

    public int getChildCount(Object node)
    {

        System.out.println("Entering GetChildCount(Object)");
        int count = -1;
        if(node instanceof DefaultTreeNode)
        {
            count =
this.getChildCount(((DefaultTreeNode)node).getWholeServerPath());
        }
        return count;
    }

    public int getChildCount(String ParentsWholePath)
    {

      System.out.println("Entering GetChildCount(String)");
      int childCount = 0;
      try
      {
        ref.ref.setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
        DefaultTreeNode node = null;
        String name = "";
        output.writeInt(ref.ref.PATH);
        output.flush();
        output.writeUTF(ParentsWholePath);
        output.flush();
        output.writeInt(ref.ref.REQUEST_CHILD_COUNT);
        output.flush();
        System.out.println("waiting for response...");
        timer = new MyTimer(this);
        timer.start();
        timer.join();
        System.out.println("ReceivedChildCount: " + ReceivedChildCount +
"\nRequestedChildCount: " + RequestedChildCount);
        ReceivedChildCount = false; //reset
        if(RequestedChildCount > 0 & NodeExpanding)
        {
            RequestChildrenFromServer(ParentsWholePath);
            NodeExpanding = false; //reset
        }

ref.ref.setCursor(Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR));
      }
      catch(InterruptedException ie){}
      catch(IOException ioe){ioe.printStackTrace();}
      catch(NullPointerException npe){npe.printStackTrace();}
      System.out.println("childCount: " + RequestedChildCount);
      return RequestedChildCount;
    }

    protected void setNodeExpanding(boolean value)
    {
       NodeExpanding = value;
    }

    protected void setReceivedChildCount(boolean value)
    {
        ReceivedChildCount = value;
    }

    protected boolean getReceivedChildCount()
    {
        return ReceivedChildCount;
    }

    protected void setRequestedChildCount(int value)
    {
        RequestedChildCount = value;
    }

    protected void setParentNodesPath(TreePath path)
    {
        ParentNodesPath = path;
    }

    protected void RequestChildrenFromServer(String ParentsWholePath)
    {
      System.out.println("Entering RequestChildrenFromServer()");
      System.out.println("ParentsWholePath: " + ParentsWholePath);
      //Request Children from server
      try
      {
        ref.ref.setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
        output.writeInt(ref.ref.PATH);
        output.flush();
        output.writeUTF(ParentsWholePath);
        output.flush();
        //Sending REQUEST_CHILDREN should cause a response
        //from the server: SENDING_TREE_DATA
        output.writeInt(ref.ref.REQUEST_CHILDREN);
        output.flush();

ref.ref.setCursor(Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR));

      }
      catch(IOException ioe){ioe.printStackTrace();}
    }

    protected void ReceiveChildrenFromServer(DefaultTreeNode parent, String
ParentsWholePath, DataInputStream input)
    {
        //If we already have the child nodes for this parent node then just
return out of here.
        if(parent.getHasChildren())return;
        System.out.println("Entering ReceiveChildrenFromServer()");
        DefaultTreeNode child = null;
        int[] childIndecies = null;
        Object[] children = null;
        String name = "";
        try
        {

ref.ref.setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
           //read in the number of children from the server
           int childCount = input.readInt();
           //System.out.println("Childcount: " + childCount);
           int nodeType = 0;//default
           //iterate through each of the children as they come in
          //from the server.
          childIndecies = new int[childCount];
          children = new DefaultTreeNode[childCount];
          for(int i = 0; i < childCount; i++)
          {
              name = input.readUTF(); //get the name
              System.out.println("child node: " + name);
              child = new DefaultTreeNode(name); //create a new child node

              //determine if this node is a directory
              //or a file. Empty directories are denoted
             //as having (nodeType == -1)
             nodeType = input.readInt();
             System.out.println("node type: " + nodeType);
             if(nodeType == 0)
             {
                  //Since a file is a leaf node
                  //we won't be needing to continue
                  //reading in nodes for it.
                  child.setAllowsChildren(false);
                  child.setHasChildren(false);
                  child.setLeadingPath(ParentsWholePath);
                  if(ref.ref.serverOS.equals("Windows"))
                      child.setSeparator("\\");
                  else
                      child.setSeparator("/");
              }
              else if(nodeType == -1)
              {
                  child.setAllowsChildren(true); //It's an empty directory
                  child.setHasChildren(false);
                  child.setLeadingPath(ParentsWholePath);
                  if(ref.ref.serverOS.equals("Windows"))
                      child.setSeparator("\\");
                  else
                      child.setSeparator("/");

              }
              else
              {
                  child.setAllowsChildren(true); //It's a directory
                  child.setHasChildren(true);
                  child.setLeadingPath(ParentsWholePath);
                  if(ref.ref.serverOS.equals("Windows"))
                      child.setSeparator("\\");
                  else
                      child.setSeparator("/");

              }

              insertNodeInto(child, parent, i);
              childIndecies[i] = i;
              children[i] = child;
          }
          Object[] path = new TreePath[1];
          path[0] = ParentNodesPath;
          this.fireTreeStructureChanged(parent, path, childIndecies,
children); //<<< Here is the method you recommeded I call

ref.ref.setCursor(Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR));
      }
      catch(IOException ioe){ioe.printStackTrace();}
      catch(NullPointerException npe){npe.printStackTrace();}

    }
}


"Tor Iver Wilhelmsen (TeamB)" <tor.wilhelmsen@ergo.no> wrote in message
news:u3cdgqvx4.fsf@ergo.no...
> "Alan Shiers" <ashiers@hfx.eastlink.ca> writes:
>
> > This method does what it is supposed to, however, once it has
> > populated the parent node, I expected the JTree to display the
> > nodes.  This is not happening.  Can someone please explain how I get
> > the JTree to then display the child nodes.
>
> You need to tell the view. In the model, call
> fireTreeStructureChanged() for the TreePath down to where they were
> inserted.
>
> (To get the fire* methods generated for you, use the BeansExpress
> events tab and click TreeModel in the list of events to fire.)
Technical Details
Message-ID: <3f9c6527$2@newsgroups.borland.com>
Path: arc1-ca.pugleaf.net!archiver1.google.com!news2.google.com!news.maxwell.syr.edu!newsfeed00.sul.t-online.de!newsfeed01.sul.t-online.de!t-online.de!newsgroups.borland.com!not-for-mail
References: <3f9ae29b$1@newsgroups.borland.com> <u3cdgqvx4.fsf@ergo.no>

Show Full Headers
Complete Article Headers
X-Google-Language: ENGLISH,ASCII-7-bit
X-Google-Thread: 111d45,63f1d22919caaa01
X-Google-Attributes: gid111d45,public
X-Google-ArrivalTime: 2003-10-26 16:39:05 PST
From: "Alan Shiers" <ashiers@hfx.eastlink.ca>
Newsgroups: borland.public.jbuilder.java.swing
References: <3f9ae29b$1@newsgroups.borland.com> <u3cdgqvx4.fsf@ergo.no>
Subject: Re: displaying child nodes on demand
Date: Sun, 26 Oct 2003 20:14:36 -0400
Lines: 289
X-Priority: 3
X-MSMail-Priority: Normal
X-Newsreader: Microsoft Outlook Express 6.00.2800.1158
X-MimeOLE: Produced By Microsoft MimeOLE V6.00.2800.1165
NNTP-Posting-Host: 24.222.101.2
Message-ID: <3f9c6527$2@newsgroups.borland.com>
X-Trace: newsgroups.borland.com 1067214119 24.222.101.2 (26 Oct 2003 16:21:59 -0700)
Path: arc1-ca.pugleaf.net!archiver1.google.com!news2.google.com!news.maxwell.syr.edu!newsfeed00.sul.t-online.de!newsfeed01.sul.t-online.de!t-online.de!newsgroups.borland.com!not-for-mail