views:

40

answers:

2

I am writing an application that is a virtual notebook. The idea is to have panels with various content (which is based on an external file) added to a panel that acts as a page. Once that page is full, its specialized add method should return false.

The problem is that I can't figure out how to accurately determine the size of the panels when I'm adding them, so I end up adding too many. The preferredSize of the panels is generally too short, and the size has 0 height. Is there a way to determine the exact size that a component is taking up in a layout?

I've tried using doLayout(), but it doesn't seem to change the size or preferredSize of my components. Maybe I'm not using it right? Here is the add method: (The contentPanel has BoxLayout, and the content panel doesn't have a set size, but is added to a panel (this) that does. The class this method is in extends JPanel)

public boolean addSpecializedgPanel(SpecializedPanel sp) {

    this.contentPanel.add(sp);

    this.doLayout();

    if (this.contentPanel.getSize().height > this.getHeight()) {
        this.contentPanel.remove(sp);
        return false;
    }

    return true;
}

Thanks for any help (even if it criticizes my whole design :) )! This has been a huge headache!

+1  A: 

I don't think you should deal with the size like that, you should use a layout manager for that. Maybe you should have a look at How to use CardLayout

Jonas
Jonas, I use CardLayout for all of the pages, and it's very useful for that. I'm not sure how it would help here, though. This is adding small panels to a larger panel that looks like a single page in the virtual notebook. I can't figure out how to know when to stop adding components so that the page isn't over-filled.
Kate
@StudentDesigner: Ok, but isn't it much better to use a JList or a JTable instead. Then you don't have to add components at runtime, that isn't recommended.
Jonas
I imagine I could use a JList with a custom renderer, but I'm not sure how that would help? The tough part is that since the information about the content of the SpecializedPanels comes from an external source (an XML file), I don't know anything about them until runtime. I think I am stuck adding them in this way, unfortunately.
Kate
+1  A: 

You want to use Container.validate() on the panel (possibly calling invalidate() first):

public void validate()

Validates this container and all of its subcomponents.

The validate method is used to cause a container to lay out its subcomponents again. It should be invoked when this container's subcomponents are modified (added to or removed from the container, or layout-related information changed) after the container has been displayed.

This should cause layout to occur, and, consequently, resizing of the components. You will then need to invalidate() after removing your failing panel, before returning false.

Software Monkey
Software Monkey, I tried your suggestion, but using printlns before and after, I saw no change in the values returned by getSize() for the panel being added. It makes me wonder why the validate isn't changing anything...
Kate
In fact, after the whole notebook is visible, from cover to cover, the size of the specialized panels still returns zero! How weird. Thanks for your suggestion --- I didn't know about invalidate() before.
Kate
@Stud: Do be sure you are doing this GUI manipulation on the EDT (Event Dispatch Thread); otherwise all bets are off.
Software Monkey
@Software Monkey, I re-asked my question in a way that has a clearer code example and is related to your advice. If you have time, maybe you could take a look? http://stackoverflow.com/questions/3482379/return-actual-size-of-jcomponent-as-displayed Thanks again for your help!
Kate
@Kate: I see your other question seems to have gotten you the answer you needed.
Software Monkey