JButton() only working when mouse hovers
Likely you have a layout problem where you're trying to add JButtons with absolute bounds into a container that uses a non-null layout manager. Suggestions
- Do not use setBounds and absolute positioning to size and place your components.
- Read up on and use the layout managers to do this heavy lifting for you: Lesson: Laying Out Components Within a Container
- Don't forget to call
pack()
on your JFrame after adding all components - Call
setVisible(true)
after callingpack()
and again call both only after adding all components to your GUI. - A null layout is available if you absolutely need to use absolute positioning of components, but regardless, you should strive to avoid using it.
JButtons only appear when mouse hover over them
Problems:
- You're using a null layout-using JPanel to hold JButtons in a JScrollPane which will make the scroll pane fail in its ability to show scroll bars and scroll effectively
- You add components into a container (the same JPanel above) without telling the GUI to repaint the container, and so the components, the added JButtons, don't display. This latter is fixed by calling
jpFullofButtons.repaint();
after adding components to the JPanel -- but the JScrollPane still won't work right
Better to use a decent layout manager, here perhaps a GridLayout, and call revalidate()
and repaint()
on the container, the jpFullofButtons JPanel, after adding components to it.
Side note about your MRE attempt: it's almost there, but you still left in the DAO requirement as well as an undefined class, DataVO
, preventing us from coping, pasting, and running your code.
My MRE example:
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.GridLayout;
import java.text.NumberFormat;
import java.util.Locale;
import javax.swing.*;
@SuppressWarnings("serial")
public class JButtonsShowUp extends JPanel {
private JButton reAddButtonsBtn = new JButton("Re-Add Buttons");
private JPanel jpFullofButtons = new JPanel(new GridLayout(0, 1));
private JScrollPane jsp = new JScrollPane(jpFullofButtons);
public JButtonsShowUp() {
reAddButtonsBtn.addActionListener(e -> reAddButtons());
JPanel topPanel = new JPanel();
topPanel.add(reAddButtonsBtn);
jsp.setPreferredSize(new Dimension(385, 450));
int gap = 20;
setBorder(BorderFactory.createEmptyBorder(gap, gap, gap, gap));
setLayout(new BorderLayout());
add(topPanel, BorderLayout.PAGE_START);
add(jsp, BorderLayout.CENTER);
}
private void reAddButtons() {
jpFullofButtons.removeAll();
int max = 100;
for (int i = 0; i < max; i++) {
String randomText = "";
for (int j = 0; j < 5; j++) {
char c = (char) ('a' + (int) (26 * Math.random()));
randomText += c;
}
double randomPrice = 10 + 20 * Math.random();
final DataVO2 data = new DataVO2(randomText, randomPrice);
String text = String.format("Text: %s%02d, Price: $%1.2f", randomText, i, randomPrice);
JButton button = new JButton(text);
button.addActionListener(e -> buttonAction(data));
jpFullofButtons.add(button);
}
jpFullofButtons.revalidate();
jpFullofButtons.repaint();
}
private void buttonAction(DataVO2 data) {
System.out.println("Button pressed: " + data);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> {
JButtonsShowUp mainPanel = new JButtonsShowUp();
JFrame frame = new JFrame("GUI");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(mainPanel);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
});
}
}
class DataVO2 {
private NumberFormat priceFormat = NumberFormat.getCurrencyInstance(Locale.US);
private String name;
private double price;
public DataVO2(String name, double price) {
this.name = name;
this.price = price;
}
public String getName() {
return name;
}
public double getPrice() {
return price;
}
@Override
public String toString() {
String priceText = priceFormat.format(price);
return "DataVO2 [name=" + name + ", price=" + priceText + "]";
}
}
JButtons Only Working When Mouse Hovers Over
Since you override paint
you need to call super.paint(g);
as the first line.
public void paint(Graphics g) {
super.paint(g); // <-- add this.
g.drawString("Under Construction...", 240, 250);
}
Also, you should move your logic off the main()
thread; like
SwingUtilities.invokeLater(new Runnable() {
public void run() {
new Main();
}
});
Components appear only when mouse hovers over them
This seems to work better.
I fixed radiobutton and checkbox positions.
I used different references for checkbox and radiobutton objects (r1, r2, chk1, chk2, chk3)
I added a buttongroup for radiobuttons.
import java.awt.Color;
import java.awt.Container;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JRadioButton;
import javax.swing.JTextField;
import javax.swing.ButtonGroup;
public class JFrameBackground extends JFrame implements ActionListener
{
private static final long serialVersionUID = 1L;
JLabel l1,l2,l3,l4;
JTextField t1;
JButton b1;
JRadioButton r1, r2;
JComboBox com1;
JCheckBox chk1, chk2, chk3;
JPanel p2;
JButton b;
public JFrameBackground()
{
p2=new JPanel();
p2.setLayout(null);
p2.setBounds(250, 0, 400, 400);
add(p2);
l1 = new JLabel("Name:");
l1.setBounds(100,10,70,30);
p2.add(l1);
t1 = new JTextField();
t1.setBounds(100,50,70,30);
p2.add(t1);
l2 = new JLabel("Gender:");
l2.setBounds(100,130,70,30);
p2.add(l2);
r1 = new JRadioButton("Male");
r1.setBounds(100,150,70,30);
p2.add(r1);
r2 = new JRadioButton("Female");
r2.setBounds(180,150,70,30);
p2.add(r2);
ButtonGroup bg=new ButtonGroup();
bg.add(r1);
bg.add(r2);
l3 = new JLabel("Course:");
l3.setBounds(100,180,70,30);
p2.add(l3);
chk1= new JCheckBox("Bca");
chk1.setBounds(100, 200, 70, 30);
p2.add(chk1);
chk2= new JCheckBox("BBA");
chk2.setBounds(180, 200, 70, 30);
p2.add(chk2);
chk3= new JCheckBox("BCOM");
chk3.setBounds(260, 200, 70, 30);
p2.add(chk3);
l4 = new JLabel("Country:");
l4.setBounds(100,220,70,30);
p2.add(l4);
String name[] = {"India","USA","UK","Rus"};
com1=new JComboBox(name);
com1.setBounds(100, 250, 70, 30);
p2.add(com1);
b1= new JButton("Submit");
b1.setBounds(140, 300, 90, 30);
p2.add(b1);
b =new JButton("Show form");
b.setBounds(0, 4, 190, 40);
b.setFocusPainted(false);
b.setBorderPainted(false);
b.addActionListener(this);
getContentPane().add(b);
b.addMouseListener(new MouseAdapter()
{
public void mouseClicked(MouseEvent me)
{
p2.setVisible(true);
}
});
Container c=getContentPane();
c.setBackground(Color.gray);
setBounds(170, 100, 1250, 500);
setLayout(null);
setVisible(true);
}
public static void main(String[] args)
{
new JFrameBackground();
}
public void actionPerformed(ActionEvent arg0)
{
}
}
JButton only show up on mouseover
Swing uses a "layering" concept for it's painting...
paint
calls paintComponent
, paintBorder
and paintChildren
. By overriding paint
and failing to call super.paint
, you've prevented the component from painting it's various layers.
In Swing, it is preferred to use paintComponent
to provide custom painting, which allows you to paint underneath any other components that might be added to the component.
public class TestPaint01 {
public static void main(String[] args) {
new TestPaint01();
}
public TestPaint01() {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (Exception ex) {
}
JFrame frame = new JFrame("Test");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestPane extends JPanel {
private Image backgroundImage;
public TestPane() {
try {
BufferedImage background = ImageIO.read(new File("/path/to/image.jpg"));
//backgroundImage = background.getScaledInstance(-1, background.getHeight() / 4, Image.SCALE_SMOOTH);
backgroundImage = background;
} catch (IOException ex) {
ex.printStackTrace();
}
setLayout(new GridBagLayout());
add(new JButton("Hello"));
}
@Override
public Dimension getPreferredSize() {
return backgroundImage == null ? super.getPreferredSize() : new Dimension(backgroundImage.getWidth(this), backgroundImage.getHeight(this));
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
int x = (getWidth() - backgroundImage.getWidth(this)) / 2;
int y = (getHeight() - backgroundImage.getHeight(this)) / 2;
g.drawImage(backgroundImage, x, y, this);
}
}
}
You might find A Closer look at the Paint Mechanism and Painting in AWT and Swing informative.
Button and JSlider only appear when I hover the screen
What i would do:
Add a MouseMotionListener to the panel:
jp.addMouseMotionListener(new MouseMotionListener() {
@Override
public void mouseDragged(MouseEvent e) {
}
@Override
public void mouseMoved(MouseEvent e) {
System.out.println("motion" + e.getPoint());
}
});
Add a ChangeListener to the penSize:
penSize.addChangeListener(new ChangeListener() {
@Override
public void stateChanged(ChangeEvent e) {
System.out.println("new pensize: " + penSize.getValue());
}
});
And so on. So you have add the lsiteners to the components and not to the frame.
I hope to have helped you for now. If you have any questions, please post a minimal reproducible example as Andrew wrote.
Steffi
Related Topics
Loss of Precision - Int -> Float or Double
Getting Xml Node Text Value with Java Dom
How to Disable Loggers of a Class or of Whole Package
How to Use Session in Jsp Pages to Get Information
Eventlisteners Using Hibernate 4.0 with Spring 3.1.0.Release
Why Can't You Reduce the Visibility of a Method in a Java Subclass
How Does System.Out.Print() Work
How to Pass a Value from One Jsp to Another Jsp Page
Netbeans How to Set Command Line Arguments in Java
Does Java Guarantee That Object.Getclass() == Object.Getclass()
Netbeans - Error: Could Not Find or Load Main Class
How to Include External Jar on My Netbeans Project
Java String Concatenation with + Operator
Hibernate/JPA - Annotating Bean Methods VS Fields
"Main Method Not Found" Error When Starting Program