Search code examples
javaswinguser-interfacelayout-managerboxlayout

Aligning Labels with TextFields


For some reason, I cannot get my Label Objects(TermLabel,DefinitionLabel) to line up with my text fields, which is weird because I'm using BoxLayout and that should line every component up. Is there something that I'm missing?

import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.BorderFactory;
import javax.swing.Box;
import javax.swing.BoxLayout;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTextArea;
import javax.swing.JTextField;


public class AddNewCard extends JFrame {

    /*
     * produces another frame for adding a new card for the set
     */
    private JButton create;
    private JButton importDefinition;
    private CardSet cardSet;
    private JLabel termLabel = new JLabel("Term");
    private JTextField termField = new JTextField();
    private JLabel definitionLabel = new JLabel("Definition");

    private JTextArea definitionArea = new JTextArea();
    private JScrollPane scrollPane;
    private boolean editing = false;
    private String term;
    private String definition;
    private AddNewCard editFrame;

    /*
     * adding a new card
     */
    public AddNewCard(int x, int y) {
        super("Add New Card");
        this.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
        this.add(new CardPanel());
        this.setSize(100,200);
        this.setLocationRelativeTo(null);
        this.pack();
        this.setVisible(true);
    }


    public Dimension getPreferredSize() {
        return new Dimension(300,300);     
    }

    private class CardPanel extends JPanel {

        public CardPanel() {

            this.setBorder(BorderFactory.createEmptyBorder(10,10,10,10));
            this.setLayout(new BoxLayout(this, BoxLayout.PAGE_AXIS));
            termField.setMaximumSize(new Dimension(1000, 20));


            this.add(termLabel);
            this.add(termField);
            this.add(definitionLabel);

            definitionArea.setOpaque(true);
            definitionArea.setText(definition);
            definitionArea.setWrapStyleWord(true);
            definitionArea.setLineWrap(true);
            definitionArea.setEditable(true);
            definitionArea.setFocusable(true);
            scrollPane = new JScrollPane(definitionArea);
            this.add(scrollPane);

            createButtons(this);
        }


        private void createButtons(CardPanel panel) {
            if (!editing)
            create = new JButton("Create");
            else
            create = new JButton("Change");
            //importDefinition.addActionListener(new ButtonListener());
            create.addActionListener(new ButtonListener());
            create.setActionCommand("1");
            //importDefinition.setActionCommand("2");

            panel.add(create);
            //panel.add(importDefinition);


        }

    }
}

Test:

import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;


public class Test {
    public static void main(String[] arg) {
         SwingUtilities.invokeLater(new Runnable() {
                public void run() {
                    createGUI(); 
                }
          });
    }

    public static void createGUI() {
        AddNewCard anc = new AddNewCard(100,100);
    }

}

Solution

  • First, take a look at How to Use BoxLayout, in particular, the Features, which clearly demonstrates how you might solve the problem.

    Essentially, you need to set each components X alignment to Component.LEFT_ALIGNMENT

    BoxLayout

    termLabel.setAlignmentX(Component.LEFT_ALIGNMENT);
    termField.setAlignmentX(Component.LEFT_ALIGNMENT);
    definitionLabel.setAlignmentX(Component.LEFT_ALIGNMENT);
    //...
    scrollPane.setAlignmentX(Component.LEFT_ALIGNMENT);
    //...
    create.setAlignmentX(Component.LEFT_ALIGNMENT);
    

    Also, favour specifying columns (and rows to text area) over using setPreferredSize (or getPreferredSize)

    private JTextField termField = new JTextField(10);
    //...
    private JTextArea definitionArea = new JTextArea(10, 20);
    

    You'll get better results where DPI and font sizes are different