diff --git a/CHANGELOG.md b/CHANGELOG.md index 857219bd..67ec3478 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,12 @@ Changelog ========== +Version 3.1.3 *(2018-01-29)* +---------------------------- + + * Allow hiding contact thumbnails + * Fix displaying and adding contacts on some devices + Version 3.1.2 *(2018-01-23)* ---------------------------- diff --git a/app/build.gradle b/app/build.gradle index 9caf6647..0b3e3353 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -10,8 +10,8 @@ android { applicationId "com.simplemobiletools.contacts" minSdkVersion 16 targetSdkVersion 27 - versionCode 7 - versionName "3.1.2" + versionCode 8 + versionName "3.1.3" setProperty("archivesBaseName", "contacts") } @@ -42,7 +42,7 @@ ext { } dependencies { - implementation 'com.simplemobiletools:commons:3.8.2' + implementation 'com.simplemobiletools:commons:3.9.5' implementation 'joda-time:joda-time:2.9.9' debugImplementation "com.squareup.leakcanary:leakcanary-android:$leakCanaryVersion" diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 6175cbd1..eb13cd3a 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -75,7 +75,7 @@ android:parentActivityName=".activities.MainActivity"/> diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/activities/ContactActivity.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/activities/EditContactActivity.kt similarity index 98% rename from app/src/main/kotlin/com/simplemobiletools/contacts/activities/ContactActivity.kt rename to app/src/main/kotlin/com/simplemobiletools/contacts/activities/EditContactActivity.kt index 29173d97..86be6271 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/activities/ContactActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/activities/EditContactActivity.kt @@ -38,7 +38,7 @@ import com.simplemobiletools.contacts.models.Contact import com.simplemobiletools.contacts.models.Email import com.simplemobiletools.contacts.models.Event import com.simplemobiletools.contacts.models.PhoneNumber -import kotlinx.android.synthetic.main.activity_contact.* +import kotlinx.android.synthetic.main.activity_edit_contact.* import kotlinx.android.synthetic.main.item_email.view.* import kotlinx.android.synthetic.main.item_event.view.* import kotlinx.android.synthetic.main.item_phone_number.view.* @@ -48,7 +48,7 @@ import java.text.DateFormat import java.text.SimpleDateFormat import java.util.* -class ContactActivity : SimpleActivity() { +class EditContactActivity : SimpleActivity() { private val INTENT_TAKE_PHOTO = 1 private val INTENT_CHOOSE_PHOTO = 2 private val INTENT_CROP_PHOTO = 3 @@ -67,7 +67,7 @@ class ContactActivity : SimpleActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) - setContentView(R.layout.activity_contact) + setContentView(R.layout.activity_edit_contact) supportActionBar?.setHomeAsUpIndicator(R.drawable.ic_cross) handlePermission(PERMISSION_READ_CONTACTS) { @@ -120,8 +120,8 @@ class ContactActivity : SimpleActivity() { var contactId = intent.getIntExtra(CONTACT_ID, 0) val action = intent.action if (contactId == 0 && (action == ContactsContract.QuickContact.ACTION_QUICK_CONTACT || - action == Intent.ACTION_VIEW || - action == Intent.ACTION_EDIT)) { + action == Intent.ACTION_VIEW || + action == Intent.ACTION_EDIT)) { val data = intent.data if (data != null) { val rawId = if (data.path.contains("lookup")) { @@ -505,11 +505,6 @@ class ContactActivity : SimpleActivity() { return } - if (contact_source.value.isEmpty()) { - toast(R.string.missing_contact_account) - return - } - contact!!.apply { val oldPhotoUri = photoUri @@ -584,7 +579,7 @@ class ContactActivity : SimpleActivity() { private fun insertNewContact() { isSaving = true toast(R.string.inserting) - if (ContactsHelper(this@ContactActivity).insertContact(contact!!)) { + if (ContactsHelper(this@EditContactActivity).insertContact(contact!!)) { finish() } else { toast(R.string.unknown_error_occurred) @@ -593,7 +588,7 @@ class ContactActivity : SimpleActivity() { private fun updateContact(photoUpdateStatus: Int) { isSaving = true - if (ContactsHelper(this@ContactActivity).updateContact(contact!!, photoUpdateStatus)) { + if (ContactsHelper(this@EditContactActivity).updateContact(contact!!, photoUpdateStatus)) { finish() } else { toast(R.string.unknown_error_occurred) diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/activities/MainActivity.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/activities/MainActivity.kt index 1ee745cb..8bbd46cd 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/activities/MainActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/activities/MainActivity.kt @@ -77,14 +77,15 @@ class MainActivity : SimpleActivity(), RefreshContactsListener { return } - if (storedShowContactThumbnails != config.showContactThumbnails) { + if (storedShowPhoneNumbers != config.showPhoneNumbers) { restartActivity() return } - if (storedShowPhoneNumbers != config.showPhoneNumbers) { - restartActivity() - return + val configShowContactThumbnails = config.showContactThumbnails + if (storedShowContactThumbnails != configShowContactThumbnails) { + contacts_fragment.showContactThumbnailsChanged(configShowContactThumbnails) + favorites_fragment.showContactThumbnailsChanged(configShowContactThumbnails) } val configTextColor = config.textColor @@ -217,13 +218,11 @@ class MainActivity : SimpleActivity(), RefreshContactsListener { private fun initFragments() { viewpager.adapter = ViewPagerAdapter(this) - viewpager.setOnPageChangeListener(object : ViewPager.OnPageChangeListener { + viewpager.addOnPageChangeListener(object : ViewPager.OnPageChangeListener { override fun onPageScrollStateChanged(state: Int) { if (isSearchOpen) { getCurrentFragment().onSearchQueryChanged("") - if (searchMenuItem != null) { - MenuItemCompat.collapseActionView(searchMenuItem) - } + searchMenuItem?.collapseActionView() } } diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/adapters/ContactsAdapter.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/adapters/ContactsAdapter.kt index 2d4d265c..fc72ab44 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/adapters/ContactsAdapter.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/adapters/ContactsAdapter.kt @@ -27,16 +27,19 @@ import com.simplemobiletools.contacts.models.Contact import kotlinx.android.synthetic.main.item_contact_with_number.view.* import java.util.* -class ContactsAdapter(activity: SimpleActivity, var contactItems: MutableList, val listener: RefreshContactsListener?, - val isFavoritesFragment: Boolean, recyclerView: MyRecyclerView, fastScroller: FastScroller, itemClick: (Any) -> Unit) : +class ContactsAdapter(activity: SimpleActivity, var contactItems: MutableList, private val listener: RefreshContactsListener?, + private val isFavoritesFragment: Boolean, recyclerView: MyRecyclerView, fastScroller: FastScroller, itemClick: (Any) -> Unit) : MyRecyclerViewAdapter(activity, recyclerView, fastScroller, itemClick) { - lateinit private var contactDrawable: Drawable + private lateinit var contactDrawable: Drawable var config = activity.config var startNameWithSurname: Boolean var showContactThumbnails: Boolean var showPhoneNumbers: Boolean + private var smallPadding = activity.resources.getDimension(R.dimen.small_margin).toInt() + private var bigPadding = activity.resources.getDimension(R.dimen.normal_margin).toInt() + init { initDrawables() showContactThumbnails = config.showContactThumbnails @@ -190,8 +193,12 @@ class ContactsAdapter(activity: SimpleActivity, var contactItems: MutableList, val displayContactSources: Set) : +class FilterContactSourcesAdapter(val activity: SimpleActivity, private val contactSources: List, private val displayContactSources: Set) : RecyclerView.Adapter() { private val itemViews = SparseArray() private val selectedPositions = HashSet() @@ -66,7 +66,7 @@ class FilterContactSourcesAdapter(val activity: SimpleActivity, val contactSourc override fun getItemCount() = contactSources.size - class ViewHolder(view: View, val adapterListener: MyAdapterListener, val activity: SimpleActivity) : RecyclerView.ViewHolder(view) { + class ViewHolder(view: View, private val adapterListener: MyAdapterListener, val activity: SimpleActivity) : RecyclerView.ViewHolder(view) { fun bindView(contactSource: String): View { itemView.apply { filter_contact_source_checkbox.setColors(activity.config.textColor, activity.getAdjustedPrimaryColor(), activity.config.backgroundColor) diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/adapters/SelectContactsAdapter.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/adapters/SelectContactsAdapter.kt index f3ec600a..cc2d5058 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/adapters/SelectContactsAdapter.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/adapters/SelectContactsAdapter.kt @@ -13,6 +13,7 @@ import com.bumptech.glide.signature.ObjectKey import com.simplemobiletools.commons.extensions.beVisibleIf import com.simplemobiletools.commons.extensions.getAdjustedPrimaryColor import com.simplemobiletools.commons.extensions.getColoredDrawableWithColor +import com.simplemobiletools.commons.extensions.isActivityDestroyed import com.simplemobiletools.commons.interfaces.MyAdapterListener import com.simplemobiletools.contacts.R import com.simplemobiletools.contacts.activities.SimpleActivity @@ -22,16 +23,20 @@ import com.simplemobiletools.contacts.models.Contact import kotlinx.android.synthetic.main.item_add_favorite_with_number.view.* import java.util.* -class SelectContactsAdapter(val activity: SimpleActivity, val contacts: List, val selectedContacts: ArrayList, val allowPickMultiple: Boolean, - val itemClick: ((Contact) -> Unit)? = null) : RecyclerView.Adapter() { +class SelectContactsAdapter(val activity: SimpleActivity, val contacts: List, private val selectedContacts: ArrayList, private val allowPickMultiple: Boolean, + private val itemClick: ((Contact) -> Unit)? = null) : RecyclerView.Adapter() { private val itemViews = SparseArray() private val selectedPositions = HashSet() private val config = activity.config private val textColor = config.textColor private val contactDrawable = activity.resources.getColoredDrawableWithColor(R.drawable.ic_person, textColor) private val startNameWithSurname = config.startNameWithSurname + private val showContactThumbnails = config.showContactThumbnails private val itemLayout = if (config.showPhoneNumbers) R.layout.item_add_favorite_with_number else R.layout.item_add_favorite_without_number + private var smallPadding = activity.resources.getDimension(R.dimen.small_margin).toInt() + private var bigPadding = activity.resources.getDimension(R.dimen.normal_margin).toInt() + init { contacts.forEachIndexed { index, contact -> if (selectedContacts.contains(contact.id.toString())) { @@ -75,15 +80,16 @@ class SelectContactsAdapter(val activity: SimpleActivity, val contacts: List Unit)?) : RecyclerView.ViewHolder(view) { - fun bindView(contact: Contact, startNameWithSurname: Boolean, contactDrawable: Drawable, config: Config): View { + class ViewHolder(view: View, private val adapterListener: MyAdapterListener, val activity: SimpleActivity, private val showCheckbox: Boolean, + private val itemClick: ((Contact) -> Unit)?) : RecyclerView.ViewHolder(view) { + fun bindView(contact: Contact, startNameWithSurname: Boolean, contactDrawable: Drawable, config: Config, showContactThumbnails: Boolean, + smallPadding: Int, bigPadding: Int): View { itemView.apply { contact_checkbox.beVisibleIf(showCheckbox) contact_checkbox.setColors(config.textColor, context.getAdjustedPrimaryColor(), config.backgroundColor) @@ -91,8 +97,12 @@ class SelectContactsAdapter(val activity: SimpleActivity, val contacts: List Unit) { +class AddFavoritesDialog(val activity: SimpleActivity, private val callback: () -> Unit) { private var dialog: AlertDialog? = null private var view = activity.layoutInflater.inflate(R.layout.layout_select_contact, null) private val config = activity.config diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ChangeSortingDialog.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ChangeSortingDialog.kt index c791ca61..22a63539 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ChangeSortingDialog.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ChangeSortingDialog.kt @@ -11,7 +11,7 @@ import com.simplemobiletools.contacts.R import com.simplemobiletools.contacts.extensions.config import kotlinx.android.synthetic.main.dialog_change_sorting.view.* -class ChangeSortingDialog(val activity: BaseSimpleActivity, val callback: () -> Unit) { +class ChangeSortingDialog(val activity: BaseSimpleActivity, private val callback: () -> Unit) { private var currSorting = 0 private var config = activity.config private var view = activity.layoutInflater.inflate(R.layout.dialog_change_sorting, null) diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ExportContactsDialog.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ExportContactsDialog.kt index 1df75ded..494ddf1a 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ExportContactsDialog.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ExportContactsDialog.kt @@ -11,7 +11,7 @@ import com.simplemobiletools.contacts.helpers.ContactsHelper import kotlinx.android.synthetic.main.dialog_export_contacts.view.* import java.io.File -class ExportContactsDialog(val activity: SimpleActivity, val path: String, val callback: (file: File, contactSources: HashSet) -> Unit) { +class ExportContactsDialog(val activity: SimpleActivity, val path: String, private val callback: (file: File, contactSources: HashSet) -> Unit) { init { val view = (activity.layoutInflater.inflate(R.layout.dialog_export_contacts, null) as ViewGroup).apply { diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/FilterContactSourcesDialog.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/FilterContactSourcesDialog.kt index c3f2d5c5..6a516e01 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/FilterContactSourcesDialog.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/FilterContactSourcesDialog.kt @@ -9,7 +9,7 @@ import com.simplemobiletools.contacts.extensions.config import com.simplemobiletools.contacts.helpers.ContactsHelper import kotlinx.android.synthetic.main.dialog_filter_contact_sources.view.* -class FilterContactSourcesDialog(val activity: SimpleActivity, val callback: () -> Unit) { +class FilterContactSourcesDialog(val activity: SimpleActivity, private val callback: () -> Unit) { private var dialog: AlertDialog? = null private val view = activity.layoutInflater.inflate(R.layout.dialog_filter_contact_sources, null) diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ImportContactsDialog.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ImportContactsDialog.kt index fde2a6fa..a83c9f87 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ImportContactsDialog.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/dialogs/ImportContactsDialog.kt @@ -13,7 +13,7 @@ import com.simplemobiletools.contacts.helpers.VcfImporter import com.simplemobiletools.contacts.helpers.VcfImporter.ImportResult.IMPORT_FAIL import kotlinx.android.synthetic.main.dialog_import_contacts.view.* -class ImportContactsDialog(val activity: SimpleActivity, val path: String, val callback: (refreshView: Boolean) -> Unit) { +class ImportContactsDialog(val activity: SimpleActivity, val path: String, private val callback: (refreshView: Boolean) -> Unit) { init { val view = (activity.layoutInflater.inflate(R.layout.dialog_import_contacts, null) as ViewGroup).apply { import_contacts_title.text = activity.config.lastUsedContactSource diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/extensions/Context.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/extensions/Context.kt index c8e5c5bd..86d978a5 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/extensions/Context.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/extensions/Context.kt @@ -13,7 +13,7 @@ import com.simplemobiletools.commons.extensions.getIntValue import com.simplemobiletools.commons.extensions.isLollipopPlus import com.simplemobiletools.commons.extensions.toast import com.simplemobiletools.contacts.BuildConfig -import com.simplemobiletools.contacts.activities.ContactActivity +import com.simplemobiletools.contacts.activities.EditContactActivity import com.simplemobiletools.contacts.helpers.CONTACT_ID import com.simplemobiletools.contacts.helpers.Config import com.simplemobiletools.contacts.models.Contact @@ -22,7 +22,7 @@ import java.io.File val Context.config: Config get() = Config.newInstance(applicationContext) fun Context.openContact(contact: Contact) { - Intent(applicationContext, ContactActivity::class.java).apply { + Intent(applicationContext, EditContactActivity::class.java).apply { putExtra(CONTACT_ID, contact.id) startActivity(this) } @@ -69,6 +69,7 @@ fun Context.getContactUriRawId(uri: Uri): Int { if (cursor.moveToFirst()) { return cursor.getIntValue(ContactsContract.Contacts.NAME_RAW_CONTACT_ID) } + } catch (ignored: Exception) { } finally { cursor?.close() } diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/fragments/ContactsFragment.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/fragments/ContactsFragment.kt index 18df3607..b6afeed0 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/fragments/ContactsFragment.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/fragments/ContactsFragment.kt @@ -3,11 +3,11 @@ package com.simplemobiletools.contacts.fragments import android.content.Context import android.content.Intent import android.util.AttributeSet -import com.simplemobiletools.contacts.activities.ContactActivity +import com.simplemobiletools.contacts.activities.EditContactActivity class ContactsFragment(context: Context, attributeSet: AttributeSet) : MyViewPagerFragment(context, attributeSet) { override fun fabClicked() { - Intent(context, ContactActivity::class.java).apply { + Intent(context, EditContactActivity::class.java).apply { context.startActivity(this) } } diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/fragments/MyViewPagerFragment.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/fragments/MyViewPagerFragment.kt index 150cfd3e..5b66c30f 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/fragments/MyViewPagerFragment.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/fragments/MyViewPagerFragment.kt @@ -24,7 +24,7 @@ abstract class MyViewPagerFragment(context: Context, attributeSet: AttributeSet) protected var activity: MainActivity? = null private var lastHashCode = 0 private var contactsIgnoringSearch = ArrayList() - lateinit private var config: Config + private lateinit var config: Config var forceListRedraw = false @@ -144,11 +144,19 @@ abstract class MyViewPagerFragment(context: Context, attributeSet: AttributeSet) (currAdapter as ContactsAdapter).apply { startNameWithSurname = config.startNameWithSurname showPhoneNumbers = config.showPhoneNumbers + showContactThumbnails = config.showContactThumbnails updateItems(contacts) } } } + fun showContactThumbnailsChanged(showThumbnails: Boolean) { + (fragment_list.adapter as? ContactsAdapter)?.apply { + showContactThumbnails = showThumbnails + notifyDataSetChanged() + } + } + fun onActivityResume() { updateViewStuff() } @@ -179,7 +187,7 @@ abstract class MyViewPagerFragment(context: Context, attributeSet: AttributeSet) } fun onSearchOpened() { - contactsIgnoringSearch = (fragment_list.adapter as? ContactsAdapter)?.contactItems as ArrayList + contactsIgnoringSearch = (fragment_list?.adapter as? ContactsAdapter)?.contactItems as? ArrayList ?: ArrayList() } fun onSearchClosed() { diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/Constants.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/Constants.kt index 755bfa8e..9bbcb459 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/Constants.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/Constants.kt @@ -3,50 +3,50 @@ package com.simplemobiletools.contacts.helpers import android.provider.ContactsContract.CommonDataKinds // shared prefs -val CALL_CONTACT_ON_CLICK = "call_contact_on_click" -val SHOW_CONTACT_THUMBNAILS = "show_contact_thumbnails" -val SHOW_PHONE_NUMBERS = "show_phone_numbers" -val DISPLAY_CONTACT_SOURCES = "display_contact_sources" -val START_NAME_WITH_SURNAME = "start_name_with_surname" -val LAST_USED_CONTACT_SOURCE = "last_used_contact_source" -val LAST_USED_VIEW_PAGER_PAGE = "last_used_view_pager_page" +const val CALL_CONTACT_ON_CLICK = "call_contact_on_click" +const val SHOW_CONTACT_THUMBNAILS = "show_contact_thumbnails" +const val SHOW_PHONE_NUMBERS = "show_phone_numbers" +const val DISPLAY_CONTACT_SOURCES = "display_contact_sources" +const val START_NAME_WITH_SURNAME = "start_name_with_surname" +const val LAST_USED_CONTACT_SOURCE = "last_used_contact_source" +const val LAST_USED_VIEW_PAGER_PAGE = "last_used_view_pager_page" -val CONTACT_ID = "contact_id" +const val CONTACT_ID = "contact_id" // contact photo changes -val PHOTO_ADDED = 1 -val PHOTO_REMOVED = 2 -val PHOTO_CHANGED = 3 -val PHOTO_UNCHANGED = 4 +const val PHOTO_ADDED = 1 +const val PHOTO_REMOVED = 2 +const val PHOTO_CHANGED = 3 +const val PHOTO_UNCHANGED = 4 // default contact values -val DEFAULT_EMAIL_TYPE = CommonDataKinds.Email.TYPE_HOME -val DEFAULT_PHONE_NUMBER_TYPE = CommonDataKinds.Phone.TYPE_MOBILE -val DEFAULT_EVENT_TYPE = CommonDataKinds.Event.TYPE_BIRTHDAY +const val DEFAULT_EMAIL_TYPE = CommonDataKinds.Email.TYPE_HOME +const val DEFAULT_PHONE_NUMBER_TYPE = CommonDataKinds.Phone.TYPE_MOBILE +const val DEFAULT_EVENT_TYPE = CommonDataKinds.Event.TYPE_BIRTHDAY // export/import -val BEGIN_VCARD = "BEGIN:VCARD" -val END_VCARD = "END:VCARD" -val N = "N:" -val TEL = "TEL" -val BDAY = "BDAY:" -val ANNIVERSARY = "ANNIVERSARY:" -val PHOTO = "PHOTO" -val EMAIL = "EMAIL" -val ENCODING = "ENCODING" -val BASE64 = "BASE64" -val JPEG = "JPEG" -val VERSION_2_1 = "VERSION:2.1" +const val BEGIN_VCARD = "BEGIN:VCARD" +const val END_VCARD = "END:VCARD" +const val N = "N:" +const val TEL = "TEL" +const val BDAY = "BDAY:" +const val ANNIVERSARY = "ANNIVERSARY:" +const val PHOTO = "PHOTO" +const val EMAIL = "EMAIL" +const val ENCODING = "ENCODING" +const val BASE64 = "BASE64" +const val JPEG = "JPEG" +const val VERSION_2_1 = "VERSION:2.1" // phone number/email types -val CELL = "CELL" -val WORK = "WORK" -val HOME = "HOME" -val PREF = "PREF" -val MAIN = "MAIN" -val FAX = "FAX" -val WORK_FAX = "WORK;FAX" -val HOME_FAX = "HOME;FAX" -val PAGER = "PAGER" -val MOBILE = "MOBILE" -val VOICE = "VOICE" +const val CELL = "CELL" +const val WORK = "WORK" +const val HOME = "HOME" +const val PREF = "PREF" +const val MAIN = "MAIN" +const val FAX = "FAX" +const val WORK_FAX = "WORK;FAX" +const val HOME_FAX = "HOME;FAX" +const val PAGER = "PAGER" +const val MOBILE = "MOBILE" +const val VOICE = "VOICE" diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/ContactsHelper.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/ContactsHelper.kt index 6827551e..be32e742 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/ContactsHelper.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/ContactsHelper.kt @@ -253,6 +253,10 @@ class ContactsHelper(val activity: BaseSimpleActivity) { } private fun getContactSourceType(accountName: String): String { + if (accountName.isEmpty()) { + return "" + } + val uri = ContactsContract.RawContacts.CONTENT_URI val projection = arrayOf(ContactsContract.RawContacts.ACCOUNT_TYPE) val selection = "${ContactsContract.RawContacts.ACCOUNT_NAME} = ?" diff --git a/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/VcfExporter.kt b/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/VcfExporter.kt index b45bd0af..6bf5d141 100644 --- a/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/VcfExporter.kt +++ b/app/src/main/kotlin/com/simplemobiletools/contacts/helpers/VcfExporter.kt @@ -7,6 +7,7 @@ import android.provider.MediaStore import android.util.Base64 import com.simplemobiletools.commons.activities.BaseSimpleActivity import com.simplemobiletools.commons.extensions.getFileOutputStream +import com.simplemobiletools.commons.extensions.showErrorToast import com.simplemobiletools.commons.extensions.writeLn import com.simplemobiletools.contacts.helpers.VcfExporter.ExportResult.* import com.simplemobiletools.contacts.models.Contact @@ -24,59 +25,63 @@ class VcfExporter { private var contactsFailed = 0 fun exportContacts(activity: BaseSimpleActivity, file: File, contacts: ArrayList, callback: (result: ExportResult) -> Unit) { - activity.getFileOutputStream(file) { - if (it == null) { - callback(EXPORT_FAIL) - return@getFileOutputStream - } + try { + activity.getFileOutputStream(file) { + if (it == null) { + callback(EXPORT_FAIL) + return@getFileOutputStream + } - it.bufferedWriter().use { out -> - for (contact in contacts) { - out.writeLn(BEGIN_VCARD) - out.writeLn(VERSION_2_1) - out.writeLn("$N${contact.surname};${contact.firstName};${contact.middleName};;") + it.bufferedWriter().use { out -> + for (contact in contacts) { + out.writeLn(BEGIN_VCARD) + out.writeLn(VERSION_2_1) + out.writeLn("$N${contact.surname};${contact.firstName};${contact.middleName};;") - contact.phoneNumbers.forEach { - out.writeLn("$TEL;${getPhoneNumberLabel(it.type)}:${it.value}") - } - - contact.emails.forEach { - val type = getEmailTypeLabel(it.type) - val delimiterType = if (type.isEmpty()) "" else ";$type" - out.writeLn("$EMAIL$delimiterType:${it.value}") - } - - contact.events.forEach { - if (it.type == CommonDataKinds.Event.TYPE_BIRTHDAY) { - out.writeLn("$BDAY${it.value}") + contact.phoneNumbers.forEach { + out.writeLn("$TEL;${getPhoneNumberLabel(it.type)}:${it.value}") } + + contact.emails.forEach { + val type = getEmailTypeLabel(it.type) + val delimiterType = if (type.isEmpty()) "" else ";$type" + out.writeLn("$EMAIL$delimiterType:${it.value}") + } + + contact.events.forEach { + if (it.type == CommonDataKinds.Event.TYPE_BIRTHDAY) { + out.writeLn("$BDAY${it.value}") + } + } + + if (contact.thumbnailUri.isNotEmpty()) { + val firstLine = "$PHOTO;$ENCODING=$BASE64;$JPEG:" + val bitmap = MediaStore.Images.Media.getBitmap(activity.contentResolver, Uri.parse(contact.thumbnailUri)) + val byteArrayOutputStream = ByteArrayOutputStream() + bitmap.compress(Bitmap.CompressFormat.JPEG, 85, byteArrayOutputStream) + bitmap.recycle() + val byteArray = byteArrayOutputStream.toByteArray() + val encoded = Base64.encodeToString(byteArray, Base64.NO_WRAP) + + val encodedFirstLineSection = encoded.substring(0, ENCODED_PHOTO_LINE_LENGTH - firstLine.length) + out.writeLn(firstLine + encodedFirstLineSection) + var curStartIndex = encodedFirstLineSection.length + do { + val part = encoded.substring(curStartIndex, Math.min(curStartIndex + ENCODED_PHOTO_LINE_LENGTH - 1, encoded.length)) + out.writeLn(" $part") + curStartIndex += ENCODED_PHOTO_LINE_LENGTH - 1 + } while (curStartIndex < encoded.length) + + out.writeLn("") + } + + out.writeLn(END_VCARD) + contactsExported++ } - - if (contact.thumbnailUri.isNotEmpty()) { - val firstLine = "$PHOTO;$ENCODING=$BASE64;$JPEG:" - val bitmap = MediaStore.Images.Media.getBitmap(activity.contentResolver, Uri.parse(contact.thumbnailUri)) - val byteArrayOutputStream = ByteArrayOutputStream() - bitmap.compress(Bitmap.CompressFormat.JPEG, 85, byteArrayOutputStream) - bitmap.recycle() - val byteArray = byteArrayOutputStream.toByteArray() - val encoded = Base64.encodeToString(byteArray, Base64.NO_WRAP) - - val encodedFirstLineSection = encoded.substring(0, ENCODED_PHOTO_LINE_LENGTH - firstLine.length) - out.writeLn(firstLine + encodedFirstLineSection) - var curStartIndex = encodedFirstLineSection.length - do { - val part = encoded.substring(curStartIndex, Math.min(curStartIndex + ENCODED_PHOTO_LINE_LENGTH - 1, encoded.length)) - out.writeLn(" $part") - curStartIndex += ENCODED_PHOTO_LINE_LENGTH - 1 - } while (curStartIndex < encoded.length) - - out.writeLn("") - } - - out.writeLn(END_VCARD) - contactsExported++ } } + } catch (e: Exception) { + activity.showErrorToast(e) } callback(when { diff --git a/app/src/main/res/layout/activity_contact.xml b/app/src/main/res/layout/activity_edit_contact.xml similarity index 100% rename from app/src/main/res/layout/activity_contact.xml rename to app/src/main/res/layout/activity_edit_contact.xml diff --git a/app/src/main/res/layout/item_add_favorite_with_number.xml b/app/src/main/res/layout/item_add_favorite_with_number.xml index 7a8900d7..be9e0498 100644 --- a/app/src/main/res/layout/item_add_favorite_with_number.xml +++ b/app/src/main/res/layout/item_add_favorite_with_number.xml @@ -12,7 +12,7 @@ diff --git a/app/src/main/res/layout/item_add_favorite_without_number.xml b/app/src/main/res/layout/item_add_favorite_without_number.xml index cc142472..ef21a1f7 100644 --- a/app/src/main/res/layout/item_add_favorite_without_number.xml +++ b/app/src/main/res/layout/item_add_favorite_without_number.xml @@ -25,27 +25,20 @@ diff --git a/app/src/main/res/layout/item_contact_with_number.xml b/app/src/main/res/layout/item_contact_with_number.xml index 7e982ee7..7f29b5ca 100644 --- a/app/src/main/res/layout/item_contact_with_number.xml +++ b/app/src/main/res/layout/item_contact_with_number.xml @@ -13,7 +13,7 @@ @@ -40,10 +38,10 @@ android:id="@+id/contact_number" android:layout_width="match_parent" android:layout_height="wrap_content" + android:layout_alignLeft="@+id/contact_name" android:layout_below="@+id/contact_name" android:layout_toRightOf="@+id/contact_tmb" android:maxLines="1" - android:paddingLeft="@dimen/small_margin" android:textSize="@dimen/normal_text_size" tools:text="0123 456 789"/> diff --git a/app/src/main/res/layout/item_contact_without_number.xml b/app/src/main/res/layout/item_contact_without_number.xml index f7de65da..fc5eee9e 100644 --- a/app/src/main/res/layout/item_contact_without_number.xml +++ b/app/src/main/res/layout/item_contact_without_number.xml @@ -26,15 +26,11 @@ diff --git a/app/src/main/res/values-de/strings.xml b/app/src/main/res/values-de/strings.xml index 2869c5d4..db5df3c6 100644 --- a/app/src/main/res/values-de/strings.xml +++ b/app/src/main/res/values-de/strings.xml @@ -4,7 +4,7 @@ Adresse Einfügen… Aktualisiere… - Bitte wähle einen Account aus, zu dem der Kontakt gehört + Gerätespeicher Neuer Kontakt Kontakt bearbeiten @@ -23,7 +23,11 @@ Kontakt bei Klick anrufen Namen mit Nachnamen beginnen Zeige Telefonnummern im Hauptmenü - Show contact thumbnails + Zeige Vorschaubilder für Kontakte + Beim Klicken auf den Kontakt + Kontakt anrufen + Kontakt bearbeiten + Kontaktdetails ansehen Email diff --git a/app/src/main/res/values-ko-rKR/strings.xml b/app/src/main/res/values-ko-rKR/strings.xml index c59531a6..08c93d35 100644 --- a/app/src/main/res/values-ko-rKR/strings.xml +++ b/app/src/main/res/values-ko-rKR/strings.xml @@ -4,7 +4,7 @@ 주소 등록중… 수정중… - 연락처가 포함된 계정을 선택하세요. + Phone storage 새로운 연락처 연락처 수정 @@ -24,6 +24,10 @@ 성을 먼저 표시 메인 스크린에 전화번호 표시 Show contact thumbnails + On contact click + Call contact + Open contact editor + View contact details 이메일 diff --git a/app/src/main/res/values-pt/strings.xml b/app/src/main/res/values-pt/strings.xml index a79e127a..4831a362 100644 --- a/app/src/main/res/values-pt/strings.xml +++ b/app/src/main/res/values-pt/strings.xml @@ -4,7 +4,7 @@ Address Inserting… Updating… - Please select an account to which the contact belongs + Phone storage Novo contacto Editar contacto @@ -24,6 +24,10 @@ Start name with surname Show phone numbers on the main screen Show contact thumbnails + On contact click + Call contact + Open contact editor + View contact details E-mail diff --git a/app/src/main/res/values-ru/strings.xml b/app/src/main/res/values-ru/strings.xml index 78dab7be..02f1e14b 100644 --- a/app/src/main/res/values-ru/strings.xml +++ b/app/src/main/res/values-ru/strings.xml @@ -4,7 +4,7 @@ Адрес Добавление… Обновление… - Пожалуйста, выберите учётную запись, к которой относится контакт + Phone storage Новый контакт Редактировать контакт @@ -24,6 +24,10 @@ Показывать сначала фамилию Показывать номера телефонов на главном экране Показывать фото контакта + При нажатии на контакт + Позвонить контакту + Открыть редактор контактов + Просмотреть подробности о контакте Эл. почта diff --git a/app/src/main/res/values-sk/strings.xml b/app/src/main/res/values-sk/strings.xml index aa9203c8..a9fd79d1 100644 --- a/app/src/main/res/values-sk/strings.xml +++ b/app/src/main/res/values-sk/strings.xml @@ -4,7 +4,7 @@ Adresa Vytvára sa… Upravuje sa… - Prosím zvoľte účet, ktorému patrí daný kontakt + Úložisko mobilu Nový kontakt Upraviť kontakt @@ -24,6 +24,10 @@ Začať meno priezviskom Zobraziť telefónne čísla na hlavnej obrazovke Zobraziť obrázky kontaktov + Po kliknutí na kontakt + Zavolať kontakt + Otvoriť editor kontaktov + Zobraziť údaje kontaktu Email diff --git a/app/src/main/res/values-sv/strings.xml b/app/src/main/res/values-sv/strings.xml index 3a2dff9e..aadd2363 100644 --- a/app/src/main/res/values-sv/strings.xml +++ b/app/src/main/res/values-sv/strings.xml @@ -4,7 +4,7 @@ Adress Lägger till… Uppdaterar… - Du måste välja vilket konto kontakten ska tillhöra + Phone storage Ny kontakt Redigera kontakt @@ -24,6 +24,10 @@ Visa efternamn först Visa telefonnummer i huvudvyn Show contact thumbnails + On contact click + Call contact + Open contact editor + View contact details E-post diff --git a/app/src/main/res/values/dimens.xml b/app/src/main/res/values/dimens.xml index 2cb204b0..bb8f1a28 100644 --- a/app/src/main/res/values/dimens.xml +++ b/app/src/main/res/values/dimens.xml @@ -3,4 +3,5 @@ 80dp 45dp 40dp + 48dp diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 975e9b84..0a735653 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -4,7 +4,7 @@ Address Inserting… Updating… - Please select an account to which the contact belongs + Phone storage New contact Edit contact @@ -24,6 +24,10 @@ Start name with surname Show phone numbers on the main screen Show contact thumbnails + On contact click + Call contact + Open contact editor + View contact details Email diff --git a/build.gradle b/build.gradle index 97726280..a3b736f3 100644 --- a/build.gradle +++ b/build.gradle @@ -1,7 +1,7 @@ // Top-level build file where you can add configuration options common to all sub-projects/modules. buildscript { - ext.kotlin_version = '1.2.20' + ext.kotlin_version = '1.2.21' repositories { google()