iOS - 图形绘制

webp介绍

2016-05-26  本文已影响1585人  ZachChen

图片格式

  1. 传统格式
  1. 新兴格式

移动端图片类型的支持情况

Android 和 iOS 目前的图片编解码架构

静态图片的编码与解码库

  1. JPEG
  1. PNG
  1. WebP

动态图片的编码与解码

在解码动图时,解码器通常采用所谓"画布模式"进行渲染

  1. GIF
  2. APNG
  3. libwebp
    WebP 动图实际上是把多个单帧 WebP 数据简单打包到一个文件内,而并不是由单帧 WebP 扩展而来

WebP 的优势

WebP 的优势体现在它具有更优的图像数据压缩算法,能带来更小的图片体积,而且拥有肉眼识别无差异的图像质量;同时具备了无损和有损的压缩模式、Alpha 透明以及动画的特性,在 JPEG 和 PNG 上的转化效果都非常优秀、稳定和统一

  1. 同等质量但是图片更小
sample.jpg (27.9KB) sample.jpg (Q30% - 10.6KB) Paste_Image.png
+ (UIImage *)sd_imageWithData:(NSData *)data {
    if (!data) {
        return nil;
    }
    
    UIImage *image;
    NSString *imageContentType = [NSData sd_contentTypeForImageData:data];
    if ([imageContentType isEqualToString:@"image/gif"]) {
        image = [UIImage sd_animatedGIFWithData:data];
    }
#ifdef SD_WEBP
    else if ([imageContentType isEqualToString:@"image/webp"])
    {
        image = [UIImage sd_imageWithWebPData:data];
    }
#endif
    else {
        image = [[UIImage alloc] initWithData:data];
        UIImageOrientation orientation = [self sd_imageOrientationFromImageData:data];
        if (orientation != UIImageOrientationUp) {
            image = [UIImage imageWithCGImage:image.CGImage
                                        scale:image.scale
                                  orientation:orientation];
        }
    }

    return image;
}
  1. 在webView中使用webP

A. 在网页加载出后截取到 HTML 及内部的 JS 后,调用 JS 预先准备好的方法获取需要转码的 webP 格式图片下载地址(其实一个一个的遍历也行).
B. 在App 本地开启线程下载图片,下载完成后,将图片转码由 webP—> png—>Base64
B1. 在App 本地开启线程下载图片,下载完成后,将图片转码由 webP—> png->file 生成自定义URL 例如:yxy://image/xxx.png
C. 将 Base64及原图片下载地址一一对应调用 JS 准备好的方法进行替换
C1. 将 自定义URL及原图片下载地址一一对应调用 JS 准备好的方法进行替换
D. 将下载后的图片进行缓存,并进行管理

NSURLProtocol是 iOS里面的URL Loading System的一部分

  • 可以拦截UIWebView,基于系统的NSUIConnection或者NSUISession进行封装的网络请求。
  • 忽略网络请求,直接返回自定义的Response
  • 修改request(请求地址,认证信息等等)
  • 返回数据拦截
- (void)startLoading
{
    // 标示改request已经处理过了,防止无限循环
    NSMutableURLRequest *mutableReqeust = [[self request] mutableCopy];
    
    if ([[mutableReqeust.URL.absoluteString lowercaseString] hasPrefix:YXYOpenConnectBaseUrl] ||
        [[mutableReqeust.URL.absoluteString lowercaseString] hasPrefix:YXYOpenConnectDevBaseUrl]) {
        mutableReqeust = [NSURLProtocolCustom changeRequset:mutableReqeust];
    }
    
    [NSURLProtocol setProperty:@YES forKey:YXYURLProtocolHandledKey inRequest:mutableReqeust];
    
    if ([mutableReqeust.URL.scheme caseInsensitiveCompare:@"yxy"] == NSOrderedSame) {
        // 处理图片
        NSString *tempPath = NSTemporaryDirectory();
        NSString *imageTempPath = [NSString stringWithFormat:@"%@%@", tempPath, self.request.URL.host];
        NSData *data = [NSData dataWithContentsOfFile:imageTempPath];
        NSUInteger length = [data length];
        NSHTTPURLResponse *response = [[NSHTTPURLResponse alloc] initWithURL:[self request].URL statusCode:200 HTTPVersion:@"HTTP/1.1" headerFields:@{@"Access-Control-Allow-Origin" : @"*", @"Content-Type" : @"image/png", @"Content-Length" : [NSString stringWithFormat:@"%lu", (unsigned long)length]}];
        
        [[self client] URLProtocol:self didReceiveResponse:response cacheStoragePolicy:NSURLCacheStorageAllowed];
        [[self client] URLProtocol:self didLoadData:data];
        [[self client] URLProtocolDidFinishLoading:self];
    } else {
        if ([NSURLProtocolCustom isOssImageUrl:mutableReqeust]) {
            NSString *urlString = [mutableReqeust.URL absoluteString];
            NSURL *url = [NSURL URLWithString:[urlString stringByAppendingString:@"@1o.webp"]];
            @weakify(self);
            [[SDWebImageManager sharedManager] downloadImageWithURL:url options:SDWebImageLowPriority|SDWebImageRetryFailed progress:nil completed:^(UIImage *image, NSError *error, SDImageCacheType cacheType, BOOL finished, NSURL *imageURL) {
                @strongify(self);
                if (!error) {
                    if (image) {
                        NSData *jpgData = UIImageJPEGRepresentation(image, 1.0f);
                        NSUInteger length = [jpgData length];
                        NSHTTPURLResponse *response = [[NSHTTPURLResponse alloc] initWithURL:mutableReqeust.URL statusCode:200 HTTPVersion:@"HTTP/1.1" headerFields:@{@"Content-Type" : @"image/jpg", @"Content-Length" : [NSString stringWithFormat:@"%lu", (unsigned long)length]}];
                        [[self client] URLProtocol:self didReceiveResponse:response cacheStoragePolicy:NSURLCacheStorageAllowed];
                        [[self client] URLProtocol:self didLoadData:jpgData];
                        [[self client] URLProtocolDidFinishLoading:self];
                    }
                } else {
                    [self.client URLProtocol:self didFailWithError:error];
                }
            }];
        } else {
            // 处理第三方统一接入
            self.connection = [NSURLConnection connectionWithRequest:mutableReqeust delegate:self];
        }
    }
}

上一篇下一篇

猜你喜欢

热点阅读