最近写东西的时候,后台给我的数据好多都是需要调JS才能得到,找了好多资料,终于给搞出来了,贴出部分代码分享一下,希望可以帮到某一些遇到同样困难的小伙伴,虾面上代码。
viewController.h文件
#import <UIKit/UIKit.h>
#import "AFNetworking.h"
#import "WebViewJavascriptBridge.h"
#import "SDWebImageManager.h"
#import "imageInfo.h"
@interface ViewController : UIViewController<UIWebViewDelegate>
@end
viewController.m文件
#import "ViewController.h"
@interface ViewController ()
/*
网页*/
@property (nonatomic, strong)UIWebView *webView;
/*
图片类型,一张或者两张*/
@property (nonatomic, copy)NSString *detailID;
/*
请求字符串*/
@property (nonatomic, copy)NSMutableString *requestUrlString;
/*
帮助JS调用本地方法*/
@property (nonatomic, strong)WebViewJavascriptBridge *bridge;
@end
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
[self initWebView];
[self initJSbirdge];
[self setupRequest];
}
/*
网页*/
- (void)initWebView {
self.webView = [[UIWebView alloc] initWithFrame:self.view.bounds];
_webView.opaque = NO;
_webView.backgroundColor = [UIColor colorWithWhite:0.95 alpha:0.95];
[self.view addSubview:_webView];
}
/*
桥*/
- (void)initJSbirdge {
[WebViewJavascriptBridge enableLogging];
_bridge = [WebViewJavascriptBridge bridgeForWebView:_webView webViewDelegate:self handler:^(id data, WVJBResponseCallback responseCallback) {
//NSLog(@"ObjC received message from JS: %@", data);//从JS得到的信息
responseCallback(@"Response for message from ObjC");
}];
[_bridge registerHandler:@"testObjcCallback" handler:^(id data, WVJBResponseCallback responseCallback) {
//NSLog(@"testObjcCallback called: %@", data);//测试回调的数据
responseCallback(@"Response from testObjcCallback");
}];
}
/*
设置请求*/
- (void)setupRequest {
self.detailID = @"AQ72N9QG00051CA1";//一张图片(网页里一张图片的数据)
self.detailID = @"AQ4RPLHG00964LQ9";//多张图片(网页里多张图片的数据)
NSMutableString *urlStr = [NSMutableString stringWithString:@"http://c.m.163.com/nc/article/xukunhenwuliao/full.html"];
[urlStr replaceOccurrencesOfString:@"xukunhenwuliao" withString:_detailID options:NSCaseInsensitiveSearch range:[urlStr rangeOfString:@"xukunhenwuliao"]];
NSLog(@"网址:%@",urlStr);
AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager];
[manager GET:urlStr parameters:nil success:^(AFHTTPRequestOperation *operation, id responseObject) {
NSLog(@"++++++++++++++++++返回数据:%@",responseObject);
//处理数据
[self setupWebViewByData:responseObject];
} failure:^(AFHTTPRequestOperation *operation, NSError *error) {
NSLog(@"error == %@",error);
}];
}
/*
数据处理*/
- (void)setupWebViewByData:(id)data{
if (data!= nil) {
//解析的字典
NSDictionary *dic = (NSMutableDictionary *)data;
NSDictionary *bodyDic = [dic objectForKey:_detailID];
NSMutableString *bodyStr = [[NSMutableString alloc] initWithString:[bodyDic objectForKey:@"body"]];
//写一段接收主标题的html字符串,直接拼接到字符串
//标题
NSMutableString *titleStr= [bodyDic objectForKey:@"title"];
//来源
NSMutableString *sourceStr = [bodyDic objectForKey:@"source"];
//时间
NSMutableString *ptimeStr = [bodyDic objectForKey:@"ptime"];
//设置字体,大小,字号,胖廋
NSMutableString *allTitleStr =[NSMutableString stringWithString:@"<style type='text/css'> p.thicker{font-weight: 900}p.light{font-weight: 0}p{font-size: 108%}h2 {font-size: 120%}h3 {font-size: 80%}</style> <h2 class = 'thicker'>xukun</h2><h3>hehe lala</h3>"];
//设置标题
[allTitleStr replaceOccurrencesOfString:@"xukun" withString:titleStr options:NSCaseInsensitiveSearch range:[allTitleStr rangeOfString:@"xukun"]];
//设置时间
[allTitleStr replaceOccurrencesOfString:@"hehe" withString:sourceStr options:NSCaseInsensitiveSearch range:[allTitleStr rangeOfString:@"hehe"]];
//设置数据来源
[allTitleStr replaceOccurrencesOfString:@"lala" withString:ptimeStr options:NSCaseInsensitiveSearch range:[allTitleStr rangeOfString:@"lala"]];
//NSLog(@"字体:%@",allTitleStr);
NSArray *imageArray = [bodyDic objectForKey:@"img"];
if ([imageArray count]==0) {
//NSLog(@"新闻没图片");
NSString * str5 = [allTitleStr stringByAppendingString:bodyStr];
[_webView loadHTMLString:str5 baseURL:[[NSURL URLWithString:_requestUrlString] baseURL]];
}else{
//NSLog(@"新闻内容里面有图片");
NSMutableArray *images = [NSMutableArray arrayWithCapacity:[imageArray count]];
for (NSDictionary *d in imageArray) {
imageInfo *info = [[imageInfo alloc] initWithInfo:d];//kvc
[images addObject:info];
//设置图片宽高
NSRange range = [bodyStr rangeOfString:info.ref];//
NSArray *wh = [info.pixel componentsSeparatedByString:@"*"];
CGFloat width = [[wh objectAtIndex:0] floatValue];
CGFloat rate = (self.view.bounds.size.width-15)/ width;//比例
CGFloat height = [[wh objectAtIndex:1] floatValue];
CGFloat newWidth = width * rate;
CGFloat newHeight = height *rate;
//设置图片间距
NSString *imageStr = [NSString stringWithFormat:@"<img src = 'loading' id = '%@' width = '%.0f' height = '%.0f' hspace='0.0' vspace='5'>",[self replaceUrlSpecialString:info.src],newWidth,newHeight];
//处理过的链接地址
[bodyStr replaceOccurrencesOfString:info.ref withString:imageStr options:NSCaseInsensitiveSearch range:range];
}
[self getImageFromDownloaderOrDiskByImageUrlArray:imageArray];
[bodyStr replaceOccurrencesOfString:@"<p> " withString:@"<p>" options:NSCaseInsensitiveSearch range:[bodyStr rangeOfString:@"<p> "]];
NSString * str5 = [allTitleStr stringByAppendingString:bodyStr];
//NSLog(@"新闻链接数据:%@",str5);
NSString* htmlPath = [[NSBundle mainBundle] pathForResource:@"webViewHtml" ofType:@"html"];
NSMutableString* appHtml = [NSMutableString stringWithContentsOfFile:htmlPath encoding:NSUTF8StringEncoding error:nil];
NSRange range = [appHtml rangeOfString:@"<p>mainnews</p>"];
[appHtml replaceOccurrencesOfString:@"<p>mainnews</p>" withString:str5 options:NSCaseInsensitiveSearch range:range];
NSURL *baseURL = [NSURL fileURLWithPath:htmlPath];
NSLog(@"---------------加载链接:%@ ++++++++++++++++++appHtml:%@",baseURL,appHtml);
[_webView loadHTMLString:appHtml baseURL:baseURL];
//[_webView loadHTMLString:@"http://zam.ccxcc.cc/m.php?m=api&c=s_l&i=50" baseURL:<#(nullable NSURL *)#>]
//NSLog(@"网页加载链接:%@",baseURL);
}
}
}
/*
设置图片 */
- (void)getImageFromDownloaderOrDiskByImageUrlArray:(NSArray *)imageArray {
SDWebImageManager *imageManager = [SDWebImageManager sharedManager];
[[SDWebImageManager sharedManager] setCacheKeyFilter:^(NSURL *url) {
url = [[NSURL alloc] initWithScheme:url.scheme host:url.host path:url.path];
NSString *str = [self replaceUrlSpecialString:[url absoluteString]];
return str;
}];
//沙盒路径
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES);
NSString *filePath = [[paths objectAtIndex:0] stringByAppendingPathComponent:@"com.hackemist.SDWebImageCache.default"];
for (NSDictionary *d in imageArray) {
NSMutableArray *images = [NSMutableArray arrayWithCapacity:[imageArray count]];
imageInfo *info = [[imageInfo alloc] initWithInfo:d];//kvc
[images addObject:info];
NSURL *imageUrl = [NSURL URLWithString:info.src];
if ([imageManager diskImageExistsForURL:imageUrl]) {
NSString *cacheKey = [imageManager cacheKeyForURL:imageUrl];
NSString *imagePaths = [NSString stringWithFormat:@"%@/%@",filePath,[imageManager.imageCache cachedFileNameForKey:cacheKey]];
//NSLog(@"imagePaths === %@",imagePaths);
//调本地方法,加载网络图片
[_bridge send:[NSString stringWithFormat:@"replaceimage%@,%@",[self replaceUrlSpecialString:info.src],imagePaths]];
}else {
[imageManager downloadImageWithURL:imageUrl options:SDWebImageRetryFailed progress:^(NSInteger receivedSize, NSInteger expectedSize) {
} completed:^(UIImage *image, NSError *error, SDImageCacheType cacheType, BOOL finished, NSURL *imageURL) {
if (image && finished) {//如果下载成功
NSString *cacheKey = [imageManager cacheKeyForURL:imageUrl];
NSString *imagePaths = [NSString stringWithFormat:@"%@/%@",filePath,[imageManager.imageCache cachedFileNameForKey:cacheKey]];
//NSLog(@"imagePaths === %@",imagePaths);
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(1.0f * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
[_bridge send:[NSString stringWithFormat:@"replaceimage%@,%@",[self replaceUrlSpecialString:info.src],imagePaths]];
});
}else {
}
}];
}
}
}
- (NSString *)replaceUrlSpecialString:(NSString *)string {
return [string stringByReplacingOccurrencesOfString:@"/"withString:@"_"];
}
代码里面出现的WebViewJavascriptBridge是调JS的一个第三方,文中出现的imageInfo是一个解析返回数据的一个类,可以根据自己后台给的参数自行设置。
还有一个webViewHtml.html文件这里也贴出来
<!DOCTYPE html>
<html>
<body>
<script>
// 这2句是必须写的
function connectWebViewJavascriptBridge(callback) {
if (window.WebViewJavascriptBridge) {
callback(WebViewJavascriptBridge)
} else {
document.addEventListener('WebViewJavascriptBridgeReady', function() {
callback(WebViewJavascriptBridge)
}, false)
}
}
// 这2句是必须写的
connectWebViewJavascriptBridge(function(bridge) {
/* Init your app here */
// 从OC bridge.send 方法过来的 就会调用到这个方法
bridge.init(function(message, responseCallback) {
// alert('Received message: ' + message)
if (message.match("replaceimage")) {
//先截取图片id
var index=message.indexOf(",")
var messagereplace=message.substring(0,index)
//截取到本地图片的路径
var messagepath=message.substring(index+1)
messagereplace=messagereplace.replace(/replaceimage/,"")
element=document.getElementById(messagereplace)
if (element.src.match("loading"))
{
element.src = messagepath
}
}
if (responseCallback) {
responseCallback("send Right back atcha")
}
})
// 从oc通过Handler发送过来的就会调用这个函数
bridge.registerHandler('testJavascriptHandler', function(data, responseCallback) {
var responseData = { 'Javascript Says':'Right back atcha!' }
alert('Received message: ' + data)
if (responseCallback) {
responseCallback(responseData)
}
})
// TODO: 想做点什么在这边(connectWebViewJavascriptBridge函数里面)
//send
var button1 = document.getElementById('button1')
button1.onclick = function() {
var data = 'Hello from JS button'
bridge.send(data, function(responseData) {
})
}
// call handler
var button2 = document.getElementById('button2')
button2.onclick = function() {
// 注意标示要一致
bridge.callHandler('testObjcCallback', {'foo': 'bar'}, function(response) {
})
}
})
</script>
<p>mainnews</p>
</body>
</html>