Skip to content

Commit 21ca1b0

Browse files
committed
Add avatars to Address Book entries
1 parent 98d91b3 commit 21ca1b0

File tree

11 files changed

+255
-42
lines changed

11 files changed

+255
-42
lines changed

app/src/main/java/io/scalaproject/vault/AddressBookFragment.java

Lines changed: 88 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -21,26 +21,30 @@
2121

2222
package io.scalaproject.vault;
2323

24+
import android.app.Activity;
2425
import android.app.AlertDialog;
2526
import android.content.Context;
2627
import android.content.DialogInterface;
28+
import android.content.Intent;
29+
import android.graphics.Bitmap;
2730
import android.os.Bundle;
2831
import androidx.annotation.Nullable;
2932

3033
import com.google.android.material.dialog.MaterialAlertDialogBuilder;
3134
import com.google.android.material.textfield.TextInputLayout;
3235
import androidx.fragment.app.Fragment;
33-
import androidx.recyclerview.widget.LinearLayoutManager;
3436
import androidx.recyclerview.widget.RecyclerView;
3537

3638

39+
import android.provider.MediaStore;
3740
import android.view.LayoutInflater;
3841
import android.view.Menu;
3942
import android.view.MenuInflater;
4043
import android.view.View;
4144
import android.view.ViewGroup;
4245
import android.view.WindowManager;
4346
import android.widget.Button;
47+
import android.widget.ImageView;
4448
import android.widget.LinearLayout;
4549

