iOS載入圖片不顯示的問題

來源:互聯網
上載者:User

標籤:setimage   三方   eid   pre   字串   false   count   位元影像   ref   

一、具體問題  

  開發的過程中,發現某個介面部分圖片的顯示出現了問題只顯示佔位圖片,取出圖片的url在瀏覽器卻是能開啟的,各種嘗試甚至找同行的朋友幫忙在他們項目裡展示都會存在問題,最終發現通過第三方架構SDWebImage或者YYWebImage下載帶有逗號的url圖片連結都會下載失敗,在下載方法完成的回調block裡面列印資訊如下:

Error Domain=NSURLErrorDomain Code=403 "(null)"

  現列舉兩個不能正常展示的圖片url:

http://img1.imgtn.bdimg.com/it/u=3044191397,2911599132&fm=27&gp=0.jpghttp://img2.imgtn.bdimg.com/it/u=3509004173,840437551&fm=27&gp=0.jpg

  有興趣的小夥伴可以拿到自己的項目裡試試

二、問題原因

  網上有小夥伴提出是因為缺少User-Agent使用者代理程式導致的。只有設定了使用者代理程式,才能訪問到這張帶有逗號的url圖片。至於這個使用者代理程式的格式,只要有值或者約定的特定格式字串都可以。

三、具體解決

1.第三方架構YYWebImage

  找到YYWebImageManager.m檔案,定位到設定http要求標頭的屬性即_headers的地方,加入一個User-Agent的索引值對,具體改動可以看下面的方法

