JPanel使用mouseMoved方法闪烁

时间:2014-09-09 17:59:13

标签: java swing jpanel paintcomponent mouse-listeners

我有一个简单的JPanel,我用它来显示图像。我想要一些功能,我可以通过拖动来平移图像。我有类似的东西(请注意我编译并运行正常的代码;下面的代码被严重截断,以便了解我正在做的事情):

public class Data2DPanel extends JPanel { 
    public Data2DPanel(Data2D data) {
        // Set image
        this.image = Data2D.data2DToBufferedImage(data);

        // Set mouse listener
        Data2DMouseAdapter data2DMouseAdapter = new Data2DMouseAdapter();
        this.addMouseListener(data2DMouseAdapter);
        this.addMouseMotionListener(data2DMouseAdapter);
    }

    private class Data2DMouseAdapter extends MouseAdapter {
        @Override
        public void mouseDragged(MouseEvent e) {
            if (SwingUtilities.isLeftMouseButton(e)) {
                switch (actionState) {
                    case PAN:
                        xOffset = xOffsetInit + e.getX()-xPosInit;
                        yOffset = yOffsetInit + e.getY()-yPosInit;
                        paintComponent(getGraphics());
                        break;                                
                }
            }
        }
    }

    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        Graphics2D g2 = (Graphics2D)g;
        g2.setRenderingHint(RenderingHints.KEY_INTERPOLATION,
                            RenderingHints.VALUE_INTERPOLATION_NEAREST_NEIGHBOR);

        // Paint image
        g2.drawImage(image,x,y,width,height,this);
        }
    }
}

问题在于有很多闪烁。我已经检查了stackoverflow / google,似乎很多闪烁的问题都是因为人们覆盖了paint方法而不是paintComponent方法。我还检查了isDoubleBuffered,然后返回true。直觉上,我觉得mouseDragged方法可能会更新paintComponent()以保持跟上,但我认为双缓冲仍然可以防止出现闪烁。我的问题是,这种方法是否存在固有的错误,以及是否有标准或优雅的解决方案。

1 个答案:

答案 0 :(得分:3)

paintComponent(getGraphics());应为repaint()。复杂的问题。

  1. 你永远不想打电话给getGraphics()进行自定义绘画。用于绘制的唯一Graphics对象应该是paint方法中提供的对象。
  2. 您永远不应该致电paintXxx尝试"强制" 重新绘制该组件。您应该调用repaint()并允许RepaintManager处理所有更新和绘制周期