Manage my keys wizard

This commit is contained in:
Dominik Schürmann
2015-03-19 17:16:23 +01:00
parent 0bcc2793c3
commit 98817d13ee
35 changed files with 462 additions and 437 deletions

View File

@@ -22,6 +22,7 @@ import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentTransaction;
import org.sufficientlysecure.keychain.R;
import org.sufficientlysecure.keychain.util.Passphrase;
import java.util.ArrayList;
@@ -29,12 +30,67 @@ public class CreateKeyActivity extends BaseActivity {
public static final String EXTRA_NAME = "name";
public static final String EXTRA_EMAIL = "email";
public static final String EXTRA_FIRST_TIME = "first_time";
public static final String EXTRA_ADDITIONAL_EMAILS = "additional_emails";
public static final String EXTRA_PASSPHRASE = "passphrase";
public class State {
String name;
String email;
ArrayList<String> additionalEmails;
char[] passphrase;
public static final String FRAGMENT_TAG = "currentFragment";
String mName;
String mEmail;
ArrayList<String> mAdditionalEmails;
Passphrase mPassphrase;
boolean mFirstTime;
Fragment mCurrentFragment;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// Check whether we're recreating a previously destroyed instance
if (savedInstanceState != null) {
// Restore value of members from saved state
mName = savedInstanceState.getString(EXTRA_NAME);
mEmail = savedInstanceState.getString(EXTRA_EMAIL);
mAdditionalEmails = savedInstanceState.getStringArrayList(EXTRA_ADDITIONAL_EMAILS);
mPassphrase = savedInstanceState.getParcelable(EXTRA_PASSPHRASE);
mFirstTime = savedInstanceState.getBoolean(EXTRA_FIRST_TIME);
mCurrentFragment = getSupportFragmentManager().findFragmentByTag(FRAGMENT_TAG);
} else {
// Initialize members with default values for a new instance
mName = getIntent().getStringExtra(EXTRA_NAME);
mEmail = getIntent().getStringExtra(EXTRA_EMAIL);
mFirstTime = getIntent().getBooleanExtra(EXTRA_FIRST_TIME, false);
// Start with first fragment of wizard
CreateKeyStartFragment frag = CreateKeyStartFragment.newInstance();
loadFragment(frag, FragAction.START);
}
if (mFirstTime) {
setTitle(R.string.app_name);
setActionBarIcon(R.drawable.ic_launcher);
} else {
setTitle(R.string.title_manage_my_keys);
}
}
@Override
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
outState.putString(EXTRA_NAME, mName);
outState.putString(EXTRA_EMAIL, mEmail);
outState.putStringArrayList(EXTRA_ADDITIONAL_EMAILS, mAdditionalEmails);
outState.putParcelable(EXTRA_PASSPHRASE, mPassphrase);
outState.putBoolean(EXTRA_FIRST_TIME, mFirstTime);
}
@Override
protected void initLayout() {
setContentView(R.layout.create_key_activity);
}
public static enum FragAction {
@@ -43,41 +99,17 @@ public class CreateKeyActivity extends BaseActivity {
TO_LEFT
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// pass extras into fragment
CreateKeyNameFragment frag =
CreateKeyNameFragment.newInstance(
getIntent().getStringExtra(EXTRA_NAME),
getIntent().getStringExtra(EXTRA_EMAIL)
);
loadFragment(savedInstanceState, frag, FragAction.START);
}
@Override
protected void initLayout() {
setContentView(R.layout.create_key_activity);
}
public void loadFragment(Bundle savedInstanceState, Fragment fragment, FragAction action) {
// However, if we're being restored from a previous state,
// then we don't need to do anything and should return or else
// we could end up with overlapping fragments.
if (savedInstanceState != null) {
return;
}
public void loadFragment(Fragment fragment, FragAction action) {
mCurrentFragment = fragment;
// Add the fragment to the 'fragment_container' FrameLayout
// NOTE: We use commitAllowingStateLoss() to prevent weird crashes!
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
switch (action) {
case START:
transaction.setCustomAnimations(0, 0);
transaction.replace(R.id.create_key_fragment_container, fragment)
.commitAllowingStateLoss();
transaction.replace(R.id.create_key_fragment_container, fragment, FRAGMENT_TAG)
.commit();
break;
case TO_LEFT:
getSupportFragmentManager().popBackStackImmediate();
@@ -86,8 +118,8 @@ public class CreateKeyActivity extends BaseActivity {
transaction.setCustomAnimations(R.anim.frag_slide_in_from_right, R.anim.frag_slide_out_to_left,
R.anim.frag_slide_in_from_left, R.anim.frag_slide_out_to_right);
transaction.addToBackStack(null);
transaction.replace(R.id.create_key_fragment_container, fragment)
.commitAllowingStateLoss();
transaction.replace(R.id.create_key_fragment_container, fragment, FRAGMENT_TAG)
.commit();
break;
}

View File

@@ -46,16 +46,12 @@ import java.util.List;
public class CreateKeyEmailFragment extends Fragment {
public static final String ARG_NAME = "name";
public static final String ARG_EMAIL = "email";
CreateKeyActivity mCreateKeyActivity;
EmailEditText mEmailEdit;
RecyclerView mEmailsRecyclerView;
View mBackButton;
View mNextButton;
String mName;
ArrayList<EmailAdapter.ViewModel> mAdditionalEmailModels;
EmailAdapter mEmailAdapter;
@@ -63,13 +59,10 @@ public class CreateKeyEmailFragment extends Fragment {
/**
* Creates new instance of this fragment
*/
public static CreateKeyEmailFragment newInstance(String name, String email) {
public static CreateKeyEmailFragment newInstance() {
CreateKeyEmailFragment frag = new CreateKeyEmailFragment();
Bundle args = new Bundle();
args.putString(ARG_NAME, name);
args.putString(ARG_EMAIL, email);
frag.setArguments(args);
return frag;
@@ -106,31 +99,33 @@ public class CreateKeyEmailFragment extends Fragment {
mEmailsRecyclerView = (RecyclerView) view.findViewById(R.id.create_key_emails);
// initial values
mName = getArguments().getString(ARG_NAME);
String email = getArguments().getString(ARG_EMAIL);
mEmailEdit.setText(email);
mEmailEdit.setText(mCreateKeyActivity.mEmail);
// focus empty edit fields
if (email == null) {
if (mCreateKeyActivity.mEmail == null) {
mEmailEdit.requestFocus();
}
mBackButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
mCreateKeyActivity.loadFragment(null, null, FragAction.TO_LEFT);
mCreateKeyActivity.loadFragment(null, FragAction.TO_LEFT);
}
});
mNextButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
createKeyCheck();
nextClicked();
}
});
mEmailsRecyclerView.setHasFixedSize(true);
mEmailsRecyclerView.setLayoutManager(new LinearLayoutManager(getActivity()));
mEmailsRecyclerView.setItemAnimator(new DefaultItemAnimator());
// initial values
mAdditionalEmailModels = new ArrayList<>();
if (mCreateKeyActivity.mAdditionalEmails != null) {
setAdditionalEmails(mCreateKeyActivity.mAdditionalEmails);
}
mEmailAdapter = new EmailAdapter(mAdditionalEmailModels, new View.OnClickListener() {
@Override
public void onClick(View v) {
@@ -171,25 +166,38 @@ public class CreateKeyEmailFragment extends Fragment {
mCreateKeyActivity = (CreateKeyActivity) getActivity();
}
private void createKeyCheck() {
private void nextClicked() {
if (isEditTextNotEmpty(getActivity(), mEmailEdit)) {
// save state
mCreateKeyActivity.mEmail = mEmailEdit.getText().toString();
mCreateKeyActivity.mAdditionalEmails = getAdditionalEmails();
ArrayList<String> emails = new ArrayList<>();
for (EmailAdapter.ViewModel holder : mAdditionalEmailModels) {
emails.add(holder.toString());
}
CreateKeyPassphraseFragment frag =
CreateKeyPassphraseFragment.newInstance(
mName,
mEmailEdit.getText().toString(),
emails
);
mCreateKeyActivity.loadFragment(null, frag, FragAction.TO_RIGHT);
CreateKeyPassphraseFragment frag = CreateKeyPassphraseFragment.newInstance();
mCreateKeyActivity.loadFragment(frag, FragAction.TO_RIGHT);
}
}
private ArrayList<String> getAdditionalEmails() {
ArrayList<String> emails = new ArrayList<>();
for (EmailAdapter.ViewModel holder : mAdditionalEmailModels) {
emails.add(holder.toString());
}
return emails;
}
private void setAdditionalEmails(ArrayList<String> emails) {
for (String email : emails) {
mAdditionalEmailModels.add(new EmailAdapter.ViewModel(email));
}
}
@Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
// save state in activity
mCreateKeyActivity.mAdditionalEmails = getAdditionalEmails();
}
public static class EmailAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {
private List<ViewModel> mDataset;
private View.OnClickListener mFooterOnClickListener;

View File

@@ -65,32 +65,15 @@ public class CreateKeyFinalFragment extends Fragment {
TextView mEditText;
View mEditButton;
public static final String ARG_NAME = "name";
public static final String ARG_EMAIL = "email";
public static final String ARG_ADDITIONAL_EMAILS = "emails";
public static final String ARG_PASSPHRASE = "passphrase";
String mName;
String mEmail;
ArrayList<String> mAdditionalEmails;
Passphrase mPassphrase;
SaveKeyringParcel mSaveKeyringParcel;
/**
* Creates new instance of this fragment
*/
public static CreateKeyFinalFragment newInstance(String name, String email,
ArrayList<String> additionalEmails,
Passphrase passphrase) {
public static CreateKeyFinalFragment newInstance() {
CreateKeyFinalFragment frag = new CreateKeyFinalFragment();
Bundle args = new Bundle();
args.putString(ARG_NAME, name);
args.putString(ARG_EMAIL, email);
args.putStringArrayList(ARG_ADDITIONAL_EMAILS, additionalEmails);
args.putParcelable(ARG_PASSPHRASE, passphrase);
frag.setArguments(args);
return frag;
@@ -108,17 +91,11 @@ public class CreateKeyFinalFragment extends Fragment {
mEditText = (TextView) view.findViewById(R.id.create_key_edit_text);
mEditButton = view.findViewById(R.id.create_key_edit_button);
// get args
mName = getArguments().getString(ARG_NAME);
mEmail = getArguments().getString(ARG_EMAIL);
mAdditionalEmails = getArguments().getStringArrayList(ARG_ADDITIONAL_EMAILS);
mPassphrase = getArguments().getParcelable(ARG_PASSPHRASE);
// set values
mNameEdit.setText(mName);
if (mAdditionalEmails != null && mAdditionalEmails.size() > 0) {
String emailText = mEmail + ", ";
Iterator<?> it = mAdditionalEmails.iterator();
mNameEdit.setText(mCreateKeyActivity.mName);
if (mCreateKeyActivity.mAdditionalEmails != null && mCreateKeyActivity.mAdditionalEmails.size() > 0) {
String emailText = mCreateKeyActivity.mEmail + ", ";
Iterator<?> it = mCreateKeyActivity.mAdditionalEmails.iterator();
while (it.hasNext()) {
Object next = it.next();
emailText += next;
@@ -128,7 +105,7 @@ public class CreateKeyFinalFragment extends Fragment {
}
mEmailEdit.setText(emailText);
} else {
mEmailEdit.setText(mEmail);
mEmailEdit.setText(mCreateKeyActivity.mEmail);
}
mCreateButton.setOnClickListener(new View.OnClickListener() {
@@ -141,7 +118,7 @@ public class CreateKeyFinalFragment extends Fragment {
mBackButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
mCreateKeyActivity.loadFragment(null, null, FragAction.TO_LEFT);
mCreateKeyActivity.loadFragment(null, FragAction.TO_LEFT);
}
});
@@ -157,6 +134,12 @@ public class CreateKeyFinalFragment extends Fragment {
return view;
}
@Override
public void onAttach(Activity activity) {
super.onAttach(activity);
mCreateKeyActivity = (CreateKeyActivity) getActivity();
}
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
switch (requestCode) {
@@ -187,17 +170,22 @@ public class CreateKeyFinalFragment extends Fragment {
Algorithm.RSA, 4096, null, KeyFlags.SIGN_DATA, 0L));
mSaveKeyringParcel.mAddSubKeys.add(new SaveKeyringParcel.SubkeyAdd(
Algorithm.RSA, 4096, null, KeyFlags.ENCRYPT_COMMS | KeyFlags.ENCRYPT_STORAGE, 0L));
String userId = KeyRing.createUserId(new KeyRing.UserId(mName, mEmail, null));
String userId = KeyRing.createUserId(
new KeyRing.UserId(mCreateKeyActivity.mName, mCreateKeyActivity.mEmail, null)
);
mSaveKeyringParcel.mAddUserIds.add(userId);
mSaveKeyringParcel.mChangePrimaryUserId = userId;
if (mAdditionalEmails != null && mAdditionalEmails.size() > 0) {
for (String email : mAdditionalEmails) {
String thisUserId = KeyRing.createUserId(new KeyRing.UserId(mName, email, null));
if (mCreateKeyActivity.mAdditionalEmails != null
&& mCreateKeyActivity.mAdditionalEmails.size() > 0) {
for (String email : mCreateKeyActivity.mAdditionalEmails) {
String thisUserId = KeyRing.createUserId(
new KeyRing.UserId(mCreateKeyActivity.mName, email, null)
);
mSaveKeyringParcel.mAddUserIds.add(thisUserId);
}
}
mSaveKeyringParcel.mNewUnlock = mPassphrase != null
? new ChangeUnlockParcel(mPassphrase, null)
mSaveKeyringParcel.mNewUnlock = mCreateKeyActivity.mPassphrase != null
? new ChangeUnlockParcel(mCreateKeyActivity.mPassphrase, null)
: null;
}
}

View File

@@ -24,34 +24,26 @@ import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.inputmethod.InputMethodManager;
import android.widget.EditText;
import org.sufficientlysecure.keychain.R;
import org.sufficientlysecure.keychain.ui.CreateKeyActivity.FragAction;
import org.sufficientlysecure.keychain.ui.widget.EmailEditText;
import org.sufficientlysecure.keychain.ui.widget.NameEditText;
public class CreateKeyNameFragment extends Fragment {
public static final String ARG_NAME = "name";
public static final String ARG_EMAIL = "email";
CreateKeyActivity mCreateKeyActivity;
NameEditText mNameEdit;
View mBackButton;
View mNextButton;
String mEmail;
/**
* Creates new instance of this fragment
*/
public static CreateKeyNameFragment newInstance(String name, String email) {
public static CreateKeyNameFragment newInstance() {
CreateKeyNameFragment frag = new CreateKeyNameFragment();
Bundle args = new Bundle();
args.putString(ARG_NAME, name);
args.putString(ARG_EMAIL, email);
frag.setArguments(args);
@@ -84,21 +76,26 @@ public class CreateKeyNameFragment extends Fragment {
View view = inflater.inflate(R.layout.create_key_name_fragment, container, false);
mNameEdit = (NameEditText) view.findViewById(R.id.create_key_name);
mBackButton = view.findViewById(R.id.create_key_back_button);
mNextButton = view.findViewById(R.id.create_key_next_button);
// initial values
String name = getArguments().getString(ARG_NAME);
mEmail = getArguments().getString(ARG_EMAIL);
mNameEdit.setText(name);
mNameEdit.setText(mCreateKeyActivity.mName);
// focus empty edit fields
if (name == null) {
if (mCreateKeyActivity.mName == null) {
mNameEdit.requestFocus();
}
mBackButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
mCreateKeyActivity.loadFragment(null, FragAction.TO_LEFT);
}
});
mNextButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
createKeyCheck();
nextClicked();
}
});
@@ -111,16 +108,13 @@ public class CreateKeyNameFragment extends Fragment {
mCreateKeyActivity = (CreateKeyActivity) getActivity();
}
private void createKeyCheck() {
private void nextClicked() {
if (isEditTextNotEmpty(getActivity(), mNameEdit)) {
// save state
mCreateKeyActivity.mName = mNameEdit.getText().toString();
CreateKeyEmailFragment frag =
CreateKeyEmailFragment.newInstance(
mNameEdit.getText().toString(),
mEmail
);
mCreateKeyActivity.loadFragment(null, frag, FragAction.TO_RIGHT);
CreateKeyEmailFragment frag = CreateKeyEmailFragment.newInstance();
mCreateKeyActivity.loadFragment(frag, FragAction.TO_RIGHT);
}
}

View File

@@ -21,6 +21,7 @@ import android.app.Activity;
import android.content.Context;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.text.Editable;
import android.text.method.HideReturnsTransformationMethod;
import android.text.method.PasswordTransformationMethod;
import android.view.LayoutInflater;
@@ -37,18 +38,10 @@ import org.sufficientlysecure.keychain.ui.widget.PassphraseEditText;
import org.sufficientlysecure.keychain.util.Passphrase;
import java.util.ArrayList;
import java.util.Arrays;
public class CreateKeyPassphraseFragment extends Fragment {
public static final String ARG_NAME = "name";
public static final String ARG_EMAIL = "email";
public static final String ARG_ADDITIONAL_EMAILS = "emails";
// model
String mName;
String mEmail;
ArrayList<String> mAdditionalEmails;
// view
CreateKeyActivity mCreateKeyActivity;
PassphraseEditText mPassphraseEdit;
@@ -60,15 +53,10 @@ public class CreateKeyPassphraseFragment extends Fragment {
/**
* Creates new instance of this fragment
*/
public static CreateKeyPassphraseFragment newInstance(String name, String email,
ArrayList<String> additionalEmails) {
public static CreateKeyPassphraseFragment newInstance() {
CreateKeyPassphraseFragment frag = new CreateKeyPassphraseFragment();
Bundle args = new Bundle();
args.putString(ARG_NAME, name);
args.putString(ARG_EMAIL, email);
args.putStringArrayList(ARG_ADDITIONAL_EMAILS, additionalEmails);
frag.setArguments(args);
return frag;
@@ -121,9 +109,12 @@ public class CreateKeyPassphraseFragment extends Fragment {
mNextButton = view.findViewById(R.id.create_key_next_button);
// initial values
mName = getArguments().getString(ARG_NAME);
mEmail = getArguments().getString(ARG_EMAIL);
mAdditionalEmails = getArguments().getStringArrayList(ARG_ADDITIONAL_EMAILS);
// TODO: using String here is unsafe...
if (mCreateKeyActivity.mPassphrase != null) {
mPassphraseEdit.setText(Arrays.toString(mCreateKeyActivity.mPassphrase.getCharArray()));
mPassphraseEditAgain.setText(Arrays.toString(mCreateKeyActivity.mPassphrase.getCharArray()));
}
mPassphraseEdit.requestFocus();
mBackButton.setOnClickListener(new View.OnClickListener() {
@Override
@@ -134,7 +125,7 @@ public class CreateKeyPassphraseFragment extends Fragment {
mNextButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
createKeyCheck();
nextClicked();
}
});
mShowPassphrase.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
@@ -162,23 +153,19 @@ public class CreateKeyPassphraseFragment extends Fragment {
private void back() {
hideKeyboard();
mCreateKeyActivity.loadFragment(null, null, FragAction.TO_LEFT);
mCreateKeyActivity.loadFragment(null, FragAction.TO_LEFT);
}
private void createKeyCheck() {
private void nextClicked() {
if (isEditTextNotEmpty(getActivity(), mPassphraseEdit)
&& areEditTextsEqual(getActivity(), mPassphraseEdit, mPassphraseEditAgain)) {
CreateKeyFinalFragment frag =
CreateKeyFinalFragment.newInstance(
mName,
mEmail,
mAdditionalEmails,
new Passphrase(mPassphraseEdit.getText())
);
// save state
mCreateKeyActivity.mPassphrase = new Passphrase(mPassphraseEdit);
CreateKeyFinalFragment frag = CreateKeyFinalFragment.newInstance();
hideKeyboard();
mCreateKeyActivity.loadFragment(null, frag, FragAction.TO_RIGHT);
mCreateKeyActivity.loadFragment(frag, FragAction.TO_RIGHT);
}
}

View File

@@ -0,0 +1,157 @@
/*
* Copyright (C) 2014 Dominik Schürmann <dominik@dominikschuermann.de>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.sufficientlysecure.keychain.ui;
import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.os.Messenger;
import android.support.v4.app.Fragment;
import android.support.v7.widget.DefaultItemAnimator;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.view.KeyEvent;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageButton;
import android.widget.TextView;
import org.sufficientlysecure.keychain.Constants;
import org.sufficientlysecure.keychain.R;
import org.sufficientlysecure.keychain.ui.CreateKeyActivity.FragAction;
import org.sufficientlysecure.keychain.ui.dialog.AddEmailDialogFragment;
import org.sufficientlysecure.keychain.ui.dialog.SetPassphraseDialogFragment;
import org.sufficientlysecure.keychain.ui.widget.EmailEditText;
import org.sufficientlysecure.keychain.util.Log;
import org.sufficientlysecure.keychain.util.Preferences;
import java.util.ArrayList;
import java.util.List;
public class CreateKeyStartFragment extends Fragment {
CreateKeyActivity mCreateKeyActivity;
View mCreateKey;
View mImportKey;
View mYubiKey;
TextView mCancel;
public static final int REQUEST_CODE_CREATE_OR_IMPORT_KEY = 0x00007012;
/**
* Creates new instance of this fragment
*/
public static CreateKeyStartFragment newInstance() {
CreateKeyStartFragment frag = new CreateKeyStartFragment();
Bundle args = new Bundle();
frag.setArguments(args);
return frag;
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.create_key_start_fragment, container, false);
mCreateKey = view.findViewById(R.id.create_key_create_key_button);
mImportKey = view.findViewById(R.id.create_key_import_button);
// mYubiKey = view.findViewById(R.id.create_key_yubikey_button);
mCancel = (TextView) view.findViewById(R.id.create_key_cancel);
if (mCreateKeyActivity.mFirstTime) {
mCancel.setText(R.string.first_time_skip);
} else {
mCancel.setText(R.string.btn_do_not_save);
}
mCreateKey.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
CreateKeyNameFragment frag = CreateKeyNameFragment.newInstance();
mCreateKeyActivity.loadFragment(frag, FragAction.TO_RIGHT);
}
});
mImportKey.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent(mCreateKeyActivity, ImportKeysActivity.class);
intent.setAction(ImportKeysActivity.ACTION_IMPORT_KEY_FROM_FILE_AND_RETURN);
startActivityForResult(intent, REQUEST_CODE_CREATE_OR_IMPORT_KEY);
}
});
mCancel.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
finishSetup(null);
}
});
return view;
}
private void finishSetup(Intent srcData) {
if (mCreateKeyActivity.mFirstTime) {
Preferences prefs = Preferences.getPreferences(mCreateKeyActivity);
prefs.setFirstTime(false);
}
Intent intent = new Intent(mCreateKeyActivity, MainActivity.class);
// give intent through to display notify
if (srcData != null) {
intent.putExtras(srcData);
}
startActivity(intent);
mCreateKeyActivity.finish();
}
// workaround for https://code.google.com/p/android/issues/detail?id=61394
// @Override
// public boolean onKeyDown(int keyCode, KeyEvent event) {
// return keyCode == KeyEvent.KEYCODE_MENU || super.onKeyDown(keyCode, event);
// }
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == REQUEST_CODE_CREATE_OR_IMPORT_KEY) {
if (resultCode == Activity.RESULT_OK) {
finishSetup(data);
}
} else {
Log.e(Constants.TAG, "No valid request code!");
}
}
@Override
public void onAttach(Activity activity) {
super.onAttach(activity);
mCreateKeyActivity = (CreateKeyActivity) getActivity();
}
}

View File

@@ -1,110 +0,0 @@
/*
* Copyright (C) 2014 Dominik Schürmann <dominik@dominikschuermann.de>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.sufficientlysecure.keychain.ui;
import android.content.Intent;
import android.os.Bundle;
import android.view.KeyEvent;
import android.view.View;
import android.view.Window;
import org.sufficientlysecure.keychain.Constants;
import org.sufficientlysecure.keychain.R;
import org.sufficientlysecure.keychain.util.Log;
import org.sufficientlysecure.keychain.util.Preferences;
public class FirstTimeActivity extends BaseActivity {
View mCreateKey;
View mImportKey;
View mSkipSetup;
public static final int REQUEST_CODE_CREATE_OR_IMPORT_KEY = 0x00007012;
@Override
protected void onCreate(Bundle savedInstanceState) {
supportRequestWindowFeature(Window.FEATURE_NO_TITLE);
super.onCreate(savedInstanceState);
mCreateKey = findViewById(R.id.first_time_create_key);
mImportKey = findViewById(R.id.first_time_import_key);
mSkipSetup = findViewById(R.id.first_time_cancel);
mSkipSetup.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
finishSetup(null);
}
});
mImportKey.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent(FirstTimeActivity.this, ImportKeysActivity.class);
intent.setAction(ImportKeysActivity.ACTION_IMPORT_KEY_FROM_FILE_AND_RETURN);
startActivityForResult(intent, REQUEST_CODE_CREATE_OR_IMPORT_KEY);
}
});
mCreateKey.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent(FirstTimeActivity.this, CreateKeyActivity.class);
startActivityForResult(intent, REQUEST_CODE_CREATE_OR_IMPORT_KEY);
}
});
}
@Override
protected void initLayout() {
setContentView(R.layout.first_time_activity);
}
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == REQUEST_CODE_CREATE_OR_IMPORT_KEY) {
if (resultCode == RESULT_OK) {
finishSetup(data);
}
} else {
Log.e(Constants.TAG, "No valid request code!");
}
}
private void finishSetup(Intent srcData) {
Preferences prefs = Preferences.getPreferences(this);
prefs.setFirstTime(false);
Intent intent = new Intent(this, MainActivity.class);
// give intent through to display notify
if (srcData != null) {
intent.putExtras(srcData);
}
startActivity(intent);
finish();
}
// workaround for https://code.google.com/p/android/issues/detail?id=61394
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
return keyCode == KeyEvent.KEYCODE_MENU || super.onKeyDown(keyCode, event);
}
}

View File

@@ -489,7 +489,8 @@ public class KeyListFragment extends LoaderFragment
case R.id.menu_key_list_debug_first_time:
Preferences prefs = Preferences.getPreferences(getActivity());
prefs.setFirstTime(true);
Intent intent = new Intent(getActivity(), FirstTimeActivity.class);
Intent intent = new Intent(getActivity(), CreateKeyActivity.class);
intent.putExtra(CreateKeyActivity.EXTRA_FIRST_TIME, true);
startActivity(intent);
getActivity().finish();
return true;

View File

@@ -54,7 +54,9 @@ public class MainActivity extends MaterialNavigationDrawer implements FabContain
// if this is the first time show first time activity
Preferences prefs = Preferences.getPreferences(this);
if (prefs.isFirstTime()) {
startActivity(new Intent(this, FirstTimeActivity.class));
Intent intent = new Intent(this, CreateKeyActivity.class);
intent.putExtra(CreateKeyActivity.EXTRA_FIRST_TIME, true);
startActivity(intent);
finish();
return;
}

View File

@@ -58,9 +58,10 @@ public class EmailEditText extends AutoCompleteTextView {
}
private void init() {
this.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_EMAIL_ADDRESS);
this.addTextChangedListener(textWatcher);
removeFlag();
setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_EMAIL_ADDRESS);
reenableKeyboardSuggestions();
addTextChangedListener(textWatcher);
initAdapter();
}
@@ -104,7 +105,7 @@ public class EmailEditText extends AutoCompleteTextView {
* Hack to re-enable keyboard auto correction in AutoCompleteTextView.
* From http://stackoverflow.com/a/22512858
*/
private void removeFlag() {
private void reenableKeyboardSuggestions() {
int inputType = getInputType();
inputType &= ~EditorInfo.TYPE_TEXT_FLAG_AUTO_COMPLETE;
setRawInputType(inputType);

View File

@@ -50,7 +50,7 @@ public class NameEditText extends AutoCompleteTextView {
}
private void init() {
removeFlag();
reenableKeyboardSuggestions();
initAdapter();
}
@@ -62,10 +62,10 @@ public class NameEditText extends AutoCompleteTextView {
}
/**
* Hack to re-enable keyboard auto correction in AutoCompleteTextView.
* Hack to re-enable keyboard suggestions in AutoCompleteTextView.
* From http://stackoverflow.com/a/22512858
*/
private void removeFlag() {
private void reenableKeyboardSuggestions() {
int inputType = getInputType();
inputType &= ~EditorInfo.TYPE_TEXT_FLAG_AUTO_COMPLETE;
setRawInputType(inputType);