1

I have a problem with obtaining ID / Variable Name of buttons. Generally I want create lights out game. I created panel of buttons (NxN, N from combo box) but I don't know how to get single button's ID after press. Any idea?

    private void p1ActionPerformed(java.awt.event.ActionEvent evt) {                                             
    String temp = jComboBox1.getSelectedItem().toString();
    ile=Integer.parseInt(temp);

    jPanel1.removeAll();
    jPanel1.setLayout(new GridLayout(ile,ile));
    for (int i = 0; i < ile; i++) {
        for (int j = 0; j < ile; j++) {  
            JButton btn = new JButton();
            btn.setPreferredSize(new Dimension(40, 40));
            btn.setBackground(Color.green);
            btn.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e)
            {          
        /*What put here?*/
            }
            });
            jPanel1.add(btn);  
            revalidate();
            pack();
        }
    }
}  
Andrew Thompson
  • 168,117
  • 40
  • 217
  • 433
venik
  • 13
  • 1
  • 3

3 Answers3

8

You can get a reference to the button pushed through the ActionEvent's getSource() method.

e.g.,

public void actionPerformed(ActionEvent e)  {          
   JButton selectedButton = (JButton) e.getSource();
}

Now, if you need to know where the button is in your grid, you will need to do more work, such as putting your buttons into an array or ArrayList, and then iterating through the array finding the index number of the selected button.

e.g.,

// changes to code marked with a //!! comment
private void p1ActionPerformed(java.awt.event.ActionEvent evt) {
  String temp = jComboBox1.getSelectedItem().toString();
  ile = Integer.parseInt(temp);

  jPanel1.removeAll();
  jPanel1.setLayout(new GridLayout(ile, ile));

  final JButton[][] buttons = new JButton[ile][ile]; //!!

  for (int i = 0; i < ile; i++) {
     for (int j = 0; j < ile; j++) {
        JButton btn = new JButton();
        btn.setPreferredSize(new Dimension(40, 40));
        btn.setBackground(Color.green);
        btn.addActionListener(new ActionListener() {
           public void actionPerformed(ActionEvent e) {
              //!!
              JButton source = (JButton) e.getSource();
              for (int k = 0; k < buttons.length; k++) {
                 for (int l = 0; l < buttons[k].length; l++) {
                    if (buttons[k][l] == source) {
                       System.out.printf("row: %d, col: %d%n", l, k);
                       return;
                    }
                 }
              }
           }
        });
        jPanel1.add(btn);
        buttons[i][j] = btn; //!!
        //!! revalidate();
        //!! pack();
     }
  }
  jPanel1.revalidate(); //!!
  jPanel1.repaint(); //!!
}

As a side note, whenever I see removeAll() I think that perhaps this can be better achieved by using a CardLayout


As a second side note, I always cringe when I see "get variable name" in questions. Variable "names" aren't really all that important, don't exist for many objects, and almost don't exist in compiled code. And if an object is referred to by several variables, which one represents the "name" for this object? Much more important are object references, which is what most of the answers to your question have been dealing with.

Hovercraft Full Of Eels
  • 283,665
  • 25
  • 256
  • 373
2

The suggestion of Hovercraft Full Of Eels is good. Alternatively in your case you can use the button defined in your code, but you should make it final.

for (int i = 0; i < ile; i++) {
    for (int j = 0; j < ile; j++) {  
        final JButton btn = new JButton();
        btn.setPreferredSize(new Dimension(40, 40));
        btn.setBackground(Color.green);
        btn.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent e)
        {          
           // here we can use the variable btn - java will create an access method automatically
           System.out.println(btn.getText());
        }
        });
        jPanel1.add(btn);  
        revalidate();
        pack();
    }
}
Sergiy Medvynskyy
  • 11,160
  • 1
  • 32
  • 48
2

You have a ton of options (as you can see).

You can also use set/getName and/or set/getActionCommand, even set/getText, but I personally wouldn't rely on this...

for (int i = 0; i < ile; i++) {
    for (int j = 0; j < ile; j++) {  
        JButton btn = new JButton();
        btn.setBackground(Color.green);
        String id = Integer.toString(i) + "x" + Integer.toString(j);
        btn.setName(id);
        // and/or
        btn.setActionCommand(id);
        btn.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e)
            {          
                JButton btn = (JButton)e.getSource();
                String id = btn.getName();
                // and/or
                String id = btn.getActionCommand();
            }
        });
        jPanel1.add(btn);  
    }
}
pack();
MadProgrammer
  • 343,457
  • 22
  • 230
  • 366