1

today i'm having a little problem, that probably is nothing for pros here :)

I want to have my Swing compononents in one horizontal line. I used FlowLayout and changed size of components on componentResized() according to the frame size, but it often bugged (sometimes the last component was placed in next row)... I've decided to use BoxLayout, but on that code:

    down=new JPanel(new BoxLayout(down,BoxLayout.X_AXIS));
    down.setBorder(BorderFactory.createEmptyBorder(0, 10, 10, 10));
    down.add(Box.createHorizontalGlue());
    down.setPreferredSize(new Dimension(300,35));

it crashes with:

Exception in thread "AWT-EventQueue-0" java.awt.AWTError: BoxLayout can't be shared
at javax.swing.BoxLayout.checkContainer(Unknown Source)
at javax.swing.BoxLayout.invalidateLayout(Unknown Source)
at javax.swing.BoxLayout.addLayoutComponent(Unknown Source)
at java.awt.Container.addImpl(Unknown Source)
at java.awt.Container.add(Unknown Source)
at ButtonFrame.<init>(chat.java:278)
at chat$1.run(chat.java:20)
aso...

I dont know what to do, maybe i can make FlowLayout unable to make 2nd row, or make box layout work?

Thanks for any replies!

noisy cat
  • 2,865
  • 5
  • 33
  • 51

4 Answers4

5

Copy-pasted from the Swing tutorial about BoxLayouts

JPanel listPane = new JPanel();
listPane.setLayout(new BoxLayout(listPane, BoxLayout.PAGE_AXIS));

See how the panel is first created without any layout, and then the layout is set and created with the existing panel. This is different with your

down=new JPanel(new BoxLayout(down,BoxLayout.X_AXIS));

Adjusting this line (making it two separate statements as in the example) will remove the exception.

Oh yeah, a BoxLayout should allow to fulfill your requirement

Robin
  • 36,233
  • 5
  • 47
  • 99
  • Yes, the problem was that you were attempting create the JPanel's layout with itself.. And at that point the JPanel had not been properly initialized and cannot be used safely. – Alex Jan 17 '12 at 15:16
2

Take a look at http://www.miglayout.com/ which blows away anything Java provides itself. As soon as you need to do anything complex, it'll make your life worlds easier.

Reverend Gonzo
  • 39,701
  • 6
  • 59
  • 77
2

FlowLayout or BoxLayout are layout managers. The goal of a layout manager is to compute components position and size automatically, so you should not modify your components' size directly. Here, with componentResized() you are notified that a component has been resized. It may have been resized by layout manager automatically. If you modify your components' size here, it may trigger another automatic layout procedure, etc.

The preferred way to specify a size for your component is to set their preferred size before adding components to their container.

yohann.martineau
  • 1,523
  • 1
  • 17
  • 24
1

I often find that GridBagLayout has enough flexibility and control to do what I need.

Mitch
  • 989
  • 1
  • 9
  • 25