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

如何在JFrame登录窗口的JTextField中实现Ghosttext/Hiddentext?

实现Swing输入框的占位符(Ghost Text)功能

要实现你说的“幽灵文本”(也就是占位符提示),Swing原生的JTextField并没有直接提供这个功能,但我们可以通过两种常用方式来实现:自定义组件或者使用焦点监听器。下面分别给出具体方案,同时顺便提醒你:密码输入建议用JPasswordField而不是JTextField,我也会包含这个的实现。


方法一:自定义占位符输入框(推荐,复用性高)

我们可以继承JTextField(以及JPasswordField),重写paintComponent方法来绘制占位符文本,同时处理焦点和内容变化,这种方式更优雅且便于复用。

自定义PlaceholderTextField类

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import javax.swing.JTextField;

public class PlaceholderTextField extends JTextField {
    private String placeholder;
    private Color placeholderColor = Color.GRAY;

    public PlaceholderTextField(String placeholder) {
        super();
        this.placeholder = placeholder;
    }

    public PlaceholderTextField(String placeholder, int columns) {
        super(columns);
        this.placeholder = placeholder;
    }

    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        // 当输入框为空且无焦点时,绘制灰色占位符
        if (getText().isEmpty() && !hasFocus()) {
            Graphics2D g2 = (Graphics2D) g.create();
            g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
            g2.setColor(placeholderColor);
            // 调整绘制位置,和默认文本对齐逻辑一致
            g2.drawString(placeholder, getInsets().left, g.getFontMetrics().getMaxAscent() + getInsets().top);
            g2.dispose();
        }
    }

    // 提供占位符颜色的设置方法
    public void setPlaceholderColor(Color color) {
        this.placeholderColor = color;
        repaint();
    }

    public String getPlaceholder() {
        return placeholder;
    }

    public void setPlaceholder(String placeholder) {
        this.placeholder = placeholder;
        repaint();
    }
}

自定义PlaceholderPasswordField类(密码输入专用)

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import javax.swing.JPasswordField;

public class PlaceholderPasswordField extends JPasswordField {
    private String placeholder;
    private Color placeholderColor = Color.GRAY;

    public PlaceholderPasswordField(String placeholder) {
        super();
        this.placeholder = placeholder;
    }

    public PlaceholderPasswordField(String placeholder, int columns) {
        super(columns);
        this.placeholder = placeholder;
    }

    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        // 当密码为空且无焦点时绘制占位符
        if (getPassword().length == 0 && !hasFocus()) {
            Graphics2D g2 = (Graphics2D) g.create();
            g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
            g2.setColor(placeholderColor);
            g2.drawString(placeholder, getInsets().left, g.getFontMetrics().getMaxAscent() + getInsets().top);
            g2.dispose();
        }
    }

    public void setPlaceholderColor(Color color) {
        this.placeholderColor = color;
        repaint();
    }

    public String getPlaceholder() {
        return placeholder;
    }

    public void setPlaceholder(String placeholder) {
        this.placeholder = placeholder;
        repaint();
    }
}

在你的代码中使用

修改setJFrame1方法里的输入框初始化代码,替换原来的tfName和tfPassword:

// 用户名输入框
tfName = new PlaceholderTextField("Benutzername", 20);
// 密码框换成专用的占位符密码输入框
tfPassword = new PlaceholderPasswordField("Passwort", 20);

这样设置后,输入框在空状态且无焦点时会显示灰色占位符,获得焦点后自动隐藏;输入内容后占位符也不会出现,完全符合你的需求。


方法二:使用FocusListener(快速实现,无需自定义类)

如果你不想自定义组件,可以给普通的JTextField和JPasswordField添加焦点监听器,通过切换文本内容和颜色来模拟占位符效果:

修改你的setJFrame1方法

public static void setJFrame1() {
    // Programming the login Screen
    JFrame1.setResizable(false);
    JFrame1.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
    JFrame1.setTitle("Zeiterfassungsytem");
    JFrame1.setSize(250, 200);
    JFrame1.setLocationRelativeTo(null);
    JPanel panel = new JPanel();
    JLabel labelname = new JLabel("Ihre Daten:");
    panel.add(labelname);
    JFrame1.getContentPane().add(panel);

    // 用户名输入框设置
    tfName = new JTextField("Benutzername", 20);
    tfName.setForeground(Color.GRAY);
    tfName.addFocusListener(new java.awt.event.FocusAdapter() {
        public void focusGained(java.awt.event.FocusEvent evt) {
            if (tfName.getText().equals("Benutzername")) {
                tfName.setText("");
                tfName.setForeground(Color.BLACK);
            }
        }
        public void focusLost(java.awt.event.FocusEvent evt) {
            if (tfName.getText().isEmpty()) {
                tfName.setText("Benutzername");
                tfName.setForeground(Color.GRAY);
            }
        }
    });
    panel.add(tfName);

    // 密码输入框设置(改用JPasswordField更安全)
    JPasswordField tfPassword = new JPasswordField("Passwort", 20);
    tfPassword.setForeground(Color.GRAY);
    tfPassword.addFocusListener(new java.awt.event.FocusAdapter() {
        public void focusGained(java.awt.event.FocusEvent evt) {
            if (new String(tfPassword.getPassword()).equals("Passwort")) {
                tfPassword.setText("");
                tfPassword.setForeground(Color.BLACK);
            }
        }
        public void focusLost(java.awt.event.FocusEvent evt) {
            if (new String(tfPassword.getPassword()).isEmpty()) {
                tfPassword.setText("Passwort");
                tfPassword.setForeground(Color.GRAY);
            }
        }
    });
    panel.add(tfPassword);

    // Creating login Button
    JButton buttonanmelden = new JButton("Anmelden");
    panel.add(buttonanmelden);
    buttonanmelden.addActionListener(new Login());
    JFrame1.setVisible(true);
}

注意:用这种方法时,获取输入内容需要判断是否是占位符文本,比如获取用户名时:

inputName = tfName.getText().equals("Benutzername") ? "" : tfName.getText();
// 密码同理
inputPassword = new String(tfPassword.getPassword()).equals("Passwort") ? "" : new String(tfPassword.getPassword());

额外建议

  1. 密码输入一定要用JPasswordField,而不是JTextField,这样输入的内容会以圆点/星号隐藏,更安全。
  2. 自定义组件的方式更优雅,也更容易维护和复用,推荐使用这种方案。

内容的提问来源于stack exchange,提问作者C.Ser

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.28 07:27:36