From d5e47f6da5b08b13ecdfa7f1edc7e12aeb83fab9 Mon Sep 17 00:00:00 2001 From: Eric Erfanian Date: Wed, 15 Mar 2017 14:41:07 -0700 Subject: Update Dialer source from latest green build. * Refactor voicemail component * Add new enriched calling components Test: treehugger, manual aosp testing Change-Id: I521a0f86327d4b42e14d93927c7d613044ed5942 --- .../android/dialer/postcall/AndroidManifest.xml | 28 ++++ java/com/android/dialer/postcall/PostCall.java | 182 +++++++++++++++++++++ .../android/dialer/postcall/PostCallActivity.java | 151 +++++++++++++++++ .../postcall/res/layout/post_call_activity.xml | 38 +++++ .../android/dialer/postcall/res/values/strings.xml | 31 ++++ .../android/dialer/postcall/res/values/values.xml | 19 +++ 6 files changed, 449 insertions(+) create mode 100644 java/com/android/dialer/postcall/AndroidManifest.xml create mode 100644 java/com/android/dialer/postcall/PostCall.java create mode 100644 java/com/android/dialer/postcall/PostCallActivity.java create mode 100644 java/com/android/dialer/postcall/res/layout/post_call_activity.xml create mode 100644 java/com/android/dialer/postcall/res/values/strings.xml create mode 100644 java/com/android/dialer/postcall/res/values/values.xml (limited to 'java/com/android/dialer/postcall') diff --git a/java/com/android/dialer/postcall/AndroidManifest.xml b/java/com/android/dialer/postcall/AndroidManifest.xml new file mode 100644 index 000000000..2bf07bca2 --- /dev/null +++ b/java/com/android/dialer/postcall/AndroidManifest.xml @@ -0,0 +1,28 @@ + + + + + + + diff --git a/java/com/android/dialer/postcall/PostCall.java b/java/com/android/dialer/postcall/PostCall.java new file mode 100644 index 000000000..cfe7c867b --- /dev/null +++ b/java/com/android/dialer/postcall/PostCall.java @@ -0,0 +1,182 @@ +/* + * 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 + */ + +package com.android.dialer.postcall; + +import android.app.Activity; +import android.content.Context; +import android.content.Intent; +import android.content.SharedPreferences; +import android.preference.PreferenceManager; +import android.support.design.widget.BaseTransientBottomBar.BaseCallback; +import android.support.design.widget.Snackbar; +import android.view.View; +import android.view.View.OnClickListener; +import com.android.dialer.buildtype.BuildType; +import com.android.dialer.common.Assert; +import com.android.dialer.common.ConfigProvider; +import com.android.dialer.common.ConfigProviderBindings; +import com.android.dialer.common.LogUtil; +import com.android.dialer.logging.Logger; +import com.android.dialer.logging.nano.DialerImpression; +import com.android.dialer.util.DialerUtils; +import com.android.dialer.util.IntentUtil; + +/** Helper class to handle all post call actions. */ +public class PostCall { + + private static final String KEY_POST_CALL_CALL_CONNECT_TIME = "post_call_call_connect_time"; + private static final String KEY_POST_CALL_CALL_DISCONNECT_TIME = "post_call_call_disconnect_time"; + private static final String KEY_POST_CALL_CALL_NUMBER = "post_call_call_number"; + private static final String KEY_POST_CALL_MESSAGE_SENT = "post_call_message_sent"; + + public static void promptUserForMessageIfNecessary(Activity activity, View rootView) { + if (isEnabled(activity)) { + if (shouldPromptUserToViewSentMessage(activity)) { + promptUserToViewSentMessage(activity, rootView); + } else if (shouldPromptUserToSendMessage(activity)) { + promptUserToSendMessage(activity, rootView); + } + } + } + + private static void promptUserToSendMessage(Activity activity, View rootView) { + LogUtil.i("PostCall.promptUserToSendMessage", "returned from call, showing post call SnackBar"); + String message = activity.getString(R.string.post_call_message); + String addMessage = activity.getString(R.string.post_call_add_message); + OnClickListener onClickListener = + v -> { + Logger.get(activity) + .logImpression(DialerImpression.Type.POST_CALL_PROMPT_USER_TO_SEND_MESSAGE_CLICKED); + activity.startActivity(PostCallActivity.newIntent(activity, getPhoneNumber(activity))); + }; + + Snackbar.make(rootView, message, Snackbar.LENGTH_INDEFINITE) + .setAction(addMessage, onClickListener) + .setActionTextColor( + activity.getResources().getColor(R.color.dialer_snackbar_action_text_color)) + .show(); + Logger.get(activity).logImpression(DialerImpression.Type.POST_CALL_PROMPT_USER_TO_SEND_MESSAGE); + PreferenceManager.getDefaultSharedPreferences(activity) + .edit() + .remove(KEY_POST_CALL_CALL_DISCONNECT_TIME) + .apply(); + } + + private static void promptUserToViewSentMessage(Activity activity, View rootView) { + LogUtil.i( + "PostCall.promptUserToViewSentMessage", + "returned from sending a post call message, message sent."); + String message = activity.getString(R.string.post_call_message_sent); + String addMessage = activity.getString(R.string.view); + OnClickListener onClickListener = + v -> { + Logger.get(activity) + .logImpression( + DialerImpression.Type.POST_CALL_PROMPT_USER_TO_VIEW_SENT_MESSAGE_CLICKED); + Intent intent = IntentUtil.getSendSmsIntent(getPhoneNumber(activity)); + DialerUtils.startActivityWithErrorToast(activity, intent); + }; + + Snackbar.make(rootView, message, Snackbar.LENGTH_INDEFINITE) + .setAction(addMessage, onClickListener) + .setActionTextColor( + activity.getResources().getColor(R.color.dialer_snackbar_action_text_color)) + .addCallback( + new BaseCallback() { + @Override + public void onDismissed(Snackbar snackbar, int i) { + super.onDismissed(snackbar, i); + clear(snackbar.getContext()); + } + }) + .show(); + Logger.get(activity) + .logImpression(DialerImpression.Type.POST_CALL_PROMPT_USER_TO_VIEW_SENT_MESSAGE); + PreferenceManager.getDefaultSharedPreferences(activity) + .edit() + .remove(KEY_POST_CALL_MESSAGE_SENT) + .apply(); + } + + public static void onCallDisconnected(Context context, String number, long callConnectedMillis) { + PreferenceManager.getDefaultSharedPreferences(context) + .edit() + .putLong(KEY_POST_CALL_CALL_CONNECT_TIME, callConnectedMillis) + .putLong(KEY_POST_CALL_CALL_DISCONNECT_TIME, System.currentTimeMillis()) + .putString(KEY_POST_CALL_CALL_NUMBER, number) + .apply(); + } + + public static void onMessageSent(Context context, String number) { + PreferenceManager.getDefaultSharedPreferences(context) + .edit() + .putString(KEY_POST_CALL_CALL_NUMBER, number) + .putBoolean(KEY_POST_CALL_MESSAGE_SENT, true) + .apply(); + } + + private static void clear(Context context) { + PreferenceManager.getDefaultSharedPreferences(context) + .edit() + .remove(KEY_POST_CALL_CALL_DISCONNECT_TIME) + .remove(KEY_POST_CALL_CALL_NUMBER) + .remove(KEY_POST_CALL_MESSAGE_SENT) + .remove(KEY_POST_CALL_CALL_CONNECT_TIME) + .apply(); + } + + private static boolean shouldPromptUserToSendMessage(Context context) { + SharedPreferences manager = PreferenceManager.getDefaultSharedPreferences(context); + long disconnectTimeMillis = manager.getLong(KEY_POST_CALL_CALL_DISCONNECT_TIME, -1); + long connectTimeMillis = manager.getLong(KEY_POST_CALL_CALL_CONNECT_TIME, -1); + + long timeSinceDisconnect = System.currentTimeMillis() - disconnectTimeMillis; + long callDurationMillis = disconnectTimeMillis - connectTimeMillis; + + ConfigProvider binding = ConfigProviderBindings.get(context); + return disconnectTimeMillis != -1 + && connectTimeMillis != -1 + && binding.getLong("postcall_last_call_threshold", 30_000) > timeSinceDisconnect + && binding.getLong("postcall_call_duration_threshold", 60_000) > callDurationMillis; + } + + private static boolean shouldPromptUserToViewSentMessage(Context context) { + return PreferenceManager.getDefaultSharedPreferences(context) + .getBoolean(KEY_POST_CALL_MESSAGE_SENT, false); + } + + private static String getPhoneNumber(Context context) { + return PreferenceManager.getDefaultSharedPreferences(context) + .getString(KEY_POST_CALL_CALL_NUMBER, null); + } + + private static boolean isEnabled(Context context) { + @BuildType.Type int type = BuildType.get(); + switch (type) { + case BuildType.BUGFOOD: + case BuildType.DOGFOOD: + case BuildType.FISHFOOD: + case BuildType.TEST: + return ConfigProviderBindings.get(context).getBoolean("enable_post_call", true); + case BuildType.RELEASE: + return ConfigProviderBindings.get(context).getBoolean("enable_post_call_prod", true); + default: + Assert.fail(); + return false; + } + } +} diff --git a/java/com/android/dialer/postcall/PostCallActivity.java b/java/com/android/dialer/postcall/PostCallActivity.java new file mode 100644 index 000000000..8da03dcd1 --- /dev/null +++ b/java/com/android/dialer/postcall/PostCallActivity.java @@ -0,0 +1,151 @@ +/* + * 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 + */ + +package com.android.dialer.postcall; + +import android.Manifest.permission; +import android.content.Context; +import android.content.Intent; +import android.content.pm.PackageManager; +import android.net.Uri; +import android.os.Bundle; +import android.provider.Settings; +import android.support.annotation.NonNull; +import android.support.annotation.Nullable; +import android.support.v7.app.AppCompatActivity; +import android.telephony.SmsManager; +import android.widget.Toolbar; +import com.android.dialer.common.Assert; +import com.android.dialer.common.LogUtil; +import com.android.dialer.enrichedcall.EnrichedCallCapabilities; +import com.android.dialer.enrichedcall.EnrichedCallComponent; +import com.android.dialer.enrichedcall.EnrichedCallManager; +import com.android.dialer.util.PermissionsUtil; +import com.android.dialer.widget.MessageFragment; + +/** Activity used to send post call messages after a phone call. */ +public class PostCallActivity extends AppCompatActivity implements MessageFragment.Listener { + + public static final String KEY_PHONE_NUMBER = "phone_number"; + public static final String KEY_MESSAGE = "message"; + private static final int REQUEST_CODE_SEND_SMS = 1; + + private boolean useRcs; + + public static Intent newIntent(@NonNull Context context, @NonNull String number) { + Intent intent = new Intent(Assert.isNotNull(context), PostCallActivity.class); + intent.putExtra(KEY_PHONE_NUMBER, Assert.isNotNull(number)); + return intent; + } + + @Override + protected void onCreate(@Nullable Bundle bundle) { + super.onCreate(bundle); + setContentView(R.layout.post_call_activity); + + Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar); + toolbar.setTitle(getString(R.string.post_call_message)); + toolbar.setNavigationOnClickListener(v -> finish()); + + useRcs = canUseRcs(getIntent().getStringExtra(KEY_PHONE_NUMBER)); + LogUtil.i("PostCallActivity.onCreate", "useRcs: %b", useRcs); + + int postCallCharLimit = + useRcs + ? getResources().getInteger(R.integer.post_call_char_limit) + : MessageFragment.NO_CHAR_LIMIT; + String[] messages = + new String[] { + getString(R.string.post_call_message_1), + getString(R.string.post_call_message_2), + getString(R.string.post_call_message_3) + }; + MessageFragment fragment = + MessageFragment.builder() + .setCharLimit(postCallCharLimit) + .showSendIcon() + .setMessages(messages) + .build(); + getSupportFragmentManager() + .beginTransaction() + .replace(R.id.message_container, fragment) + .commit(); + } + + private boolean canUseRcs(@NonNull String number) { + EnrichedCallCapabilities capabilities = + getEnrichedCallManager().getCapabilities(Assert.isNotNull(number)); + LogUtil.i( + "PostCallActivity.canUseRcs", + "number: %s, capabilities: %s", + LogUtil.sanitizePhoneNumber(number), + capabilities); + return capabilities != null && capabilities.supportsPostCall(); + } + + @Override + public void onMessageFragmentSendMessage(@NonNull String message) { + String number = Assert.isNotNull(getIntent().getStringExtra(KEY_PHONE_NUMBER)); + getIntent().putExtra(KEY_MESSAGE, message); + + if (useRcs) { + LogUtil.i("PostCallActivity.onMessageFragmentSendMessage", "sending post call Rcs."); + getEnrichedCallManager().sendPostCallNote(number, message); + PostCall.onMessageSent(this, number); + finish(); + } else if (PermissionsUtil.hasPermission(this, permission.SEND_SMS)) { + LogUtil.i("PostCallActivity.sendMessage", "Sending post call SMS."); + SmsManager smsManager = SmsManager.getDefault(); + smsManager.sendMultipartTextMessage( + number, null, smsManager.divideMessage(message), null, null); + PostCall.onMessageSent(this, number); + finish(); + } else if (PermissionsUtil.isFirstRequest(this, permission.SEND_SMS) + || shouldShowRequestPermissionRationale(permission.SEND_SMS)) { + LogUtil.i("PostCallActivity.sendMessage", "Requesting SMS_SEND permission."); + requestPermissions(new String[] {permission.SEND_SMS}, REQUEST_CODE_SEND_SMS); + } else { + LogUtil.i( + "PostCallActivity.sendMessage", "Permission permanently denied, sending to settings."); + Intent intent = new Intent(Intent.ACTION_VIEW); + intent.setAction(Settings.ACTION_APPLICATION_DETAILS_SETTINGS); + intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); + intent.setData(Uri.parse("package:" + this.getPackageName())); + startActivity(intent); + } + } + + @Override + public void onMessageFragmentAfterTextChange(String message) {} + + @Override + public void onRequestPermissionsResult( + int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) { + if (permissions.length > 0 && permissions[0].equals(permission.SEND_SMS)) { + PermissionsUtil.permissionRequested(this, permissions[0]); + } + if (requestCode == REQUEST_CODE_SEND_SMS + && grantResults.length > 0 + && grantResults[0] == PackageManager.PERMISSION_GRANTED) { + onMessageFragmentSendMessage(getIntent().getStringExtra(KEY_MESSAGE)); + } + } + + @NonNull + private EnrichedCallManager getEnrichedCallManager() { + return EnrichedCallComponent.get(this).getEnrichedCallManager(); + } +} diff --git a/java/com/android/dialer/postcall/res/layout/post_call_activity.xml b/java/com/android/dialer/postcall/res/layout/post_call_activity.xml new file mode 100644 index 000000000..6ea8126c5 --- /dev/null +++ b/java/com/android/dialer/postcall/res/layout/post_call_activity.xml @@ -0,0 +1,38 @@ + + + + + + + + \ No newline at end of file diff --git a/java/com/android/dialer/postcall/res/values/strings.xml b/java/com/android/dialer/postcall/res/values/strings.xml new file mode 100644 index 000000000..d5e085a05 --- /dev/null +++ b/java/com/android/dialer/postcall/res/values/strings.xml @@ -0,0 +1,31 @@ + + + + + Say why you called + + This is urgent. Call me back. + + Call me back when you have some time. + + Not urgent, we can chat later. + + Add message + + Message sent + View + \ No newline at end of file diff --git a/java/com/android/dialer/postcall/res/values/values.xml b/java/com/android/dialer/postcall/res/values/values.xml new file mode 100644 index 000000000..64fe9f6c8 --- /dev/null +++ b/java/com/android/dialer/postcall/res/values/values.xml @@ -0,0 +1,19 @@ + + + + 60 + \ No newline at end of file -- cgit v1.2.3