Calling ActionListener twice - java

I feel like there's an easy solution to this but for some reason, I can't wrap my head around it.
I have a situation where one button has to be clicked first in order for another one to be clicked. The options the user chooses for those 2 JButtons will determine the program's next step. This would mean I'd have to call actionListener twice, right? How would I do this in one actionPerformed method?
I don't think I could do if (e.getSource() == square[1][4] && e.getSource() == up) { } in the actionPerformed method...
EDIT: I have a board of 4x4 buttons that I made using a 2d array of JButtons and they contain 2 pieces. I also have 4 JButtons to represent north, east, south, west. The user has to click a piece on the 4x4 board and then click the direction in order for the piece to move.
public class Board extends JPanel implements actionListener
{
// other variables listed
private JButton[][] square;
private boolean circleSelected = false;
private boolean triangleSelected = false;
// other irrelevant methods
public void actionPerformed(actionEvent e)
{
// I don't know how to go about this part
}
}
If it's needed, I have square[0][0] containing the circle piece and square[2][3] containing the triangle piece. However, since the x and y will keep changing, I don't want to specify the exact placement. Instead, I'd rather determine the circleSelected variables from the image that's clicekd i.e. if the user clicks on the button[x][y] that has an image of a circle on it, then circleSelected = true if that makes sense...

This would mean I'd have to call actionListener twice, right?
Not quite. You shouldn't directly call an ActionListener once but rather these listeners should respond to user action only.
I don't think I could do if (e.getSource() == square[1][4] && e.getSource() == up) { } in the actionPerformed method...
Correct, this would be very wrong since the ActionEvent's source property refers to one and only one object.
Likely what you should do is use a private instance field of your class, or multiple fields, to hold state information that is used in your listeners. In other words, have a variable or variables hold information that tells the class if a button has been pressed previously, which button, etc, and then base what happens in a listener by what is held by these state variables. For more specific details and answers, please consider asking a more specific question, including pertinent code, preferably a minimal example program.
As an aside, most buttons should have their own listener, often as an anonymous inner class.
Aside #2: if a button should not be pressed until another button is pressed, then that button, or its Action, should be disabled until it is supposed to be pressed. This can be changed by calling .setEnabled(...) on the button or on its Action (if it has an Action).
For example, try compiling and running the code below. Here I use firstButton as my state field, the one that changes the behavior of the ActionListener. You can use booleans, or any instance fields of the class for this purpose:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class Board extends JPanel {
public static final int ROWS = 4;
private JButton[][] square = new JButton[ROWS][ROWS];
private JButton firstButton = null;
public Board() {
JPanel squarePanel = new JPanel(new GridLayout(ROWS, ROWS));
for (int i = 0; i < square.length; i++) {
for (int j = 0; j < square.length; j++) {
String text = String.format("[%d, %d]", j, i);
square[i][j] = new JButton(text);
square[i][j].setFont(square[i][j].getFont().deriveFont(32f));
square[i][j].addActionListener(e -> squareListener(e));
squarePanel.add(square[i][j]);
}
}
setLayout(new BorderLayout());
add(squarePanel);
}
private void squareListener(ActionEvent e) {
if (firstButton == null) {
firstButton = (JButton) e.getSource();
firstButton.setEnabled(false);
} else {
JButton secondButton = (JButton) e.getSource();
secondButton.setEnabled(false);
String text = "First Button: " + firstButton.getActionCommand() + "; Second Button: " + secondButton.getActionCommand();
JOptionPane.showMessageDialog(this, text, "Selected Buttons", JOptionPane.PLAIN_MESSAGE);
for (JButton[] row : square) {
for (JButton button : row) {
button.setEnabled(true);
}
}
firstButton = null;
}
}
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> {
JFrame frame = new JFrame("GUI");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new Board());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
});
}
}

just create a boolean variable isButtonOneClicked that can show if the first button is clicked and if Button 2 is Clicked and the variable's value is true then your next actions will be performed
boolean isButtonOneClicked=false;
button1.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e){
isButtonOneClicked=true;
}
});
button2.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e){
if(isButtonOneClicked){
//perform next steps
}
else{
// button 1 isn't clicked
// can't proceed to next Steps
}
}
});

Related

How to determine which panel holds a button that was pressed - Application Window

