【问题标题】:Creating a new thread for UI in Android在 Android 中为 UI 创建一个新线程
【发布时间】:2011-06-24 20:08:06
【问题描述】:

我创建了一个 Activity,之后我创建了一个线程,它从电话簿中读取数据,进行一些字符串操作并根据规则,在主 UI 上创建各种按钮。

我有下面的代码,但有一些应用程序如何终止。

谁能帮帮我。

public class Phone extends Activity {
    /** Called when the activity is first created. */
    ProgressDialog pbarDialog;
    LinearLayout ll;
    Button b;

    @Override    
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        ScrollView sv = new ScrollView(this);
        ll = new LinearLayout(this);
        ll.setOrientation(LinearLayout.VERTICAL);
        sv.addView(ll);
        setContentView(sv);
        pbarDialog = new ProgressDialog(this);
        pbarDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
        pbarDialog.setMessage("Reading from Phone Book");
        pbarDialog.setCancelable(false);
        pbarDialog.show();
        pbarDialog.incrementProgressBy(0);     



        new TheTask().execute();                       

    }


    private class TheTask extends AsyncTask<Void, Integer, Void>{

        @Override
        protected void onPreExecute() {
            pbarDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
            pbarDialog.setMessage("Reading from Phone Book");
            pbarDialog.setCancelable(false);
            pbarDialog.show();
            pbarDialog.incrementProgressBy(0);         
        }

        @Override
        protected Void doInBackground(Void... params) {
            ReadPhoneBook();
            return null;
        }

        @Override
        protected void onPostExecute(Void result) {
            pbarDialog.dismiss();
        }

    }    



    private void ReadPhoneBook() {
        int i=0;             
        int count=0;
        //this is a temp function, it just creates buttons, does not read the phone book.
        for (i=0;i<10;i++)
        {           
            b = new Button(this);
            b.setText("Testing");            
            b.setId(1);
            final Activity self = this;
            b.setOnClickListener(new OnClickListener(){
                @Override
                public void onClick(View v){
                    initiateACall(v,self);
                }
            });
            ll.addView(b);  
            if (i%3 == 0){
                pbarDialog.incrementProgressBy(30*i/3);
            }
        }

    }

我收到以下错误:

