这一行:
f.setVisible(true);
在其当前状态呈现您的 GUI,这是 JFrame 的默认 BorderLayout 生效的状态。请注意,BorderLayout 会忽略 setBounds(...) 方法。
这一行:
f.setLayout(null);
删除 JFrame contentPane 的 BorderLayout,因此您的 GUI 将在没有布局的情况下呈现,更改添加的 JPanel 的位置 - 尊重此处的 setBounds(...) 方法调用。
如果您在 GUI 渲染完成后调用它,它不会有任何效果,除非您执行一些触发布局管理器重新布局组件的操作,例如重新调整大小图形用户界面。
我自己,我不会使用 AWT,但会使用 Swing,我会使用 Rectangle 对象在 JPanel 的 paintComponent 方法中绘制矩形。这样,我可以监视鼠标与矩形的关系,并改变它的状态。例如,试试这个程序,看看当鼠标悬停在矩形上时会发生什么:
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import javax.swing.*;
@SuppressWarnings("serial")
public class GuiButton2 extends JPanel {
private static final int PREF_W = 400;
private static final int PREF_H = PREF_W;
private static final int RECT_X = 40;
private static final int RECT_Y = 80;
private static final int RECT_W = 200;
private static final Color DEFAULT_RECT_COLOR = Color.GRAY;
private static final Color HOVER_RECT_COLOR = Color.PINK;
private Rectangle rectangle = new Rectangle(RECT_X, RECT_Y, RECT_W, RECT_W);
private boolean hover = false;
public GuiButton2() {
setPreferredSize(new Dimension(PREF_W, PREF_H));
addMouseMotionListener(new MouseAdapter() {
@Override
public void mouseMoved(MouseEvent e) {
// hover true if mouse is hovering over the rectangle
hover = rectangle.contains(e.getPoint());
repaint();
}
});
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2 = (Graphics2D) g;
// if hover true -- use hover color, otherwise use default color
Color c = hover ? HOVER_RECT_COLOR : DEFAULT_RECT_COLOR;
g2.setColor(c);
g2.fill(rectangle); // draw rectangle
}
private static void createAndShowGui() {
GuiButton2 mainPanel = new GuiButton2();
JFrame frame = new JFrame("GUI Button");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(mainPanel);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> createAndShowGui());
}
}
旁注1:
虽然空布局和setBounds() 对于 Swing 新手来说似乎是创建复杂 GUI 的最简单和最好的方法,但创建的 Swing GUI 越多,使用它们时遇到的困难就越严重。当 GUI 调整大小时,它们不会调整您的组件大小,它们是增强或维护的皇家女巫,放置在滚动窗格中时它们完全失败,在与原始不同的所有平台或屏幕分辨率上查看时它们看起来很糟糕.
旁注2:
你会想学习和使用Java naming conventions。变量名应全部以小写字母开头,而类名应以大写字母开头。学习这一点并遵循这一点将使我们能够更好地理解您的代码,并让您更好地理解其他人的代码。