I have an array of Tile objects (Panel, Button to a tile) in a JPanel, 20x20. If button 1 is clicked, a thing happens, button 2 is pressed, a thing happens, etc.
I want a specific function to happen every time a button other than one in the top row is clicked (the top row of buttons all have functions assigned, the other 380 buttons do not have assigned functions).
So in the top buttons' cases I have the code:
if(e.getSource() == tiles[0][0].button)
{
//do stuff
}
else if(e.getSource() == tiles[0][1].button)
{
//do stuff
}
For the other buttons, I want something along the lines of:
JButton button;
button = e.getSource();
JPanel hostPanel = button.PanelInWhichButtonisContained();
but I'm not sure what the syntax or what sort I would to do achieve that task. I don't really have any code to present prior attempts because I'm not sure how to approach this task, but I haven't been able to find anything on the World Wide Web to help me in this task.
I'm currently just using default application window libraries and classes (javax.swing, java.awt, etc) but I'm completely open to downloading external libraries.
Determining the "source" of an action like a button press in the actionPerformed method is usually brittle (and fortunately, hardly ever necessary).
This means that this is highly questionable:
class ButtonListener implements ActionListener {
#Override
public void actionPerformed(ActionEvent e) {
// DON'T DO THIS!
if (e.getSource() == someButton) doThis();
if (e.getSource() == someOtherButton) doThad();
}
}
You should usually NOT do this.
And of course, it's even worse to add casts and walk up some container hierarchy:
// DON'T DO THIS!
Object source = e.getSource();
Component button = (Component)source;
Component parent = button.getParent();
if (parent == somePanel) doThis();
if (parent == someOtherPanel) doThat();
In basically all cases, it is far more flexible and elegant to attach a listener to the button that is specific for the button - meaning that it knows what the button should do.
For individual buttons, this can be solved the old-fashioned way, using an anonymous inner class:
class Gui {
void create() {
JButton startButton = new JButton("Start");
startButton.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
startSomething();
}
});
}
private void startSomething() { ... }
}
The same can be written far more concisely using lambda expressions with Java 8:
class Gui {
void create() {
JButton startButton = new JButton("Start");
startButton.addActionListener(e -> startSomething());
}
private void startSomething() { ... }
}
(A side note: I consider it as a good practice to only call a single method in the ActionListener implementation anyhow. The actionPerformed method should not contain many lines of code, and particularly no "business logic". There should be a dedicated method for what the button does - for example, to startSomething, as in the example above)
For buttons that are contained in arrays, as in the example in your question, there is a neat trick to retain the information about the button that was clicked:
class Gui {
JButton buttons[];
void create() {
buttons = new JButton[5];
for (int i=0; j<buttons.length; i++) {
int index = i;
buttons[i] = new JButton("Button " + i);
buttons[i].addActionListener(e -> clickedButton(index));
}
}
private void clickedButton(int index) {
System.out.println("Clicked button at index " + index);
}
}
In many cases, you then don't even have to keep the JButton buttons[] array any more. Often you can just create the buttons, add them to some panel, and then are only interested in the index that is passed to the clickedButton method. (The button[] array may be necessary in some cases, though - for example, if you want to change the label of a button after it was clicked).

How Can I make this TicTacToe Code I wrote tell me who is the winner at the end?

