跨线程操作UI
来源:互联网 发布:东北农业大学网络 编辑:程序博客网 时间:2024/04/29 06:43
由于众所周知的原因,一般只有一个线程操作UI。对于多线程程序,怎么让工作线程去操作UI呢?在C++里,可以很方便地利用Windows消息,sendMessage和postMessage。在C#中,MSDN中也给出了用委托的方法。那Java中呢?
Java中观察者模式非常常见。跨线程操作UI也可以用观察者模式来实现。UI线程作为观察者,当工作线程有“动静”时,主动通知UI线程。
- import java.util.Observable;
- import java.util.Observer;
- public class MyAction extends Observable{
- public void test(){
- this.setChanged();
- this.notifyObservers();
- }
- }
被观察的对象“MyAction”通过test方法来通知观察者。MyAction应该在工作线程中。
- public class MainFrame extends JFrame implements Observer {
- @Override
- protected void frameInit() {
- // TODO Auto-generated method stub
- super.frameInit();
- this.setLayout(null);
- JButton jb = new JButton("test");
- jb.setSize(100, 100);
- jb.addActionListener(new ActionListener() {
- @Override
- public void actionPerformed(ActionEvent e) {
- // TODO Auto-generated method stub
- Thread t = new Thread(){
- @Override
- public void run() {
- // TODO Auto-generated method stub
- MyAction action = new MyAction();
- //注册观察者
- action.addObserver(MainFrame.this);
- try {
- this.sleep(5000);
- } catch (InterruptedException e) {
- // TODO Auto-generated catch block
- e.printStackTrace();
- }
- action.test();
- }
- };
- t.start();
- }
- });
- this.add(jb);
- }
- /**
- * @param args
- */
- public static void main(String[] args) {
- // TODO Auto-generated method stub
- MainFrame f = new MainFrame();
- f.setVisible(true);
- f.setDefaultCloseOperation(EXIT_ON_CLOSE);
- f.setSize(200, 200);
- }
- @Override
- public void update(Observable o, Object arg) {
- // TODO Auto-generated method stub
- JOptionPane.showMessageDialog(null, "message");
- }
- }
观察者收到通知时,update方法就会被调用,在这个方法里更新UI即可。
纠错:
这种方法不能实现跨线程操作UI。测试方法,在update方法中获取Thread.currentThread().getId(),发现是非UI线程的ID。看了Observable的代码,确实没有跨线程的内容。
不过下述JComponent方法是安全的,可以从任何线程调用:repaint()、revalidate()、和invalidate()。(repaint()和revalidate()方法为事件派发线程对请求排队,并分别调用paint()和validate()方法。invalidate()方法只在需要确认时标记一个组件和它的所有直接祖先。)所以,可以重写这些方法,来更新UI。
另外,一般也不能使用Timer来主动获取工作线程的数据,因为Timer运行在其它线程上,不过可以参考http://jianshusoft.blog.51cto.com/2380869/764382。
- 跨线程操作UI
- WPF 跨线程操作UI
- 非UI线程的跨线程操作
- C# 跨线程操作UI(界面)
- Android UI 线程操作
- RCP 非UI线程调用UI操作
- RCP 非UI线程调用UI操作
- c#子线程操作ui
- Swing UI线程安全操作
- Sciter:线程中操作UI
- android子线程操作ui
- Android 子线程中操作UI线程
- [WinForm]WinForm跨线程UI操作常用控件类大全
- Android在非UI线程发起UI线程操作
- android UI 操作 不要在子线程中操作UI
- 跨线程访问UI
- 关于抛出跨线程操作UI线程的异常的处理
- Android单线程操作UI的理解
- 安宁四会1384520135205
- 阳泉盘锦1384520145080
- 阳江海城1384520145127
- POJ 多项式加法
- android之AlarmManager
- 跨线程操作UI
- opencv学习-imgprocess- sobel算子
- 特殊的ip地址
- 浅谈Java中的几种随机数
- C/C++程序员面试大纲
- 常用API
- 记录慢慢成形的学习过程
- 武冈宜兴1384520350049
- 舒兰中山1384520350080