Java 获取组件的最后一次调整大小事件

Java 获取组件的最后一次调整大小事件,java,swing,resize,Java,Swing,Resize,当使用ComponentListener获取调整大小事件的通知时,如果用户将窗口角拖动到新的大小,则可能会获得大量事件 现在,我需要对调整大小事件进行一些昂贵的计算。如果这种情况经常发生,那就太多了。可以忽略大多数事件,只对最后一个事件做出反应(例如,如果用户释放鼠标按钮)。问题是,我不知道如何找出上次调整大小事件是什么。如果我做了天真的假设: this.addComponentListener(new ComponentAdapter() { @Override public void

当使用ComponentListener获取调整大小事件的通知时,如果用户将窗口角拖动到新的大小,则可能会获得大量事件

现在,我需要对调整大小事件进行一些昂贵的计算。如果这种情况经常发生,那就太多了。可以忽略大多数事件,只对最后一个事件做出反应(例如,如果用户释放鼠标按钮)。问题是,我不知道如何找出上次调整大小事件是什么。如果我做了天真的假设:

this.addComponentListener(new ComponentAdapter() {
  @Override
  public void componentResized(final ComponentEvent e) {
    if (calculationInProgress){
      return;
    }

    calculationInProgress= true;
    doExpensiveCalculation();
    calculationInProgress= false;        
  }
});
在最后一次计算之后,窗口的大小可能会进一步调整,因此计算结果与正确的最终尺寸不匹配


有什么好的解决方案呢?

以下是评论中讨论的基于
定时器的解决方案的一个简单示例:

package mcve;

import java.awt.event.*;
import javax.swing.*;

public abstract class ComponentResizeEndListener
extends    ComponentAdapter
implements ActionListener {

    private final Timer timer;

    public ComponentResizeEndListener() {
        this(200);
    }

    public ComponentResizeEndListener(int delayMS) {
        timer = new Timer(delayMS, this);
        timer.setRepeats(false);
        timer.setCoalesce(false);
    }

    @Override
    public void componentResized(ComponentEvent e) {
        timer.restart();
    }

    @Override
    public void actionPerformed(ActionEvent e) {
        resizeTimedOut();
    }

    public abstract void resizeTimedOut();
}
然后:

comp.addComponentListener(new ComponentResizeEndListener() {
    @Override
    public void resizeTimedOut() {
        doExpensiveCalculation();
    }
});

使用一个不重复的
javax.swing.Timer
,有一个很短的延迟,比如说250毫秒左右。每次调用
ComponentResistized
时,重新启动计时器。触发计时器后,您可以尝试开始计算。根据计算的性质,您还可以使用
SwingWorker
。@mad程序员:这是个好主意!多亏了你。它工作得很好。参见答案(我答案底部的更新后代码标题),它显示了
组件化
计时器的使用