UIWebView的委托方法shouldStartLoadWithRequest:相当于WKWebView?

我的iOS 7+应用程序中有一个模块,它是一个UIWebView。 该HTML页面加载一个JavaScript,创build自定义形状的button(使用Raphaeljs库)。 使用UIWebView,我将委托设置为self。 每次按下我的自定义button时,都会调用委托方法webView: shouldStartLoadWithRequest: navigationType: 请求不应该由html处理,而应该由iOS代码处理。 所以我使用了“inapp”作为我的请求的scheme的请求约定(在这里读取stackoverflow的地方)。 然后我检查主机并采取适当的行动。

这个代码可以在iOS 7上正常工作。但是,在iOS 8上,web视图显示为空白(bug?),所以我决定使用WKWebView for iOS 8设备。 网页视图现在渲染罚款(和惊人的更快!),但我的button没有任何效果。

我尝试使用- (WKNaviation *)loadRequest:(NSURLRequest *)request ,但它不被调用。

我无法findUIWebView委托方法webView: shouldStartLoadWithRequest: navigationType:的直接等价物webView: shouldStartLoadWithRequest: navigationType: 用WKWebView处理这些请求的最好方法是什么?

重新阅读你的描述,看起来你真正需要知道的是如何使用WKWebView重新实现Javascript / Objective-C桥接。

我刚刚自己做了这个,按照http://tetontech.wordpress.com/2014/07/17/objective-c-wkwebview-to-javascript-and-back/上的教程以及http&#xFF1A://上的信息nshipster.com/wkwebkit/

WKWebView有一个内置的Javascript和Objective-C / Swift: WKScriptMessageHandler

首先,在你的视图控制器的头文件中包含WebKit头文件和WKScriptMessageHandler协议:

 #import <UIKit/UIKit.h> #import <WebKit/WebKit.h> @interface ViewController : UIViewController <WKScriptMessageHandler> @end 

在初始化你的WKWebView ,你需要用一个脚本消息处理器来configuration它。 任何你想要的名称,但对我来说,它似乎是命名为您的应用程序是有道理的。

  WKWebViewConfiguration *theConfiguration = [[WKWebViewConfiguration alloc] init]; [theConfiguration.userContentController addScriptMessageHandler:self name:@"myApp"]; _theWebView = [[WKWebView alloc] initWithFrame:self.view.frame configuration:theConfiguration]; [_theWebView loadRequest:request]; [self.view addSubview:_theWebView]; 

现在,实现userContentController:didReceiveScriptMessage: 这会在你的webview收到一条消息时触发,所以它会完成你之前用webView:shouldStartLoadWithRequest:navigationType:做的工作webView:shouldStartLoadWithRequest:navigationType:

 - (void)userContentController:(WKUserContentController *)userContentController didReceiveScriptMessage:(WKScriptMessage *)message { NSDictionary *sentData = (NSDictionary *)message.body; NSString *messageString = sentData[@"message"]; NSLog(@"Message received: %@", messageString); } 

您现在准备好接收来自Javascript的消息。 你需要添加到你的Javascript的函数调用是这样的:

 window.webkit.messageHandlers.myApp.postMessage({"message":"Hello there"}); 

要回答原来的问题,相当于webView:shouldStartLoadWithRequest:navigationType:在UIWebView中是webView:decidePolicyForNavigationAction:decisionHandler:在WKWebView中。 这些方法在每个请求(包括初始请求)之前被调用,并提供允许/禁止的能力。

我一直在寻找一个好的解释,但没有find一个。 我已经在我的应用程序中使用了以下内容,似乎一切正常( 编辑:基于ccoroom的评论更新):

 UIWebViewDelegate - webView:shouldStartLoadWithRequest:navigationType: WKNavigationDelegate - webView:decidePolicyForNavigationAction:decisionHandler: 

以下是其他的UIWebViewDelegate方法:

 UIWebViewDelegate - webViewDidStartLoad: WKNavigationDelegate - webView:didCommitNavigation: UIWebViewDelegate - webViewDidFinishLoad: WKNavigationDelegate - webView:didFinishNavigation: UIWebViewDelegate - webView:didFailLoadWithError: WKNavigationDelegate - webView:didFailNavigation:withError: - webView:didFailProvisionalNavigation:withError: 

我很想有人为我确认这一点。

编辑:其实,我已经回答了你在标题中的问题(虽然我不再相信webView:didCommitNavigation:在生命周期中的确切位置被调用),但重新阅读你的描述,看起来像什么您实际上需要了解的是如何使用WKWebView重新实现Javascript / Objective-C桥接。 所以看看我的其他答案。

只要使用下面的方法,它是WKNavigationDelegate的一部分

 - (void)webView:(WKWebView *)webView decidePolicyForNavigationAction:(WKNavigationAction *)navigationAction decisionHandler:(void (^)(WKNavigationActionPolicy))decisionHandler { NSURLRequest *request = navigationAction.request; NSString *url = [[request URL]absoluteString]; decisionHandler(WKNavigationActionPolicyAllow); } 

Swift中你可以做这样的事情:

 func webView(webView: WKWebView, decidePolicyForNavigationAction navigationAction: WKNavigationAction, decisionHandler: (WKNavigationActionPolicy) -> Void) { switch navigationAction.request.URLString { case "http://action.is.needed/some-action": self.someFunc() decisionHandler(.Cancel) break default: decisionHandler(.Allow) break } } 

这是网页中的链接:

 <a href="http://action.is.needed/some-action">Hello world!</a> 

你可以为你的WKWebView添加Observer

  static void* keyValueObservingContext = &keyValueObservingContext; [webView addObserver:self forKeyPath:@"URL" options:0 context:keyValueObservingContext]; - (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context { if ([keyPath isEqualToString:@"URL"]){ // do something } } 

不要忘记在viewWillDisappear中删除它

 -(void)viewWillDisappear:(BOOL)animated{ [super viewWillDisappear:animated]; [webView removeObserver:self forKeyPath:@"URL"]; }