Ok, so I wrote this because I wanted to write a code for tictactoe with multiple classes instead of just one class. I can not for the life of me figure out how to make it tall me who won. If anyone can help, I would be very grateful.
RUNNER CLASS
public class TicTacToe
{
//runs the game
public static void main(String[] args)
{
new createWindow();
}
}
BUTTON CLASS
import java.awt.event.*;
import javax.swing.*;
public class XOButton extends JButton implements ActionListener
{
private static int click = 0;
private String letter;
public void actionPerformed(ActionEvent a)
{
click++;
//Calculate Who's Turn It Is(X is always first)
if(click == 1 || click == 3 || click == 5 || click == 7 || click == 9|| click == 11)
{
letter = "<html><font color = blue>"+ "X"+"</font></html>";
this.setText(letter);
this.removeActionListener(this);
}
else if(click == 2 || click == 4 || click == 6 || click == 8 || click == 10)
{
letter = "<html><font color = red>"+ "O"+"</font></html>";
this.setText(letter);
//removes action listener so button can't be pressed again
this.removeActionListener(this);
}
}
public XOButton()
{
this.addActionListener(this);
}
}
WINDOW CLASS
import java.awt.*;
import javax.swing.*;
public class createWindow extends JFrame
{
private static JFrame window = new JFrame("Tic-Tac-Toe");
//creates buttons to fill window
private JButton button1 = new XOButton();
private JButton button2 = new XOButton();
private JButton button3 = new XOButton();
private JButton button4 = new XOButton();
private JButton button5 = new XOButton();
private JButton button6 = new XOButton();
private JButton button7 = new XOButton();
private JButton button8 = new XOButton();
private JButton button9 = new XOButton();
public createWindow()
{
/*Create Window Parameters*/
window.setSize(300,300);
window.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
window.setLayout(new GridLayout(3,3));
//fills window with buttons
window.add(button1);
window.add(button2);
window.add(button3);
window.add(button4);
window.add(button5);
window.add(button6);
window.add(button7);
window.add(button8);
window.add(button9);
window.setVisible(true);
}
}
Of course you can keep track of the Xs and Os in the XOButton. Just look at its name. ;)
To achieve this, simply implement a member variable, like
private String label;
and maybe a getter
public String getLabel()
{
return this.label;
}
and modify your void actionPerformed(ActionEvent) as follows:
public void actionPerformed(ActionEvent a)
{
click++;
//Calculate Who's Turn It Is(X is always first)
if(click % 2 != 0) // click is odd
{
this.label = "X";
// set text
}
else // click is even
{
this.label = "O";
// set text
}
// remove action listener
}
However, you know have to evaluate the pattern to see whether any player has won. For example if button1, button5 and button9 all have "X".equals(button.getLabel()), then player X has won (full diagonal row). Same for (1, 2, 3), (2, 5, 8) and so on ...
Above numbers assume that the buttons are arranged in a 3x3 grid.
Edit
I just pointed myself to the actual problem. Now there's still the problem with how to evaluate the result regarding all buttons. This is a little more complex if you want to do it right.
So you created two classes
createWindow: manages the window and the buttons
XOButton: manages user input
Q: Now, which class should probably be responsible of evaluating which player has won?
A: It's createWindow, because it holds all buttons.
Q: And how is it possible to 'get here' from the void actionPerformed(ActionEvent) method in XOButton? An XOButton doesn't know a createWindow.
A: By implementing an ActionListener, just as you do to do your stuff when the XOButton is clicked.
Hence createWindow also implements ActionListener and everytime it creates an XOButton it registers itself:
XOButton buttonN = new XOButton();
buttonN.addActionListener(this);
Now you can implement a method with the signature void actionPerformed(ActionEvent) in createWindow and evaluate the game result there.
Edit 2
Now there's the problem that we cannot decide which ActionListener will be executed first. However, the order the ActionListeners are executed is decided by the JButton and though it's deterministic (from last to first) I don't like to rely on it.
So what you can do here is define your own ActionListener. This is in fact as simple as it could be - just extend the interface.
interface PostActionListener extends ActionListener
{
// empty
}
Now you have to manage this sort of Event in your XOButton. To do this you can mostly follow the basic operations that are necessary to handle an ActionListener.
First you need a method in XOButton to register a listener of the type you defined.
public void addPostActionListener(PostActionListener l)
{
this.listenerList.add(PostActionListener.class, l);
}
Note: listenerList is a protected member of JButton (more precisely of AbstractButton, but it ultimately boils down to the same)
Second you need to notify all listeners when the action took place. In your case as the last action of actionPerformed(ActionEvent a) in XOButton.
public void actionPerformed(ActionEvent a)
{
// do your magic
// now as the last action notify 'child' listeners
for(PostActionListener l : this.listenerList.getListeners(PostActionListener.class))
{
l.actionPerformed(a);
}
}
Note: This simple loop is often extracted to a separate method that, following the convention, would look like protected void firePostActionPerformed(ActionEvent a).
Last but not least you change everything in createWindow from ActionListener to PostActionListener.
You can have a 2 by 2 array. On every button click, you set the letter entered (either X or O) on the position of the array that the user clicked. And after every click you can have a method which checks if the puzzle was won by either of the parties.
This was the approach I had, and on looking at the comments, Gabriele B-David got the same idea here before me. So I am just complementing his original answer.

How to set the ActionListener for multiple different nameless JButtons. How can they be treated independently when they all have the same or no name?

