在Windows上,当“Shell.Explorer”ActiveX控件嵌入到应用程序中时,可以在实现IDispatch的对象上注册“外部”处理程序,这样网页上的脚本就可以调用托管应用
<button onclick="window.external.Test('called from script code')">test</button>
现在,我转向Mac开发,并认为我可以从我的Cocoa应用程序中嵌入的WebKit中获得类似的功能。但是,似乎没有任何工具允许脚本回调托管应用程序。
一条建议是挂钩window.alert
并获取脚本以将格式化的消息字符串作为警报字符串传递。
我也想知道是否可以使用NPPVpluginScriptableNPObject将WebKit定向到应用程序托管的NPAPI插件。
我错过了什么吗?托管WebView并允许脚本与主机交互真的很难吗?
答案 0 :(得分:31)
您需要实现各种WebScripting协议方法。这是一个基本的例子:
@interface WebController : NSObject
{
IBOutlet WebView* webView;
}
@end
@implementation WebController
//this returns a nice name for the method in the JavaScript environment
+(NSString*)webScriptNameForSelector:(SEL)sel
{
if(sel == @selector(logJavaScriptString:))
return @"log";
return nil;
}
//this allows JavaScript to call the -logJavaScriptString: method
+ (BOOL)isSelectorExcludedFromWebScript:(SEL)sel
{
if(sel == @selector(logJavaScriptString:))
return NO;
return YES;
}
//called when the nib objects are available, so do initial setup
- (void)awakeFromNib
{
//set this class as the web view's frame load delegate
//we will then be notified when the scripting environment
//becomes available in the page
[webView setFrameLoadDelegate:self];
//load a file called 'page.html' from the app bundle into the WebView
NSString* pagePath = [[NSBundle mainBundle] pathForResource:@"page" ofType:@"html"];
NSURL* pageURL = [NSURL fileURLWithPath:pagePath];
[[webView mainFrame] loadRequest:[NSURLRequest requestWithURL:pageURL]];
}
//this is a simple log command
- (void)logJavaScriptString:(NSString*) logText
{
NSLog(@"JavaScript: %@",logText);
}
//this is called as soon as the script environment is ready in the webview
- (void)webView:(WebView *)sender didClearWindowObject:(WebScriptObject *)windowScriptObject forFrame:(WebFrame *)frame
{
//add the controller to the script environment
//the "Cocoa" object will now be available to JavaScript
[windowScriptObject setValue:self forKey:@"Cocoa"];
}
@end
在您的控制器中实现此代码后,您现在可以从JavaScript环境中调用Cocoa.log('foo');
,并且将调用logJavaScriptString:
方法。
答案 1 :(得分:1)
将WebScriptObject API与JavaScriptCore框架结合使用非常容易。