summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--res/values/strings.xml7
-rw-r--r--res/values/styles.xml2
-rw-r--r--src/com/android/contacts/common/interactions/ImportExportDialogFragment.java93
-rw-r--r--src/com/android/contacts/common/list/ContactTileAdapter.java3
-rw-r--r--src/com/android/contacts/common/util/AccountSelectionUtil.java23
-rw-r--r--src/com/android/contacts/common/vcard/ImportProcessor.java12
-rw-r--r--src/com/android/contacts/common/vcard/ImportVCardActivity.java10
-rw-r--r--src/com/android/contacts/common/vcard/NotificationImportExportListener.java8
8 files changed, 117 insertions, 41 deletions
diff --git a/res/values/strings.xml b/res/values/strings.xml
index c3df2457..77c38d7d 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -421,8 +421,11 @@ a ren't members of any other group. [CHAR LIMIT=25] -->
<!-- Action string for selecting SIM for importing contacts -->
<string name="import_from_sim">Import from SIM card</string>
- <!-- Action string for selecting SIM for importing contacts, when more than one SIM card -->
- <string name="import_from_sim_number">Import from SIM card #<xliff:g id="sim_number" example="2">%d</xliff:g></string>
+ <!-- Action string for selecting a SIM subscription for importing contacts -->
+ <string name="import_from_sim_summary">Import from SIM <xliff:g id="sim_name">%1$s</xliff:g> - <xliff:g id="sim_number">%2$s</xliff:g></string>
+
+ <!-- Action string for selecting a SIM subscription for importing contacts, without a phone number -->
+ <string name="import_from_sim_summary_no_number">Import from SIM <xliff:g id="sim_name">%1$s</xliff:g></string>
<!-- Action string for selecting (USB) storage for importing contacts [CHAR LIMIT=30] -->
<string name="import_from_sdcard" product="default">Import from storage</string>
diff --git a/res/values/styles.xml b/res/values/styles.xml
index 54d5f8c8..802b8b7a 100644
--- a/res/values/styles.xml
+++ b/res/values/styles.xml
@@ -78,7 +78,7 @@ background and text color. See also android:style/Widget.Holo.TextView.ListSepar
<item name="android:layout_height">match_parent</item>
</style>
- <style name="BackgroundOnlyTheme" parent="@android:style/Theme.Holo.Light">
+ <style name="BackgroundOnlyTheme" parent="@android:style/Theme.Material.Light">
<item name="android:windowBackground">@null</item>
<item name="android:windowContentOverlay">@null</item>
<item name="android:windowAnimationStyle">@null</item>
diff --git a/src/com/android/contacts/common/interactions/ImportExportDialogFragment.java b/src/com/android/contacts/common/interactions/ImportExportDialogFragment.java
index 8d87714b..99b8df58 100644
--- a/src/com/android/contacts/common/interactions/ImportExportDialogFragment.java
+++ b/src/com/android/contacts/common/interactions/ImportExportDialogFragment.java
@@ -28,7 +28,10 @@ import android.database.Cursor;
import android.net.Uri;
import android.os.Bundle;
import android.provider.ContactsContract.Contacts;
+import android.telephony.SubInfoRecord;
+import android.telephony.SubscriptionManager;
import android.telephony.TelephonyManager;
+import android.text.TextUtils;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
@@ -47,6 +50,7 @@ import com.android.contacts.common.vcard.ExportVCardActivity;
import com.android.contacts.common.vcard.VCardCommonArguments;
import com.android.dialerbind.analytics.AnalyticsDialogFragment;
+import java.util.Collections;
import java.util.List;
/**
@@ -57,6 +61,7 @@ public class ImportExportDialogFragment extends AnalyticsDialogFragment
public static final String TAG = "ImportExportDialogFragment";
private static final String KEY_RES_ID = "resourceId";
+ private static final String KEY_SUBSCRIPTION_ID = "subscriptionId";
private static final String ARG_CONTACTS_ARE_AVAILABLE = "CONTACTS_ARE_AVAILABLE";
private final String[] LOOKUP_PROJECTION = new String[] {
@@ -91,15 +96,14 @@ public class ImportExportDialogFragment extends AnalyticsDialogFragment
VCardCommonArguments.ARG_CALLING_ACTIVITY);
// Adapter that shows a list of string resources
- final ArrayAdapter<Integer> adapter = new ArrayAdapter<Integer>(getActivity(),
+ final ArrayAdapter<AdapterEntry> adapter = new ArrayAdapter<AdapterEntry>(getActivity(),
R.layout.select_dialog_item) {
@Override
public View getView(int position, View convertView, ViewGroup parent) {
final TextView result = (TextView)(convertView != null ? convertView :
dialogInflater.inflate(R.layout.select_dialog_item, parent, false));
- final int resId = getItem(position);
- result.setText(resId);
+ result.setText(getItem(position).mLabel);
return result;
}
};
@@ -107,21 +111,32 @@ public class ImportExportDialogFragment extends AnalyticsDialogFragment
final TelephonyManager manager =
(TelephonyManager) getActivity().getSystemService(Context.TELEPHONY_SERVICE);
- if (manager != null && manager.hasIccCard()
- && res.getBoolean(R.bool.config_allow_sim_import)) {
- adapter.add(R.string.import_from_sim);
- }
if (res.getBoolean(R.bool.config_allow_import_from_sdcard)) {
- adapter.add(R.string.import_from_sdcard);
+ adapter.add(new AdapterEntry(getString(R.string.import_from_sdcard),
+ R.string.import_from_sdcard));
+ }
+ if (manager != null && res.getBoolean(R.bool.config_allow_sim_import)) {
+ final List<SubInfoRecord> subInfoRecords = getAllSubInfoList();
+ if (subInfoRecords.size() == 1) {
+ adapter.add(new AdapterEntry(getString(R.string.import_from_sim),
+ R.string.import_from_sim, subInfoRecords.get(0).subId));
+ } else {
+ for (SubInfoRecord record : subInfoRecords) {
+ adapter.add(new AdapterEntry(getSubDescription(record),
+ R.string.import_from_sim, record.subId));
+ }
+ }
}
if (res.getBoolean(R.bool.config_allow_export_to_sdcard)) {
if (contactsAreAvailable) {
- adapter.add(R.string.export_to_sdcard);
+ adapter.add(new AdapterEntry(getString(R.string.export_to_sdcard),
+ R.string.export_to_sdcard));
}
}
if (res.getBoolean(R.bool.config_allow_share_visible_contacts)) {
if (contactsAreAvailable) {
- adapter.add(R.string.share_visible_contacts);
+ adapter.add(new AdapterEntry(getString(R.string.share_visible_contacts),
+ R.string.share_visible_contacts));
}
}
@@ -130,11 +145,12 @@ public class ImportExportDialogFragment extends AnalyticsDialogFragment
@Override
public void onClick(DialogInterface dialog, int which) {
boolean dismissDialog;
- final int resId = adapter.getItem(which);
+ final int resId = adapter.getItem(which).mChoiceResourceId;
switch (resId) {
case R.string.import_from_sim:
case R.string.import_from_sdcard: {
- dismissDialog = handleImportRequest(resId);
+ dismissDialog = handleImportRequest(resId,
+ adapter.getItem(which).mSubscriptionId);
break;
}
case R.string.export_to_sdcard: {
@@ -207,7 +223,7 @@ public class ImportExportDialogFragment extends AnalyticsDialogFragment
*
* @return {@code true} if the dialog show be closed. {@code false} otherwise.
*/
- private boolean handleImportRequest(int resId) {
+ private boolean handleImportRequest(int resId, long subscriptionId) {
// There are three possibilities:
// - more than one accounts -> ask the user
// - just one account -> use the account without asking the user
@@ -219,6 +235,7 @@ public class ImportExportDialogFragment extends AnalyticsDialogFragment
// Send over to the account selector
final Bundle args = new Bundle();
args.putInt(KEY_RES_ID, resId);
+ args.putLong(KEY_SUBSCRIPTION_ID, subscriptionId);
SelectAccountDialogFragment.show(
getFragmentManager(), this,
R.string.dialog_new_contact_account,
@@ -231,7 +248,7 @@ public class ImportExportDialogFragment extends AnalyticsDialogFragment
}
AccountSelectionUtil.doImport(getActivity(), resId,
- (size == 1 ? accountList.get(0) : null));
+ (size == 1 ? accountList.get(0) : null), subscriptionId);
return true; // Close the dialog.
}
@@ -240,7 +257,8 @@ public class ImportExportDialogFragment extends AnalyticsDialogFragment
*/
@Override
public void onAccountChosen(AccountWithDataSet account, Bundle extraArgs) {
- AccountSelectionUtil.doImport(getActivity(), extraArgs.getInt(KEY_RES_ID), account);
+ AccountSelectionUtil.doImport(getActivity(), extraArgs.getInt(KEY_RES_ID),
+ account, extraArgs.getLong(KEY_SUBSCRIPTION_ID));
// At this point the dialog is still showing (which is why we can use getActivity() above)
// So close it.
@@ -252,4 +270,49 @@ public class ImportExportDialogFragment extends AnalyticsDialogFragment
// See onAccountChosen() -- at this point the dialog is still showing. Close it.
dismiss();
}
+
+ /**
+ * Return the same values as {@link SubscriptionManager#getAllSubInfoList()} without relying
+ * on any hidden methods.
+ */
+ // TODO: replace with a method that doesn't make assumptions about the number of SIM slots
+ private static List<SubInfoRecord> getAllSubInfoList() {
+ final List<SubInfoRecord> subInfoRecords0 = SubscriptionManager.getSubInfoUsingSlotId(0);
+ final List<SubInfoRecord> subInfoRecords1 = SubscriptionManager.getSubInfoUsingSlotId(1);
+ if (subInfoRecords0 == null && subInfoRecords1 != null) {
+ return subInfoRecords1;
+ }
+ if (subInfoRecords0 != null && subInfoRecords1 == null) {
+ return subInfoRecords0;
+ }
+ if (subInfoRecords0 == null && subInfoRecords1 == null) {
+ return Collections.EMPTY_LIST;
+ }
+ subInfoRecords0.addAll(subInfoRecords1);
+ return subInfoRecords0;
+ }
+
+ private String getSubDescription(SubInfoRecord record) {
+ if (TextUtils.isEmpty(record.number)) {
+ // Don't include the phone number in the description, since we don't know the number.
+ return getString(R.string.import_from_sim_summary_no_number, record.displayName);
+ }
+ return getString(R.string.import_from_sim_summary, record.displayName, record.number);
+ }
+
+ private static class AdapterEntry {
+ public final String mLabel;
+ public final int mChoiceResourceId;
+ public final long mSubscriptionId;
+
+ public AdapterEntry(String label, int resId, long subscriptionId) {
+ mLabel = label;
+ mChoiceResourceId = resId;
+ mSubscriptionId = subscriptionId;
+ }
+
+ public AdapterEntry(String label, int resId) {
+ this(label, resId, SubscriptionManager.INVALID_SUB_ID);
+ }
+ }
}
diff --git a/src/com/android/contacts/common/list/ContactTileAdapter.java b/src/com/android/contacts/common/list/ContactTileAdapter.java
index 04f415dc..789ca026 100644
--- a/src/com/android/contacts/common/list/ContactTileAdapter.java
+++ b/src/com/android/contacts/common/list/ContactTileAdapter.java
@@ -562,7 +562,8 @@ public class ContactTileAdapter extends BaseAdapter {
// Just line up children horizontally.
for (int i = 0; i < count; i++) {
- final View child = getChildAt(i);
+ final int rtlAdjustedIndex = isLayoutRtl() ? count - i - 1 : i;
+ final View child = getChildAt(rtlAdjustedIndex);
// Note MeasuredWidth includes the padding.
final int childWidth = child.getMeasuredWidth();
diff --git a/src/com/android/contacts/common/util/AccountSelectionUtil.java b/src/com/android/contacts/common/util/AccountSelectionUtil.java
index ab327369..68217b94 100644
--- a/src/com/android/contacts/common/util/AccountSelectionUtil.java
+++ b/src/com/android/contacts/common/util/AccountSelectionUtil.java
@@ -22,6 +22,7 @@ import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.net.Uri;
+import android.telephony.SubscriptionManager;
import android.util.Log;
import android.view.ContextThemeWrapper;
import android.view.LayoutInflater;
@@ -54,22 +55,31 @@ public class AccountSelectionUtil {
final private Context mContext;
final private int mResId;
+ final private long mSubscriptionId;
final protected List<AccountWithDataSet> mAccountList;
public AccountSelectedListener(Context context, List<AccountWithDataSet> accountList,
- int resId) {
+ int resId, long subscriptionId) {
if (accountList == null || accountList.size() == 0) {
Log.e(LOG_TAG, "The size of Account list is 0.");
}
mContext = context;
mAccountList = accountList;
mResId = resId;
+ mSubscriptionId = subscriptionId;
+ }
+
+ public AccountSelectedListener(Context context, List<AccountWithDataSet> accountList,
+ int resId) {
+ // Subscription id is only needed for importing from SIM card. We can safely ignore
+ // its value for SD card importing.
+ this(context, accountList, resId, SubscriptionManager.INVALID_SUB_ID);
}
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
- doImport(mContext, mResId, mAccountList.get(which));
+ doImport(mContext, mResId, mAccountList.get(which), mSubscriptionId);
}
}
@@ -150,10 +160,11 @@ public class AccountSelectionUtil {
.create();
}
- public static void doImport(Context context, int resId, AccountWithDataSet account) {
+ public static void doImport(Context context, int resId, AccountWithDataSet account,
+ long subscriptionId) {
switch (resId) {
case R.string.import_from_sim: {
- doImportFromSim(context, account);
+ doImportFromSim(context, account, subscriptionId);
break;
}
case R.string.import_from_sdcard: {
@@ -163,7 +174,8 @@ public class AccountSelectionUtil {
}
}
- public static void doImportFromSim(Context context, AccountWithDataSet account) {
+ public static void doImportFromSim(Context context, AccountWithDataSet account,
+ long subscriptionId) {
Intent importIntent = new Intent(Intent.ACTION_VIEW);
importIntent.setType("vnd.android.cursor.item/sim-contact");
if (account != null) {
@@ -171,6 +183,7 @@ public class AccountSelectionUtil {
importIntent.putExtra("account_type", account.type);
importIntent.putExtra("data_set", account.dataSet);
}
+ importIntent.putExtra("subscription_id", subscriptionId);
importIntent.setClassName("com.android.phone", "com.android.phone.SimContacts");
context.startActivity(importIntent);
}
diff --git a/src/com/android/contacts/common/vcard/ImportProcessor.java b/src/com/android/contacts/common/vcard/ImportProcessor.java
index 37128755..219ec144 100644
--- a/src/com/android/contacts/common/vcard/ImportProcessor.java
+++ b/src/com/android/contacts/common/vcard/ImportProcessor.java
@@ -194,14 +194,14 @@ public class ImportProcessor extends ProcessorBase implements VCardEntryHandler
Log.i(LOG_TAG, "Successfully finished importing one vCard file: " + uri);
List<Uri> uris = committer.getCreatedUris();
if (mListener != null) {
- if (uris != null && uris.size() > 0) {
- // TODO: construct intent showing a list of imported contact list.
+ if (uris != null && uris.size() == 1) {
mListener.onImportFinished(mImportRequest, mJobId, uris.get(0));
} else {
- // Not critical, but suspicious.
- Log.w(LOG_TAG,
- "Created Uris is null or 0 length " +
- "though the creation itself is successful.");
+ if (uris == null || uris.size() == 0) {
+ // Not critical, but suspicious.
+ Log.w(LOG_TAG, "Created Uris is null or 0 length " +
+ "though the creation itself is successful.");
+ }
mListener.onImportFinished(mImportRequest, mJobId, null);
}
}
diff --git a/src/com/android/contacts/common/vcard/ImportVCardActivity.java b/src/com/android/contacts/common/vcard/ImportVCardActivity.java
index 70c98215..62e8431c 100644
--- a/src/com/android/contacts/common/vcard/ImportVCardActivity.java
+++ b/src/com/android/contacts/common/vcard/ImportVCardActivity.java
@@ -109,8 +109,6 @@ public class ImportVCardActivity extends Activity {
final static String CACHED_URIS = "cached_uris";
- private AccountSelectionUtil.AccountSelectedListener mAccountSelectionListener;
-
private AccountWithDataSet mAccount;
private ProgressDialog mProgressDialogForScanVCard;
@@ -891,14 +889,6 @@ public class ImportVCardActivity extends Activity {
@Override
protected Dialog onCreateDialog(int resId, Bundle bundle) {
switch (resId) {
- case R.string.import_from_sdcard: {
- if (mAccountSelectionListener == null) {
- throw new NullPointerException(
- "mAccountSelectionListener must not be null.");
- }
- return AccountSelectionUtil.getSelectAccountDialog(this, resId,
- mAccountSelectionListener, mCancelListener);
- }
case R.id.dialog_searching_vcard: {
if (mProgressDialogForScanVCard == null) {
String message = getString(R.string.searching_vcard_message);
diff --git a/src/com/android/contacts/common/vcard/NotificationImportExportListener.java b/src/com/android/contacts/common/vcard/NotificationImportExportListener.java
index 41f6a50f..a85825f1 100644
--- a/src/com/android/contacts/common/vcard/NotificationImportExportListener.java
+++ b/src/com/android/contacts/common/vcard/NotificationImportExportListener.java
@@ -26,6 +26,7 @@ import android.content.Intent;
import android.net.Uri;
import android.os.Handler;
import android.os.Message;
+import android.provider.ContactsContract;
import android.provider.ContactsContract.RawContacts;
import android.widget.Toast;
@@ -125,7 +126,8 @@ public class NotificationImportExportListener implements VCardImportExportListen
RawContacts.CONTENT_URI, rawContactId));
intent = new Intent(Intent.ACTION_VIEW, contactUri);
} else {
- intent = null;
+ intent = new Intent(Intent.ACTION_VIEW);
+ intent.setType(ContactsContract.Contacts.CONTENT_TYPE);
}
final Notification notification =
NotificationImportExportListener.constructFinishNotification(mContext,
@@ -220,6 +222,7 @@ public class NotificationImportExportListener implements VCardImportExportListen
.setProgress(totalCount, currentCount, totalCount == - 1)
.setTicker(tickerText)
.setContentTitle(description)
+ .setColor(context.getResources().getColor(R.color.dialtacts_theme_color))
.setSmallIcon(type == VCardService.TYPE_IMPORT
? android.R.drawable.stat_sys_download
: android.R.drawable.stat_sys_upload)
@@ -243,6 +246,7 @@ public class NotificationImportExportListener implements VCardImportExportListen
return new Notification.Builder(context)
.setAutoCancel(true)
.setSmallIcon(android.R.drawable.stat_notify_error)
+ .setColor(context.getResources().getColor(R.color.dialtacts_theme_color))
.setContentTitle(description)
.setContentText(description)
.setContentIntent(PendingIntent.getActivity(context, 0, new Intent(), 0))
@@ -260,6 +264,7 @@ public class NotificationImportExportListener implements VCardImportExportListen
Context context, String title, String description, Intent intent) {
return new Notification.Builder(context)
.setAutoCancel(true)
+ .setColor(context.getResources().getColor(R.color.dialtacts_theme_color))
.setSmallIcon(android.R.drawable.stat_sys_download_done)
.setContentTitle(title)
.setContentText(description)
@@ -278,6 +283,7 @@ public class NotificationImportExportListener implements VCardImportExportListen
Context context, String reason) {
return new Notification.Builder(context)
.setAutoCancel(true)
+ .setColor(context.getResources().getColor(R.color.dialtacts_theme_color))
.setSmallIcon(android.R.drawable.stat_notify_error)
.setContentTitle(context.getString(R.string.vcard_import_failed))
.setContentText(reason)