So I want to put a button in a JPanel
, but I want to keep it invisible/hidden unless the mouse pointer hovers over it. At this point, the button should be made visible, react to clicks and so on. When the mouse leaves the area, it should be hidden again.
I tried adding a MouseListener
to my JButton
and use setVisible()
, but when I hide the button (setVisible(false)
), then the listener doesn't work anymore - the application behaves as if the button is not there at all.
What's the correct way to implement this behavior?
Edit: I am using an absolute layout (setLayout(null)
) and I am manually placing my component using setBounds(x, y, width, height)
.
The setRolloverSelectedIcon method lets you specify the rollover icon when the button is selected — this is useful for two-state buttons such as toggle buttons. Setting the rollover icon automatically calls setRollover(true) , enabling rollover.
A Toggle Button is a two state button. It is either pressed or not pressed. Following example showcase how to modify the default appearance of a Button in a Java Swing application.
Use icons to reveal (colored) or hide (transparent) the button respectively.
import java.awt.*;
import java.awt.image.BufferedImage;
import javax.swing.*;
class InvisiButton {
public static void main(String[] args) {
Runnable r = new Runnable() {
@Override
public void run() {
int size = 30;
JPanel gui = new JPanel(new GridLayout(4,10,4,4));
for (int ii=0; ii<40; ii++) {
JButton b = new JButton();
b.setContentAreaFilled(false);
b.setIcon(new ImageIcon(
new BufferedImage(size,size,BufferedImage.TYPE_INT_RGB)));
b.setRolloverIcon(new ImageIcon(
new BufferedImage(size,size,BufferedImage.TYPE_INT_ARGB)));
b.setBorder(null);
gui.add(b);
}
JOptionPane.showMessageDialog(null, gui);
}
};
// Swing GUIs should be created and updated on the EDT
// http://docs.oracle.com/javase/tutorial/uiswing/concurrency/initial.html
SwingUtilities.invokeLater(r);
}
}
One approach is to give the button no text, no border, and an empty icon sized to match a real rollover icon.
Addendum: This updated example relies on @Andrew's succinct empty icon seen here.
import java.awt.EventQueue;
import java.awt.GridLayout;
import java.awt.image.BufferedImage;
import javax.swing.BorderFactory;
import javax.swing.Icon;
import javax.swing.ImageIcon;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
/** @see https://stackoverflow.com/a/14410594/230513 */
public class RollButton {
private static final int N = 64;
private void display() {
JFrame f = new JFrame("RollButton");
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JPanel p = new JPanel(new GridLayout());
p.setBorder(BorderFactory.createEmptyBorder(N, N, N, N));
p.add(createButton(UIManager.getIcon("OptionPane.errorIcon")));
f.add(p);
f.pack();
f.setLocationRelativeTo(null);
f.setVisible(true);
}
private JButton createButton(Icon icon) {
JButton b = new JButton();
b.setBorderPainted(false);
b.setText("");
// https://stackoverflow.com/a/14410597/230513
b.setIcon(new ImageIcon(new BufferedImage(icon.getIconWidth(),
icon.getIconHeight(), BufferedImage.TYPE_INT_ARGB)));
b.setRolloverEnabled(true);
b.setRolloverIcon(icon);
return b;
}
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
new RollButton().display();
}
});
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With