AppletTalk.com Forum Index AppletTalk.com
Java discussions newsgroups
 
Archives   FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

Strange behaviour from recursive function

 
Post new topic   Reply to topic    AppletTalk.com Forum Index -> Java Help
View previous topic :: View next topic  
Author Message
grasshopper
Guest





PostPosted: Thu Jun 17, 2004 11:13 am    Post subject: Strange behaviour from recursive function Reply with quote



Hi,
I am trying to write a method that toggles the display of a Swing
component(e.g. a JButton) inside a container (e.g. a JPanel).
The method below essentially does a depth-first search until it
reaches a
container with no child components (since e.g. a JButton is actually a
java.awt.Container this was the only way I could think of to
differentiate it
from e.g. a JPanel) and is supposed to remove the child component from
the parent container and place it in a holder vector, or if it is not
found in
the container, remove it from the holder and place it in the
container.

If the component is present in the container, the method presently
succeeds in placing it in the holder and then removing it from the
container.
The problem occurs when the component is not present in the container
and it
is added to the container from the holder. The next step, removing the
component from the holder, is executed twice despite the presence of a
return
statement which I assumed would terminate the method. I can't figure
out what
is causing the problem. I've included a log of the console output,
hopefully
someone may be able to shed some light on this, I'm stumped.

Thanks,

Brian


public void toggleComponent(String id, Container c) {
System.out.println("toggleComponent("+id+","+c+")");
Component[] children = c.getComponents();
Component cur; // current component

for (int i = 0; i < children.length; i++) {
System.out.println("inside for, i="+i);
cur = children[i];

if ((cur instanceof Container) &&
( ((Container) cur).getComponentCount() > 0 ) ) {

// current component is a non-empty container
toggleComponent(id, (Container)cur);
} else {

// current component is either
// a) an empty container, or
// b) not a container
// in any case, we want to compare it to the specified
// component specified by the 'id' argument
if (pruneXY(cur.toString()).compareTo(id) == 0) {
// the current component matches the supplied argument
// so add current componentto holder & remove from container
found = true;
Container parent = cur.getParent();
//System.out.println("Add to holdernid =t"+cur.toString());
componentHolder.add(cur);
parent.remove(cur);
// redraw
//parent.repaint();
//parent.validate();

// exit method
//System.out.println("about to return from method");
//System.out.println(found);
return;
}
}
}
System.out.println(found);
if (!found) {
// after iterating thru all child components of container c,
// target component not found. Therefore remove from holder
// and add to container c.
System.out.println("Remove from holdernid =t"+id);
c.add(componentHolder.get(id));
//c.repaint();
//c.validate();
System.out.println("about to return from method");
return;
}
System.out.println("after return statement");
}

-------
Output:

