2010-11-28 152 views
57

我最近發現我的UIWebView在ITMS鏈接上窒息。具體來說,從我的應用程序的UIWebView,如果我導航到一個網站,如this one,並點擊「在App Store上可用」鏈接,UIWebView將錯誤出現「錯誤域= WebKitErrorDomain代碼= 101 URL無法顯示「。如何處理UIWebView中的應用程序URL?

經過一番Google搜索,我意識到我需要捕捉應用程序鏈接的請求,並讓iOS處理它們。我首先看看-webView:shouldStartLoadWithRequest:navigationType:中的方案是否以「itms」開頭,但意識到系統可能會處理其他類型的應用程序鏈接。所以,我想出了這個,而是:

- (void)webView:(UIWebView *)wv didFailLoadWithError:(NSError *)error { 
    // Give iOS a chance to open it. 
    NSURL *url = [NSURL URLWithString:[error.userInfo objectForKey:@"NSErrorFailingURLStringKey"]]; 
    if ([error.domain isEqual:@"WebKitErrorDomain"] 
     && error.code == 101 
     && [[UIApplication sharedApplication]canOpenURL:url]) 
    { 
     [[UIApplication sharedApplication]openURL:url]; 
     return; 
    } 

    // Normal error handling… 
} 

我對這個兩個問題:

  1. 這是理智?我特別檢查錯誤域和錯誤代碼,並從userInfo獲取URL字符串。這些東西可能會保留嗎?
  2. 這對於上面鏈接的應用商店鏈接起作用,但是當我切換回我的應用程序時,似乎出現了一個後來失敗的請求,出現「幀負載中斷」失敗。我怎麼能擺脫那個?當我有操作系統處理來自-webView:shouldStartLoadWithRequest:navigationType:的請求時,不會發生這種情況,所以這有點煩人。

如何處理此類請求?

回答

88

這是我想出來的。在webView:shouldStartLoadWithRequest:navigationType:,我問OS處理任何非HTTP和非HTTPS請求是可以的,就像這樣:

- (BOOL)webView:(UIWebView *)wv shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType { 

    // Determine if we want the system to handle it. 
    NSURL *url = request.URL; 
    if (![url.scheme isEqual:@"http"] && ![url.scheme isEqual:@"https"]) { 
     if ([[UIApplication sharedApplication]canOpenURL:url]) { 
      [[UIApplication sharedApplication]openURL:url]; 
      return NO; 
     } 
    } 
    return YES; 
} 

這工作得很好,除了錯誤的血腥「中斷幀的負載」。我曾經想過,通過從webView:shouldStartLoadWithRequest:navigationType:返回false,web視圖不會加載請求,因此不會有錯誤需要處理。但即使我上面返回NO,我仍然「幀負載中斷」錯誤。這是爲什麼?

無論如何,我假設它可以在-webView:didFailLoadWithError:被忽略:

- (void)webView:(UIWebView *)wv didFailLoadWithError:(NSError *)error { 
    // Ignore NSURLErrorDomain error -999. 
    if (error.code == NSURLErrorCancelled) return; 

    // Ignore "Fame Load Interrupted" errors. Seen after app store links. 
    if (error.code == 102 && [error.domain isEqual:@"WebKitErrorDomain"]) return; 

    // Normal error handling… 
} 

現在的iTunes網址正常工作,因爲這樣做mailto: S和應用程序的鏈接。

+1

不只是iTunes - 我也是通過網絡瀏覽器登錄Facebook的。 – Adam 2012-11-13 06:10:51

-2

如果您註冊您的應用程序以處理itms,它有幫助嗎?

例如 http://inchoo.net/iphone-development/launching-application-via-url-scheme/

你可以開始與方案http但隨後得到itms重定向,如果您的應用程序未註冊爲處理該方案,該方案可能會失敗。

+1

我不希望我的應用程序處理`itms`方案。我想知道什麼時候有人點擊UIWebView中的視圖本身無法處理的鏈接,然後檢查iOS是否可以處理它,如果有,請讓它執行此操作。無論我是否爲自己的應用程序註冊了URL方案,都沒有關係。 – theory 2010-11-29 02:36:16

+0

從查看URL無法判斷。處理失敗(如你所示)可能是最好的方法。我懷疑「Frame Load Interrupted」可能來自重定向到itms scheme URL,這就是爲什麼我建議將您的應用程序註冊爲有效的原因。 – 2010-12-01 00:51:08

8

從理論代碼開始,檢查「itms」方案的URL(由於重定向可以多次調用此方法)。一旦看到「itms」方案,停止加載webView並使用Safari打開URL。我的WebView恰好位於NavigationController中,所以在打開Safari後彈出(不太閃爍)。

- (BOOL)webView:(UIWebView*)webView shouldStartLoadWithRequest:(NSURLRequest*)request 
    navigationType:(UIWebViewNavigationType)navigationType 
{ 
    if ([[[request URL] scheme] isEqualToString:@"itms-apps"]) { 
     [webView stopLoading]; 
     [[UIApplication sharedApplication] openURL:[request URL]]; 
     [self.navigationController popViewControllerAnimated:YES]; 
     return NO; 
    } else { 
     return YES; 
    } 
} 
相關問題