我想让我的android webview应用程序打开tel:电话链接。每次打开电话链接时,它都能很好地打开电话。然而,一旦我完成了我的通话并返回应用程序,它就会出现在“未找到网页电话:0000000000”的页面上。然后我必须再次点击后退按钮才能进入我点击电话号码的页面。
有没有办法让它打开TEL链接而不试图在webview中找到该页面并在手机上打开它?
这是我在WebView中使用的代码,用于覆盖其对TEL和Mailto链接的处理:
public boolean shouldOverrideUrlLoading(WebView view, String url) {
if (url.startsWith("mailto:") || url.startsWith("tel:")) {
Intent intent = new Intent(Intent.ACTION_VIEW,
Uri.parse(url));
startActivity(intent);
}
view.loadUrl(url);
return true;
}
任何帮助将不胜感激。我花了最近2个小时来搜索goodle并且没有得到任何答案。
答案 0 :(得分:100)
好的,所以我解决了我认为的问题。我只需要按如下方式分隔URL覆盖:
public boolean shouldOverrideUrlLoading(WebView view, String url) {
if (url.startsWith("tel:")) {
Intent intent = new Intent(Intent.ACTION_DIAL, Uri.parse(url));
startActivity(intent);
view.reload();
return true;
}
view.loadUrl(url);
return true;
}
现在我的常规链接和tel链接一样。我还可以在那里添加地理位置:链接,如果我需要,它不会给我以前在手机上打开地图时遇到的问题。
答案 1 :(得分:52)
不要调用loadUrl(url)
,而只是为不应该覆盖的网址返回false:
public boolean shouldOverrideUrlLoading(WebView view, String url) {
if( URLUtil.isNetworkUrl(url) ) {
return false;
}
// Otherwise allow the OS to handle it
Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
startActivity( intent );
return true;
}
我发现VIEWing tel:在我们尝试过的所有手机上按预期工作。由于DIAL的行动,不需要特殊情况。
我注意到YouTube视频等在WebView中不起作用,因此您可能也想要检测这些视频。
整个过程可能会被querying the PackageManager for Activities that handle your URI的各种URI推广,这些URI也不是嵌入式浏览器。这可能是过度的,并被其他已安装的浏览器搞糊涂了。
答案 2 :(得分:17)
答案 3 :(得分:7)
注意: - Android Nouget shouldOverrideUrlLoading
已弃用后
您需要使用shouldOverrideUrlLoading
和shouldOverrideUrlLoading
来获得更好的支持。您还可以检查网址是否包含mailto:
或tel
:,这些网址在HTML5中分别用于触发邮件客户端和电话拨号。
现在,完整的解决方案将如下所示
@SuppressWarnings("deprecation")
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
if (url.startsWith("mailto:")) {
//Handle mail Urls
startActivity(new Intent(Intent.ACTION_SENDTO, Uri.parse(url)));
} else if (url.startsWith("tel:")) {
//Handle telephony Urls
startActivity(new Intent(Intent.ACTION_DIAL, Uri.parse(url)));
} else {
view.loadUrl(url);
}
return true;
}
@TargetApi(Build.VERSION_CODES.N)
@Override
public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) {
final Uri uri = request.getUrl();
if (uri.toString().startsWith("mailto:")) {
//Handle mail Urls
startActivity(new Intent(Intent.ACTION_SENDTO, uri));
} else if (uri.toString().startsWith("tel:")) {
//Handle telephony Urls
startActivity(new Intent(Intent.ACTION_DIAL, uri));
} else {
//Handle Web Urls
view.loadUrl(uri.toString());
}
return true;
}
答案 4 :(得分:3)
如果没有为WebView分配WebViewClient,默认情况下,WebView会要求活动管理器为URL选择正确的处理程序。如果提供了WebViewClient,您应该自己处理不同的URL并在WebViewClient.shouldOverrideUrlLoading()中返回true,否则它将尝试向URL发送请求并获取错误,然后触发onReceiveError()。
Check document: WebViewClient.shouldOverrideUrlLoading
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
if (url.startsWith("tel:")) {
// ...TODO: launch a Dial app or send SMS or add to contact, etc...
return true;
}
else if (url.startsWith("mailto:")) {
// ...TODO: send email to someone or add to contact, etc...
return true;
}
else {
// ...TODO: Handle URL here
boolean handled = yourHandleUrlMethod(url);
return handled;
}
}
答案 5 :(得分:3)
SELECT *, A + B + C + D + E + F + G + H + I + J + K + L + M AS Total
FROM Table1
ORDER BY Total DESC
LIMIT 30;
这是我发现的修复。你必须使用这种方法。
public class MainActivity extends Activity {
private static final String HTML ="<!DOCTYPE html><html><body><a
href='tel:867-5309'>Click here to call!</a></body></html>";
private static final String TEL_PREFIX = "tel:";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
WebView wv = (WebView) findViewById(R.id.webview);
wv.setWebViewClient(new CustomWebViewClient());
wv.loadData(HTML, "text/html", "utf-8");
}
private class CustomWebViewClient extends WebViewClient {
@Override
public boolean shouldOverrideUrlLoading(WebView wv, String url) {
if(url.startsWith(TEL_PREFIX)) {
Intent intent = new Intent(Intent.ACTION_DIAL);
intent.setData(Uri.parse(url));
startActivity(intent);
return true;
}
return false;
}
}
}
答案 6 :(得分:1)
public boolean shouldOverrideUrlLoading(WebView view, String url)
{Uri query_string=Uri.parse(url);
String query_scheme=query_string.getScheme();
String query_host=query_string.getHost();
if ((query_scheme.equalsIgnoreCase("https") || query_scheme.equalsIgnoreCase("http"))
&& query_host!=null && query_host.equalsIgnoreCase(Uri.parse(URL_SERVER).getHost())
&& query_string.getQueryParameter("new_window")==null
)
{return false;//handle the load by webview
}
try
{Intent intent=new Intent(Intent.ACTION_VIEW, query_string);
String[] body=url.split("\\?body=");
if (query_scheme.equalsIgnoreCase("sms") && body.length>1)
{intent=new Intent(Intent.ACTION_VIEW, Uri.parse(body[0]));
intent.putExtra("sms_body", URLDecoder.decode(body[1]));
}
view.getContext().startActivity(intent);//handle the load by os
}
catch (Exception e) {}
return true;
}
答案 7 :(得分:1)
在WebView
类中,某些常量是静态的。您应该使用Intent.ACTION_VIEW
而不是Intent.ACTION_DIAL
或ACTION_SENDTO
:
@Override
public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) {
String url = request.getUrl().toString();
if (url.startsWith(WebView.SCHEME_TEL)
|| url.startsWith("sms:")
|| url.startsWith(WebView.SCHEME_MAILTO)
|| url.startsWith(WebView.SCHEME_GEO)) {
Intent intent = new Intent(Intent.ACTION_VIEW);
intent.setData(Uri.parse(url));
startActivity(intent); // view.context.startActivity(intent);
}
return true;
}
答案 8 :(得分:0)
public ActionResult Create()
{
AddressVM model = new AddressVM();
ConfigureViewModel(model);
return View(model);
}
[HttpPost]
public ActionResult Create(AddressVM model)
{
if (!ModelState.IsValid)
{
ConfigureViewModel(model);
return View(model);
}
.... // initailize an Address data model, map its properties from the view model
.... // save and redirect
}
答案 9 :(得分:0)
对于那些尝试使用@jeff Thomas回答但出现以下错误的人:
cannot find symbol view.startActivity(intent);
您可以使用以下代码:
public boolean shouldOverrideUrlLoading(WebView view, String url) {
if (url.startsWith("tel:")) {
Intent intent = new Intent(Intent.ACTION_DIAL, Uri.parse(url));
view.getContext().startActivity(intent);
view.reload();
return true;
}
view.loadUrl(url);
return true;
}
我刚刚将startActivity(intent)
更改为view.getContext().startActivity(intent)
,这对我有用。
答案 10 :(得分:0)
看着Hitesh Sahu和kam C的答案,我找到了解决方案。
在API 21中,它引发了一个异常:“ android.util.AndroidRuntimeException:从Activity上下文外部调用startActivity()需要FLAG_ACTIVITY_NEW_TASK标志。这真的是您想要的吗?”
如diyism所示,也可能找不到活动。因此,我处理了这些情况。
class MyWebViewClient : WebViewClient() {
@Suppress("DEPRECATION")
override fun shouldOverrideUrlLoading(view: WebView?, url: String?): Boolean {
if (view != null && url != null) {
return resolveUri(view.context, Uri.parse(url))
}
return super.shouldOverrideUrlLoading(view, url)
}
@TargetApi(Build.VERSION_CODES.N)
override fun shouldOverrideUrlLoading(view: WebView?, request: WebResourceRequest?): Boolean {
val uri = request?.url
if (view != null && uri != null) {
return resolveUri(view.context, uri)
}
return super.shouldOverrideUrlLoading(view, request)
}
private fun resolveUri(context: Context, uri: Uri): Boolean {
val url = uri.toString()
URL_SCHEMES.forEach {
if (url.startsWith(it)) {
val intent = Intent(Intent.ACTION_VIEW).apply {
data = uri
addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
}
try {
context.startActivity(intent)
} catch (e: ActivityNotFoundException) {
}
return true
}
}
return false
}
companion object {
private val URL_SCHEMES = arrayOf(WebView.SCHEME_TEL,
WebView.SCHEME_MAILTO, WebView.SCHEME_GEO, "sms:", "smsto:", "mms:", "mmsto:")
}
}