You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Swing开发异常:JPanel鼠标悬停时出现JFrame副本,需实现文字悬停变红效果

解决Swing组件悬停时显示父JFrame副本的问题

我看到你遇到了Swing组件悬停时意外显示父JFrame副本的问题,而你只是想实现鼠标悬停时文字变红的效果。这个问题主要和你使用的透明背景设置方式以及Swing的绘制机制有关,咱们一步步来解决它。

问题根源分析

  • 你使用new Color(1f,0f,0f,0f)这种完全透明的颜色作为背景,Swing对这种完全透明的背景处理存在缺陷,会导致组件重绘时错误地渲染父容器的内容。
  • null布局(setLayout(null))会让Swing的布局管理器无法正确管理组件的尺寸和位置,进一步加重了重绘异常的问题。
  • mouseEntered和mouseExited中重复设置透明背景的操作完全多余,还可能触发不必要的重绘,加剧异常表现。

修改后的代码实现

package com.system.reservation.airline.panels;
import javax.swing.*;
import java.awt.*;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;

public class FooterPanel extends JPanel {
    public FooterPanel(){
        // 用Swing标准方式实现透明,替代全透明颜色
        this.setOpaque(false);
        this.setPreferredSize(new Dimension(400, 100));
        // 替换null布局为BorderLayout,让布局管理器自动处理组件位置
        this.setLayout(new BorderLayout());
        this.setBorder(BorderFactory.createLineBorder(Color.blue, 3));
        CreateAccount_JPanel createAccount_jPanel = new CreateAccount_JPanel();
        this.add(createAccount_jPanel, BorderLayout.CENTER);
    }

    JLabel createAccount = new JLabel("<html><body>Don't have an account?<br>Click here and set one up!</body></html>");

    class CreateAccount_JPanel extends JPanel implements MouseListener {
        public CreateAccount_JPanel(){
            // 同样用标准方式设置透明
            this.setOpaque(false);
            this.setBorder(BorderFactory.createLineBorder(Color.green, 3));
            createAccount.setHorizontalAlignment(JLabel.CENTER);
            createAccount.setFont(new Font("Arial", Font.PLAIN, 15));
            createAccount.addMouseListener(this);
            this.add(createAccount, BorderLayout.CENTER);
        }

        @Override
        public void mouseClicked(MouseEvent e) {}

        @Override
        public void mousePressed(MouseEvent e) {}

        @Override
        public void mouseReleased(MouseEvent e) {}

        @Override
        public void mouseEntered(MouseEvent e) {
            System.out.println("Hello");
            createAccount.setForeground(Color.red);
            // 如果需要悬停放大面板,添加以下代码(示例尺寸)
            this.setPreferredSize(new Dimension(500, 150));
            this.revalidate();
            this.repaint();
        }

        @Override
        public void mouseExited(MouseEvent e) {
            createAccount.setForeground(Color.black);
            // 恢复原尺寸
            this.setPreferredSize(new Dimension(400, 100));
            this.revalidate();
            this.repaint();
        }
    }
}

关键改动说明

  1. 替换透明实现方式:用setOpaque(false)替代自定义全透明颜色,这是Swing实现透明组件的标准做法,能避免重绘时的父容器内容泄漏问题。
  2. 移除null布局:改用BorderLayout让布局管理器自动管理组件的尺寸和位置,避免手动定位带来的重绘异常。如果需要更复杂的布局,推荐使用GridBagLayout等合适的布局管理器,尽量避免null布局。
  3. 优化悬停逻辑:移除多余的背景设置,若需要动态改变面板尺寸,调用revalidate()和repaint()方法让Swing正确更新布局和重绘。

内容的提问来源于stack exchange,提问作者OrlandoVSilva

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.28 20:42:34