Here is an example. I have a grid of different buttons (adding each to Grid Layout) and I don't want names for any of them but want to carry out different commands for each of them. How can I tell the difference when Overriding actionPerformed?
/* MULTIPLE BLANK JBUTTONS WHAT DO????????? */
JButton temp;
for(int i = 0; i < BOARD_WIDTH*BOARD_HEIGHT; i++){
temp = new JButton();
temp.setActionEvent("a" + i);
temp.addActionListener(new ActionListener{
//Anonymous Class????? Is there a better way?
}
});
this.add(temp);
Use JButton#setActionCommand(String) to create a unique identifier for each JButton in your loop.
In this situation it's better to have private implementation of ActionListener interface in your container (JPanel, JFrame, ...) instead of having an anonymous ActionListener implementation in the loop. It's cleaner in this way and on the other hand as #MadProgrammer mentioned does not provide a public access to actionPerformed as well.
So In the actionPerformed method you can use ActionEvent#getActionCommand to find out which button is pressed. For example:
public class GameBoard extends JPanel {
public void init(){
MyButtonActionListener actionListener = new MyButtonActionListener();
/* MULTIPLE BLANK JBUTTONS WHAT DO????????? */
JButton temp;
for(int i = 0; i < BOARD_WIDTH*BOARD_HEIGHT; i++){
temp = new JButton();
//temp.setActionEvent("a" + i);
temp.setActionCommand(""+i); // <- Unique Identifier
temp.addActionListener(actionListener);
this.add(temp);
}
}
private static class MyButtonActionListener implements ActionListener{
public void actionPerformed(ActionEvent e){
String actionCommand = e.getActionCommand();
// Decide what to do for each button:
// ...
}
}
}
This can be boosted if you create a two dimensional array of JButton and according to the actionCommand you can find out which button is pressed by doing the calculation of indices in the two dimensional array.
Hope this help.

How to reference JButtons objects for Tic-tac-Toe Game Logic(Tic Tac Toe Game in Java)

