Save and restore UI state when screen is rotated.

Fixes issue #3611920, but keep the issue open because more activities
will be added.
This commit is contained in:
akwizgran
2013-04-30 17:24:04 +01:00
parent d5720c085f
commit 1aa701ceee
12 changed files with 128 additions and 13 deletions

View File

@@ -203,6 +203,7 @@ public class HomeScreenActivity extends RoboActivity {
layout.addView(enterPassword);
final EditText passwordEntry = new EditText(this);
passwordEntry.setId(1);
passwordEntry.setMaxLines(1);
int inputType = TYPE_CLASS_TEXT | TYPE_TEXT_VARIATION_PASSWORD;
passwordEntry.setInputType(inputType);

View File

@@ -79,6 +79,7 @@ public class SetupActivity extends RoboActivity implements OnClickListener {
enableOrDisableContinueButton();
}
};
nicknameEntry.setId(1);
nicknameEntry.setMaxLines(1);
int inputType = TYPE_CLASS_TEXT | TYPE_TEXT_FLAG_CAP_WORDS;
nicknameEntry.setInputType(inputType);
@@ -98,6 +99,7 @@ public class SetupActivity extends RoboActivity implements OnClickListener {
enableOrDisableContinueButton();
}
};
passwordEntry.setId(2);
passwordEntry.setMaxLines(1);
inputType = TYPE_CLASS_TEXT | TYPE_TEXT_VARIATION_PASSWORD;
passwordEntry.setInputType(inputType);
@@ -117,6 +119,7 @@ public class SetupActivity extends RoboActivity implements OnClickListener {
enableOrDisableContinueButton();
}
};
passwordConfirmation.setId(3);
passwordConfirmation.setMaxLines(1);
inputType = TYPE_CLASS_TEXT | TYPE_TEXT_VARIATION_PASSWORD;
passwordConfirmation.setInputType(inputType);

View File