toggleComponent(javax.swing.JLabel[,50x16,alignmentX=0.0,alignmentY=null,border=,flags=0,maximumSize=,minimumSize=,preferredSize=,defaultIcon=,disabledIcon=,horizontalAlignment=LEADING,horizontalTextPosition=TRAILING,iconTextGap=4,labelFor=,text=My
Label,verticalAlignment=CENTER,verticalTextPosition=CENTER],javax.swing.JPanel[,86,40,606x426,alignmentX=null,alignmentY=null,border=,flags=9,maximumSize=,minimumSize=,preferredSize=])
inside for, i=0
toggleComponent(javax.swing.JLabel[,50x16,alignmentX=0.0,alignmentY=null,border=,flags=0,maximumSize=,minimumSize=,preferredSize=,defaultIcon=,disabledIcon=,horizontalAlignment=LEADING,horizontalTextPosition=TRAILING,iconTextGap=4,labelFor=,text=My
Label,verticalAlignment=CENTER,verticalTextPosition=CENTER],SimplePanel[,0,0,300x200,layout=java.awt.FlowLayout,alignmentX=null,alignmentY=null,border=,flags=9,maximumSize=,minimumSize=,preferredSize=])
inside for, i=0
true
after return statement
toggleComponent(javax.swing.JLabel[,50x16,alignmentX=0.0,alignmentY=null,border=,flags=0,maximumSize=,minimumSize=,preferredSize=,defaultIcon=,disabledIcon=,horizontalAlignment=LEADING,horizontalTextPosition=TRAILING,iconTextGap=4,labelFor=,text=My
Label,verticalAlignment=CENTER,verticalTextPosition=CENTER],javax.swing.JPanel[,86,40,606x426,invalid,alignmentX=null,alignmentY=null,border=,flags=9,maximumSize=,minimumSize=,preferredSize=])
inside for, i=0
toggleComponent(javax.swing.JLabel[,50x16,alignmentX=0.0,alignmentY=null,border=,flags=0,maximumSize=,minimumSize=,preferredSize=,defaultIcon=,disabledIcon=,horizontalAlignment=LEADING,horizontalTextPosition=TRAILING,iconTextGap=4,labelFor=,text=My
Label,verticalAlignment=CENTER,verticalTextPosition=CENTER],SimplePanel[,0,0,300x200,invalid,layout=java.awt.FlowLayout,alignmentX=null,alignmentY=null,border=,flags=9,maximumSize=,minimumSize=,preferredSize=])
inside for, i=0
inside for, i=1
false
Remove from holder
id = javax.swing.JLabel[,50x16,alignmentX=0.0,alignmentY=null,border=,flags=0,maximumSize=,minimumSize=,preferredSize=,defaultIcon=,disabledIcon=,horizontalAlignment=LEADING,horizontalTextPosition=TRAILING,iconTextGap=4,labelFor=,text=My
Label,verticalAlignment=CENTER,verticalTextPosition=CENTER]
about to return from method
false
Remove from holder
id = javax.swing.JLabel[,50x16,alignmentX=0.0,alignmentY=null,border=,flags=0,maximumSize=,minimumSize=,preferredSize=,defaultIcon=,disabledIcon=,horizontalAlignment=LEADING,horizontalTextPosition=TRAILING,iconTextGap=4,labelFor=,text=My
Label,verticalAlignment=CENTER,verticalTextPosition=CENTER]
java.lang.NullPointerException
Back to top
Andrew Hobbs
Guest





PostPosted: Tue Jun 22, 2004 1:05 am    Post subject: Re: Strange behaviour from recursive function Reply with quote




"grasshopper" <googleN0SPAM (AT) eyeonik (DOT) com> wrote

Quote:
Hi,
I am trying to write a method that toggles the display of a Swing
component(e.g. a JButton) inside a container (e.g. a JPanel).
The method below essentially does a depth-first search until it
reaches a
container with no child components (since e.g. a JButton is actually a
java.awt.Container this was the only way I could think of to
differentiate it
from e.g. a JPanel) and is supposed to remove the child component from
the parent container and place it in a holder vector, or if it is not
found in
the container, remove it from the holder and place it in the
container.

If the component is present in the container, the method presently
succeeds in placing it in the holder and then removing it from the
container.
The problem occurs when the component is not present in the container
and it
is added to the container from the holder. The next step, removing the
component from the holder, is executed twice despite the presence of a
return
statement which I assumed would terminate the method. I can't figure
out what
is causing the problem. I've included a log of the console output,
hopefully
someone may be able to shed some light on this, I'm stumped.

Thanks,

Brian

Generally it is not a good idea to toggle a button by removing and adding
back. Swing isn't really designed for it. Plus it causes confusion for the
user.

If you want to 'remove' it from view I would suggest calling its
setVisible(boolean) method. However, note that removing it from view
whichever you do it, will result in the LayoutManager re-layingout the rest
of the components, possibly causing confusion if it occurs while the user
can see it and all the rest of the components jump around and resize.

A better way would be to inactivate the button. Use a boolean to determine
whether the button should respond and if not replace its icon with an
'inactive' icon or gray out the text by changing its color. That way the
components don't jump about, the user knows where they are but the button
still cannot be used.

This still leaves the problem of identifying the button. You need to work
out a better way. You are testing the String obtained using the toString()
method which as you have found is a string representation of the button's
state. Not only is this a very long string it also may change as the button
changes state, so that you never find the correct button. Also since you
are testing for identity and not its lexicographical order you should use
equals() or equalsIgnoreCase().

Surely a better way would be to test to see if it is a JButton and then test
identity against the button text perhaps.

Alternatively if you are writing the program yourself why not simply write
it so that you do not need to search through all the components in the first
place.

Cheers

Andrew





Back to top
Display posts from previous:   
Post new topic   Reply to topic    AppletTalk.com Forum Index -> Java Help All times are GMT
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2006 phpBB Group
SEO toolkit © 2004-2006 webmedic.