2010-12-02 8 views
56

tel : link to the phone : 내 안드로이드 webview 앱을 tel : link에 연결하려고합니다. 내가 전화 링크를 열 때마다 그것은 잘 작동하고 전화를 엽니 다. 그러나 일단 전화가 끝나고 앱으로 돌아 가면 "웹 페이지를 찾을 수 없음 tel : 0000000000"이라는 페이지에 있습니다. 그런 다음 전화 번호를 클릭 한 페이지로 이동하려면 뒤로 버튼을 한 번 더 눌러야합니다.안드로이드 WebView "tel :"링크가 웹 페이지를 찾을 수 없음

전화로 열뿐만 아니라 webview에서 페이지를 찾으려고하지 않고 TEL 링크를 여는 방법이 있습니까? 어떤 도움을 주시면 감사하겠습니다

 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; 
     } 

:

이 내가 전화의 그것의 처리를 오버라이드 (override) 웹보기에서 사용하고 코드와 이메일 링크 링크입니다. 나는 지난 2 시간 동안 음식을 챙기고 어떤 대답도하지 못했습니다.

+1

해보십시오 ACTION_DIAL : 링크? – EboMike

+0

잠깐, 문서는 실제로 ACTION_VIEW가 괜찮다고 말합니다. http://developer.android.com/reference/android/content/Intent.html 신경 쓰지 마세요 ... – EboMike

+0

바보 같은 질문 : 'WebViewClient'를 올바르게 설정 했습니까? ? 그 밖의 모든 기능은 작동합니까? – EboMike

답변

94

그래, 내가 생각하는 문제를 해결했다. 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 링크가 작동합니다. 또한 지리적 링크를 추가 할 수도 있습니다. 필요한 경우 링크를 사용하면 이전에 전화로지도를 여는 데 문제가되지 않습니다.

+2

Duh. 방금 view.LoadUrl (url)을 tel : link라고 부르는 것을 깨달았습니다. 'startActivity()'다음에'return true'를 추가 할 수도 있습니다. – EboMike

+6

Manifest에 을 추가하십시오. – jasonflaherty

+6

@jasonflaherty 실제로 CALL_PHONE 권한은 ACTION_CALL이 아니고 ACTION_DIAL입니다. 따라서 위 코드는 허가 없이도 잘 작동합니다. –

47

오히려 전화 loadUrl(url)보다, 그냥 무시해서는 안 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; 
} 

내가보기 전화를 발견했습니다 : 우리가 그것을 시도 한 모든 휴대폰에서 예상대로 작동합니다. DIAL 동작 때문에 특별한 경우가 필요 없습니다.

YouTube 동영상 등이 WebViews에서 작동하지 않는 것을 확인 했으므로이를 감지 할 수도 있습니다.

전체 프로세스는 임베디드 브라우저가 아닌 querying the PackageManager for Activities that handle your URI에 의해 모든 종류의 URI에 대해 일반화 될 수 있습니다. 그것은 과도 할 수도 있고 다른 설치된 브라우저에 혼동을 줄 수도 있습니다.

+1

http/https (및 기타) 검사에 URLUtil.isNetworkUrl (url)을 사용할 수 있습니다. – xnagyg

+1

큰 제안, @xnagyg. 코드 스 니펫을 업데이트했습니다. – Anm

+0

개별 URL 스키마를 추가하는 것보다 훨씬 실용적입니다. –

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; 
     } 
+1

해결책을 조금 설명해 주시겠습니까? 특히 URL_SERVER (누락 된 URL_SERVER) 테스트는 모든 사람에게 명확하지 않을 수 있습니다. – Ivin

+0

URL_SERVER가 "http://your.app.domain.com"이고 "false가 반환됩니다." 귀하의 사이트에있는 페이지가 응용 프로그램에서 열리 며 안드로이드 브라우저에서 열리지 않음을 의미합니다. – diyism

15

내 경험을 바탕으로 documentation과에 따르면, Intent.ACTION_VIEW완벽하게 정상적으로tel:, sms:, smsto:, mms:mmsto: 링크를 구문 분석하는 것입니다.

은 여기 5 1 :

의 URL에 대한 적절한 핸들러를 선택하는 작업 관리자를 요청합니다 기본 웹보기로 웹보기에 할당 된 WebViewClient가없는 경우
@Override 
    public boolean shouldOverrideUrlLoading(WebView webview, String url) 
    { 
    if (url.startsWith("tel:") || url.startsWith("sms:") || url.startsWith("smsto:") || url.startsWith("mms:") || url.startsWith("mmsto:")) 
     { 
     Intent intent = new Intent(Intent.ACTION_VIEW,Uri.parse(url)); 
     startActivity(intent); 
     return true; 
     } 
    return false; 
    } 
2

. 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

참고 : - 안드로이드 Nouget shouldOverrideUrlLoading

를 추천하지 않습니다 후에 당신은 더 나은 지원을 위해 shouldOverrideUrlLoading와 함께 shouldOverrideUrlLoading를 사용해야합니다. 또한 URL에 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; 
    } 
+0

Perfect ... 프리 누 그와 누가를 처리합니다.고맙습니다. –

0
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; 
    } 
} 

} 

지금과 같이 표시됩니다. 이 방법을 사용해야합니다. 텔에 대한

wv.setWebViewClient(new CustomWebViewClient()); 
0
@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 { 
    @SuppressWarnings("deprecated") 
    @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; 
    } 
+0

위의 게시 된이 메서드를 사용하려고했지만 "shouldoverrideurlloading"을 추가하면이 메서드가 더 이상 사용되지 않는다는 오류가 발생합니다. 이 코드를 사용하는 API에 대한 제한이 있습니까? .. 내 휴대 전화 안에 이것을 설치하려고했지만 앱이 스스로를 죽입니다. 어떻게 해결할 수 있습니까? .. 제발 도와주세요. –

관련 문제