- (instancetype)initWithCache:(YYImageCache *)cache queue:(NSOperationQueue *)queue{    self = [super init];    if (!self) return nil;    _cache = cache;    _queue = queue;    _timeout = 15.0;        NSString *userAgent = @"";    userAgent = [NSString stringWithFormat:@"%@/%@ (%@; iOS %@; Scale/%0.2f)", [[[NSBundle mainBundle] infoDictionary] objectForKey:(__bridge NSString *)kCFBundleExecutableKey] ?: [[[NSBundle mainBundle] infoDictionary] objectForKey:(__bridge NSString *)kCFBundleIdentifierKey], [[[NSBundle mainBundle] infoDictionary] objectForKey:@"CFBundleShortVersionString"] ?: [[[NSBundle mainBundle] infoDictionary] objectForKey:(__bridge NSString *)kCFBundleVersionKey], [[UIDevice currentDevice] model], [[UIDevice currentDevice] systemVersion], [[UIScreen mainScreen] scale]];        if (userAgent) {        if (![userAgent canBeConvertedToEncoding:NSASCIIStringEncoding]) {            NSMutableString *mutableUserAgent = [userAgent mutableCopy];            if (CFStringTransform((__bridge CFMutableStringRef)(mutableUserAgent), NULL, (__bridge CFStringRef)@"Any-Latin; Latin-ASCII; [:^ASCII:] Remove", false)) {                userAgent = mutableUserAgent;            }        }    }    //帶有逗號的圖片url不顯示的問題,重要的是設定代理才能解決    if (YYImageWebPAvailable()) {        _headers = @{ @"Accept" : @"image/webp,image/*;q=0.8", @"User-Agent" : userAgent};    } else {        _headers = @{ @"Accept" : @"image/*;q=0.8", @"User-Agent" : userAgent};    }    return self;}

2.第三方架構SDWebImage

  找到SDWebImageDownloader.m檔案,也是定位到設定http要求標頭的屬性即_HTTPHeaders的地方,加入一個User-Agent的索引值對,具體改動可以看下面的方法

- (id)init {    if ((self = [super init])) {        _operationClass = [SDWebImageDownloaderOperation class];        _shouldDecompressImages = YES;        _executionOrder = SDWebImageDownloaderFIFOExecutionOrder;        _downloadQueue = [NSOperationQueue new];        _downloadQueue.maxConcurrentOperationCount = 6;        _URLCallbacks = [NSMutableDictionary new];        /***********************/        NSString *userAgent = @"";        userAgent = [NSString stringWithFormat:@"%@/%@ (%@; iOS %@; Scale/%0.2f)", [[[NSBundle mainBundle] infoDictionary] objectForKey:(__bridge NSString *)kCFBundleExecutableKey] ?: [[[NSBundle mainBundle] infoDictionary] objectForKey:(__bridge NSString *)kCFBundleIdentifierKey], [[[NSBundle mainBundle] infoDictionary] objectForKey:@"CFBundleShortVersionString"] ?: [[[NSBundle mainBundle] infoDictionary] objectForKey:(__bridge NSString *)kCFBundleVersionKey], [[UIDevice currentDevice] model], [[UIDevice currentDevice] systemVersion], [[UIScreen mainScreen] scale]];                if (userAgent) {            if (![userAgent canBeConvertedToEncoding:NSASCIIStringEncoding]) {                NSMutableString *mutableUserAgent = [userAgent mutableCopy];                if (CFStringTransform((__bridge CFMutableStringRef)(mutableUserAgent), NULL, (__bridge CFStringRef)@"Any-Latin; Latin-ASCII; [:^ASCII:] Remove", false)) {                    userAgent = mutableUserAgent;                }            }        }        /***********************/#ifdef SD_WEBP        _HTTPHeaders = [@{@"Accept": @"image/webp,image/*;q=0.8", userAgent : @"User-Agent"} mutableCopy];#else        _HTTPHeaders = [@{@"Accept": @"image/*;q=0.8", userAgent : @"User-Agent"} mutableCopy];#endif        _barrierQueue = dispatch_queue_create("com.hackemist.SDWebImageDownloaderBarrierQueue", DISPATCH_QUEUE_CONCURRENT);        _downloadTimeout = 15.0;    }    return self;}

或者是直接在UIImageView+WebCache.m檔案中,在統一下載圖片入口最前面添加如下代碼

- (void)sd_setImageWithURL:(NSURL *)url placeholderImage:(UIImage *)placeholder options:(SDWebImageOptions)options progress:(SDWebImageDownloaderProgressBlock)progressBlock completed:(SDWebImageCompletionBlock)completedBlock {    /***********************/    NSString *userAgent = @"";    userAgent = [NSString stringWithFormat:@"%@/%@ (%@; iOS %@; Scale/%0.2f)", [[[NSBundle mainBundle] infoDictionary] objectForKey:(__bridge NSString *)kCFBundleExecutableKey] ?: [[[NSBundle mainBundle] infoDictionary] objectForKey:(__bridge NSString *)kCFBundleIdentifierKey], [[[NSBundle mainBundle] infoDictionary] objectForKey:@"CFBundleShortVersionString"] ?: [[[NSBundle mainBundle] infoDictionary] objectForKey:(__bridge NSString *)kCFBundleVersionKey], [[UIDevice currentDevice] model], [[UIDevice currentDevice] systemVersion], [[UIScreen mainScreen] scale]];        if (userAgent) {        if (![userAgent canBeConvertedToEncoding:NSASCIIStringEncoding]) {            NSMutableString *mutableUserAgent = [userAgent mutableCopy];            if (CFStringTransform((__bridge CFMutableStringRef)(mutableUserAgent), NULL, (__bridge CFStringRef)@"Any-Latin; Latin-ASCII; [:^ASCII:] Remove", false)) {                userAgent = mutableUserAgent;            }        }                [[SDWebImageDownloader sharedDownloader] setValue:userAgent forHTTPHeaderField:@"User-Agent"];    }    /***********************/    [self sd_cancelCurrentImageLoad];        ........省略原源碼}

3.其他第三方下載圖片的架構

  直接全域搜尋字串"Accept",因為雖然缺少設定User-Agent使用者代理程式,但是http要求標頭一般都會有設定"Accept",所以定位後,直接再加一個User-Agent的索引值對就可以了

 

 

iOS載入圖片不顯示的問題

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.