Я не могу понять, почему память моего приложения РАСПРОСТРАНЯЕТСЯ, как только я начинаю прокручивать представление коллекции с представлениями изображений, заполненными SDWebImage. Если они еще не загружены, то какое-то время все в порядке. Но как только каждое изображение загружено, если я даже ПРИКАСАТЬСЯ к прокрутке, пользовательский интерфейс приложения перестает отвечать на запросы, а объем памяти становится настолько большим (более 1 ГБ), что не только происходит сбой приложения, но и вся ОС падает и перезагружается.
У меня есть таблица с несколькими ячейками, одна из которых имеет коллекцию, которую я могу прокручивать. У меня есть объект данных, который я использую для заполнения всех меток и изображений в collectionViewCell. CellForItem был очень сложным (множество операторов if и switch), поэтому я попытался перенести часть кода оттуда и переместить его в метод didSet свойства, которое я установил в collectionViewCell для хранения объекта данных. Затем я просто установил объект данных в свойство в itemForRow (в фоновом потоке), которое вызвало метод didSet отдельной коллекцииViewCell для заполнения меток и установки изображения с помощью метода sd_set_image. Вот соответствующий код в tableViewCell:
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
print(indexPath.row)
if itemStyle == .Grid {
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: self.resourceCellIdentifier, for: indexPath) as! ResourceCollectionViewCell
cell.delegate = self
cell.tag = indexPath.row
if self.filter == Filter.Collections || self.resourceArray?[indexPath.row].actionContent == nil {
let resource: ActionContentTemplate?
if self.filter == Filter.Collections {
resource = self.collectionResourceArray?[indexPath.row].actionContentTemplate
} else {
resource = self.resourceArray?[indexPath.row].actionContentTemplate
}
DispatchQueue.global(qos: .userInitiated).async {
cell.dataObject = resource
}
return cell
} else {.....
А это метод didSet в самой CollectionViewCell:
var dataObject: ActionContentTemplate? {
didSet {
var cellRow: Int = 0
if self.actionContentTemplate != nil {
....
DispatchQueue.main.async {
cellRow = self.tag
.....
switch self.actionContentTemplate?.contentTypeID?.uintValue {
case ContentTypeVideo.rawValue,
ContentTypeVideoRecording.rawValue,
ContentTypeScreenRecording.rawValue:
.......
case ContentTypeAttachment.rawValue:
let fileType = (self.actionContentTemplate?.contentFileName as NSString?)?.pathExtension.lowercased()
var placeholderImage: UIImage
if fileType == "pdf" {
placeholderImage = UIImage(named: "pdf")!
} else if fileType == "doc" {
placeholderImage = UIImage(named: "doc")!
} else if fileType == "docx" {
placeholderImage = UIImage(named: "doc")!
} else if fileType == "xls" {
placeholderImage = UIImage(named: "xls")!
} else if fileType == "xlsx" {
placeholderImage = UIImage(named: "xls")!
} else if fileType == "ppt" {
placeholderImage = UIImage(named: "ppt")!
} else if fileType == "pptx" {
placeholderImage = UIImage(named: "ppt")!
} else {
placeholderImage = UIImage(named: "plain")!
}
if let urlString = self.actionContentTemplate?.thumbnailURL {
let imageURL = URL(string: urlString)
SDWebImageManager.shared().loadImage(with: imageURL, options: [.continueInBackground, .scaleDownLargeImages], progress: nil) { (image, data, err, cacheType, finished, url) in
DispatchQueue.main.async {
if cellRow == self.tag {
self.activityIndicator?.stopAnimating()
self.imageView.image = image
UIAnimation.fadeTransitionImageView(self.imageView)
}
}
}
}
} else {
DispatchQueue.main.async {
self.activityIndicator?.stopAnimating()
self.imageView.image = placeholderImage
}
}
break
.....
На самом деле я переключился на метод loadImage, так как метод sd_setimage тоже не работал.
SDWebImageManager.shared().loadImage(with: imageURL, options: [.continueInBackground, .scaleDownLargeImages], progress: nil) { (image, data, err, cacheType, finished, url) in
DispatchQueue.main.async {
if cellRow == self.tag {
//IF I COMMENT OUT THESE TWO LINES BELOW THE ISSUES STOP (I think it is only the self.imageView.image = image line that is causing issues)
// self.activityIndicator?.stopAnimating()
// self.imageView.image = image
UIAnimation.fadeTransitionImageView(self.imageView)
}
}
}
Может ли кто-нибудь объяснить мне, почему это происходит и что я могу сделать, чтобы это исправить?
РЕДАКТИРОВАТЬ - забыл добавить эти настройки в делегат приложения на вопрос:
//Settings for image caching
[[SDWebImageDownloader sharedDownloader] setShouldDecompressImages:NO];
[[[SDImageCache sharedImageCache] config] setShouldDecompressImages:NO];
[[[SDImageCache sharedImageCache] config] setShouldCacheImagesInMemory:NO];
[[[SDImageCache sharedImageCache] config] setMaxCacheSize:1024 * 1024 * 100];
[[[SDImageCache sharedImageCache] config] setMaxCacheAge:3600 * 24 * 7];
[[SDImageCache sharedImageCache] setMaxMemoryCost:1024 * 1024 * 15];