需求:在APP啟動時加載一段動畫
我們所知的實現(xiàn)方式
- 加載一段視頻實現(xiàn)
- 使用GIF格式的動畫(類似多張PNG用UIImageView做動畫效果)
- .......
關于使用SDWebImage加載GIF格式動畫的實現(xiàn)
-
原理
** 使用UIImageView加載多張PNG,在一定時間內(nèi)按幀數(shù)顯示即可 *
此處附上3張圖表示使用動畫前后和優(yōu)化之后的內(nèi)存占比(此處截圖為模擬器Run):
未加載動畫.png

加載動畫之后.png

優(yōu)化動畫加載之后.png
** 是不是發(fā)現(xiàn)1.46G被嚇壞了。。諾諾的裝個逼,此時貌似只有我的手機可以跑(iPhone 7 Plus) **
- 優(yōu)化過程
- 首先我們肯定是先發(fā)現(xiàn)這個問題,使用真機運行用Instruments中的Allocations(內(nèi)存分配檢測)效果如圖:

內(nèi)存分配查看.png

內(nèi)存來源.png
- 通過上面的圖來分析,SDWebImage的源碼(初始化方法)
+ (UIImage *)sd_animatedGIFNamed:(NSString *)name;
+ (UIImage *)sd_animatedGIFWithData:(NSData *)data;
- (UIImage *)sd_animatedImageByScalingAndCroppingToSize:(CGSize)size;
** 此處省略....看重點唯一注釋處---數(shù)組沒有得到釋放 **
+ (UIImage *)sd_animatedGIFWithData:(NSData *)data {
if (!data) {
return nil;
}
CGImageSourceRef source = CGImageSourceCreateWithData((__bridge CFDataRef)data, NULL);
size_t count = CGImageSourceGetCount(source);
UIImage *animatedImage;
if (count <= 1) {
animatedImage = [[UIImage alloc] initWithData:data];
}
else {
NSMutableArray *images = [NSMutableArray array];
NSTimeInterval duration = 0.0f;
for (size_t i = 0; i < count; i++) {
CGImageRef image = CGImageSourceCreateImageAtIndex(source, i, NULL);
if (!image) {
continue;
}
duration += [self sd_frameDurationAtIndex:i source:source];
//數(shù)組沒有得到釋放
[images addObject:[UIImage imageWithCGImage:image scale:[UIScreen mainScreen].scale orientation:UIImageOrientationUp]];
CGImageRelease(image);
}
if (!duration) {
duration = (1.0f / 10.0f) * count;
}
animatedImage = [UIImage animatedImageWithImages:images duration:duration];
}
CFRelease(source);
return animatedImage;
}
大約計算375張的GIF圖片*4M 約等于1.4G,得到我們的猜測是正確的
解決方案
- 采用YY_WebImage框架:https://github.com/ibireme/YYWebImage
- 使用SDWebImage:https://github.com/rs/SDWebImage;
在我們加載動畫之前需要設置
{
SDImageCache *canche = [SDImageCache sharedImageCache];
SDImageCacheOldShouldDecompressImages = canche.shouldDecompressImages;
canche.shouldDecompressImages = NO;
SDWebImageDownloader *downloder = [SDWebImageDownloader sharedDownloader];
SDImagedownloderOldShouldDecompressImages = downloder.shouldDecompressImages;
downloder.shouldDecompressImages = NO;
}
在控制器dealloc中
{
SDImageCache *canche = [SDImageCache sharedImageCache];
canche.shouldDecompressImages = SDImageCacheOldShouldDecompressImages;
SDWebImageDownloader *downloder = [SDWebImageDownloader sharedDownloader];
downloder.shouldDecompressImages = SDImagedownloderOldShouldDecompressImages;
[[SDImageCache sharedImageCache] clearMemory];
[[SDImageCache sharedImageCache] clearDisk];
[[SDImageCache sharedImageCache] cleanDisk];
[[SDImageCache sharedImageCache] setValue:nil forKey:@"memCache"];
}
- 使用FLAnimatedImage:https://github.com/Flipboard/FLAnimatedImage
附上學習文章給大家(下文出自其他作者)
- 使用SDWebImage加載大量圖片后造成內(nèi)存泄露的解決辦法:http://www.cnblogs.com/ziip/p/4664234.html
- SDWebImage加載.gif 內(nèi)存狂飆問題:http://www.itdecent.cn/p/6c71f0ca96f6
- SDWebImage 加載顯示 GIF 與性能問題:http://www.cnblogs.com/silence-cnblogs/p/6682867.html
- Github的描述:https://github.com/rs/SDWebImage/issues/538
- 以上文章如需其他注明,請聯(lián)系我,謝謝。
** 文章寫得不是很好,不過希望大家能有所獲,謝謝大家的支持?。?! **
