Android中启动线程的问题

发布于 2024-11-24 01:44:15 字数 3620 浏览 3 评论 0原文

我在 Android 中有一个活动,它显示一张图片作为背景。当我点击背景时,我使用 intent 去另一个活动...... 我的代码如下所示:

public class Precisari extends Activity{

    protected boolean _active = true;
    protected int _splashTime = 10000;
    public SplashThread  splashThread;


    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.precisari);

     splashThread=new SplashThread();

    }


    public class SplashThread extends Thread
    {
        public SplashThread()
        {

        }


        public void run() {

            try {

                int waited = 0;
                while (_active && (waited < _splashTime)) {
                    sleep(100);
                    if (_active) {

                        waited += 100;
                    }
                }
            } catch (InterruptedException e) {
                // do nothing
            } finally {
                //finish();
                Intent i = new Intent(getBaseContext(), com.SplashScreen.ConnectWithFb.class);
                startActivity(i);
                stop();

            }
        }

    }



    public boolean onTouchEvent(MotionEvent event){
        if(event.getAction()==MotionEvent.ACTION_DOWN){

            _active=false;
            }
        return true;
    }


    public void onResume(){
        super.onResume();
        _active=true;
        splashThread.start();
    }

    public void onPause()
    {
        super.onPause();
        splashThread.stop();

    }


}

我正在使用在 onResume() 中启动的线程...该线程循环直到布尔变量 _active 设置为 false 。当我单击模拟器的屏幕时,该变量设置为 false:

public boolean onTouchEvent(MotionEvent event){
            if(event.getAction()==MotionEvent.ACTION_DOWN){

                _active=false;
                }
            return true;
        }

然后我使用意图传递到下一个活动:

Intent i = new Intent(getBaseContext(), com.SplashScreen.ConnectWithFb.class);

线程在 onResume() 中启动,并在onPause()。这个想法是,当我回到这个活动时,我希望同样的想法起作用......当我点击屏幕时传递到下一个活动!

这是我的 logcat 的样子:

 Uncaught handler: thread main exiting due to uncaught exception
 java.lang.RuntimeException: Unable to resume activity {com.SplashScreen/com.SplashScreen.Precisari}: java.lang.IllegalThreadStateException: Thread already started.
    at android.app.ActivityThread.performResumeActivity(ActivityThread.java:2950)
    at android.app.ActivityThread.handleResumeActivity(ActivityThread.java:2965)
    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1889)
    at android.os.Handler.dispatchMessage(Handler.java:99)
    at android.os.Looper.loop(Looper.java:123)
    at android.app.ActivityThread.main(ActivityThread.java:4363)
    at java.lang.reflect.Method.invokeNative(Native Method)
    at java.lang.reflect.Method.invoke(Method.java:521)
    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:860)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:618)
    at dalvik.system.NativeStart.main(Native Method)
    Caused by: java.lang.IllegalThreadStateException: Thread already started.               at java.lang.Thread.start(Thread.java:1322)
    at com.SplashScreen.Precisari.onResume(Precisari.java:101)
    at android.app.Instrumentation.callActivityOnResume(Instrumentation.java:1149)
    at android.app.Activity.performResume(Activity.java:3763)
    at android.app.ActivityThread.performResumeActivity(ActivityThread.java:2937)

请有人告诉我我做错了什么?

I have an activity in Android which displays as a background a picture.When I click on the background I use an intent to go at another activity....
Here is how my code looks like:

public class Precisari extends Activity{

    protected boolean _active = true;
    protected int _splashTime = 10000;
    public SplashThread  splashThread;


    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.precisari);

     splashThread=new SplashThread();

    }


    public class SplashThread extends Thread
    {
        public SplashThread()
        {

        }


        public void run() {

            try {

                int waited = 0;
                while (_active && (waited < _splashTime)) {
                    sleep(100);
                    if (_active) {

                        waited += 100;
                    }
                }
            } catch (InterruptedException e) {
                // do nothing
            } finally {
                //finish();
                Intent i = new Intent(getBaseContext(), com.SplashScreen.ConnectWithFb.class);
                startActivity(i);
                stop();

            }
        }

    }



    public boolean onTouchEvent(MotionEvent event){
        if(event.getAction()==MotionEvent.ACTION_DOWN){

            _active=false;
            }
        return true;
    }


    public void onResume(){
        super.onResume();
        _active=true;
        splashThread.start();
    }

    public void onPause()
    {
        super.onPause();
        splashThread.stop();

    }


}

