app应该在使用ACTION_DIAL意图时检查设备是否具有呼叫功能?

时间:2014-11-18 15:26:40

标签: android android-intent

我的程序中有以下代码:

  public static void callPhoneNumber(Context context, String clientPhoneNum) {

    if (isCallingSupported(context)) {
      Intent i = new Intent(Intent.ACTION_DIAL, Uri.parse("tel:" + clientPhoneNum));
      context.startActivity(i);
    } else {
      final AlertDialog alertDialog =
          new AlertDialog.Builder(context).setMessage(context.getString(R.string.error))
              .setMessage(context.getString(R.string.no_call_functionality))
              .setPositiveButton(context.getString(R.string.ok),
                  new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialog, int which) {
                      dialog.dismiss();
                    }
                  })

              .create();

      alertDialog.show();
    }
  }

  private static boolean isCallingSupported(Context context) {
    TelephonyManager telephonyManager =
        (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);

    return (telephonyManager.getPhoneType() != TelephonyManager.PHONE_TYPE_NONE);
  }

我想知道isCallingSupported()是否有必要?我不记得为什么我这样写它,但现在当我在回顾时,我认为用户可能只是使用他的Skype或其他VOIP应用程序来拨号。我是否应该进行任何其他检查,或者在没有isCallingSupported()的情况下这是否安全(我的意思是安全,即使用户的平板电脑没有呼叫功能,也没有其他可以处理呼叫的应用程序,意图不会#39;引起崩溃)?

3 个答案:

答案 0 :(得分:9)

来自this问题:

PackageManager manager = context.getPackageManager();
List<ResolveInfo> infos = manager.queryIntentActivities(intent, 0);
if (infos.size() > 0) {
       //Then there is application can handle your intent
}else{
       //No Application can handle your intent
}

首先检查是否有任何应用已注册此意图。如果有,请使用它。如果没有,请显示您的对话框。

您最终只需使用上面的代码替换isCallingSupported函数:

private static boolean isCallingSupported(Context context) {

    boolean result = true;
    PackageManager manager = context.getPackageManager();
    List<ResolveInfo> infos = manager.queryIntentActivities(intent, 0);
    if (infos.size() <= 0) {
        result = false;
    }
    return result;

}

答案 1 :(得分:3)

我会使用PackageManagerresolveActivity()查看是否有任何内容会响应您已配置的ACTION_DIAL Intent。那将处理:

  • 没有本机电话并且没有拨号器的设备,resolveActivity()应该返回null

  • 没有本机电话但有拨号器(例如VOIP)的设备,希望该拨号器的作者有ACTION_DIAL支持

  • 的设备具有本地电话,但当前用户无权访问拨号程序(例如,受限制的配置文件)

答案 2 :(得分:0)

使用 Robin 的出色回答,我在 RunUtilities 类中创建了一个助手:

class RunUtilities {

    companion object {

        fun canMakeCalls(context: Context): Boolean {
            val intent = Intent(Intent.ACTION_DIAL)
            val infos = context.packageManager.queryIntentActivities(intent, 0)
            return infos.size > 0
        }
    }
}

示例用法:

if (!RunUtilities.canMakeCalls(this)) {
    callButton.visibility = View.GONE
}

(我对 Kotlin 还很陌生,所以欢迎指点)