WebUIDelegate Protocol Reference によると、
- webView:runJavaScriptAlertPanelWithMessage:
- webView:runJavaScriptConfirmPanelWithMessage:
- webView:runJavaScriptTextInputPanelWithPrompt:defaultText:
これらは、Deprecated in Mac OS X v10.4.11 となっている。
https://developer.apple.com/library/mac/#documentation/Cocoa/Reference/WebKit/Protocols/WebUIDelegate_Protocol/Reference/Reference.html
では、他の方法を考えると、alert はどうにかなる。しかし、confirm や prompt は、呼び出し元の JavaScript に、
BOOL か、文字列を返さないといけない。
上の delegate を使わずに confirm や prompt はどうしたらいいのか?
alert は、オーバーライドして、任意の プロトコル(http の代わりに定義するプロトコル)で、
JavaScript の document.location を書き変えて、UIWebView 側で捕捉して AlertView を実行すればよい。
-(void)webViewDidFinishLoad: ( UIWebView* ) webView の中で、以下のように、
alert をオーバライド実行する。
[self.webViewstringByEvaluatingJavaScriptFromString:@"(function(){ "
" window.alert = function() { "
" document.location=\"bridge://alert-\"+encodeURI(arguments[0]); "
" }; "
" } "
" )(); "
];
shouldStartLoadWithRequest で、@"bridge://alert-" を捕捉
- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType
{
if ([ [[request URL] absoluteString] rangeOfString:@"bridge://alert-"].location != NSNotFound){
// URL から、alert メッセージを切りだす。
NSString *str = [[[request URL] absoluteString] substringFromIndex:15];
// alert の文字列を URLデコード
NSString *decodedString = (NSString *)CFURLCreateStringByReplacingPercentEscapesUsingEncoding(NULL, (CFStringRef)str, CFSTR(""), kCFStringEncodingUTF8);
// 任意に定義するメソッドを call
[ self alertIntercept:decodedString ];
// このプロトコルは、以降、UIWebView の処理をしない。
return NO;
}
shouldStartLoadWithRequest から呼ばれるメソッドで、AlertView を表示する
-( void )alertIntercept:(NSString*)message
{
UIAlertView* dialog = [[UIAlertViewalloc] initWithTitle:nilmessage:message delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil ];
[dialog show];
[dialog autorelease];
}
alert メッセージは、URLエンコードする必要がある。