I'm using a thread which I started in onResume()...this thread loops until boolean variabile _active is set to false .The variable is set to false when I click on the screen of the emulator:

public boolean onTouchEvent(MotionEvent event){
            if(event.getAction()==MotionEvent.ACTION_DOWN){

                _active=false;
                }
            return true;
        }

and then I pass to the next activity by using an intent:

Intent i = new Intent(getBaseContext(), com.SplashScreen.ConnectWithFb.class);

The thread is started in onResume()and stopped in onPause().The idea is that when I come back to this activity I want the same idea to work....to pass to the next activity when I click the screen!

Here is how my logcat looks like:

 Uncaught handler: thread main exiting due to uncaught exception
 java.lang.RuntimeException: Unable to resume activity {com.SplashScreen/com.SplashScreen.Precisari}: java.lang.IllegalThreadStateException: Thread already started.
    at android.app.ActivityThread.performResumeActivity(ActivityThread.java:2950)
    at android.app.ActivityThread.handleResumeActivity(ActivityThread.java:2965)
    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1889)
    at android.os.Handler.dispatchMessage(Handler.java:99)
    at android.os.Looper.loop(Looper.java:123)
    at android.app.ActivityThread.main(ActivityThread.java:4363)
    at java.lang.reflect.Method.invokeNative(Native Method)
    at java.lang.reflect.Method.invoke(Method.java:521)
    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:860)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:618)
    at dalvik.system.NativeStart.main(Native Method)
    Caused by: java.lang.IllegalThreadStateException: Thread already started.               at java.lang.Thread.start(Thread.java:1322)
    at com.SplashScreen.Precisari.onResume(Precisari.java:101)
    at android.app.Instrumentation.callActivityOnResume(Instrumentation.java:1149)
    at android.app.Activity.performResume(Activity.java:3763)
    at android.app.ActivityThread.performResumeActivity(ActivityThread.java:2937)

Could please someone tell me what I'm doing wrong??

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

夏夜暖风 2024-12-01 01:44:16

您收到该异常的原因是因为停止并重新启动单个 Thread 对象实例是非法的。您分别在 onResume/onPause 中调用 start/stop,但您永远不会重新分配线程对象(来自 onCreate)。

为了停止并重新启动线程,您需要重新分配 Thread 对象。

Android 源代码在这方面相当明确:

// Thread.java, line ~178
/**
 * Reflects whether this Thread has already been started. A Thread
 * can only be started once (no recycling). Also, we need it to deduce
 * the proper Thread status.
 */
boolean hasBeenStarted = false;

// Thread.java, line ~1043
public synchronized void start()
{
    if (hasBeenStarted) {
        throw new IllegalThreadStateException("Thread already started."); // TODO Externalize?
    }

    hasBeenStarted = true;  // <--- Look here!

    VMThread.create(this, stackSize);
}

hasBeenStarted 永远不会重置回 false - 即使线程退出时也是如此。

The reason you're getting that exception is because it is illegal to stop and restart a single Thread object instance. You're calling start/stop in onResume/onPause respectively, but you're never reallocating the thread object (from onCreate).

In order to stop and restart your thread, you need to reallocate the Thread object.

The Android source is fairly explicit in this regard:

// Thread.java, line ~178
/**
 * Reflects whether this Thread has already been started. A Thread
 * can only be started once (no recycling). Also, we need it to deduce
 * the proper Thread status.
 */
boolean hasBeenStarted = false;

// Thread.java, line ~1043
public synchronized void start()
{
    if (hasBeenStarted) {
        throw new IllegalThreadStateException("Thread already started."); // TODO Externalize?
    }

    hasBeenStarted = true;  // <--- Look here!

    VMThread.create(this, stackSize);
}

hasBeenStarted is never reset back to false - even when the thread exits.

淤浪 2024-12-01 01:44:16

将 sleep(100) 放入 try catch 块中。

put sleep(100) in try catch block.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文