I am working on a Tic-Tac-Toe Game. I have added the 9 JButtons with ActionListeners. Each button properly listens for action events. Finally I am working on the logic component of the game but I am stuck on how to go about it.
If you take a look at my TicTacToeButton class, I decided to give the TicTacToeButton object that extends JButton two instance variables: an integer variable that represents the number of the button(so I know which button # was pressed. Number zero is the first number) and a character variable that will be assigned a 'o' character to the character array called boardLogic for player 1 and 'x' for player 2.
The problem is I have no knowledge of how to go about referencing my elements inside the TicTacToeButton array in my TicTacToeBoard class to perform which JButton was actually pressed in the game. Is there a method inside the Java object that tells you whether JButton with number 0 was pressed or JButton with number 1 was pressed corresponding with the code I have stated below.
import java.awt.BorderLayout;
import java.awt.Container;
import java.awt.Dimension;
import java.awt.GridLayout;
import java.awt.Point;
import javax.swing.JFrame;
import javax.swing.JPanel;
/*
* The TicTacToeBoard is an object that has characterisitics of a JFrame
*/
public class TicTacToeBoard extends JFrame {
/* create an array of characters that holds 9 elements
* to create a model for the tic-tac-toe board logic since the board has 9 boxes
* create the board from a separate class to minimize bugs and for easier debugging
* simulate the game's logic by creating an array of characters
*/
public static char[] boardLogic = {};
// number of buttons in the game
static int numOfButtons = 9;
// TicTacToeButton is an object that extends JButton
static TicTacToeButton[] buttons;
public TicTacToeBoard() {
// setTitle to the frame
setTitle("TicTacToe Game");
/* call this method to the GameFrame object if you do not call this
* method the JFrame subclass will not actually close
*/
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
/* set size to an appropriate size create a dimension object
* notice my Dimension object does not have a variable this is
* a prefer way to create this object since no further
* operations will be perform on this object besides this operation
*/
setSize(new Dimension(1000, 1000));
// upon creating the object set the location of the frame to the center of the screen
setLocation(new Point(0, 0));
// prevent the user from resizing the GameFrame object
// uncomment bottom to prevent window maximumization
//setResizable(false);
}
public void printButtons(Container contentPane) {
JPanel gamePanel = new JPanel();
gamePanel.setLayout(new GridLayout(3, 3));
// the idea of boardLogic is creating a 9 element character array to simulate the game's logic
boardLogic = new char[numOfButtons];
// creates the objects of the type JButtons
buttons = new TicTacToeButton[numOfButtons];
// create 9 buttons for the game using a for loop
for (int i = 0; i < buttons.length; i++) {
// create a new JButton object every loop
buttons[i] = new TicTacToeButton(i);
// set a default value. I use '-' for simplicity.
boardLogic[i] = buttons[i].getButtonChar();
// and add it to the frame
gamePanel.add(buttons[i]);
}
contentPane.add(gamePanel, BorderLayout.CENTER);
}
}
.
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.ImageIcon;
import javax.swing.JButton;
/* the class design is that we will create a class that has characteristics
* of what a JButton can do but can also hear for action events
*/
public class TicTacToeButton extends JButton implements ActionListener {
/* referring my Buttons with names denoted as String type
* set it empty for now. I will name the JButtons using a for loop
* the program will use buttonNumber assigned to each button
* to create the game's logic
*/
private int buttonNumber = 0;
// Each character assigned to each button is assigned a hyphen by default
private char buttonChar = '-';
public TicTacToeButton(int buttonNumber) {
// call the JButton super class constructor to initialize the JButtons
super();
// set the name of the parameter to the data member of the JButton object
this.buttonNumber = buttonNumber;
// upon creating of the JButton the button will add ActionListener to itself
addActionListener(this);
}
// a get method that retrieves the button's object data member
public int getButtonNumber() {
return buttonNumber;
}
// everytime the user press a button set the number 10 as the button number
public void setButtonChar(char buttonChar) {
if (buttonChar == 'O' || buttonChar == 'X') {
this.buttonChar = buttonChar;
}
}
public static void printArray() {
for (int i = 0; i < TicTacToeBoard.boardLogic.length; i++) {
System.out.println(TicTacToeBoard.boardLogic[i]);
}
}
public char getButtonChar() {
return buttonChar;
}
public void actionPerformed(ActionEvent e) {
/* both cases must be true before this code can happen
* After Player A turn, then is Player B turn
*/
if (e.getSource() instanceof JButton && TicTacToeBoard.currentPlayerTurn.equals(TicTacToeMain.firstPlayerName)) {
// Player A uses circle
/* the state of the image for the Buttons will change depending on the player's turn
* Player A will use the cross sign , Player B will use Circle Sign
*/
ImageIcon icon = new ImageIcon("buttonImages/circle-sign.png");
TicTacToeBoard.currentPlayerTurn = TicTacToeMain.secondPlayerName;
// set the appropriate picture as the JButton icon
setIcon(icon);
// prevent user from clicking the button more than once
setEnabled(false);
//increment buttonClick variable by one for each mouse click
TicTacToeBoard.buttonClicks += 1;
//notify both players whose turn is it
TicTacToeMain.contentPane.remove(TicTacToeBoard.currentPlayerTurnLabel);
TicTacToeBoard.printCurrentPlayerTurnLabel(TicTacToeMain.contentPane);
// Tests the Winning conditions of the player's
TicTacToeBoardLogic boardLogic = new TicTacToeBoardLogic();
boardLogic.checksWinningConditions();
} else {// After Player B turn, then is Player A turn
// Player B uses cross
/* the state of the image for the Buttons will change depending on the player's turn
* Player A will use the cross sign , Player B will use Circle Sign
*/
ImageIcon icon = new ImageIcon("buttonImages/x-sign.jpg");
TicTacToeBoard.currentPlayerTurn = TicTacToeMain.firstPlayerName;
// set the appropriate picture as the JButton icon
setIcon(icon);
// prevent user from clicking the button more than once
setEnabled(false);
//increment buttonClick variable by one for each mouse click
TicTacToeBoard.buttonClicks += 1;
//notify both players whose turn is it
TicTacToeMain.contentPane.remove(TicTacToeBoard.currentPlayerTurnLabel);
TicTacToeBoard.printCurrentPlayerTurnLabel(TicTacToeMain.contentPane);
}
// if all buttons been pressed, the game makes a decision
// Tests the Winning conditions of the player's
TicTacToeBoardLogic boardLogic = new TicTacToeBoardLogic();
boardLogic.checksWinningConditions();
}
}
Your winner here is to expand this method a little:
public TicTacToeButton(int buttonNumber) {
// call the JButton super class constructor to initialize the JButtons
super();
// set the name of the parameter to the data member of the JButton object
this.buttonNumber = buttonNumber;
// upon creating of the JButton the button will add ActionListener to itself
addActionListener(this);
setActionCommand(Integer.toString(buttonNumber));*************
}
(My addition suffixed with stars)
This will "name" the action event associated with the button.
Then in Actionperformed (ActionEvent e) you can get that ActionCommand with e.getActionCommand().
With nine your simplest may be a switch statement. Remember to use varName.equals(e.getActionCommand()) to compare it.
HTH
To know which button was pressed in the TicTacBoard class, I would suggest implement action listener inside the TicTacToe class rather than TicTacToeButton class.
Here is a little demo code for Window class, in your case TicTacToeBoard.
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JFrame;
import javax.swing.JPanel;
public class Window implements ActionListener{
static Buttons[] buttons = new Buttons[2];
public Window(){
JFrame f = new JFrame();
f.setSize(400,400);
JPanel p = new JPanel();
GridLayout gl = new GridLayout(1,2);
p.setLayout(gl);
for(int i = 0; i<2; i++){
buttons[i] = new Buttons(i);
buttons[i].addActionListener(this);
p.add(buttons[i]);
}
f.add(p);
f.setVisible(true);
}
public static void main(String... args){
new Window();
}
#Override
public void actionPerformed(ActionEvent e) {
// TODO Auto-generated method stub
if(e.getSource() == buttons[0] ){
System.out.println("0");
}
}
}
Here is demo of Buttons Class, in your case TicTacToeButton.
import javax.swing.JButton;
public class Buttons extends JButton{
int num = 0;
public Buttons(int num){
this.num = num;
}
}
You might want to consider separating out the model (the tictactoe board with the X's and O's) from the view (the JButtons). This will allow you to pass the current state of the game to whatever method you wish without the overhead of the Swing components.

Return the choice from an array of buttons

I've got an array that creates buttons from A-Z, but I want to use it in a
Method where it returns the button pressed.
this is my original code for the buttons:
String b[]={"A","B","C","D","E","F","G","H","I","J","K","L","M","N","O","P","Q","R","S","T","U","V","W","X","Y","Z"};
for(i = 0; i < buttons.length; i++)
{
buttons[i] = new JButton(b[i]);
buttons[i].setSize(80, 80);
buttons[i].setActionCommand(b[i]);
buttons[i].addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e) {
String choice = e.getActionCommand();
JOptionPane.showMessageDialog(null, "You have clicked: "+choice);
}
});
panel.add(buttons[i]);
}
I wasn't sure exactly what you question was, so I have a few answers:
If you want to pull the button creation into a method - see the getButton method in the example
If you want to access the actual button when it's clicked, you can do that by using the ActionEvent.getSource() method (not shown) or by marking the button as final during declaration (shown in example). From there you can do anything you want with the button.
If you question is "How can I create a method which takes in a array of letters and returns to me the last clicked button", you should modify you question to explicitly say that. I didn't answer that here because unless you have a very special situation, it's probably not a good approach to the problem you're working on. You could explain why you need to do that, and we can suggest a better alternative.
Example:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class TempProject extends Box{
/** Label to update with currently pressed keys */
JLabel output = new JLabel();
public TempProject(){
super(BoxLayout.Y_AXIS);
for(char i = 'A'; i <= 'Z'; i++){
String buttonText = new Character(i).toString();
JButton button = getButton(buttonText);
add(button);
}
}
public JButton getButton(final String text){
final JButton button = new JButton(text);
button.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e) {
JOptionPane.showMessageDialog(null, "You have clicked: "+text);
//If you want to do something with the button:
button.setText("Clicked"); // (can access button because it's marked as final)
}
});
return button;
}
public static void main(String args[])
{
EventQueue.invokeLater(new Runnable()
{
public void run()
{
JFrame frame = new JFrame();
frame.setDefaultCloseOperation( JFrame.EXIT_ON_CLOSE );
frame.setContentPane(new TempProject());
frame.pack();
frame.setVisible(true);
new TempProject();
}
});
}
}
ActionListener can return (every Listeners in Swing) Object that representing JButton
from this JButton you can to determine, getActionCommand() or getText()
I'm not sure what exactly you want, but what about storing the keys in a queue (e.g. a Deque<String>) and any method that needs to poll the buttons that have been pressed queries that queue. This way you would also get the order of button presses.
Alternatively, you could register other action listeners on each button (or a central one that dispatches the events) that receive the events in the moment they are fired. I'd probably prefer this approach, but it depends on your exact requirements.
try change in Action listener to this
JOptionPane.showMessageDialog(null, "You have clicked: "+((JButton)e.getSource()).getText());
1. First when you will be creating the button, please set the text on them from A to Z.
2. Now when your GUI is all ready, and you click the button, extract the text on the button, and then display the message that you have clicked this button.
Eg:
I am showing you, how you gonna extract the name of the button pressed, i am using the getText() method
butt.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e)
{
JOptionPane.showMessageDialog(null, "You have clicked: "+butt.getText());
}
});

Categories