JPanel中的闪烁​​组件

时间:2014-12-12 21:29:29

标签: jframe jpanel repaint flicker

首先,我知道这个问题很常见,但我已经阅读了很多关于双缓冲的内容,而且我找不到将解决方案转换为我自己的问题的方法

我正在制作国际象棋比赛。 我有一个扩展JFrame的Main类,以及一个扩展JPanel并实现Runnable的Echecs类。 Echecs包含计算移动等的所有方法......到目前为止,该按钮用于验证玩家选择的移动。

这是我的主要课程:

public static void main(String[] args) {
    EventQueue.invokeLater(new Runnable() {
        public void run() {
            try {
                Main m = new Main();
                m.setVisible(true);

            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    });
}

public Main(){
    setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    setBounds(100, 100, 800, 800);
    Echecs e = new Echecs();
    setContentPane(e);
    e.setLayout(null);
    e.setBorder(new EmptyBorder(5, 5, 5, 5));
}

我的国际象棋类构造函数如下所示:

public Echecs(){
    this.setBounds(100, 100, 800, 800);
    valider = new JButton("Valider");
    valider.setEnabled(false);
    valider.setBounds(685, 728, 89, 23);
    t = new Thread(this);
    t.start();
    this.add(valider);
    this.setFocusable(true);
    this.addMouseListener(new MouseListener(){

        @Override
        public void mouseClicked(MouseEvent e) {
            //HERE ARE SOME IRRELEVANT CALCULATIONS
            repaint();
        }

    });

    this.addMouseMotionListener(new MouseMotionListener(){

        @Override
        public void mouseDragged(MouseEvent e) {
            xSouris = e.getX();
            ySouris = e.getY();
            e.consume();
            repaint();
        }

        @Override
        public void mouseMoved(MouseEvent e) {
            xSouris = e.getX();
            ySouris = e.getY();
            e.consume();
            repaint();
        }

    });

    valider.addActionListener(new ActionListener(){

        @Override
        public void actionPerformed(ActionEvent e) {

            synchronized(t){
                t.notify();
            }
        }

    });

}

这些是绘画方法(我不知道的部分):

public void update(Graphics g) {
    dessinerBoard(g);
    valider.repaint();
}

public void paintComponents(Graphics g){
    super.paintComponents(g);       
}

public void paint(Graphics g){
    update(g);
}

我每次在组件中移动鼠标时都会调用repaint(),或者每次通过按钮验证移动时单击线程的run()方法中的某些区域+。

你可以想象,我尝试了不同的东西,但由于我不知道我在做什么,我希望你们能帮助我。

为什么我的按钮会闪烁?你会如何让它停止闪烁和可见? 如果我不要求按钮重新绘制,除非我点击它,否则它不会出现,如果我这样做则会闪烁。

提前致谢。

编辑:

请求的dessinerBoard()代码。

public void dessinerBoard(Graphics g){
    g.setColor(Color.blue);
    g.fillRect(0, 0, TAILLE, TAILLE);
    for(int i = 0; i < 8; i++){
        for(int j = 0; j < 8; j++){
            if(tableau[i][j].getCouleur() == Case.BLANC)
                g.setColor(Color.WHITE);
            else
                g.setColor(Color.BLACK);            
            for(int k = 0; k < nombreCoupsPossibles; k++){
                if(tableau[i][j] == coupsPossibles[k]){
                    g.setColor(Color.YELLOW);
                    break;
                }
            }
            if(caseCible == tableau[i][j])
                g.setColor(Color.MAGENTA);
            g.fillRect(Y_BOARD + (j * TAILLE_CASE), X_BOARD + (i * TAILLE_CASE), TAILLE_CASE, TAILLE_CASE);
            if(caseSelectionnee == tableau[i][j]){
                g.setColor(Color.RED);
                g.fillRect(Y_BOARD + (j * TAILLE_CASE), X_BOARD + (i * TAILLE_CASE), TAILLE_CASE, TAILLE_CASE);

            }
            if(tableau[i][j].getPiece() != null){
                int piece = tableau[i][j].getPiece().getTypePiece();
                switch(piece){
                    case 1:
                        g.setColor(Color.BLUE);
                        g.fillOval(Y_BOARD + (j * TAILLE_CASE) + 10, X_BOARD + (i * TAILLE_CASE) + 10, 60, 60);
                        break;
                    case 2:
                        g.setColor(Color.RED);
                        g.fillOval(Y_BOARD + (j * TAILLE_CASE) + 10, X_BOARD + (i * TAILLE_CASE) + 10, 60, 60);
                        break;
                    case 3:
                        g.setColor(Color.LIGHT_GRAY);
                        g.fillOval(Y_BOARD + (j * TAILLE_CASE) + 10, X_BOARD + (i * TAILLE_CASE) + 10, 60, 60);
                        break;
                    case 4:
                        g.setColor(Color.GREEN);
                        g.fillOval(Y_BOARD + (j * TAILLE_CASE) + 10, X_BOARD + (i * TAILLE_CASE) + 10, 60, 60);
                        break;
                    case 5:
                        g.setColor(Color.PINK);
                        g.fillOval(Y_BOARD + (j * TAILLE_CASE) + 10, X_BOARD + (i * TAILLE_CASE) + 10, 60, 60);
                        break;
                    case 6:
                        g.setColor(Color.ORANGE);
                        g.fillOval(Y_BOARD + (j * TAILLE_CASE) + 10, X_BOARD + (i * TAILLE_CASE) + 10, 60, 60);
                        break;
                }
            }

        }
    }
}

0 个答案:

没有答案