Import translations. DO NOT MERGE am: 36c5d92e56 -s ours
am: d999061774 -s ours
Change-Id: I36de2007f6d3c593677cb629880df18b70e6070b
diff --git a/Android.mk b/Android.mk
index 57d521e..e629e54 100644
--- a/Android.mk
+++ b/Android.mk
@@ -46,7 +46,9 @@
android-support-v4 \
com.android.vcard \
guava \
- libphonenumber
+ libphonenumber \
+ legacy-android-test \
+ junit
LOCAL_PACKAGE_NAME := Contacts
LOCAL_CERTIFICATE := shared
diff --git a/AndroidManifest.xml b/AndroidManifest.xml
index 58209ae..93b9a70 100644
--- a/AndroidManifest.xml
+++ b/AndroidManifest.xml
@@ -16,8 +16,8 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.android.contacts"
- android:versionCode="10710"
- android:versionName="1.7.10">
+ android:versionCode="10721"
+ android:versionName="1.7.21">
<uses-sdk
android:minSdkVersion="21"
diff --git a/res/drawable-anydpi-v26/ic_add_contact_shortcut.xml b/res/drawable-anydpi-v26/ic_add_contact_shortcut.xml
new file mode 100644
index 0000000..fbd7a09
--- /dev/null
+++ b/res/drawable-anydpi-v26/ic_add_contact_shortcut.xml
@@ -0,0 +1,19 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2017 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<adaptive-icon xmlns:android="http://schemas.android.com/apk/res/android">
+ <background android:drawable="@color/ic_add_contact_shortcut_background"/>
+ <foreground android:drawable="@drawable/ic_add_circle_24dp"/>
+</adaptive-icon>
\ No newline at end of file
diff --git a/res/drawable/ic_add_circle_24dp.xml b/res/drawable/ic_add_circle_24dp.xml
index ae37470..ebaab34 100644
--- a/res/drawable/ic_add_circle_24dp.xml
+++ b/res/drawable/ic_add_circle_24dp.xml
@@ -20,7 +20,7 @@
android:width="24dp"
android:viewportHeight="192.0"
android:viewportWidth="192.0">
- <path android:fillColor="#F5F5F5"
+ <path android:fillColor="@color/ic_add_contact_shortcut_background"
android:pathData="M96,8C47.38,8 8,47.38 8,96s39.38,88 88,88s88,-39.38 88,-88S144.62,8 96,8z"/>
<path android:fillColor="#039BE5"
android:pathData="M124,100h-24v24h-8v-24H68v-8h24V68h8v24h24V100z"/>
diff --git a/res/drawable/ic_add_contact_shortcut.xml b/res/drawable/ic_add_contact_shortcut.xml
new file mode 100644
index 0000000..85a7e61
--- /dev/null
+++ b/res/drawable/ic_add_contact_shortcut.xml
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2016 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<!-- A copy of ic_add_circle_24dp for use in pre O devices. -->
+<vector xmlns:android="http://schemas.android.com/apk/res/android"
+ android:height="24dp"
+ android:width="24dp"
+ android:viewportHeight="192.0"
+ android:viewportWidth="192.0">
+ <path android:fillColor="@color/ic_add_contact_shortcut_background"
+ android:pathData="M96,8C47.38,8 8,47.38 8,96s39.38,88 88,88s88,-39.38 88,-88S144.62,8 96,8z"/>
+ <path android:fillColor="#039BE5"
+ android:pathData="M124,100h-24v24h-8v-24H68v-8h24V68h8v24h24V100z"/>
+</vector>
diff --git a/res/layout/expanding_entry_card_item.xml b/res/layout/expanding_entry_card_item.xml
index 99f9174..dbbeee5 100644
--- a/res/layout/expanding_entry_card_item.xml
+++ b/res/layout/expanding_entry_card_item.xml
@@ -88,8 +88,8 @@
<ImageView
android:id="@+id/third_icon"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
+ android:layout_width="@dimen/default_clickable_icon_size"
+ android:layout_height="@dimen/default_clickable_icon_size"
android:layout_alignParentTop="true"
android:layout_toStartOf="@+id/icon_alternate"
android:layout_alignWithParentIfMissing="true"
@@ -102,8 +102,8 @@
<ImageView
android:id="@+id/icon_alternate"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
+ android:layout_width="@dimen/default_clickable_icon_size"
+ android:layout_height="@dimen/default_clickable_icon_size"
android:layout_alignParentEnd="true"
android:layout_alignParentTop="true"
android:visibility="gone"
diff --git a/res/values-gl/strings.xml b/res/values-gl/strings.xml
index 6cd2b61..6abc4e7 100644
--- a/res/values-gl/strings.xml
+++ b/res/values-gl/strings.xml
@@ -163,7 +163,7 @@
<string name="contact_directory_description" msgid="683398073603909119">"Directorio <xliff:g id="TYPE">%1$s</xliff:g>"</string>
<string name="activity_title_settings" msgid="5464130076132770781">"Configuración"</string>
<string name="menu_settings" msgid="377929915873428211">"Configuración"</string>
- <string name="menu_help" msgid="1680178646764069976">"Axuda e suxestións"</string>
+ <string name="menu_help" msgid="1680178646764069976">"Axuda e comentarios"</string>
<string name="organization_company_and_title" msgid="6718207751363732025">"<xliff:g id="COMPANY_0">%2$s</xliff:g>, <xliff:g id="COMPANY_1">%1$s</xliff:g>"</string>
<string name="non_phone_caption" msgid="1541655052330027380">"Número de teléfono"</string>
<string name="non_phone_add_to_contacts" msgid="6590985286250471169">"Engadir a contactos"</string>
diff --git a/res/values-hy/strings.xml b/res/values-hy/strings.xml
index e69e479..b8fb7ea 100644
--- a/res/values-hy/strings.xml
+++ b/res/values-hy/strings.xml
@@ -53,10 +53,10 @@
<string name="joinConfirmation_positive_button" msgid="4573092849769149516">"Պահել և միակցել"</string>
<string name="contacts_linking_progress_bar" msgid="2846494347384549277">"Կցում"</string>
<string name="contacts_unlinking_progress_bar" msgid="5989310198163726929">"Ապակցում"</string>
- <string name="menu_joinAggregate" msgid="3599512127797513606">"Միակցել"</string>
+ <string name="menu_joinAggregate" msgid="3599512127797513606">"Միավորել"</string>
<string name="menu_linkedContacts" msgid="400444389718855621">"Դիտել միակցված կոնտակտները"</string>
<string name="menu_save" msgid="1727844363591825909">"Պահել"</string>
- <string name="titleJoinContactDataWith" msgid="6825255752748313944">"Միակցել կոնտակտները"</string>
+ <string name="titleJoinContactDataWith" msgid="6825255752748313944">"Միավորել կոնտակտները"</string>
<string name="blurbJoinContactDataWith" msgid="5864256698061641841">"Ընտրեք կոնտակտը, որը ցանկանում եք միակցել <xliff:g id="NAME">%s</xliff:g>-ի հետ՝"</string>
<string name="separatorJoinAggregateSuggestions" msgid="2831414448851313345">"Առաջարկվող կոնտակները"</string>
<string name="separatorJoinAggregateAll" msgid="7939932265026181043">"Բոլոր կոնտակտները"</string>
diff --git a/res/values-in/strings.xml b/res/values-in/strings.xml
index 105d113..3dd2de8 100644
--- a/res/values-in/strings.xml
+++ b/res/values-in/strings.xml
@@ -489,7 +489,7 @@
<string name="call_subject_type_and_number" msgid="7667188212129152558">"<xliff:g id="TYPE">%1$s</xliff:g> • <xliff:g id="NUMBER">%2$s</xliff:g>"</string>
<string name="about_build_version" msgid="1765533099416999801">"Versi build"</string>
<string name="about_open_source_licenses" msgid="6479990452352919641">"Lisensi sumber terbuka"</string>
- <string name="about_open_source_licenses_summary" msgid="57418386931763994">"Detail lisensi untuk perangkat lunak sumber terbuka"</string>
+ <string name="about_open_source_licenses_summary" msgid="57418386931763994">"Detail lisensi untuk software sumber terbuka"</string>
<string name="about_privacy_policy" msgid="3705518622499152626">"Kebijakan privasi"</string>
<string name="about_terms_of_service" msgid="4642400812150296723">"Persyaratan layanan"</string>
<string name="activity_title_licenses" msgid="5467767062737708066">"Lisensi sumber terbuka"</string>
diff --git a/res/values-v26/dimens.xml b/res/values-v26/dimens.xml
new file mode 100644
index 0000000..b5737f2
--- /dev/null
+++ b/res/values-v26/dimens.xml
@@ -0,0 +1,20 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2017 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<resources>
+ <!-- On Android O, shortcut icons will be 108dp unmasked.
+ See go/o-icons-eng for more details. -->
+ <dimen name="shortcut_icon_size">108dp</dimen>
+</resources>
\ No newline at end of file
diff --git a/res/values/colors.xml b/res/values/colors.xml
index 1aa84c6..e311ff3 100644
--- a/res/values/colors.xml
+++ b/res/values/colors.xml
@@ -16,6 +16,7 @@
<resources>
<!-- Adaptive icon background layer color -->
<color name="ic_contacts_launcher_background">#2458CA</color>
+ <color name="ic_add_contact_shortcut_background">#F5F5F5</color>
<!-- 87% black -->
<color name="quantum_black_text">#dd000000</color>
diff --git a/res/values/dimens.xml b/res/values/dimens.xml
index e9fe2ad..c14d396 100644
--- a/res/values/dimens.xml
+++ b/res/values/dimens.xml
@@ -14,6 +14,8 @@
limitations under the License.
-->
<resources>
+ <!-- Size of clickable icons that are GAR-4 -->
+ <dimen name="default_clickable_icon_size">48dp</dimen>
<!-- Copied from java/com/google/android/assets/launchscreens/res/values-port-v21/dimens.xml -->
<!-- Values adjusted for nav bar size due to windowDrawsSystemBarBackgrounds -->
<dimen name="launchscreens_product_logo_bottom">64dp</dimen>
diff --git a/res/xml/shortcuts.xml b/res/xml/shortcuts.xml
index c33893a..7ce90e6 100644
--- a/res/xml/shortcuts.xml
+++ b/res/xml/shortcuts.xml
@@ -17,7 +17,7 @@
<shortcuts xmlns:android="http://schemas.android.com/apk/res/android">
<shortcut
android:enabled="true"
- android:icon="@drawable/ic_add_circle_24dp"
+ android:icon="@drawable/ic_add_contact_shortcut"
android:shortcutId="shortcut-add-contact"
android:shortcutShortLabel="@string/shortcut_add_contact">
<intent
diff --git a/src/com/android/contacts/CallUtil.java b/src/com/android/contacts/CallUtil.java
index ddde01c..7172766 100644
--- a/src/com/android/contacts/CallUtil.java
+++ b/src/com/android/contacts/CallUtil.java
@@ -23,6 +23,7 @@
import android.telecom.PhoneAccountHandle;
import android.telecom.TelecomManager;
import android.telecom.VideoProfile;
+import android.telephony.PhoneNumberUtils;
import android.text.TextUtils;
import com.android.contacts.compat.CompatUtils;
@@ -80,7 +81,17 @@
* automatically.
*/
public static Intent getCallIntent(String number) {
- return getCallIntent(getCallUri(number));
+ Uri uri = getCallUri(number);
+ return PhoneNumberUtils.isEmergencyNumber(number)
+ ? getCallIntentForEmergencyNumber(uri) : getCallIntent(uri);
+ }
+
+ /**
+ * Return an Intent to directly start Dialer when calling an emergency number. Scheme is always
+ * PhoneAccount.SCHEME_TEL.
+ */
+ private static Intent getCallIntentForEmergencyNumber(Uri uri) {
+ return new Intent(Intent.ACTION_DIAL, uri);
}
/**
diff --git a/src/com/android/contacts/DynamicShortcuts.java b/src/com/android/contacts/DynamicShortcuts.java
index e287e4a..fc0d05a 100644
--- a/src/com/android/contacts/DynamicShortcuts.java
+++ b/src/com/android/contacts/DynamicShortcuts.java
@@ -16,6 +16,7 @@
package com.android.contacts;
import android.annotation.TargetApi;
+import android.app.ActivityManager;
import android.app.job.JobInfo;
import android.app.job.JobParameters;
import android.app.job.JobScheduler;
@@ -51,6 +52,7 @@
import com.android.contacts.activities.RequestPermissionsActivity;
import com.android.contacts.compat.CompatUtils;
+import com.android.contacts.lettertiles.LetterTileDrawable;
import com.android.contacts.util.BitmapUtil;
import com.android.contacts.util.ImplicitIntentsUtil;
import com.android.contacts.util.PermissionsUtil;
@@ -95,21 +97,18 @@
private static final int SHORTCUT_TYPE_CONTACT_URI = 1;
private static final int SHORTCUT_TYPE_ACTION_URI = 2;
- // The spec specifies that it should be 44dp @ xxxhdpi
- // Note that ShortcutManager.getIconMaxWidth and ShortcutManager.getMaxHeight return different
- // (larger) values.
- private static final int RECOMMENDED_ICON_PIXEL_LENGTH = 176;
-
@VisibleForTesting
static final String[] PROJECTION = new String[] {
Contacts._ID, Contacts.LOOKUP_KEY, Contacts.DISPLAY_NAME_PRIMARY
};
private final Context mContext;
+
private final ContentResolver mContentResolver;
private final ShortcutManager mShortcutManager;
private int mShortLabelMaxLength = SHORT_LABEL_MAX_LENGTH;
private int mLongLabelMaxLength = LONG_LABEL_MAX_LENGTH;
+ private int mIconSize;
private final int mContentChangeMinUpdateDelay;
private final int mContentChangeMaxUpdateDelay;
private final JobScheduler mJobScheduler;
@@ -131,6 +130,12 @@
.getInteger(Experiments.DYNAMIC_MIN_CONTENT_CHANGE_UPDATE_DELAY_MILLIS);
mContentChangeMaxUpdateDelay = Flags.getInstance()
.getInteger(Experiments.DYNAMIC_MAX_CONTENT_CHANGE_UPDATE_DELAY_MILLIS);
+ final ActivityManager am = (ActivityManager) context
+ .getSystemService(Context.ACTIVITY_SERVICE);
+ mIconSize = context.getResources().getDimensionPixelSize(R.dimen.shortcut_icon_size);
+ if (mIconSize == 0) {
+ mIconSize = am.getLauncherLargeIconSize();
+ }
}
@VisibleForTesting
@@ -373,10 +378,8 @@
final int iconMaxHeight = mShortcutManager.getIconMaxHeight();
final int sampleSize = Math.min(
- BitmapUtil.findOptimalSampleSize(sourceWidth,
- RECOMMENDED_ICON_PIXEL_LENGTH),
- BitmapUtil.findOptimalSampleSize(sourceHeight,
- RECOMMENDED_ICON_PIXEL_LENGTH));
+ BitmapUtil.findOptimalSampleSize(sourceWidth, mIconSize),
+ BitmapUtil.findOptimalSampleSize(sourceHeight, mIconSize));
final BitmapFactory.Options opts = new BitmapFactory.Options();
opts.inSampleSize = sampleSize;
@@ -404,46 +407,26 @@
return BitmapUtil.getRoundedBitmap(bitmap, targetSize, targetSize);
}
- // If on O or higher, add padding around the bitmap.
- final int paddingW = (int) (bitmap.getWidth() *
- AdaptiveIconDrawable.getExtraInsetFraction());
- final int paddingH = (int) (bitmap.getHeight() *
- AdaptiveIconDrawable.getExtraInsetFraction());
-
- final Bitmap scaledBitmap = Bitmap.createBitmap(bitmap.getWidth() + paddingW,
- bitmap.getHeight() + paddingH, bitmap.getConfig());
-
- final Canvas scaledCanvas = new Canvas(scaledBitmap);
- scaledCanvas.drawBitmap(bitmap, paddingW / 2, paddingH / 2, null);
-
- return scaledBitmap;
+ return bitmap;
}
private Bitmap getFallbackAvatar(String displayName, String lookupKey) {
- final int width;
- final int height;
- final int padding;
- if (BuildCompat.isAtLeastO()) {
- // Add padding on >= O
- padding = (int) (RECOMMENDED_ICON_PIXEL_LENGTH *
- AdaptiveIconDrawable.getExtraInsetFraction());
- width = RECOMMENDED_ICON_PIXEL_LENGTH + padding;
- height = RECOMMENDED_ICON_PIXEL_LENGTH + padding;
- } else {
- padding = 0;
- width = RECOMMENDED_ICON_PIXEL_LENGTH;
- height = RECOMMENDED_ICON_PIXEL_LENGTH;
- }
+ // Use a circular icon if we're not on O or higher.
+ final boolean circularIcon = !BuildCompat.isAtLeastO();
final ContactPhotoManager.DefaultImageRequest request =
- new ContactPhotoManager.DefaultImageRequest(displayName, lookupKey, true);
+ new ContactPhotoManager.DefaultImageRequest(displayName, lookupKey, circularIcon);
+ if (BuildCompat.isAtLeastO()) {
+ // On O, scale the image down to add the padding needed by AdaptiveIcons.
+ request.scale = LetterTileDrawable.getAdaptiveIconScale();
+ }
final Drawable avatar = ContactPhotoManager.getDefaultAvatarDrawableForContact(
mContext.getResources(), true, request);
- final Bitmap result = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
+ final Bitmap result = Bitmap.createBitmap(mIconSize, mIconSize, Bitmap.Config.ARGB_8888);
// The avatar won't draw unless it thinks it is visible
avatar.setVisible(true, true);
final Canvas canvas = new Canvas(result);
- avatar.setBounds(padding, padding, width - padding, height - padding);
+ avatar.setBounds(0, 0, mIconSize, mIconSize);
avatar.draw(canvas);
return result;
}
diff --git a/src/com/android/contacts/Experiments.java b/src/com/android/contacts/Experiments.java
index b53ced3..b66311d 100644
--- a/src/com/android/contacts/Experiments.java
+++ b/src/com/android/contacts/Experiments.java
@@ -39,6 +39,12 @@
"Shortcuts__dynamic_min_content_change_update_delay_millis";
/**
+ * Flags for enabling video call from quick contact.
+ */
+ public static final String QUICK_CONTACT_VIDEO_CALL =
+ "QuickContact__video_call_integration";
+
+ /**
* Flags for maximum time to show spinner for a contacts sync.
*/
public static final String PULL_TO_REFRESH_CANCEL_REFRESH_MILLIS =
diff --git a/src/com/android/contacts/ShortcutIntentBuilder.java b/src/com/android/contacts/ShortcutIntentBuilder.java
index 3a0b36b..e90e786 100644
--- a/src/com/android/contacts/ShortcutIntentBuilder.java
+++ b/src/com/android/contacts/ShortcutIntentBuilder.java
@@ -40,6 +40,7 @@
import android.provider.ContactsContract.CommonDataKinds.Photo;
import android.provider.ContactsContract.Contacts;
import android.provider.ContactsContract.Data;
+import android.support.v4.graphics.drawable.IconCompat;
import android.support.v4.graphics.drawable.RoundedBitmapDrawable;
import android.support.v4.graphics.drawable.RoundedBitmapDrawableFactory;
import android.support.v4.os.BuildCompat;
@@ -49,6 +50,7 @@
import android.text.TextUtils.TruncateAt;
import com.android.contacts.ContactPhotoManager.DefaultImageRequest;
+import com.android.contacts.lettertiles.LetterTileDrawable;
import com.android.contacts.util.BitmapUtil;
import com.android.contacts.util.ImplicitIntentsUtil;
@@ -260,8 +262,14 @@
Bitmap bitmap = BitmapFactory.decodeByteArray(bitmapData, 0, bitmapData.length, null);
return new BitmapDrawable(mContext.getResources(), bitmap);
} else {
+ final DefaultImageRequest request = new DefaultImageRequest(displayName, lookupKey,
+ false);
+ if (BuildCompat.isAtLeastO()) {
+ // On O, scale the image down to add the padding needed by AdaptiveIcons.
+ request.scale = LetterTileDrawable.getAdaptiveIconScale();
+ }
return ContactPhotoManager.getDefaultAvatarDrawableForContact(mContext.getResources(),
- false, new DefaultImageRequest(displayName, lookupKey, false));
+ false, request);
}
}
@@ -285,11 +293,15 @@
final Intent shortcutIntent = ImplicitIntentsUtil.getIntentForQuickContactLauncherShortcut(
mContext, contactUri);
- final Bitmap icon = generateQuickContactIcon(drawable);
-
-
intent = intent == null ? new Intent() : intent;
- intent.putExtra(Intent.EXTRA_SHORTCUT_ICON, icon);
+
+ final Bitmap icon = generateQuickContactIcon(drawable);
+ if (BuildCompat.isAtLeastO()) {
+ final IconCompat compatIcon = IconCompat.createWithAdaptiveBitmap(icon);
+ compatIcon.addToShortcutIntent(intent);
+ } else {
+ intent.putExtra(Intent.EXTRA_SHORTCUT_ICON, icon);
+ }
intent.putExtra(Intent.EXTRA_SHORTCUT_INTENT, shortcutIntent);
intent.putExtra(Intent.EXTRA_SHORTCUT_NAME, displayName);
@@ -325,18 +337,25 @@
shortcutIntent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
Intent intent = null;
+ IconCompat compatAdaptiveIcon = null;
if (BuildCompat.isAtLeastO()) {
+ compatAdaptiveIcon = IconCompat.createWithAdaptiveBitmap(icon);
final ShortcutManager sm = (ShortcutManager)
mContext.getSystemService(Context.SHORTCUT_SERVICE);
final String id = shortcutAction + lookupKey;
final DynamicShortcuts dynamicShortcuts = new DynamicShortcuts(mContext);
final ShortcutInfo shortcutInfo = dynamicShortcuts.getActionShortcutInfo(
- id, displayName, shortcutIntent, Icon.createWithAdaptiveBitmap(icon));
+ id, displayName, shortcutIntent, compatAdaptiveIcon.toIcon());
intent = sm.createShortcutResultIntent(shortcutInfo);
}
intent = intent == null ? new Intent() : intent;
- intent.putExtra(Intent.EXTRA_SHORTCUT_ICON, icon);
+ // This will be non-null in O and above.
+ if (compatAdaptiveIcon != null) {
+ compatAdaptiveIcon.addToShortcutIntent(intent);
+ } else {
+ intent.putExtra(Intent.EXTRA_SHORTCUT_ICON, icon);
+ }
intent.putExtra(Intent.EXTRA_SHORTCUT_INTENT, shortcutIntent);
intent.putExtra(Intent.EXTRA_SHORTCUT_NAME, shortcutName);
@@ -344,7 +363,6 @@
}
private Bitmap generateQuickContactIcon(Drawable photo) {
-
// Setup the drawing classes
Bitmap bitmap = Bitmap.createBitmap(mIconSize, mIconSize, Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(bitmap);
@@ -354,6 +372,11 @@
photo.setBounds(dst);
photo.draw(canvas);
+ // Don't put a rounded border on an icon for O
+ if (BuildCompat.isAtLeastO()) {
+ return bitmap;
+ }
+
// Draw the icon with a rounded border
RoundedBitmapDrawable roundedDrawable =
RoundedBitmapDrawableFactory.create(mResources, bitmap);
@@ -421,22 +444,24 @@
// Draw the phone action icon as an overlay
int iconWidth = icon.getWidth();
- dst.set(iconWidth - ((int) (20 * density)), -1,
- iconWidth, ((int) (19 * density)));
- canvas.drawBitmap(phoneIcon, null, dst, photoPaint);
-
- canvas.setBitmap(null);
- if (!BuildCompat.isAtLeastO()) {
- return icon;
+ if (BuildCompat.isAtLeastO()) {
+ // On O we need to calculate where the phone icon goes slightly differently. The whole
+ // canvas area is 108dp, a centered circle with a diameter of 66dp is the "safe zone".
+ // So we start the drawing the phone icon at
+ // 108dp - 21 dp (distance from right edge of safe zone to the edge of the canvas)
+ // - 24 dp (size of the phone icon) on the x axis (left)
+ // The y axis is simply 21dp for the distance to the safe zone (top).
+ // See go/o-icons-eng for more details and a handy picture.
+ final int left = (int) (mIconSize - (45 * density));
+ final int top = (int) (21 * density);
+ canvas.drawBitmap(phoneIcon, left, top, photoPaint);
+ } else {
+ dst.set(iconWidth - ((int) (20 * density)), -1,
+ iconWidth, ((int) (19 * density)));
+ canvas.drawBitmap(phoneIcon, null, dst, photoPaint);
}
- // On >= O scale image up by AdaptiveIconDrawable.DEFAULT_VIEW_PORT_SCALE.
- final int scale = (int) (icon.getHeight() *
- (1f / (1 + 2 * AdaptiveIconDrawable.getExtraInsetFraction())));
- final Bitmap scaledBitmap = Bitmap.createBitmap(icon.getWidth() + scale,
- icon.getHeight() + scale, icon.getConfig());
- Canvas scaledCanvas = new Canvas(scaledBitmap);
- scaledCanvas.drawBitmap(icon, scale / 2, scale / 2, null);
- return scaledBitmap;
+ canvas.setBitmap(null);
+ return icon;
}
}
diff --git a/src/com/android/contacts/datepicker/DatePickerDialog.java b/src/com/android/contacts/datepicker/DatePickerDialog.java
index 82eed24..de04af9 100644
--- a/src/com/android/contacts/datepicker/DatePickerDialog.java
+++ b/src/com/android/contacts/datepicker/DatePickerDialog.java
@@ -78,21 +78,6 @@
/**
* @param context The context the dialog is to run in.
* @param callBack How the parent is notified that the date is set.
- * @param year The initial year of the dialog
- * @param monthOfYear The initial month of the dialog.
- * @param dayOfMonth The initial day of the dialog.
- */
- public DatePickerDialog(Context context,
- OnDateSetListener callBack,
- int year,
- int monthOfYear,
- int dayOfMonth) {
- this(context, callBack, year, monthOfYear, dayOfMonth, false);
- }
-
- /**
- * @param context The context the dialog is to run in.
- * @param callBack How the parent is notified that the date is set.
* @param year The initial year of the dialog or {@link DatePickerDialog#NO_YEAR} if no year
* has been specified
* @param monthOfYear The initial month of the dialog.
@@ -106,7 +91,7 @@
int dayOfMonth,
boolean yearOptional) {
// Don't pass a theme id. Instead use the default alert dialog theme.
- this(context, /* themeId = */ -1, callBack, year, monthOfYear, dayOfMonth,
+ this(context, /* themeId = */ 0, callBack, year, monthOfYear, dayOfMonth,
yearOptional);
}
@@ -114,24 +99,6 @@
* @param context The context the dialog is to run in.
* @param theme the theme to apply to this dialog
* @param callBack How the parent is notified that the date is set.
- * @param year The initial year of the dialog or {@link DatePickerDialog#NO_YEAR} if no year
- * has been specified
- * @param monthOfYear The initial month of the dialog.
- * @param dayOfMonth The initial day of the dialog.
- */
- public DatePickerDialog(Context context,
- int theme,
- OnDateSetListener callBack,
- int year,
- int monthOfYear,
- int dayOfMonth) {
- this(context, theme, callBack, year, monthOfYear, dayOfMonth, false);
- }
-
- /**
- * @param context The context the dialog is to run in.
- * @param theme the theme to apply to this dialog
- * @param callBack How the parent is notified that the date is set.
* @param year The initial year of the dialog or {@link DatePickerDialog#NO_YEAR} if no
* year has been specified.
* @param monthOfYear The initial month of the dialog.
@@ -183,13 +150,6 @@
updateTitle(year, month, day);
}
- public void updateDate(int year, int monthOfYear, int dayOfMonth) {
- mInitialYear = year;
- mInitialMonth = monthOfYear;
- mInitialDay = dayOfMonth;
- mDatePicker.updateDate(year, monthOfYear, dayOfMonth);
- }
-
private void updateTitle(int year, int month, int day) {
final Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.YEAR, year);
diff --git a/src/com/android/contacts/lettertiles/LetterTileDrawable.java b/src/com/android/contacts/lettertiles/LetterTileDrawable.java
index 5652ac6..b80fd4f 100644
--- a/src/com/android/contacts/lettertiles/LetterTileDrawable.java
+++ b/src/com/android/contacts/lettertiles/LetterTileDrawable.java
@@ -26,6 +26,7 @@
import android.graphics.Paint.Align;
import android.graphics.Rect;
import android.graphics.Typeface;
+import android.graphics.drawable.AdaptiveIconDrawable;
import android.graphics.drawable.Drawable;
import android.text.TextUtils;
@@ -284,4 +285,11 @@
mIsCircle = isCircle;
return this;
}
+
+ /**
+ * Returns the scale percentage as a float for LetterTileDrawables used in AdaptiveIcons.
+ */
+ public static float getAdaptiveIconScale() {
+ return 1 / (1 + (2 * AdaptiveIconDrawable.getExtraInsetFraction()));
+ }
}
diff --git a/src/com/android/contacts/model/dataitem/PhoneDataItem.java b/src/com/android/contacts/model/dataitem/PhoneDataItem.java
index 8d6cf8e..6355157 100644
--- a/src/com/android/contacts/model/dataitem/PhoneDataItem.java
+++ b/src/com/android/contacts/model/dataitem/PhoneDataItem.java
@@ -31,6 +31,11 @@
public static final String KEY_FORMATTED_PHONE_NUMBER = "formattedPhoneNumber";
+ private boolean mTachyonReachable;
+ // Stores the custom reachable data item to provide extra data to the Entry created from this
+ // PhoneDataItem.
+ private DataItem mReachableDataItem;
+
/* package */ PhoneDataItem(ContentValues values) {
super(values);
}
@@ -54,6 +59,22 @@
return getContentValues().getAsString(Phone.LABEL);
}
+ public void setTachyonReachable(boolean tachyonReachable) {
+ mTachyonReachable = tachyonReachable;
+ }
+
+ public boolean isTachyonReachable() {
+ return mTachyonReachable;
+ }
+
+ public DataItem getReachableDataItem() {
+ return mReachableDataItem;
+ }
+
+ public void setReachableDataItem(DataItem reachableDataItem) {
+ mReachableDataItem = reachableDataItem;
+ }
+
public void computeFormattedPhoneNumber(String defaultCountryIso) {
final String phoneNumber = getNumber();
if (phoneNumber != null) {
diff --git a/src/com/android/contacts/quickcontact/ExpandingEntryCardView.java b/src/com/android/contacts/quickcontact/ExpandingEntryCardView.java
index 49da4c8..b0f7800 100644
--- a/src/com/android/contacts/quickcontact/ExpandingEntryCardView.java
+++ b/src/com/android/contacts/quickcontact/ExpandingEntryCardView.java
@@ -117,6 +117,7 @@
private final int mIconResourceId;
private final int mThirdAction;
private final Bundle mThirdExtras;
+ private final boolean mShouldApplyThirdIconColor;
public Entry(int id, Drawable mainIcon, String header, String subHeader,
Drawable subHeaderIcon, String text, Drawable textIcon,
@@ -125,7 +126,7 @@
Spannable alternateContentDescription, boolean shouldApplyColor, boolean isEditable,
EntryContextMenuInfo entryContextMenuInfo, Drawable thirdIcon, Intent thirdIntent,
String thirdContentDescription, int thirdAction, Bundle thirdExtras,
- int iconResourceId) {
+ boolean shouldApplyThirdIconColor, int iconResourceId) {
mId = id;
mIcon = mainIcon;
mHeader = header;
@@ -146,6 +147,7 @@
mThirdContentDescription = thirdContentDescription;
mThirdAction = thirdAction;
mThirdExtras = thirdExtras;
+ mShouldApplyThirdIconColor = shouldApplyThirdIconColor;
mIconResourceId = iconResourceId;
}
@@ -232,6 +234,10 @@
public Bundle getThirdExtras() {
return mThirdExtras;
}
+
+ boolean shouldApplyThirdIconColor() {
+ return mShouldApplyThirdIconColor;
+ }
}
public interface ExpandingEntryCardViewListener {
@@ -607,7 +613,7 @@
alternateIcon.setColorFilter(mThemeColorFilter);
}
Drawable thirdIcon = entry.getThirdIcon();
- if (thirdIcon != null) {
+ if (thirdIcon != null && entry.shouldApplyThirdIconColor()) {
thirdIcon.mutate();
thirdIcon.setColorFilter(mThemeColorFilter);
}
diff --git a/src/com/android/contacts/quickcontact/QuickContactActivity.java b/src/com/android/contacts/quickcontact/QuickContactActivity.java
index 014e1d5..3c088b4 100644
--- a/src/com/android/contacts/quickcontact/QuickContactActivity.java
+++ b/src/com/android/contacts/quickcontact/QuickContactActivity.java
@@ -105,8 +105,11 @@
import com.android.contacts.ContactsActivity;
import com.android.contacts.ContactsUtils;
import com.android.contacts.DynamicShortcuts;
+import com.android.contacts.Experiments;
import com.android.contacts.NfcHandler;
import com.android.contacts.R;
+import com.android.contacts.ShortcutIntentBuilder;
+import com.android.contacts.ShortcutIntentBuilder.OnShortcutIntentCreatedListener;
import com.android.contacts.activities.ContactEditorActivity;
import com.android.contacts.activities.ContactSelectionActivity;
import com.android.contacts.activities.RequestDesiredPermissionsActivity;
@@ -126,8 +129,6 @@
import com.android.contacts.interactions.SmsInteractionsLoader;
import com.android.contacts.interactions.TouchPointManager;
import com.android.contacts.lettertiles.LetterTileDrawable;
-import com.android.contacts.ShortcutIntentBuilder;
-import com.android.contacts.ShortcutIntentBuilder.OnShortcutIntentCreatedListener;
import com.android.contacts.list.UiIntentActions;
import com.android.contacts.logging.Logger;
import com.android.contacts.logging.QuickContactEvent.ActionType;
@@ -175,6 +176,7 @@
import com.android.contacts.widget.MultiShrinkScroller.MultiShrinkScrollerListener;
import com.android.contacts.widget.QuickContactImageView;
import com.android.contactsbind.HelpUtils;
+import com.android.contactsbind.experiments.Flags;
import com.google.common.collect.Lists;
@@ -246,6 +248,10 @@
@SuppressWarnings("deprecation")
private static final String LEGACY_AUTHORITY = android.provider.Contacts.AUTHORITY;
+ public static final String MIMETYPE_TACHYON =
+ "vnd.android.cursor.item/com.google.android.apps.tachyon.phone";
+ private static final String TACHYON_CALL_ACTION =
+ "com.google.android.apps.tachyon.action.CALL";
private static final String MIMETYPE_GPLUS_PROFILE =
"vnd.android.cursor.item/vnd.googleplus.profile";
private static final String GPLUS_PROFILE_DATA_5_VIEW_PROFILE = "view";
@@ -430,8 +436,6 @@
}
}
- intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
-
mHasIntentLaunched = true;
try {
final int actionType = intent.getIntExtra(EXTRA_ACTION_TYPE,
@@ -439,7 +443,15 @@
final String thirdPartyAction = intent.getStringExtra(EXTRA_THIRD_PARTY_ACTION);
Logger.logQuickContactEvent(mReferrer, mContactType,
CardType.UNKNOWN_CARD, actionType, thirdPartyAction);
- ImplicitIntentsUtil.startActivityInAppIfPossible(QuickContactActivity.this, intent);
+ // For the tachyon call action, we need to use startActivityForResult and not
+ // add FLAG_ACTIVITY_NEW_TASK to the intent.
+ if (TACHYON_CALL_ACTION.equals(intent.getAction())) {
+ QuickContactActivity.this.startActivityForResult(intent, /* requestCode */ 0);
+ } else {
+ intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+ ImplicitIntentsUtil.startActivityInAppIfPossible(QuickContactActivity.this,
+ intent);
+ }
} catch (SecurityException ex) {
Toast.makeText(QuickContactActivity.this, R.string.missing_app,
Toast.LENGTH_SHORT).show();
@@ -1328,6 +1340,7 @@
/* thirdContentDescription = */ null,
/* thirdAction = */ Entry.ACTION_NONE,
/* thirdExtras = */ null,
+ /* shouldApplyThirdIconColor = */ true,
/* iconResourceId = */ 0);
List<Entry> phoneticList = new ArrayList<>();
phoneticList.add(phoneticEntry);
@@ -1390,6 +1403,7 @@
/* thirdContentDescription = */ null,
/* thirdAction = */ Entry.ACTION_NONE,
/* thirdExtras = */ null,
+ /* shouldApplyThirdIconColor = */ true,
R.drawable.quantum_ic_phone_vd_theme_24);
final List<List<Entry>> promptEntries = new ArrayList<>();
@@ -1409,6 +1423,7 @@
/* EntryContextMenuInfo = */ null, /* thirdIcon = */ null,
/* thirdIntent = */ null, /* thirdContentDescription = */ null,
/* thirdAction = */ Entry.ACTION_NONE, /* thirdExtras = */ null,
+ /* shouldApplyThirdIconColor = */ true,
R.drawable.quantum_ic_email_vd_theme_24);
promptEntries.add(new ArrayList<Entry>(1));
@@ -1443,7 +1458,6 @@
final Map<String, List<DataItem>> dataItemsMap = new HashMap<>();
- final ResolveCache cache = ResolveCache.getInstance(this);
for (RawContact rawContact : data.getRawContacts()) {
for (DataItem dataItem : rawContact.getDataItems()) {
dataItem.setRawContactId(rawContact.getId());
@@ -1451,17 +1465,19 @@
final String mimeType = dataItem.getMimeType();
if (mimeType == null) continue;
- final AccountType accountType = rawContact.getAccountType(this);
- final DataKind dataKind = AccountTypeManager.getInstance(this)
- .getKindOrFallback(accountType, mimeType);
- if (dataKind == null) continue;
+ if (!MIMETYPE_TACHYON.equals(mimeType)) {
+ final AccountType accountType = rawContact.getAccountType(this);
+ final DataKind dataKind = AccountTypeManager.getInstance(this)
+ .getKindOrFallback(accountType, mimeType);
+ if (dataKind == null) continue;
- dataItem.setDataKind(dataKind);
+ dataItem.setDataKind(dataKind);
- final boolean hasData = !TextUtils.isEmpty(dataItem.buildDataString(this,
- dataKind));
+ final boolean hasData = !TextUtils.isEmpty(dataItem.buildDataString(this,
+ dataKind));
- if (isMimeExcluded(mimeType) || !hasData) continue;
+ if (isMimeExcluded(mimeType) || !hasData) continue;
+ }
List<DataItem> dataItemListByType = dataItemsMap.get(mimeType);
if (dataItemListByType == null) {
@@ -1472,6 +1488,7 @@
}
}
Trace.endSection();
+ bindReachability(dataItemsMap);
Trace.beginSection("sort within mimetypes");
/*
@@ -1529,6 +1546,28 @@
}
/**
+ * Bind the custom data items to each {@link PhoneDataItem} that is Tachyon reachable, the data
+ * will be needed when creating the {@link Entry} for the {@link PhoneDataItem}.
+ */
+ private void bindReachability(Map<String, List<DataItem>> dataItemsMap) {
+ final List<DataItem> phoneItems = dataItemsMap.get(Phone.CONTENT_ITEM_TYPE);
+ final List<DataItem> tachyonItems = dataItemsMap.get(MIMETYPE_TACHYON);
+ if (phoneItems != null && tachyonItems != null) {
+ for (DataItem phone : phoneItems) {
+ if (phone instanceof PhoneDataItem && ((PhoneDataItem) phone).getNumber() != null) {
+ for (DataItem tachyonItem : tachyonItems) {
+ if (((PhoneDataItem) phone).getNumber().equals(
+ tachyonItem.getContentValues().getAsString(Data.DATA1))) {
+ ((PhoneDataItem) phone).setTachyonReachable(true);
+ ((PhoneDataItem) phone).setReachableDataItem(tachyonItem);
+ }
+ }
+ }
+ }
+ }
+ }
+
+ /**
* Class used to hold the About card and Contact cards' data model that gets generated
* on a background thread. All data is from CP2.
*/
@@ -1574,6 +1613,7 @@
Spannable smsContentDescription = null;
Intent intent = null;
boolean shouldApplyColor = true;
+ boolean shouldApplyThirdIconColor = true;
Drawable alternateIcon = null;
Intent alternateIntent = null;
StringBuilder alternateContentDescription = new StringBuilder();
@@ -1746,6 +1786,9 @@
boolean isPresenceEnabled =
(videoCapability & CallUtil.VIDEO_CALLING_PRESENCE) != 0;
boolean isVideoEnabled = (videoCapability & CallUtil.VIDEO_CALLING_ENABLED) != 0;
+ // Check to ensure carrier presence indicates the number supports video calling.
+ int carrierPresence = dataItem.getCarrierPresence();
+ boolean isPresent = (carrierPresence & Phone.CARRIER_PRESENCE_VT_CAPABLE) != 0;
if (CallUtil.isCallWithSubjectSupported(context)) {
thirdIcon = res.getDrawable(R.drawable.quantum_ic_perm_phone_msg_vd_theme_24);
@@ -1769,20 +1812,23 @@
phone.getFormattedPhoneNumber());
thirdExtras.putString(CallSubjectDialog.ARG_NUMBER_LABEL,
phoneLabel);
- } else if (isVideoEnabled) {
- // Check to ensure carrier presence indicates the number supports video calling.
- int carrierPresence = dataItem.getCarrierPresence();
- boolean isPresent = (carrierPresence & Phone.CARRIER_PRESENCE_VT_CAPABLE) != 0;
-
- if ((isPresenceEnabled && isPresent) || !isPresenceEnabled) {
- thirdIcon = res.getDrawable(R.drawable.quantum_ic_videocam_vd_theme_24);
- thirdAction = Entry.ACTION_INTENT;
- thirdIntent = CallUtil.getVideoCallIntent(phone.getNumber(),
- CALL_ORIGIN_QUICK_CONTACTS_ACTIVITY);
- thirdIntent.putExtra(EXTRA_ACTION_TYPE, ActionType.VIDEOCALL);
- thirdContentDescription =
- res.getString(R.string.description_video_call);
- }
+ } else if (isVideoEnabled && (!isPresenceEnabled || isPresent)) {
+ thirdIcon = res.getDrawable(R.drawable.quantum_ic_videocam_vd_theme_24);
+ thirdAction = Entry.ACTION_INTENT;
+ thirdIntent = CallUtil.getVideoCallIntent(phone.getNumber(),
+ CALL_ORIGIN_QUICK_CONTACTS_ACTIVITY);
+ thirdIntent.putExtra(EXTRA_ACTION_TYPE, ActionType.VIDEOCALL);
+ thirdContentDescription =
+ res.getString(R.string.description_video_call);
+ } else if (Flags.getInstance().getBoolean(Experiments.QUICK_CONTACT_VIDEO_CALL)
+ && ((PhoneDataItem) dataItem).isTachyonReachable()) {
+ thirdIcon = res.getDrawable(R.drawable.quantum_ic_videocam_vd_theme_24);
+ thirdAction = Entry.ACTION_INTENT;
+ thirdIntent = new Intent(TACHYON_CALL_ACTION);
+ thirdIntent.setData(
+ Uri.fromParts(PhoneAccount.SCHEME_TEL, phone.getNumber(), null));
+ thirdContentDescription = ((PhoneDataItem) dataItem).getReachableDataItem()
+ .getContentValues().getAsString(Data.DATA2);
}
}
} else if (dataItem instanceof EmailDataItem) {
@@ -1869,6 +1915,10 @@
aboutCardName.value = res.getString(R.string.about_card_title);
}
}
+ } else if (Flags.getInstance().getBoolean(Experiments.QUICK_CONTACT_VIDEO_CALL)
+ && MIMETYPE_TACHYON.equals(dataItem.getMimeType())) {
+ // Skip these actions. They will be placed by the phone number.
+ return null;
} else {
// Custom DataItem
header = dataItem.buildDataStringForDisplay(context, kind);
@@ -1881,7 +1931,6 @@
if (intent != null) {
final String mimetype = intent.getType();
-
// Build advanced entry for known 3p types. Otherwise default to ResolveCache icon.
if (MIMETYPE_HANGOUTS.equals(mimetype)) {
// If a secondDataItem is available, use it to build an entry with
@@ -1963,7 +2012,7 @@
: smsContentDescription,
shouldApplyColor, isEditable,
entryContextMenuInfo, thirdIcon, thirdIntent, thirdContentDescription, thirdAction,
- thirdExtras, iconResourceId);
+ thirdExtras, shouldApplyThirdIconColor, iconResourceId);
}
private List<Entry> dataItemsToEntries(List<DataItem> dataItems,
@@ -2264,6 +2313,7 @@
/* thirdContentDescription = */ null,
/* thirdAction = */ Entry.ACTION_NONE,
/* thirdActionExtras = */ null,
+ /* shouldApplyThirdIconColor = */ true,
interaction.getIconResourceId()));
}
return entries;
@@ -2496,7 +2546,9 @@
/* isEditable = */ false, /* EntryContextMenuInfo = */ null,
/* thirdIcon = */ null, /* thirdIntent = */ null,
/* thirdContentDescription = */ null, /* thirdAction = */ Entry.ACTION_NONE,
- /* thirdExtras = */ null, R.drawable.quantum_ic_history_vd_theme_24);
+ /* thirdExtras = */ null,
+ /* shouldApplyThirdIconColor = */ true,
+ R.drawable.quantum_ic_history_vd_theme_24);
final List<List<Entry>> permissionExplanationEntries = new ArrayList<>();
permissionExplanationEntries.add(new ArrayList<Entry>());