miatech
miatech

Reputation: 2268

GUI not showing as intended

I'm trying to draw a gui like shown in the figure, but somehow I'm not able to place the objects in right place (I guess that the problem is with the layout) the textArea is suppose to go in the middle... but is not showing at all

enter image description here

package Chapter22Collections;
import javax.swing.*;
import java.awt.*;

public class Exercise226 extends JFrame {
    private JButton jbSort;
    private JButton jbReverse;
    private JButton jbAdd;
    private JButton jbShuffle;
    private JLabel jlAddnum;
    private JTextArea jTextDisplay;
    private JTextField jTextAdd;

    public Exercise226() {
        jbSort = new JButton("Sort");
        jbReverse = new JButton("Reverse");
        jbShuffle = new JButton("Shuffle");
        jbAdd = new JButton("Add");
        jlAddnum = new JLabel("Add number here: ");
        jTextDisplay = new JTextArea();
        jTextAdd = new JTextField(8);

        setLayout(new BorderLayout());

        JPanel p1 = new JPanel(new GridLayout(1,3));
        p1.add(jlAddnum);
        p1.add(jTextAdd);
        p1.add(jbAdd);

        JPanel p2 = new JPanel(new GridLayout(1,3));
        p2.add(jbSort);
        p2.add(jbReverse);
        p2.add(jbShuffle);

        add(p1, BorderLayout.NORTH);
        add(jTextDisplay, BorderLayout.CENTER);    
        add(p2, BorderLayout.SOUTH);
    }

    public static void main(String... args) {

        Exercise226 gui = new Exercise226();
        gui.setTitle("Numbers");
        gui.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        gui.setSize(300, 200);
        gui.setLocationRelativeTo(null);
        gui.setVisible(true);   

    }     
}

Upvotes: 3

Views: 599

Answers (3)

Andrew Thompson
Andrew Thompson

Reputation: 168825

How could I add spacing/padding between the elements in the frame? So the text area is more visible and centered.

Borders and padding. E.G.

Exercise226-with-padding-and-borders

Compared with:

Exercise226

import javax.swing.*;
import java.awt.*;
import javax.swing.border.EmptyBorder;
import javax.swing.border.TitledBorder;

public class Exercise226 {
    private JButton jbSort;
    private JButton jbReverse;
    private JButton jbAdd;
    private JButton jbShuffle;
    private JLabel jlAddnum;
    private JTextArea jTextDisplay;
    private JTextField jTextAdd;

    private JPanel gui;

    public Exercise226() {
        gui = new JPanel(new BorderLayout(5,5));
        jbSort = new JButton("Sort");
        jbReverse = new JButton("Reverse");
        jbShuffle = new JButton("Shuffle");
        jbAdd = new JButton("Add");
        jlAddnum = new JLabel("Add number here: ");
        // set the size constraints using columns/rows
        jTextDisplay = new JTextArea("Here I am!", 6,20);
        jTextAdd = new JTextField(8);

        JPanel p1 = new JPanel(new GridLayout(1,3,3,3));
        p1.add(jlAddnum);
        p1.add(jTextAdd);
        p1.add(jbAdd);

        JPanel p2 = new JPanel(new GridLayout(1,3,3,3));
        p2.add(jbSort);
        p2.add(jbReverse);
        p2.add(jbShuffle);

        JPanel textAreaContainer = new JPanel(new GridLayout());
        textAreaContainer.add(new JScrollPane(jTextDisplay));
        textAreaContainer.setBorder(new TitledBorder("Text Area Here"));

        gui.add(p1, BorderLayout.PAGE_START);
        gui.add(textAreaContainer, BorderLayout.CENTER);    
        gui.add(p2, BorderLayout.PAGE_END);

        gui.setBorder(new EmptyBorder(4,4,4,4));
    }

    public Container getGui() {
        return gui;
    }

    public static void main(String... args) {
        JFrame f = new JFrame();

        Exercise226 gui = new Exercise226();
        f.setContentPane(gui.getGui());
        f.setTitle("Numbers");
        f.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
        f.pack();
        f.setLocationByPlatform(true);
        f.setVisible(true);   

    }     
}

This code:

  • Primarily provides 'white space' in the GUI using different constructors for the layouts that accept 2 int arguments for horizontal & vertical spacing.
  • Also adds 2 borders:
    1. An empty border around the entire GUI to provide some spacing between it and the frame decorations.
    2. A titled border around the text area, to make it very obvious.
  • Does implement a change for one unnecessary part of the original code. Instead of extending frame, it simply retains an instance of one.
  • Uses the JScrollPane container for the text area, as suggested by @Reimeus. It adds a nice beveled border of its own to an element that needs no scroll bars.
  • Creates a textAreaContainer specifically so that we can set a titled border to surround the scroll pane - without interfering with its existing border.
    It is possible to use a CompoundBorder for the scroll pane that consists of the existing border (scroll.getBorder()) & the titled border. However that gets complicated with buttons & other elements that might change borders on selection or action. So to set an 'outermost border' for a screen element (like the text area here) - I generally prefer to wrap the entire component in another container first.
  • Does not create and show the GUI on the EDT. Swing GUIs should be created and modified on the EDT. Left as an exercise for the user. See Concurrency in Swing for more details.

Old Code

The original code on this answer that provides the 'comparison GUI image' seen above. IT is closely based on the original code but with the text area wrapped in a scroll pane (and gaining a beveled border because of that) & given some text to display.

Exercise226

import javax.swing.*;
import java.awt.*;

public class Exercise226 extends JFrame {
    private JButton jbSort;
    private JButton jbReverse;
    private JButton jbAdd;
    private JButton jbShuffle;
    private JLabel jlAddnum;
    private JTextArea jTextDisplay;
    private JTextField jTextAdd;

    public Exercise226() {
        jbSort = new JButton("Sort");
        jbReverse = new JButton("Reverse");
        jbShuffle = new JButton("Shuffle");
        jbAdd = new JButton("Add");
        jlAddnum = new JLabel("Add number here: ");
        // set the size constraints using columns/rows
        jTextDisplay = new JTextArea("Here I am!", 6,20);
        jTextAdd = new JTextField(8);

        setLayout(new BorderLayout());

        JPanel p1 = new JPanel(new GridLayout(1,3));
        p1.add(jlAddnum);
        p1.add(jTextAdd);
        p1.add(jbAdd);

        JPanel p2 = new JPanel(new GridLayout(1,3));
        p2.add(jbSort);
        p2.add(jbReverse);
        p2.add(jbShuffle);

        add(p1, BorderLayout.NORTH);
        add(new JScrollPane(jTextDisplay), BorderLayout.CENTER);    
        add(p2, BorderLayout.SOUTH);
    }

    public static void main(String... args) {

        Exercise226 gui = new Exercise226();
        gui.setTitle("Numbers");
        gui.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        //gui.setSize(300, 200);
        gui.pack();
        //gui.setLocationRelativeTo(null);
        gui.setLocationByPlatform(true);
        gui.setVisible(true);   

    }     
}

Upvotes: 4

trashgod
trashgod

Reputation: 205785

To make the textArea re-size with the window, try BoxLayout. Box is "A lightweight container that uses a BoxLayout object as its layout manager."

Box p1 = new Box(BoxLayout.X_AXIS);

Upvotes: 4

Reimeus
Reimeus

Reputation: 159754

The JTextArea is actually where you expect it to be but has no outline border. It is usual to place the component in a JScrollPane which will give this effect:

add(new JScrollPane(jTextDisplay), BorderLayout.CENTER);

or simply

add(new JScrollPane(jTextDisplay));

Upvotes: 4

Related Questions