06-24 21:52:36.274: WARN/dalvikvm(297): threadid=7: 线程以未捕获的异常退出 (group=0x4001d800) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 致命异常: AsyncTask #1 06-24 21:52:36.436: 错误/AndroidRuntime(297): java.lang.RuntimeException: 执行 doInBackground() 时发生错误 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.os.AsyncTask$3.done(AsyncTask.java:200) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 java.util.concurrent.FutureTask$Sync.innerSetException(FutureTask.java:273) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 java.util.concurrent.FutureTask.setException(FutureTask.java:124) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:307) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 java.util.concurrent.FutureTask.run(FutureTask.java:137) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1068) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:561) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 java.lang.Thread.run(Thread.java:1096) 06-24 21:52:36.436: ERROR/AndroidRuntime(297): Caused by: android.view.ViewRoot$CalledFromWrongThreadException: 只有创建视图层次结构的原始线程才能触摸其视图。 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.view.ViewRoot.checkThread(ViewRoot.java:2802) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.view.ViewRoot.requestLayout(ViewRoot.java:594) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.view.View.requestLayout(View.java:8125) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.view.View.requestLayout(View.java:8125) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.view.View.requestLayout(View.java:8125) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.view.View.requestLayout(View.java:8125) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.widget.ScrollView.requestLayout(ScrollView.java:1200) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.view.View.requestLayout(View.java:8125) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.view.ViewGroup.addView(ViewGroup.java:1863) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.view.ViewGroup.addView(ViewGroup.java:1822) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.view.ViewGroup.addView(ViewGroup.java:1802) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 ReadPhoneBook(IndiaCalling.java:148) 06-24 21:52:36.436: 错误/AndroidRuntime(297): at access$0(IndiaCalling.java:133) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 $TheTask.doInBackground(IndiaCalling.java:79) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 $TheTask.doInBackground(IndiaCalling.java:1) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 android.os.AsyncTask$2.call(AsyncTask.java:185) 06-24 21:52:36.436: 错误/AndroidRuntime(297): 在 java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:305) 06-24 21:52:36.436: 错误/AndroidRuntime(297): ... 4 更多 06-24 21:52:36.564: WARN/ActivityManager(67): 强制完成活动 net.WhileOne.IndiaCalling/.IndiaCalling 06-24 21:52:37.534: WARN/InputManagerService(67): 窗口已经聚焦,忽略焦点增益:com.android.internal.view.IInputMethodClient$Stub$Proxy@44eab020 06-24 21:52:39.004: ERROR/WindowManager(297): Activity Phone has leaked window com.android.internal.policy.impl.PhoneWindow$DecorView@44eeacf8 最初是在这里添加的 06-24 21:52:39.004: ERROR/WindowManager(297): android.view.WindowLeaked: Activity Phone 已泄露窗口 com.android.internal.policy.impl.PhoneWindow$DecorView@44eeacf8 最初添加在这里 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.view.ViewRoot.(ViewRoot.java:247) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.view.WindowManagerImpl.addView(WindowManagerImpl.java:148) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.view.WindowManagerImpl.addView(WindowManagerImpl.java:91) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.view.Window$LocalWindowManager.addView(Window.java:424) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.app.Dialog.show(Dialog.java:241) 06-24 21:52:39.004: 错误/WindowManager(297): 在 Phone.onCreate(Phone.java:47) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1047) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2627) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2679) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.app.ActivityThread.access$2300(ActivityThread.java:125) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.app.ActivityThread$H.handleMessage(ActivityThread.java:2033) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.os.Handler.dispatchMessage(Handler.java:99) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.os.Looper.loop(Looper.java:123) 06-24 21:52:39.004: 错误/WindowManager(297): 在 android.app.ActivityThread.main(ActivityThread.java:4627) 06-24 21:52:39.004: 错误/WindowManager(297): 在 java.lang.reflect.Method.invokeNative(Native Method) 06-24 21:52:39.004: 错误/WindowManager(297): 在 java.lang.reflect.Method.invoke(Method.java:521) 06-24 21:52:39.004: 错误/WindowManager(297): 在 com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:868) 06-24 21:52:39.004: 错误/WindowManager(297): 在 com.android.internal.os.ZygoteInit.main(ZygoteInit.java:626) 06-24 21:52:39.004: ERROR/WindowManager(297): at dalvik.system.NativeStart.main(Native Method)

【问题讨论】:

  • 它是如何终止的?产生错误?日志是什么样的?

标签: ui-thread


【解决方案1】:

这会使用 Android 的 AsyncTask 类统计您的线程:

new TheTask().execute();

但是,我不明白您为什么还要盯着新线程:

new Thread(new Runnable(){
            public void run(){          
                //Thread.sleep(5*1000);
                ReadPhoneBook();
                pbarDialog.dismiss();
            }           
        }).start(); 

为什么不使用其中一个?

【讨论】:

  • 不好意思,忘记评论了,我更新一下吧……评论了还是不行……
  • 将 ReadPhoneBook 方法放入 TheTask 类或在 ReadPhoneBook 方法签名中添加“同步”
  • 尝试了 a) 将 ReadPhoneBook 方法放入 TheTAsk 类和 b) 将同步添加到 ReadPhoneBook 方法,它仍然无法正常工作...
  • 修复了这个问题。正在尝试从线程更新主活动中的视图。
【解决方案2】:

解决了这个问题。试图从线程更新主活动中的视图。

【讨论】:

    猜你喜欢
    • 2020-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-03-18
    • 1970-01-01
    • 1970-01-01
    • 2013-07-19
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多