4650
import io.scalaproject.vault.data.Contact;
@@ -232,22 +236,36 @@ public void refreshContacts() {
232236
private EditDialog editDialog = null; // for preventing opening of multiple dialogs
233237

234238
private EditDialog createEditDialog(final Contact contact) {
235-
if (editDialog != null) return null; // we are already open
239+
if(contactEditTmp != null) {
240+
if(editDialog != null) {
241+
editDialog.closeDialog();
242+
editDialog = null;
243+
}
244+
245+
return new EditDialog(contact);
246+
}
247+
248+
if (editDialog != null)
249+
return null; // we are already open
250+
236251
editDialog = new EditDialog(contact);
252+
237253
return editDialog;
238254
}
239255

256+
private Contact contactEditTmp = null;
257+
240258
class EditDialog {
241-
Contact contactEdit = null;
242-
Contact contactEditBackup = null;
259+
Contact contactEdit;
260+
Contact contactEditBackup;
243261

244262
private boolean applyChanges() {
245263
final String contactName = etContactName.getEditText().getText().toString().trim();
246264
if (contactName.isEmpty()) {
247265
etContactName.setError(getString(R.string.contact_value_empty));
248266
return false;
249267
} else {
250-
contactEdit.setName(etContactName.getEditText().getText().toString().trim());
268+
contactEdit.setName(contactName);
251269
}
252270

253271
final String walletAddress = etWalletAddress.getEditText().getText().toString().trim();
@@ -258,12 +276,24 @@ private boolean applyChanges() {
258276
etWalletAddress.setError(getString(R.string.generate_check_address));
259277
return false;
260278
} else {
261-
contactEdit.setAddress(etWalletAddress.getEditText().getText().toString().trim());
279+
contactEdit.setAddress(walletAddress);
262280
}
263281

264282
return true;
265283
}
266284

285+
private boolean applyChangesTmp() {
286+
contactEditTmp = new Contact();
287+
288+
final String contactName = etContactName.getEditText().getText().toString().trim();
289+
contactEditTmp.setName(contactName);
290+
291+
final String walletAddress = etWalletAddress.getEditText().getText().toString().trim();
292+
contactEditTmp.setAddress(walletAddress);
293+
294+
return true;
295+
}
296+
267297
private boolean shutdown = false;
268298

269299
private void apply() {
@@ -306,6 +336,9 @@ private void showKeyboard() {
306336

307337
TextInputLayout etContactName;
308338
TextInputLayout etWalletAddress;
339+
ImageView ivAvatar;
340+
341+
public static final int GET_FROM_GALLERY = 1;
309342

310343
EditDialog(final Contact contact) {
311344
MaterialAlertDialogBuilder alertDialogBuilder = new MaterialAlertDialogBuilder(getActivity(), R.style.MaterialAlertDialogCustom);
@@ -315,15 +348,33 @@ private void showKeyboard() {
315348

316349
etContactName = promptsView.findViewById(R.id.etContactName);
317350
etWalletAddress = promptsView.findViewById(R.id.etWalletAddress);
351+
ivAvatar = promptsView.findViewById(R.id.ivAvatar);
352+
353+
Button btnSelectImage = promptsView.findViewById(R.id.btnSelectImage);
354+
btnSelectImage.setOnClickListener(new View.OnClickListener() {
355+
@Override
356+
public void onClick(View view) {
357+
applyChangesTmp();
358+
pickImage();
359+
}
360+
});
318361

319362
if (contact != null) {
320363
contactEdit = contact;
321364
contactEditBackup = new Contact(contact);
322365
etContactName.getEditText().setText(contact.getName());
323366
etWalletAddress.getEditText().setText(contact.getAddress());
367+
368+
Bitmap avatar = contact.getAvatar();
369+
if(avatar != null)
370+
ivAvatar.setImageBitmap(contact.getAvatar());
371+
else {
372+
ivAvatar.setImageBitmap(Helper.getBitmap(getContext(), R.drawable.ic_contact_avatar));
373+
}
324374
} else {
325375
contactEdit = new Contact();
326376
contactEditBackup = null;
377+
ivAvatar.setImageBitmap(Helper.getBitmap(getContext(), R.drawable.ic_contact_avatar));
327378
}
328379

329380
// set dialog message
@@ -340,6 +391,7 @@ public void onClick(DialogInterface dialog, int id) {
340391
});
341392

342393
editDialog = alertDialogBuilder.create();
394+
343395
// these need to be here, since we don't always close the dialog
344396
editDialog.setOnShowListener(new DialogInterface.OnShowListener() {
345397
@Override
@@ -360,5 +412,35 @@ public void onClick(View view) {
360412

361413
refreshContacts();
362414
}
415+
416+
public void pickImage() {
417+
Intent intent = new Intent(Intent.ACTION_PICK, MediaStore.Images.Media.INTERNAL_CONTENT_URI);
418+
intent.setType("image/*");
419+
intent.putExtra("crop", "true");
420+
intent.putExtra("scale", true);
421+
intent.putExtra("outputX", 256);
422+
intent.putExtra("outputY", 256);
423+
intent.putExtra("aspectX", 1);
424+
intent.putExtra("aspectY", 1);
425+
intent.putExtra("return-data", true);
426+
427+
startActivityForResult(intent, 1);
428+
}
429+
}
430+
431+
public void onActivityResult(int requestCode, int resultCode, Intent data) {
432+
if(requestCode== EditDialog.GET_FROM_GALLERY & resultCode== Activity.RESULT_OK) {
433+
Timber.d("AddressBook.onActivityResult");
434+
435+
// Already save the cropped image
436+
Bitmap bitmap = Helper.getCroppedBitmap((Bitmap) data.getExtras().get("data"));
437+
438+
contactEditTmp.setAvatar(bitmap);
439+
440+
EditDialog diag = createEditDialog(contactEditTmp);
441+
if (diag != null) {
442+
diag.show();
443+
}
444+
}
363445
}
364446
}

app/src/main/java/io/scalaproject/vault/WalletActivity.java

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -430,6 +430,10 @@ private void onAddressBook() {
430430
}
431431
}
432432

433+
public void onActivityResult(int requestCode, int resultCode, Intent data) {
434+
super.onActivityResult(requestCode, resultCode, data);
435+
}
436+
433437
private void onEnableStealthMode() {
434438
enableStealthMode(true);
435439
}

app/src/main/java/io/scalaproject/vault/data/Contact.java

Lines changed: 34 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -21,23 +21,20 @@
2121

2222
package io.scalaproject.vault.data;
2323

24-
import io.scalaproject.levin.scanner.Dispatcher;
25-
import io.scalaproject.vault.model.NetworkType;
26-
import io.scalaproject.vault.model.WalletManager;
27-
28-
import java.io.UnsupportedEncodingException;
29-
import java.net.InetAddress;
30-
import java.net.InetSocketAddress;
31-
import java.net.URLDecoder;
32-
import java.net.URLEncoder;
33-
import java.net.UnknownHostException;
24+
import android.graphics.Bitmap;
25+
import android.graphics.BitmapFactory;
26+
import android.util.Base64;
27+
28+
import java.io.ByteArrayOutputStream;
3429
import java.util.Comparator;
3530

31+
import io.scalaproject.vault.util.Helper;
3632
import timber.log.Timber;
3733

3834
public class Contact {
3935
private String name = "";
4036
private String address = "";
37+
private Bitmap avatar = null;
4138

4239
@Override
4340
public int hashCode() {
@@ -77,9 +74,16 @@ public Contact(String contactString) {
7774
String a[] = contactString.split(":");
7875
if (a.length == 2) {
7976
this.name = a[0];
80-
this.address = a[1];
77+
78+
String av[] = a[1].split("@");
79+
this.address = av[0];
80+
81+
if(av.length == 2) { // there is an avatar
82+
byte[] b = Base64.decode(av[1], Base64.DEFAULT);
83+
this.avatar = Helper.getCroppedBitmap(BitmapFactory.decodeByteArray(b, 0, b.length));
84+
}
8185
} else {
82-
throw new IllegalArgumentException("Too many @");
86+
throw new IllegalArgumentException("Too many :");
8387
}
8488
}
8589

@@ -94,28 +98,43 @@ public String toString() {
9498
sb.append(name).append(":").append(address);
9599
}
96100

101+
if(avatar != null) {
102+
ByteArrayOutputStream baos = new ByteArrayOutputStream();
103+
avatar.compress(Bitmap.CompressFormat.JPEG, 100, baos);
104+
105+
byte[] compressImage = baos.toByteArray();
106+
String sEncodedImage = Base64.encodeToString(compressImage, Base64.DEFAULT);
107+
sb.append("@").append(sEncodedImage);
108+
}
109+
97110
return sb.toString();
98111
}
99112

100113
public String getName() {
101114
return this.name;
102115
}
103-
104116
public void setName(String name) {
105117
this.name = name;
106118
}
107119

108120
public String getAddress() {
109121
return address;
110122
}
111-
112123
public void setAddress(String address) {
113124
this.address = address;
114125
}
115126

127+
public Bitmap getAvatar() {
128+
return this.avatar;
129+
}
130+
public void setAvatar(Bitmap avatar) {
131+
this.avatar = avatar;
132+
}
133+
116134
public Contact() {
117135
this.name = "";
118136
this.address = "";
137+
this.avatar = null;
119138
}
120139

121140
public Contact(Contact anotherContact) {
@@ -125,6 +144,7 @@ public Contact(Contact anotherContact) {
125144
public void overwriteWith(Contact anotherContact) {
126145
name = anotherContact.name;
127146
address = anotherContact.address;
147+
avatar = anotherContact.avatar;
128148
}
129149

130150
static public Comparator<Contact> ContactComparator = new Comparator<Contact>() {

app/src/main/java/io/scalaproject/vault/layout/ContactInfoAdapter.java

Lines changed: 11 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -24,28 +24,22 @@
2424
import android.content.Context;
2525
import androidx.annotation.NonNull;
2626
import androidx.recyclerview.widget.RecyclerView;
27+
28+
import android.graphics.Bitmap;
2729
import android.view.LayoutInflater;
2830
import android.view.View;
2931
import android.view.ViewGroup;
30-
import android.widget.ImageButton;
3132
import android.widget.ImageView;
32-
import android.widget.RelativeLayout;
3333
import android.widget.TextView;
3434

3535
import io.scalaproject.vault.R;
3636
import io.scalaproject.vault.data.Contact;
37-
import io.scalaproject.vault.data.NodeInfo;
3837
import io.scalaproject.vault.util.Helper;
3938

40-
import java.net.HttpURLConnection;
41-
import java.text.SimpleDateFormat;
4239
import java.util.ArrayList;
43-
import java.util.Calendar;
4440
import java.util.Collection;
4541
import java.util.Collections;
46-
import java.util.Date;
4742
import java.util.List;
48-
import java.util.TimeZone;
4943

5044
public class ContactInfoAdapter extends RecyclerView.Adapter<ContactInfoAdapter.ViewHolder> {
5145

@@ -127,6 +121,7 @@ class ViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener
127121
final TextView tvName;
128122
final TextView tvAddress;
129123
final ImageView ivDelete;
124+
final ImageView ivAvatar;
130125

131126
Contact contactItem;
132127

@@ -137,6 +132,8 @@ class ViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener
137132

138133
ivDelete = itemView.findViewById(R.id.ivDelete);
139134
ivDelete.setVisibility(readonly ? View.GONE : View.VISIBLE);
135+
136+
ivAvatar = itemView.findViewById(R.id.ivAvatar);
140137
}
141138

142139
void bind(final int position) {
@@ -154,6 +151,12 @@ public void onClick(View v) {
154151
}
155152
});
156153
}
154+
155+
Bitmap avatar = contactItem.getAvatar();
156+
if(avatar != null)
157+
ivAvatar.setImageBitmap(contactItem.getAvatar());
158+
else
159+
ivAvatar.setImageBitmap(Helper.getBitmap(context, R.drawable.ic_contact_avatar));
157160
}
158161

159162
@Override

0 commit comments

Comments
 (0)