iOS 加載webView進(jìn)度條

webViewLoading.gif

簡介##

為了項目的敏捷性和簡單性,現(xiàn)在的app常常會嵌入不少的H5頁面,而如何優(yōu)雅的顯示這些web頁面呢,我這里參照微信顯示web頁面的方式,做了一個導(dǎo)航欄下的加載進(jìn)度條.因為項目最低支持iOS7,所以不能使用WKWebView來加載網(wǎng)頁,只能使用 UIWebView,查看 UIWebView的API可以發(fā)現(xiàn),并沒有代理或是通知告訴我們webView加載了多少,所以這個進(jìn)度條我決定用虛擬的方式來做,就是假裝知道加載了多少.

加載WebView的控制器WYWebController

@interface WYWebController : UIViewController

@property (nonatomic, copy) NSString *url;

@end


#import "WLWebController.h"
#import "WLWebProgressLayer.h"
#import "UIView+Frame.h"

@interface WLWebController ()<UIWebViewDelegate>

@end

@implementation WLWebController
{
    UIWebView *_webView;
    
    WLWebProgressLayer *_progressLayer; ///< 網(wǎng)頁加載進(jìn)度條
}

- (void)viewDidLoad {
    [super viewDidLoad];

    self.view.backgroundColor = [UIColor whiteColor];
    [self setupUI];
}

- (void)setupUI {
    _webView = [[UIWebView alloc] initWithFrame:self.view.bounds];
    _webView.delegate = self;
    NSURLRequest *request = [NSURLRequest requestWithURL:[NSURL URLWithString:self.url]];
    [_webView loadRequest:request];
    
    _webView.backgroundColor = [UIColor whiteColor];
    
    _progressLayer = [WLWebProgressLayer new];
    _progressLayer.frame = CGRectMake(0, 42, SCREEN_WIDTH, 2);
    
    [self.navigationController.navigationBar.layer addSublayer:_progressLayer];
    [self.view addSubview:_webView];
}

#pragma mark - UIWebViewDelegate
/// 網(wǎng)頁開始加載
- (void)webViewDidStartLoad:(UIWebView *)webView {
    [_progressLayer startLoad];
}

/// 網(wǎng)頁完成加載
- (void)webViewDidFinishLoad:(UIWebView *)webView {
    [_progressLayer finishedLoad];

// 獲取h5的標(biāo)題
    self.title = [webView stringByEvaluatingJavaScriptFromString:@"document.title"];
    
}

/// 網(wǎng)頁加載失敗
- (void)webView:(UIWebView *)webView didFailLoadWithError:(NSError *)error {
    [_progressLayer finishedLoad];
}

- (void)dealloc {
    
    [_progressLayer closeTimer];
    [_progressLayer removeFromSuperlayer];
    _progressLayer = nil;
    NSLog(@"i am dealloc");
}

@end

進(jìn)度條WYWebProgressLayer.h

#define SCREEN_WIDTH [UIScreen mainScreen].bounds.size.width

@interface WYWebProgressLayer : CAShapeLayer

- (void)finishedLoad;
- (void)startLoad;

- (void)closeTimer;

@end

WYWebProgressLayer.m這個類主要繼承自CAShapeLayer,這里我主要想要使用CAShaperLayerstrokeStart[默認(rèn)0]和strokeEnd[默認(rèn)1]這兩個屬性來對進(jìn)度條進(jìn)行渲染,使用定時器更改strokeEnd的值使其看起來就像在一點一點的加載一樣.

#import "WYWebProgressLayer.h"
#import "NSTimer+addition.h"

static NSTimeInterval const kFastTimeInterval = 0.003;

@implementation WYWebProgressLayer {
   CAShapeLayer *_layer;
   
   NSTimer *_timer;
   CGFloat _plusWidth; ///< 增加點
}

- (instancetype)init {
   if (self = [super init]) {
       [self initialize];
   }
   return self;
}

- (void)initialize {
   self.lineWidth = 2;
   self.strokeColor = [UIColor greenColor].CGColor;
   
   _timer = [NSTimer scheduledTimerWithTimeInterval:kFastTimeInterval target:self selector:@selector(pathChanged:) userInfo:nil repeats:YES];
   [_timer pause];
   
   UIBezierPath *path = [UIBezierPath bezierPath];
   [path moveToPoint:CGPointMake(0, 2)];
   [path addLineToPoint:CGPointMake(SCREEN_WIDTH, 2)];
   
   self.path = path.CGPath;
   self.strokeEnd = 0;
   _plusWidth = 0.01;
}

- (void)pathChanged:(NSTimer *)timer {
   self.strokeEnd += _plusWidth;
   
   if (self.strokeEnd > 0.8) {
       _plusWidth = 0.002;
   }
}

- (void)startLoad {
   [_timer resumeWithTimeInterval:kFastTimeInterval];
}

- (void)finishedLoad {
   [self closeTimer];
   
   self.strokeEnd = 1.0;
   dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.25 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
       self.hidden = YES;
       [self removeFromSuperlayer];
   });
}

- (void)dealloc {
//    NSLog(@"progressView dealloc");
   [self closeTimer];
}

#pragma mark - private
- (void)closeTimer {
   [_timer invalidate];
   _timer = nil; 
}

Demo:https://github.com/wangyansnow/WYWebViewDemo

如何放到項目中用##

只需要下載demo,然后把demo中的整個web文件夾拖入到項目中,使用方式例:

WYWebController *webVC = [WYWebController new];
webVC.url = @"https://www.baidu.com";
[self.navigationController pushViewController:webVC animated:YES];
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

推薦閱讀更多精彩內(nèi)容