0

Hello - I've used a for loop to fill an array of JButtons with text. Each JButton contains a letter of the alphabet. I've been successful in doing this and adding each button to a panel I created. But my problem is that I've tried, unsuccessfully, to add ActionListener's to each of the JButtons. When I press the button it should print the text in the JButton.

Any idea's?

5
Contributors
7
Replies
10
Views
6 Years
Discussion Span
Last Post by ztini
0

You can use the getSource() method of the ActionEvent to get a reference to the button that was clicked. You will need to cast it to JButton yourself to use it, since getSource() returns Object.

0

You can also try using the getActionCommand() inside the actionPerformed part of the listener.
This function returns a String so you should be able to avoid casting.

0

or the obvious guys....

add the actionlistener to the loop---or even better, separate the creation of the button all together...shazam!

import java.awt.BorderLayout;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.ArrayList;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JTextField;
import javax.swing.SwingConstants;


public class ButtonClicker extends JFrame {

	private static final long serialVersionUID = 1L;
	private JTextField output = new JTextField();
	private ArrayList<JButton> list = new ArrayList<JButton>();

	public ButtonClicker() {
		configLayout();
		configFrame();
	}
	
	private void configFrame() {
		setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		setVisible(true);
		setResizable(false);
		setLocation(400, 200);
		pack();
	}
	
	private void configLayout() {
		getContentPane().setLayout(new BorderLayout());
		output.setHorizontalAlignment(SwingConstants.RIGHT);
		output.setFocusable(false);
		getContentPane().add(output, BorderLayout.NORTH);

		JPanel panel = new JPanel();
		getContentPane().add(panel, BorderLayout.CENTER);
		panel.setLayout(new GridLayout(3, 3));
		
		for (int i = 1; i <= 9; i++)
			panel.add(createButton(i));

		getContentPane().add(createButton(0), BorderLayout.SOUTH);
	}
	
	private JButton createButton(final int text) {
		JButton button = new JButton(Integer.toString(text));
		button.setFocusable(false);
		button.addActionListener(new ActionListener() {
			@Override
			public void actionPerformed(ActionEvent e) {
				output.setText(output.getText() + text);
			}
		});
		list.add(button);
		return button;
	}
	
	public static void main(String[] args) {
		new ButtonClicker();		
	}
}
0

just some ..., no FW (that's about e.getSource())

- have to create GUI on EDT (main method)
- have to place, size, pack TopLayoutContainer, and then visible container
- you are set LayoutManager correctly, then there is no longer needed something about ContentPane, (hmmmm, sure backGround Color, but just for empty container)
- if you want to create thread safe outPut from Listener, then you have put

outPut to Swing Action or
outPut pack to SwingUtilities.invokeLater(...

there is ...

import java.awt.*;
import java.awt.event.*;
import java.util.ArrayList;
import javax.swing.*;

public class ButtonClicker extends JFrame {

    private static final long serialVersionUID = 1L;
    private JTextField output = new JTextField();
    private ArrayList<JButton> list = new ArrayList<JButton>();

    public ButtonClicker() {
        configLayout();
        configFrame();
    }

    private void configFrame() {
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setResizable(false);
        setLocation(400, 200);
        pack();
        setVisible(true);
    }

    private void configLayout() {
        setLayout(new BorderLayout());
        output.setHorizontalAlignment(SwingConstants.RIGHT);
        output.setFocusable(false);
        add(output, BorderLayout.NORTH);
        JPanel panel = new JPanel();
        add(panel, BorderLayout.CENTER);
        panel.setLayout(new GridLayout(3, 3));
        for (int i = 1; i <= 9; i++) {
            panel.add(createButton(i));
        }
        add(createButton(0), BorderLayout.SOUTH);
    }

    private JButton createButton(final int text) {
        JButton button = new JButton(Integer.toString(text));
        button.setFocusable(false);
        button.addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent e) {
                Runnable doRun = new Runnable() {

                    public void run() {
                        output.setText(output.getText() + text);
                    }
                };
                SwingUtilities.invokeLater(doRun);
            }
        });
        list.add(button);
        return button;
    }

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {

            public void run() {
                ButtonClicker bC = new ButtonClicker();
            }
        });
    }
}
0

Yo - cheers all for reply's. I examined all entries and made up my own. It does the job so here is my simple code for solving my problem:

// Constructor for panel class; added to main frame in separate class

public dummyPanel()
	{
		int j = 0;
		
		while( j < 3 )
		{
			add( crteBttn( ""+j ) );
			j++;
		}
	}

// Create and add the Button to the screen
public JButton crteBttn( String text )
	{
		final JButton aBttn = new JButton( "Button "+text );
		aBttn.addActionListener( new ActionListener()
		{
			public void actionPerformed( ActionEvent evt)
			{
				String txt = aBttn.getText();
				System.out.println( txt );
			}
		});
		return aBttn;
	}
0

I think that not, it doesn't, what will be happends if you'll need to set separated action from each JButton, isn't it

0

mKorbel -- read the poster's original post. They just need it to create buttons A through Z that update a Label. Where are you getting that they need threading and separate actions? Regardless---the OP solved this thread.

Best of luck Katana, your code looks great.

This question has already been answered. Start a new discussion instead.
Have something to contribute to this discussion? Please be thoughtful, detailed and courteous, and be sure to adhere to our posting rules.