为什么要使用Handler?

Sya*_*asu 9 android

我在一个非常基本的Handler教程中遇到了这段代码.代码工作正常,但我不明白为什么我必须使用Handler progressDialog.dismiss()??? 我删除了处理程序部分并放置 progressDialog.dismiss()run()方法中,它工作正常.那么为什么使用Handler ???

 import android.app.Activity;
    import android.app.ProgressDialog;
    import android.os.Bundle;
    import android.os.Handler;
    import android.os.Message;
    import android.view.View;
    import android.view.View.OnClickListener;
    import android.widget.Button;
    import android.widget.Toast;


    public class HandlerThread extends Activity{

    private Button start;
    private ProgressDialog progressDialog;

    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        start = (Button) findViewById(R.id.Button01);
        start.setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View arg0) {
                // TODO Auto-generated method stub
                fetchData();
            }

        });
    }



    protected void fetchData() {
        // TODO Auto-generated method stub
        progressDialog = ProgressDialog.show(this, "", "Doing...");
        new Thread() {
            public void run() {
                try {

                    Thread.sleep(8000);

                    } catch (InterruptedException e) {

                    }
                      messageHandler.sendEmptyMessage(0);

                    }
        }.start();


    }



    private Handler messageHandler = new Handler() {

        public void handleMessage(Message msg) {
            super.handleMessage(msg);
            progressDialog.dismiss();

        }
    };
}
Run Code Online (Sandbox Code Playgroud)

Dev*_*ath 31

为什么在Android中使用Handler?


第一:让我们知道什么是线程:

  • 线程有助于多任务处理
  • 线程可以作为在主进程下运行的迷你进程来教授
  • 线程至少启用外观并行执行

第二:告诉我们应用程序线程: -

  • 当Android应用程序首次启动时,运行时系统将创建一个主线程,这个主线程将负责执行android中的所有组件

Android UI-Toolkit不是线程安全的

  • 如上所述,android主线程中有许多组件,现在假设其中一个组件需要很长时间才能执行,这会使主线程无响应,并且会显示应用程序无响应
  • 子线程无法直接操作android中的应用程序(主)线程
  • 处理程序充当接口并从子线程收集消息,并在消息到达时逐个更新主应用程序线程,线程处理程序在主线程中实现.

处理程序类:

  • 出于多线程的目的,我们将使用来自包的处理程序类 android.os.Handler
  • 每个线程由一个处理程序类实例处理

数字

  • 从上图中我们可以看到每个线程都由Handler类的一个实例处理
  • 线程在消息的帮助下相互通信
  • 这个处理程序类通过允许它们一起运行实现多线程,有助于维护同步协调黑线程的类型

处理程序的实例

Handler handlerObject = new Handler();
Run Code Online (Sandbox Code Playgroud)

使用处理程序的最后一件事是使用Runnable Interface:

  • handler类利用runnable接口实现多线程
  • 我们重写run方法以在指定的时间内执行一个线程

Class NameOfClass implements Runnable
{
    Public void run()
    {
        //Body of run method
    }
}
Run Code Online (Sandbox Code Playgroud)

全部放在一起

//Create handler in the thread it should be associated with 
//in this case the UI thread
final Handler handler = new Handler();
Runnable runnable = new Runnable() {
    public void run() {
        while(running){
            //Do time consuming stuff

            //The handler schedules the new runnable on the UI thread
            handler.post(new Runnable() {
                //Ex.. using progressbar to set the pogress
                            //Updating the UI is done inside the Handler
            });
        }
    }
};
new Thread(runnable).start();
Run Code Online (Sandbox Code Playgroud)

  • @Marek .....我已经更新了答案并使示例更加简单:) (2认同)

Dhe*_*.S. 18

来自以下文件View:

在任何视图上调用任何方法时,您必须始终位于UI线程上.如果您正在处理其他线程并希望从该线程更新视图的状态,则应使用a Handler.

在您的示例中,当您根据上述文档调用dismiss()方法时ProgressDialog,必须从UI线程执行此操作.在messageHandler实例化类HandlerHandlerThread(可能在UI线程上)初始化为a的实例.

来自以下文件Handler:

每个Handler实例都与一个线程和该线程的消息队列相关联.当你创建一个新的Handler,它被绑定到创建它的线程的线程/消息队列 - 从那时起,它将消息和runnables传递给该消息队列并在它们从消息队列中出来时执行它们.

因此,要从新线程与UI线程进行通信,只需将消息发布到HandlerUI线程上创建的消息.

如果View从UI线程外部调用方法,它会调用未定义的行为,这意味着它可能看起来工作正常.但它并不总能保证工作正常.


Mar*_*rek 5

越容易越好。您可以尝试使用以下代码来代替使用处理程序:

runOnUiThread(
    new Runnable() { 
        public void run() 
        { 

        //Update user interface here

        } 
    }
);
Run Code Online (Sandbox Code Playgroud)

不要让生活变得复杂;)

  • 您需要引用活动以发布到UI线程中,而使用处理程序则只需要它自己。如果您只想保留Views引用,则另一个解决方案是使用View.post(Runnable action)。 (4认同)