diff --git a/briar-android/src/main/java/org/briarproject/briar/android/activity/ActivityComponent.java b/briar-android/src/main/java/org/briarproject/briar/android/activity/ActivityComponent.java
index 730880e1d..79bca962b 100644
--- a/briar-android/src/main/java/org/briarproject/briar/android/activity/ActivityComponent.java
+++ b/briar-android/src/main/java/org/briarproject/briar/android/activity/ActivityComponent.java
@@ -17,8 +17,10 @@ import org.briarproject.briar.android.blog.RssFeedManageActivity;
import org.briarproject.briar.android.blog.WriteBlogPostActivity;
import org.briarproject.briar.android.contact.ContactLinkInputActivity;
import org.briarproject.briar.android.contact.ContactLinkOutputActivity;
+import org.briarproject.briar.android.contact.ContactLinkOutputFragment;
import org.briarproject.briar.android.contact.ContactListFragment;
import org.briarproject.briar.android.contact.ContactModule;
+import org.briarproject.briar.android.contact.ContactQrCodeOutputFragment;
import org.briarproject.briar.android.contact.ConversationActivity;
import org.briarproject.briar.android.contact.PendingRequestsActivity;
import org.briarproject.briar.android.forum.CreateForumActivity;
@@ -173,6 +175,8 @@ public interface ActivityComponent {
void inject(ContactLinkOutputActivity activity);
void inject(ContactLinkInputActivity activity);
void inject(PendingRequestsActivity activity);
+ void inject(ContactLinkOutputFragment activity);
+ void inject(ContactQrCodeOutputFragment activity);
// Fragments
void inject(AuthorNameFragment fragment);
diff --git a/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactLinkOutputActivity.java b/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactLinkOutputActivity.java
index 05aa748d7..87b594e03 100644
--- a/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactLinkOutputActivity.java
+++ b/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactLinkOutputActivity.java
@@ -1,27 +1,23 @@
package org.briarproject.briar.android.contact;
-import android.content.ClipData;
-import android.content.ClipboardManager;
-import android.content.Intent;
import android.os.Bundle;
import android.support.v7.app.ActionBar;
+import android.view.Menu;
+import android.view.MenuInflater;
import android.view.MenuItem;
-import android.widget.Button;
-import android.widget.TextView;
-import android.widget.Toast;
import org.briarproject.briar.R;
import org.briarproject.briar.android.activity.ActivityComponent;
import org.briarproject.briar.android.activity.BriarActivity;
+import org.briarproject.briar.android.fragment.BaseFragment.BaseFragmentListener;
import javax.annotation.Nullable;
-import static android.content.Intent.ACTION_SEND;
-import static android.content.Intent.EXTRA_TEXT;
-import static android.widget.Toast.LENGTH_SHORT;
-import static org.briarproject.bramble.util.StringUtils.getRandomBase32String;
+public class ContactLinkOutputActivity extends BriarActivity implements
+ BaseFragmentListener {
-public class ContactLinkOutputActivity extends BriarActivity {
+ private Menu menu;
+ private boolean showQrCode = true;
@Override
public void injectActivity(ActivityComponent component) {
@@ -32,38 +28,25 @@ public class ContactLinkOutputActivity extends BriarActivity {
public void onCreate(@Nullable Bundle state) {
super.onCreate(state);
- setContentView(R.layout.activity_contact_link_output);
+ setContentView(R.layout.activity_fragment_container);
ActionBar ab = getSupportActionBar();
if (ab != null) {
ab.setDisplayHomeAsUpEnabled(true);
}
- String link = "briar://" + getRandomBase32String(64);
+ if (state == null) {
+ showInitialFragment(new ContactQrCodeOutputFragment());
+ }
+ }
- TextView linkView = findViewById(R.id.linkView);
- linkView.setText(link);
-
- ClipboardManager clipboard = (ClipboardManager)
- getSystemService(CLIPBOARD_SERVICE);
- if (clipboard == null) throw new AssertionError();
- ClipData clip = ClipData.newPlainText(
- getString(R.string.link_clip_label), link);
-
- Button copyButton = findViewById(R.id.copyButton);
- copyButton.setOnClickListener(v -> {
- clipboard.setPrimaryClip(clip);
- Toast.makeText(this, R.string.link_copied_toast, LENGTH_SHORT)
- .show();
- });
-
- Button shareButton = findViewById(R.id.shareButton);
- shareButton.setOnClickListener(v -> {
- Intent i = new Intent(ACTION_SEND);
- i.putExtra(EXTRA_TEXT, link);
- i.setType("text/plain");
- startActivity(i);
- });
+ @Override
+ public boolean onCreateOptionsMenu(Menu menu) {
+ MenuInflater inflater = getMenuInflater();
+ inflater.inflate(R.menu.contact_output_actions, menu);
+ menu.findItem(R.id.action_switch)
+ .setTitle(showQrCode ? R.string.show_link : R.string.show_code);
+ return super.onCreateOptionsMenu(menu);
}
@Override
@@ -72,9 +55,21 @@ public class ContactLinkOutputActivity extends BriarActivity {
case android.R.id.home:
onBackPressed();
return true;
+ case R.id.action_switch:
+ switchFragment();
+ return true;
default:
return super.onOptionsItemSelected(item);
}
}
+ private void switchFragment() {
+ if (showQrCode) {
+ showInitialFragment(new ContactLinkOutputFragment());
+ } else {
+ showInitialFragment(new ContactQrCodeOutputFragment());
+ }
+ showQrCode = !showQrCode;
+ }
+
}
diff --git a/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactLinkOutputFragment.java b/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactLinkOutputFragment.java
new file mode 100644
index 000000000..140f0f9c0
--- /dev/null
+++ b/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactLinkOutputFragment.java
@@ -0,0 +1,82 @@
+package org.briarproject.briar.android.contact;
+
+import android.content.ClipData;
+import android.content.ClipboardManager;
+import android.content.Intent;
+import android.os.Bundle;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.Button;
+import android.widget.TextView;
+import android.widget.Toast;
+
+import org.briarproject.bramble.api.nullsafety.NotNullByDefault;
+import org.briarproject.briar.R;
+import org.briarproject.briar.android.activity.ActivityComponent;
+import org.briarproject.briar.android.fragment.BaseFragment;
+
+import javax.annotation.Nullable;
+
+import static android.content.Context.CLIPBOARD_SERVICE;
+import static android.content.Intent.ACTION_SEND;
+import static android.content.Intent.EXTRA_TEXT;
+import static android.widget.Toast.LENGTH_SHORT;
+import static org.briarproject.bramble.util.StringUtils.getRandomBase32String;
+
+@NotNullByDefault
+public class ContactLinkOutputFragment extends BaseFragment {
+
+ @Nullable
+ @Override
+ public View onCreateView(LayoutInflater inflater,
+ @Nullable ViewGroup container,
+ @Nullable Bundle savedInstanceState) {
+
+ getActivity().setTitle(R.string.send_link_title);
+
+ View v = inflater.inflate(R.layout.fragment_contact_link_output,
+ container, false);
+
+ String link = "briar://" + getRandomBase32String(64);
+
+ TextView linkView = v.findViewById(R.id.linkView);
+ linkView.setText(link);
+
+ ClipboardManager clipboard = (ClipboardManager)
+ getContext().getSystemService(CLIPBOARD_SERVICE);
+ if (clipboard == null) throw new AssertionError();
+ ClipData clip = ClipData.newPlainText(
+ getString(R.string.link_clip_label), link);
+
+ Button copyButton = v.findViewById(R.id.copyButton);
+ copyButton.setOnClickListener(view -> {
+ clipboard.setPrimaryClip(clip);
+ Toast.makeText(getContext(), R.string.link_copied_toast,
+ LENGTH_SHORT).show();
+ });
+
+ Button shareButton = v.findViewById(R.id.shareButton);
+ shareButton.setOnClickListener(view -> {
+ Intent i = new Intent(ACTION_SEND);
+ i.putExtra(EXTRA_TEXT, link);
+ i.setType("text/plain");
+ startActivity(i);
+ });
+ return v;
+ }
+
+ public static final String TAG = ContactLinkOutputFragment.class.getName();
+
+ @Override
+ public String getUniqueTag() {
+ return TAG;
+ }
+
+ @Override
+ public void injectFragment(ActivityComponent component) {
+ component.inject(this);
+ }
+
+
+}
diff --git a/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactQrCodeOutputFragment.java b/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactQrCodeOutputFragment.java
new file mode 100644
index 000000000..54424740d
--- /dev/null
+++ b/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactQrCodeOutputFragment.java
@@ -0,0 +1,68 @@
+package org.briarproject.briar.android.contact;
+
+import android.graphics.Bitmap;
+import android.os.Bundle;
+import android.util.DisplayMetrics;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+
+import org.briarproject.bramble.api.nullsafety.NotNullByDefault;
+import org.briarproject.briar.R;
+import org.briarproject.briar.android.activity.ActivityComponent;
+import org.briarproject.briar.android.fragment.BaseFragment;
+import org.briarproject.briar.android.view.QrCodeView;
+
+import javax.annotation.Nullable;
+
+import static android.view.View.GONE;
+import static android.view.View.VISIBLE;
+import static org.briarproject.bramble.util.StringUtils.getRandomBase32String;
+import static org.briarproject.briar.android.keyagreement.QrCodeUtils.createQrCode;
+
+@NotNullByDefault
+public class ContactQrCodeOutputFragment extends BaseFragment
+ implements QrCodeView.FullscreenListener {
+
+ private View linkIntro;
+
+ @Nullable
+ @Override
+ public View onCreateView(LayoutInflater inflater,
+ @Nullable ViewGroup container,
+ @Nullable Bundle savedInstanceState) {
+
+ getActivity().setTitle(R.string.send_code_title);
+
+ View v = inflater.inflate(R.layout.fragment_contact_qr_code_output,
+ container, false);
+ linkIntro = v.findViewById(R.id.linkIntro);
+
+ String link = "briar://" + getRandomBase32String(64);
+ DisplayMetrics dm = getResources().getDisplayMetrics();
+ Bitmap qrCode = createQrCode(dm, link);
+ QrCodeView qrCodeView = v.findViewById(R.id.qrCodeView);
+ qrCodeView.setQrCode(qrCode);
+ qrCodeView.setFullscreenListener(this);
+
+ return v;
+ }
+
+ public static final String TAG = ContactQrCodeOutputFragment.class.getName();
+
+ @Override
+ public String getUniqueTag() {
+ return TAG;
+ }
+
+ @Override
+ public void injectFragment(ActivityComponent component) {
+ component.inject(this);
+ }
+
+ @Override
+ public void setFullscreen(boolean fullscreen) {
+ linkIntro.setVisibility(fullscreen ? GONE : VISIBLE);
+ }
+
+}
diff --git a/briar-android/src/main/java/org/briarproject/briar/android/keyagreement/QrCodeUtils.java b/briar-android/src/main/java/org/briarproject/briar/android/keyagreement/QrCodeUtils.java
index 617f84b99..658cffa1e 100644
--- a/briar-android/src/main/java/org/briarproject/briar/android/keyagreement/QrCodeUtils.java
+++ b/briar-android/src/main/java/org/briarproject/briar/android/keyagreement/QrCodeUtils.java
@@ -21,13 +21,13 @@ import static java.util.logging.Level.WARNING;
import static org.briarproject.bramble.util.LogUtils.logException;
@NotNullByDefault
-class QrCodeUtils {
+public class QrCodeUtils {
private static final Logger LOG =
Logger.getLogger(QrCodeUtils.class.getName());
@Nullable
- static Bitmap createQrCode(DisplayMetrics dm, String input) {
+ public static Bitmap createQrCode(DisplayMetrics dm, String input) {
int smallestDimen = Math.min(dm.widthPixels, dm.heightPixels);
try {
// Generate QR code
diff --git a/briar-android/src/main/res/drawable/ic_qr_code.xml b/briar-android/src/main/res/drawable/ic_qr_code.xml
new file mode 100644
index 000000000..513193b4a
--- /dev/null
+++ b/briar-android/src/main/res/drawable/ic_qr_code.xml
@@ -0,0 +1,9 @@
+