我对代码中的错误进行了最小化的重复。创建一个空应用并粘贴以下内容:
<!-- content_main.xml -->
<EditText
android:id="@+id/main_editText"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
// MainActivity.java
private static SpannableStringBuilder sText;
private EditText mEditText;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
if (sText == null) {
sText = new SpannableStringBuilder("Hello world!");
}
mEditText = (EditText) findViewById(R.id.main_editText);
mEditText.setEditableFactory(new Editable.Factory() {
@Override
public Editable newEditable(CharSequence source) {
return (Editable) source;
}
});
mEditText.setText(sText, TextView.BufferType.EDITABLE);
workLoop(0);
}
private void workLoop(final int index) {
SpannableStringBuilder text = sText;
if (index == text.length()) {
return;
}
text.setSpan(new ForegroundColorSpan(Color.BLUE), index, index + 1, Spannable.SPAN_INCLUSIVE_EXCLUSIVE);
Handler uiThreadHandler = new Handler(Looper.getMainLooper());
uiThreadHandler.postDelayed(new Runnable() {
@Override
public void run() {
workLoop(index + 1);
}
}, 5000);
}
说明:此代码会将文本Hello, world!
放入EditText中,然后在每隔5秒后将每个字母的颜色设置为蓝色。
但是,如果我旋转屏幕,导致活动被销毁/重新创建,文本将停止变色。为什么会这样?
答案 0 :(得分:1)
会发生这种情况,因为轮换后Activity
会调用onRestoreInstanceState()
回调方法并覆盖EditText
的值。你应该添加这样的东西:
@Override
protected void onRestoreInstanceState(Bundle savedInstanceState) {
super.onRestoreInstanceState(savedInstanceState);
mEditText.setText(sText, TextView.BufferType.EDITABLE);
}
此处还要注意:
uiThreadHandler.postDelayed(new Runnable() {
@Override
public void run() {
workLoop(index + 1);
}
}, 5000);
由于屏幕轮换,匿名Runnable
保持运行并在创建MainActivity
的新实例后引用旧MainActivity
实例。我建议在Handler
方法中清除Activity.onDestroy()
的回调。