以特定时间间隔更改背景图像

时间:2014-01-29 15:50:27

标签: java android

我正在尝试开发一个Android应用程序,其中后台每5秒更改一次,我编写的代码如下:

public class BgView extends Activity implements Runnable {
    ImageView img;
    int [] setImg = {R.drawable.one,R.drawable.two};
    RelativeLayout layout;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_bg_view);
        layout = (RelativeLayout) findViewById(R.id.first);
        Thread t = new Thread(new BigView);
            t.start();

    }

    @Override
    public void run() {
        for (int i = 0; i < 2; ++i) {
            layout.setBackgroundResource(setImg[i]);
            try {
                Thread.sleep(5000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

} 

它编译得很好但是当我试图在模拟器中运行它时它在5秒后停止并且在logcat中我看到一个异常,它说我无法从其他函数或类似的东西触及Activity类视图。

所以我把整个 for循环放在onCreate()方法中,现在我没有得到任何异常,但我看到的是一个空白屏幕5秒后我得到最后一张图片

我知道这个问题已经重复,但我只是不想复制粘贴代码...我想知道为什么会发生这种情况,我们怎样才能让这项工作变得更少

<小时/> 编辑: 我得到以下异常:  E / AndroidRuntime(904):android.view.ViewRootImpl $ CalledFromWrongThreadException:只有创建视图层次结构的原始线程才能触及其视图。
我想知道为什么将整个for循环放在onCreate()方法中不起作用

3 个答案:

答案 0 :(得分:2)

只有UI线程可以/应该更新UI视图,在您的代码中,您尝试直接从新线程更新视图。

您应该在活动中创建一个处理程序,然后以所需的时间间隔从您的线程调用该处理程序。然后处理程序应该更新UI。尝试代码(我没有编译代码,只是键入它,因此可能是拼写错误/错误)

public class BgView extends Activity implements Runnable {
    ImageView img;
    final int [] setImg = {R.drawable.one,R.drawable.two};
    RelativeLayout layout;

    interface MyHandler {
     void letMeKnow(int i);
    }
    private MyHandler handler = new MyHandler(){

       @Override
       void letMeKnow(int i){
         layout.setBackgroundResource(setImg[i]);
       }
    }
@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_bg_view);
    layout = (RelativeLayout) findViewById(R.id.first);
    Thread t = new Thread(new BigView);
        t.start();

}

@Override
public void run() {
    for (int i = 0; i < 2; ++i) {
        handler.letMeKnow(i);
        try {
            Thread.sleep(5000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

}`

答案 1 :(得分:1)

将此行放在ui线程中,因为您无法在另一个线程的ui线程中进行修改

runOnUiThread(new Runnable() {
    @Override
    public void run() 
    {
    layout.setBackgroundResource(setImg[i]);
    }
});

我认为正确的方法是使用闹钟。请参阅此链接Android alarms

希望这有帮助。

答案 2 :(得分:0)

您的run方法应该重写如下:

public void run() {
    for (int i = 0; i < 2; ++i) {
        runOnUiThread(new Runnable() {

            public void run() 
            {
                layout.setBackgroundResource(setImg[i]);
            }
        });

        try {
            Thread.sleep(5000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}