Это в ответ на этот блог:
http://blog.bignerdranch.com/3784-javascriptcore-and-ios-7/
Мысли от разработчиков iOS на SO?
Это в ответ на этот блог:
http://blog.bignerdranch.com/3784-javascriptcore-and-ios-7/
Мысли от разработчиков iOS на SO?
Вы можете получить JSContext из UIWebView с помощью ключевого пути:
UIWebView *webView = [[UIWebView alloc] init];
JSContext *ctx = [webView valueForKeyPath:@"documentView.webView.mainFrame.javaScriptContext"];
ctx[@"document"][@"body"][@"style"][@"background"] = @"steelblue";
Apple никогда не собиралась документировать какие-либо новые API JavaScriptCore, поэтому я не уверен, что это считается внутренним/недокументированным API или нет. У меня есть одобренное приложение, которое использует этот метод.
Обновление. Еще одно альтернативное решение, предложенное в https://github.com/TomSwift/UIWebView-TS_JavaScriptContext, - это сделать категорию на NSObject
и использовать чтобы реализовать WebKit документированный ответный вызов делегата didCreateJavaScriptContext
. Чтобы перефразировать эту реализацию, вы можете просто вызвать [NSObject contextForWebView:myWebView]
, чтобы захватить JSContext для UIWebView:
@implementation NSObject(JSContextTracker)
+ (NSMapTable *)JSContextTrackerMap {
static NSMapTable *contextTracker;
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
contextTracker = [NSMapTable strongToWeakObjectsMapTable];
});
return contextTracker;
}
- (void)webView:(id)unused didCreateJavaScriptContext:(JSContext *)ctx forFrame:(id)alsoUnused {
NSAssert([ctx isKindOfClass:[JSContext class]], @"bad context");
if (!ctx)
return;
NSMapTable *map = [NSObject JSContextTrackerMap];
static long contexts = 0;
NSString *contextKey = [NSString stringWithFormat:@"jsctx_%@", @(contexts++)];
[map setObject:ctx forKey:contextKey];
ctx[@"JSContextTrackerMapKey"] = contextKey; // store the key to the map in the context itself
}
+ (JSContext *)contextForWebView:(UIWebView *)webView {
// this will trigger didCreateJavaScriptContext if it hasn't already been called
NSString *contextKey = [webView stringByEvaluatingJavaScriptFromString:@"JSContextTrackerMapKey"];
JSContext *ctx = [[NSObject JSContextTrackerMap] objectForKey:contextKey];
return ctx;
}
@end
Я придумал подход, чтобы получить UIWebView
JSContext
, который отличается от подхода KVC.
В принципе, зная некоторые подробности о WebKit, мы можем внедрить метод обратного вызова делегата в NSObject и передать его при создании. Подробности здесь:
Это было бы полезно для запуска JavaScript, не связанного с веб-сайтом, размещенного внутри вашего приложения. Подумайте, есть ли у вас куча существующего кода, написанного на JavaScript, который вы не хотели переписывать? Вы можете использовать JavaScriptCore без UIWebView для размещения этого кода в вашем процессе. Я также могу предположить, что он используется для добавления пользовательской возможности для приложений iOS. Возможности бесконечны!
Еще одна вещь, о которой стоит упомянуть, заключается в том, что UIWebView очень ресурсоемкий (в конце концов, он вроде запускает копию Safari в вашем процессе); Он выделяет TON памяти, который вы просто никогда не вернетесь. Если вам не требуется веб-рендеринг, JavaScriptCore может многое сделать с гораздо меньшим количеством ресурсов. Подробнее о потреблении ресурсов UIWebView см. здесь.
Вы можете реализовать логику приложения в JavaScript и использовать JS-код на iOS и других платформах. Это сокращает работу по поддержке приложения на iOS, Android, Web и т.д.
Calatrava является основой этой идеи.
Вы можете писать приложения ios7 с помощью JavaScript: