tags:

views:

502

answers:

4

I need to make a button that will display different things depending on the state if the app. So for example if nothing has been opened its title will be "Lesson Plans" and if project B is open it will be "project B Lesson Plan", I am using the java.awt.Button class for this. My question, is there a way to determine how big the button should be to fit the given text. For example can I somehow get the width of each character in the given font used by the button then multiply this by the characters in the title I want to use? How would I get this character width or is there some better way? Thanks!

+4  A: 

Measuring widths of individual characters in particular fonts (not all characters are the same width) gets complicated, especially if you want to take into account the spaces between characters, and add some margin either side so they don't butt up against the edges of the button. (N.B. Others have provided a few ways of doing this more simply than I realized was possible!)

Much better/more usual solution is to let Java do the work for you. If you're using using a java.awt.Button (or javax.swing.JButton), then it will usually automatically size to the text on it. If your particular button is behaving strangely, then you probably have a layout problem. Check the section of the Java tutorial on Layout Managers for more information.

As an example (in Swing, rather than AWT - sorry!), these two buttons end up being the right size for the text on them:

import javax.swing.*;

public class ButtonTest {
    public static void main(String[] args) {
        JButton button1 = new JButton("Some label");
        JButton button2 = new JButton("Some much longer label");
        JFrame frame = new JFrame();
        JPanel panel = new JPanel();
        panel.add(button1);
        panel.add(button2);
        frame.getContentPane().add(panel);
        frame.pack();
        frame.setVisible(true);
    }
}

If you really do want the size, rather than just letting Java do its best, then I would recommend calling button1.getPreferredSize() and button2.getPreferredSize() after the call to frame.pack().

Martin McNulty
Yeah my button seems to always seems to take up as much space as it can so I must have some sort of layout problem I will check out that link. Thanks a lot.
Mike2012
Just a guess, but you might be using BorderLayout - that stretches components to fit available space, rather than leaving them at their preferred size. If that's the problem, you can try adding your button to a panel then add the panel instead. Might be completely wrong though as I don't know what the actual problem is! :)
Martin McNulty
A: 

Just a quick glance at the API Docs shows:

public Rectangle2D getStringBounds(String str, FontRenderContext frc)

in java.awt.Font

Returns the logical bounds of the specified String in the specified FontRenderContext. The logical bounds contains the origin, ascent, advance, and height, which includes the leading.

So that should help you.

Jan Gressmann
A: 

Have you tried using either getMinimumSize() or getPreferredSize() on the button? I believe one of these will tell you the minimum size the button needs to be to display its label.

Laurence Gonsalves
A: 

On the awt Button you can call getFontMetrics and then ask for the getStringBounds. This you can then set the preferred size of the button based on this. It won't take into account the extra spacing you'll need for the borders though (which varies depending on platform).

I'd try setting each to the strings in turn, getting the preferred sizes and then just set the preferred size for the largest size.

Tom