Why didn't the animation on this JPanel erase the original?

this is a simple exercise program in which a small letter on the window moves left and right according to the input of the keyboard.
however, I found that while moving, the original letters were not erased?
it is said on the Internet that the paint method needs to call the parent method to avoid this, but I have already called it?

import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
public class KeyEventDemo extends JFrame
{
    private KeypboardPanel keyboardPanel=new KeypboardPanel();
    public KeyEventDemo() 
    {
        add(keyboardPanel);
        keyboardPanel.setFocusable(true);
    }
    public static void main(String[] args) 
    {
        JFrame frame=new KeyEventDemo();
        frame.setTitle("KeyEventDemo");
        frame.setLocationRelativeTo(null);
        frame.setDefaultCloseOperation(EXIT_ON_CLOSE);
        frame.setSize(300,300);
        frame.setVisible(true);
    }
    static class KeypboardPanel extends JPanel
    {
        private int x=100,y=100;
        private char keyChar="A";
        public KeypboardPanel() 
        {
            addKeyListener(
                new KeyAdapter()
                {
                    public void keyPressed(KeyEvent e)
                    {
                        switch(e.getKeyCode())
                        {
                            case KeyEvent.VK_DOWN:y+=10;break;
                            case KeyEvent.VK_UP:y-=10;break;
                            case KeyEvent.VK_LEFT:x-=10;break;
                            case KeyEvent.VK_RIGHT:x+=10;break;
                            default:keyChar=e.getKeyChar();
                        }
                        repaint();
                    }
                });
        }
        protected void paintComponent(Graphics g)
        {
            super.paintComponents(g);
            g.setFont(new Font("TimesRoman",Font.PLAIN,24));
            g.drawString(String.valueOf(keyChar),x,y);
        }
    }
}

Mar.28,2021

in fact, you have already found the problem, that is, the original letter was not erased. After you monitored the button, you only rewrote a new letter, and the original letter is still there, so your code lacks the erasure operation, repait () can only guarantee that if you panel the new content in the picture, it can be displayed immediately, and there are many ways to erase it. Here is a relatively simple reference:
protected void paintComponent (Graphics g)
{

super.paintComponents(g);
g.setFont(new Font("TimesRoman",Font.PLAIN,24));
g.clearRect(0, 0, 300, 300);
g.drawString(String.valueOf(keyChar),x,y);

}

Menu