@@ -87,6 +87,7 @@ SelectContactsDialog.Listener {
layout.setGravity(CENTER_HORIZONTAL);
subscribeCheckBox = new CheckBox(this);
subscribeCheckBox.setId(1);
subscribeCheckBox.setText(R.string.subscribe_to_this_blog);
subscribeCheckBox.setChecked(subscribed);
subscribeCheckBox.setOnClickListener(this);
@@ -96,21 +97,21 @@ SelectContactsDialog.Listener {
radioGroup.setOrientation(VERTICAL);
visibleToAll = new RadioButton(this);
visibleToAll.setId(1);
visibleToAll.setId(2);
visibleToAll.setText(R.string.blog_visible_to_all);
visibleToAll.setEnabled(subscribed);
visibleToAll.setOnClickListener(this);
radioGroup.addView(visibleToAll);
visibleToSome = new RadioButton(this);
visibleToSome.setId(2);
visibleToSome.setId(3);
visibleToSome.setText(R.string.blog_visible_to_some);
visibleToSome.setEnabled(subscribed);
visibleToSome.setOnClickListener(this);
radioGroup.addView(visibleToSome);
if(!subscribed || all) radioGroup.check(1);
else radioGroup.check(2);
if(!subscribed || all) radioGroup.check(visibleToAll.getId());
else radioGroup.check(visibleToSome.getId());
layout.addView(radioGroup);
doneButton = new Button(this);

View File

@@ -99,6 +99,7 @@ SelectContactsDialog.Listener {
enableOrDisableCreateButton();
}
};
nameEntry.setId(1);
nameEntry.setMaxLines(1);
nameEntry.setInputType(TYPE_CLASS_TEXT | TYPE_TEXT_FLAG_CAP_SENTENCES);
nameEntry.setOnEditorActionListener(this);
@@ -108,11 +109,13 @@ SelectContactsDialog.Listener {
radioGroup.setOrientation(VERTICAL);
visibleToAll = new RadioButton(this);
visibleToAll.setId(2);
visibleToAll.setText(R.string.blog_visible_to_all);
visibleToAll.setOnClickListener(this);
radioGroup.addView(visibleToAll);
visibleToSome = new RadioButton(this);
visibleToSome.setId(3);
visibleToSome.setText(R.string.blog_visible_to_some);
visibleToSome.setOnClickListener(this);
radioGroup.addView(visibleToSome);

View File

@@ -24,6 +24,7 @@ import net.sf.briar.android.identity.LocalAuthorItem;
import net.sf.briar.android.identity.LocalAuthorItemComparator;
import net.sf.briar.android.identity.LocalAuthorSpinnerAdapter;
import net.sf.briar.android.widgets.HorizontalSpace;
import net.sf.briar.api.AuthorId;
import net.sf.briar.api.LocalAuthor;
import net.sf.briar.api.android.DatabaseUiExecutor;
import net.sf.briar.api.crypto.CryptoComponent;
@@ -67,13 +68,14 @@ implements OnItemSelectedListener, OnClickListener {
private Spinner fromSpinner = null, toSpinner = null;
private ImageButton sendButton = null;
private EditText content = null;
private AuthorId localAuthorId = null;
private GroupId localGroupId = null;
// Fields that are accessed from background threads must be volatile
@Inject private volatile DatabaseComponent db;
@Inject @DatabaseUiExecutor private volatile Executor dbUiExecutor;
private volatile LocalAuthor localAuthor = null;
private volatile LocalGroup localGroup = null;
private volatile GroupId localGroupId = null;
private volatile MessageId parentId = null;
@Override
@@ -86,6 +88,13 @@ implements OnItemSelectedListener, OnClickListener {
b = i.getByteArrayExtra("net.sf.briar.PARENT_ID");
if(b != null) parentId = new MessageId(b);
if(state != null) {
b = state.getByteArray("net.sf.briar.LOCAL_AUTHOR_ID");
if(b != null) localAuthorId = new AuthorId(b);
b = state.getByteArray("net.sf.briar.LOCAL_GROUP_ID");
if(b != null) localGroupId = new GroupId(b);
}
LinearLayout layout = new LinearLayout(this);
layout.setLayoutParams(MATCH_WRAP);
layout.setOrientation(VERTICAL);
@@ -136,6 +145,7 @@ implements OnItemSelectedListener, OnClickListener {
layout.addView(header);
content = new EditText(this);
content.setId(1);
int inputType = TYPE_CLASS_TEXT | InputType.TYPE_TEXT_FLAG_MULTI_LINE
| TYPE_TEXT_FLAG_CAP_SENTENCES;
content.setInputType(inputType);
@@ -187,6 +197,17 @@ implements OnItemSelectedListener, OnClickListener {
fromAdapter.add(new LocalAuthorItem(a));
fromAdapter.sort(LocalAuthorItemComparator.INSTANCE);
fromAdapter.notifyDataSetChanged();
int count = fromAdapter.getCount();
for(int i = 0; i < count; i++) {
LocalAuthorItem item = fromAdapter.getItem(i);
if(item == LocalAuthorItem.ANONYMOUS) continue;
if(item == LocalAuthorItem.NEW) continue;
if(item.getLocalAuthor().getId().equals(localAuthorId)) {
localAuthor = item.getLocalAuthor();
fromSpinner.setSelection(i);
break;
}
}
}
});
}
@@ -226,6 +247,7 @@ implements OnItemSelectedListener, OnClickListener {
LocalGroupItem item = toAdapter.getItem(i);
if(item == LocalGroupItem.NEW) continue;
if(item.getLocalGroup().getId().equals(localGroupId)) {
localGroup = item.getLocalGroup();
toSpinner.setSelection(i);
break;
}
@@ -234,6 +256,19 @@ implements OnItemSelectedListener, OnClickListener {
});
}
@Override
public void onSaveInstanceState(Bundle state) {
super.onSaveInstanceState(state);
if(localAuthorId != null) {
byte[] b = localAuthorId.getBytes();
state.putByteArray("net.sf.briar.LOCAL_AUTHOR_ID", b);
}
if(localGroupId != null) {
byte[] b = localGroupId.getBytes();
state.putByteArray("net.sf.briar.LOCAL_GROUP_ID", b);
}
}
@Override
public void onDestroy() {
super.onDestroy();
@@ -246,15 +281,20 @@ implements OnItemSelectedListener, OnClickListener {
LocalAuthorItem item = fromAdapter.getItem(position);
if(item == LocalAuthorItem.ANONYMOUS) {
localAuthor = null;
localAuthorId = null;
} else if(item == LocalAuthorItem.NEW) {
localAuthor = null;
localAuthorId = null;
startActivity(new Intent(this, CreateIdentityActivity.class));
} else {
localAuthor = item.getLocalAuthor();
localAuthorId = localAuthor.getId();
}
} else if(parent == toSpinner) {
LocalGroupItem item = toAdapter.getItem(position);
if(item == LocalGroupItem.NEW) {
localGroup = null;
localGroupId = null;
startActivity(new Intent(this, CreateBlogActivity.class));
} else {
localGroup = item.getLocalGroup();
@@ -267,6 +307,7 @@ implements OnItemSelectedListener, OnClickListener {
public void onNothingSelected(AdapterView<?> parent) {
if(parent == fromSpinner) {
localAuthor = null;
localAuthorId = null;
} else if(parent == toSpinner) {
localGroup = null;
localGroupId = null;
@@ -287,6 +328,7 @@ implements OnItemSelectedListener, OnClickListener {
finish();
}
// FIXME: This should happen on a CryptoExecutor thread
private Message createMessage(byte[] body) throws IOException,
GeneralSecurityException {
KeyParser keyParser = crypto.getSignatureKeyParser();

View File

@@ -85,6 +85,7 @@ SelectContactsDialog.Listener {
layout.setGravity(CENTER_HORIZONTAL);
subscribeCheckBox = new CheckBox(this);
subscribeCheckBox.setId(1);
subscribeCheckBox.setText(R.string.subscribe_to_this_group);
subscribeCheckBox.setChecked(subscribed);
subscribeCheckBox.setOnClickListener(this);
@@ -94,21 +95,21 @@ SelectContactsDialog.Listener {
radioGroup.setOrientation(VERTICAL);
visibleToAll = new RadioButton(this);
visibleToAll.setId(1);
visibleToAll.setId(2);
visibleToAll.setText(R.string.group_visible_to_all);
visibleToAll.setEnabled(subscribed);
visibleToAll.setOnClickListener(this);
radioGroup.addView(visibleToAll);
visibleToSome = new RadioButton(this);
visibleToSome.setId(2);
visibleToSome.setId(3);
visibleToSome.setText(R.string.group_visible_to_some);
visibleToSome.setEnabled(subscribed);
visibleToSome.setOnClickListener(this);
radioGroup.addView(visibleToSome);
if(!subscribed || all) radioGroup.check(1);
else radioGroup.check(2);
if(!subscribed || all) radioGroup.check(visibleToAll.getId());
else radioGroup.check(visibleToSome.getId());
layout.addView(radioGroup);
doneButton = new Button(this);

View File

@@ -94,6 +94,7 @@ SelectContactsDialog.Listener {
enableOrDisableCreateButton();
}
};
nameEntry.setId(1);
nameEntry.setMaxLines(1);
nameEntry.setInputType(TYPE_CLASS_TEXT | TYPE_TEXT_FLAG_CAP_SENTENCES);
nameEntry.setOnEditorActionListener(this);
@@ -103,11 +104,13 @@ SelectContactsDialog.Listener {
radioGroup.setOrientation(VERTICAL);
visibleToAll = new RadioButton(this);
visibleToAll.setId(2);
visibleToAll.setText(R.string.blog_visible_to_all);
visibleToAll.setOnClickListener(this);
radioGroup.addView(visibleToAll);
visibleToSome = new RadioButton(this);
visibleToSome.setId(3);
visibleToSome.setText(R.string.blog_visible_to_some);
visibleToSome.setOnClickListener(this);
radioGroup.addView(visibleToSome);

View File

@@ -27,6 +27,7 @@ import net.sf.briar.android.identity.LocalAuthorItem;
import net.sf.briar.android.identity.LocalAuthorItemComparator;
import net.sf.briar.android.identity.LocalAuthorSpinnerAdapter;
import net.sf.briar.android.widgets.HorizontalSpace;
import net.sf.briar.api.AuthorId;
import net.sf.briar.api.LocalAuthor;
import net.sf.briar.api.android.DatabaseUiExecutor;
import net.sf.briar.api.crypto.CryptoComponent;
@@ -70,13 +71,14 @@ implements OnItemSelectedListener, OnClickListener {
private Spinner fromSpinner = null, toSpinner = null;
private ImageButton sendButton = null;
private EditText content = null;
private AuthorId localAuthorId = null;
private GroupId groupId = null;
// Fields that are accessed from background threads must be volatile
@Inject private volatile DatabaseComponent db;
@Inject @DatabaseUiExecutor private volatile Executor dbUiExecutor;
private volatile LocalAuthor localAuthor = null;
private volatile Group group = null;
private volatile GroupId groupId = null;
private volatile MessageId parentId = null;
@Override
@@ -89,6 +91,13 @@ implements OnItemSelectedListener, OnClickListener {
b = i.getByteArrayExtra("net.sf.briar.PARENT_ID");
if(b != null) parentId = new MessageId(b);
if(state != null) {
b = state.getByteArray("net.sf.briar.LOCAL_AUTHOR_ID");
if(b != null) localAuthorId = new AuthorId(b);
b = state.getByteArray("net.sf.briar.GROUP_ID");
if(b != null) groupId = new GroupId(b);
}
LinearLayout layout = new LinearLayout(this);
layout.setLayoutParams(MATCH_WRAP);
layout.setOrientation(VERTICAL);
@@ -139,6 +148,7 @@ implements OnItemSelectedListener, OnClickListener {
layout.addView(header);
content = new EditText(this);
content.setId(1);
int inputType = TYPE_CLASS_TEXT | InputType.TYPE_TEXT_FLAG_MULTI_LINE
| TYPE_TEXT_FLAG_CAP_SENTENCES;
content.setInputType(inputType);
@@ -190,6 +200,17 @@ implements OnItemSelectedListener, OnClickListener {
fromAdapter.add(new LocalAuthorItem(a));
fromAdapter.sort(LocalAuthorItemComparator.INSTANCE);
fromAdapter.notifyDataSetChanged();
int count = fromAdapter.getCount();
for(int i = 0; i < count; i++) {
LocalAuthorItem item = fromAdapter.getItem(i);
if(item == LocalAuthorItem.ANONYMOUS) continue;
if(item == LocalAuthorItem.NEW) continue;
if(item.getLocalAuthor().getId().equals(localAuthorId)) {
localAuthor = item.getLocalAuthor();
fromSpinner.setSelection(i);
break;
}
}
}
});
}
@@ -231,6 +252,7 @@ implements OnItemSelectedListener, OnClickListener {
GroupItem g = toAdapter.getItem(i);
if(g == GroupItem.NEW) continue;
if(g.getGroup().getId().equals(groupId)) {
group = g.getGroup();
toSpinner.setSelection(i);
break;
}
@@ -239,6 +261,19 @@ implements OnItemSelectedListener, OnClickListener {
});
}
@Override
public void onSaveInstanceState(Bundle state) {
super.onSaveInstanceState(state);
if(localAuthorId != null) {
byte[] b = localAuthorId.getBytes();
state.putByteArray("net.sf.briar.LOCAL_AUTHOR_ID", b);
}
if(groupId != null) {
byte[] b = groupId.getBytes();
state.putByteArray("net.sf.briar.GROUP_ID", b);
}
}
@Override
public void onDestroy() {
super.onDestroy();
@@ -251,15 +286,20 @@ implements OnItemSelectedListener, OnClickListener {
LocalAuthorItem item = fromAdapter.getItem(position);
if(item == LocalAuthorItem.ANONYMOUS) {
localAuthor = null;
localAuthorId = null;
} else if(item == LocalAuthorItem.NEW) {
localAuthor = null;
localAuthorId = null;
startActivity(new Intent(this, CreateIdentityActivity.class));
} else {
localAuthor = item.getLocalAuthor();
localAuthorId = localAuthor.getId();
}
} else if(parent == toSpinner) {
GroupItem item = toAdapter.getItem(position);
if(item == GroupItem.NEW) {
group = null;
groupId = null;
startActivity(new Intent(this, CreateGroupActivity.class));
} else {
group = item.getGroup();
@@ -272,6 +312,7 @@ implements OnItemSelectedListener, OnClickListener {
public void onNothingSelected(AdapterView<?> parent) {
if(parent == fromSpinner) {
localAuthor = null;
localAuthorId = null;
} else if(parent == toSpinner) {
group = null;
groupId = null;
@@ -292,6 +333,7 @@ implements OnItemSelectedListener, OnClickListener {
finish();
}
// FIXME: This should happen on a CryptoExecutor thread
private Message createMessage(byte[] body) throws IOException,
GeneralSecurityException {
if(localAuthor == null) {

View File

@@ -88,6 +88,7 @@ implements OnEditorActionListener, OnClickListener {
createButton.setEnabled(getText().length() > 0);
}
};
nicknameEntry.setId(1);
nicknameEntry.setMaxLines(1);
int inputType = TYPE_CLASS_TEXT | TYPE_TEXT_FLAG_CAP_WORDS;
nicknameEntry.setInputType(inputType);

View File

@@ -174,8 +174,8 @@ implements InvitationListener {
public void onSaveInstanceState(Bundle state) {
super.onSaveInstanceState(state);
if(localAuthorId != null) {
state.putByteArray("net.sf.briar.LOCAL_AUTHOR_ID",
localAuthorId.getBytes());
byte[] b = localAuthorId.getBytes();
state.putByteArray("net.sf.briar.LOCAL_AUTHOR_ID", b);
}
state.putInt("net.sf.briar.LOCAL_CODE", localInvitationCode);
state.putInt("net.sf.briar.REMOTE_CODE", remoteInvitationCode);

View File

@@ -54,6 +54,7 @@ implements OnEditorActionListener, OnClickListener {
continueButton.setEnabled(getText().length() == 6);
}
};
codeEntry.setId(1);
codeEntry.setTextSize(26);
codeEntry.setOnEditorActionListener(this);
codeEntry.setMinEms(5);

View File

@@ -83,6 +83,11 @@ implements OnItemSelectedListener, OnClickListener {
byte[] b = i.getByteArrayExtra("net.sf.briar.PARENT_ID");
if(b != null) parentId = new MessageId(b);
if(state != null) {
id = state.getInt("net.sf.briar.CONTACT_ID", -1);
if(id != -1) contactId = new ContactId(id);
}
LinearLayout layout = new LinearLayout(this);
layout.setLayoutParams(MATCH_WRAP);
layout.setOrientation(VERTICAL);
@@ -127,6 +132,7 @@ implements OnItemSelectedListener, OnClickListener {
layout.addView(header);
content = new EditText(this);
content.setId(1);
int inputType = TYPE_CLASS_TEXT | InputType.TYPE_TEXT_FLAG_MULTI_LINE
| TYPE_TEXT_FLAG_CAP_SENTENCES;
content.setInputType(inputType);
@@ -188,6 +194,13 @@ implements OnItemSelectedListener, OnClickListener {
});
}
@Override
public void onSaveInstanceState(Bundle state) {
super.onSaveInstanceState(state);
if(contactId != null)
state.putInt("net.sf.briar.CONTACT_ID", contactId.getInt());
}
@Override
public void onDestroy() {
super.onDestroy();
@@ -198,12 +211,16 @@ implements OnItemSelectedListener, OnClickListener {
long id) {
ContactItem item = adapter.getItem(position);
if(item == ContactItem.NEW) {
contactId = null;
localAuthor = null;
startActivity(new Intent(this, AddContactActivity.class));
} else {
Contact c = item.getContact();
loadLocalAuthor(c.getLocalAuthorId());
contactId = c.getId();
localAuthor = null;
loadLocalAuthor(c.getLocalAuthorId());
}
sendButton.setEnabled(false);
}
private void loadLocalAuthor(final AuthorId a) {