Add reject via text capability to calls
* Add REJECT_VIA_TEXT capability to calls
* Move allowRespondViaSmsForCall to RejectWithTextManager
Bug: 10424370
Change-Id: I059550d82e3b44cc4cc42d5eb06e40551497f063
diff --git a/src/com/android/phone/RejectWithTextMessageManager.java b/src/com/android/phone/RejectWithTextMessageManager.java
index 8324bd4..b03211a 100644
--- a/src/com/android/phone/RejectWithTextMessageManager.java
+++ b/src/com/android/phone/RejectWithTextMessageManager.java
@@ -32,7 +32,9 @@
import android.graphics.drawable.Drawable;
import android.net.Uri;
import android.os.Handler;
+import android.telephony.PhoneNumberUtils;
import android.telephony.TelephonyManager;
+import android.text.TextUtils;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
@@ -46,6 +48,7 @@
import com.android.internal.telephony.Call;
import com.android.internal.telephony.Connection;
import com.android.internal.telephony.PhoneConstants;
+
import com.google.android.collect.Lists;
import java.util.ArrayList;
@@ -128,29 +131,6 @@
}
/**
- * @return true if the "Respond via SMS" feature should be enabled
- * for the specified incoming call.
- *
- * The general rule is that we *do* allow "Respond via SMS" except for
- * the few (relatively rare) cases where we know for sure it won't
- * work, namely:
- * - a bogus or blank incoming number
- * - a call from a SIP address
- * - a "call presentation" that doesn't allow the number to be revealed
- *
- * In all other cases, we allow the user to respond via SMS.
- *
- * Note that this behavior isn't perfect; for example we have no way
- * to detect whether the incoming call is from a landline (with most
- * networks at least), so we still enable this feature even though
- * SMSes to that number will silently fail.
- */
- public static boolean allowRespondViaSmsForCall(Context context, Call ringingCall) {
- // TODO(klp) implement this!
- return true;
- }
-
- /**
* Sends a text message without any interaction from the user.
*/
private void sendText(String phoneNumber, String message, ComponentName component) {
@@ -199,7 +179,7 @@
* Queries the System to determine what packages contain services that can handle the instant
* text response Action AND have permissions to do so.
*/
- private ArrayList<ComponentName> getPackagesWithInstantTextPermission() {
+ private static ArrayList<ComponentName> getPackagesWithInstantTextPermission() {
final PackageManager packageManager = PhoneGlobals.getInstance().getPackageManager();
final ArrayList<ComponentName> componentsWithPermission = new ArrayList<ComponentName>();
@@ -251,8 +231,8 @@
return intent;
}
- public void rejectCallWithNewMessage(Call call) {
- launchSmsCompose(call.getLatestConnection().getAddress());
+ public void rejectCallWithNewMessage(String number) {
+ launchSmsCompose(number);
}
private ComponentName getSmsService() {
@@ -302,15 +282,105 @@
}
- public void rejectCallWithMessage(Call call, String message) {
+ public void rejectCallWithMessage(final String number, String message) {
final ComponentName componentName = getSmsService();
if (componentName != null) {
- sendTextAndExit(call.getLatestConnection().getAddress(), message, componentName,
+ sendTextAndExit(number, message, componentName,
false);
}
}
+ /**
+ * @return true if the "Respond via SMS" feature should be enabled
+ * for the specified incoming call.
+ *
+ * The general rule is that we *do* allow "Respond via SMS" except for
+ * the few (relatively rare) cases where we know for sure it won't
+ * work, namely:
+ * - a bogus or blank incoming number
+ * - a call from a SIP address
+ * - a "call presentation" that doesn't allow the number to be revealed
+ *
+ * In all other cases, we allow the user to respond via SMS.
+ *
+ * Note that this behavior isn't perfect; for example we have no way
+ * to detect whether the incoming call is from a landline (with most
+ * networks at least), so we still enable this feature even though
+ * SMSes to that number will silently fail.
+ */
+ public static boolean allowRespondViaSmsForCall(
+ com.android.services.telephony.common.Call call, Connection conn) {
+ if (DBG) log("allowRespondViaSmsForCall(" + call + ")...");
+
+ // First some basic sanity checks:
+ if (call == null) {
+ Log.w(TAG, "allowRespondViaSmsForCall: null ringingCall!");
+ return false;
+ }
+ if (!(call.getState() == com.android.services.telephony.common.Call.State.INCOMING) &&
+ !(call.getState() ==
+ com.android.services.telephony.common.Call.State.CALL_WAITING)) {
+ // The call is in some state other than INCOMING or WAITING!
+ // (This should almost never happen, but it *could*
+ // conceivably happen if the ringing call got disconnected by
+ // the network just *after* we got it from the CallManager.)
+ Log.w(TAG, "allowRespondViaSmsForCall: ringingCall not ringing! state = "
+ + call.getState());
+ return false;
+ }
+
+ if (conn == null) {
+ // The call doesn't have any connections! (Again, this can
+ // happen if the ringing call disconnects at the exact right
+ // moment, but should almost never happen in practice.)
+ Log.w(TAG, "allowRespondViaSmsForCall: null Connection!");
+ return false;
+ }
+
+ // Check the incoming number:
+ final String number = conn.getAddress();
+ if (DBG) log("- number: '" + number + "'");
+ if (TextUtils.isEmpty(number)) {
+ Log.w(TAG, "allowRespondViaSmsForCall: no incoming number!");
+ return false;
+ }
+ if (PhoneNumberUtils.isUriNumber(number)) {
+ // The incoming number is actually a URI (i.e. a SIP address),
+ // not a regular PSTN phone number, and we can't send SMSes to
+ // SIP addresses.
+ // (TODO: That might still be possible eventually, though. Is
+ // there some SIP-specific equivalent to sending a text message?)
+ Log.i(TAG, "allowRespondViaSmsForCall: incoming 'number' is a SIP address.");
+ return false;
+ }
+
+ // Finally, check the "call presentation":
+ int presentation = conn.getNumberPresentation();
+ if (DBG) log("- presentation: " + presentation);
+ if (presentation == PhoneConstants.PRESENTATION_RESTRICTED) {
+ // PRESENTATION_RESTRICTED means "caller-id blocked".
+ // The user isn't allowed to see the number in the first
+ // place, so obviously we can't let you send an SMS to it.
+ Log.i(TAG, "allowRespondViaSmsForCall: PRESENTATION_RESTRICTED.");
+ return false;
+ }
+
+ // Allow the feature only when there's a destination for it.
+ if (getPackagesWithInstantTextPermission().size() < 1) {
+ return false;
+ }
+
+ // TODO: with some carriers (in certain countries) you *can* actually
+ // tell whether a given number is a mobile phone or not. So in that
+ // case we could potentially return false here if the incoming call is
+ // from a land line.
+
+ // If none of the above special cases apply, it's OK to enable the
+ // "Respond via SMS" feature.
+ return true;
+ }
+
private static void log(String msg) {
Log.d(TAG, msg);
}