По моему личному интуитивному ощущению JButton
, вероятно, не подходит для вашей желаемой цели.
По сути, вы хотите контролировать, когда и как изменяется "выбранное" состояние пьесы.
Лично у меня был бы какой-то контроллер, который каким-то образом отслеживал бы события мыши (возможно, компонент штук делегирует событие обратно контроллеру) и какая-то модель, которая контролирует, когда куски становятся выбранными, это затем уведомляло бы контроллер изменения состояния, и он будет делать соответствующие обновления пользовательского интерфейса.
Но это долгий процесс настройки. Вместо этого я демонстрирую простую концепцию, где компонент может быть выбран с помощью мыши, но только контроллер может отменить выбор. В этом примере это позволит выбрать только один кусок
import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.GridLayout;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.border.LineBorder;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
public class Main {
public static void main(String[] args) {
new Main();
}
public Main() {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
JFrame frame = new JFrame();
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestPane extends JPanel {
public TestPane() {
setLayout(new GridLayout(5, 5));
ChangeListener listener = new ChangeListener() {
private PiecePane selectedPiece;
@Override
public void stateChanged(ChangeEvent e) {
if (!(e.getSource() instanceof PiecePane)) { return; }
PiecePane piece = (PiecePane) e.getSource();
// Want to ignore events from the selected piece, as this
// might interfer with the changing of the pieces
if (selectedPiece == piece) { return; }
if (selectedPiece != null) {
selectedPiece.setSelecetd(false);
selectedPiece = null;
}
selectedPiece = piece;
}
};
for (int index = 0; index < 5 * 5; index++) {
PiecePane pane = new PiecePane();
pane.addChangeListener(listener);
add(pane);
}
}
}
public class PiecePane extends JPanel {
private boolean selecetd;
private Color selectedBackground;
private Color normalBackground;
private MouseListener mouseListener;
public PiecePane() {
setBorder(new LineBorder(Color.DARK_GRAY));
mouseListener = new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
setSelecetd(true);
}
};
setNormalBackground(Color.BLUE);
setSelectedBackground(Color.RED);
}
@Override
public Dimension getPreferredSize() {
return new Dimension(50, 50);
}
@Override
public void addNotify() {
super.addNotify();
addMouseListener(mouseListener);
}
@Override
public void removeNotify() {
super.removeNotify();
removeMouseListener(mouseListener);
}
public void addChangeListener(ChangeListener listener) {
listenerList.add(ChangeListener.class, listener);
}
public void removeChangeListener(ChangeListener listener) {
listenerList.remove(ChangeListener.class, listener);
}
protected void fireSelectionChanged() {
ChangeListener[] listeners = listenerList.getListeners(ChangeListener.class);
if (listeners.length == 0) {
return;
}
ChangeEvent evt = new ChangeEvent(this);
for (int index = listeners.length - 1; index >= 0; index--) {
listeners[index].stateChanged(evt);
}
}
public boolean isSelected() {
return selecetd;
}
public void setSelecetd(boolean selecetd) {
if (selecetd == this.selecetd) { return; }
this.selecetd = selecetd;
updateSelectedState();
fireSelectionChanged();
}
public Color getSelectedBackground() {
return selectedBackground;
}
public void setSelectedBackground(Color selectedBackground) {
this.selectedBackground = selectedBackground;
updateSelectedState();
}
public Color getNormalBackground() {
return normalBackground;
}
public void setNormalBackground(Color normalBackground) {
this.normalBackground = normalBackground;
updateSelectedState();
}
protected void updateSelectedState() {
if (isSelected()) {
setBackground(getSelectedBackground());
} else {
setBackground(getNormalBackground());
}
}
}
}