我想,以填补一个UITableView会的图像,拉伸到全宽,并自动设置其高度。我试过设置estimatedHeightForRowAtIndexPath
和heightForRowAt
到UITableView.automaticDimension
,但他们似乎显示了非常小的。
我CustomTableViewCell与设置为0在各方面的约束一个UIImage。
我开始认为这可能是是与main.storyboard是含一个UITableView,其设置为视图控制器的数据源和委托一个的viewController。如若main.storyboard反而是一个UITableViewController?
谁能告诉我什么,我做错了什么?
这是它目前的样子:
class ViewController: UIViewController {
@IBOutlet weak var tableView: UITableView!
private var imageUrls:[String] = ["https://via.placeholder.com/200","https://via.placeholder.com/400","https://via.placeholder.com/600"]
override func viewDidLoad() {
super.viewDidLoad()
tableView.estimatedRowHeight = 320
tableView.rowHeight = UITableView.automaticDimension
let textFieldCell = UINib(nibName: "CustomTableViewCell",
bundle: nil)
tableView.register(textFieldCell, forCellReuseIdentifier: "CustomTableViewCell")
}
}
extension ViewController: UITableViewDataSource {
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return imageUrls.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
if let cell = tableView.dequeueReusableCell(withIdentifier: "CustomTableViewCell") as? CustomTableViewCell {
let imageUrl = imageUrls[indexPath.row]
cell.messageImage.sd_setImage(with: URL(string: imageUrl), placeholderImage: nil , options: SDWebImageOptions(rawValue: 0))
return cell
}
return UITableViewCell()
}
func tableView(_ tableView: UITableView, estimatedHeightForRowAtIndexPath indexPath: IndexPath) -> CGFloat {
return 320
}
func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
return UITableView.automaticDimension
}
}
EDIT: here is what it looks like when then image content mode is set to Aspect Fill.
I've also just noticed a warning:
[Warning] Warning once only: Detected a case where constraints ambiguously suggest a height of zero for a table view cell's content view. We're considering the collapse unintentional and using standard height instead.
The problem is that, there is no way you can update the height of a cell after it was created and drawn onto the screen. But what you can do is when you download an image, you notify the TableView to reload that specific row to which the image belongs to. This will call the heightForRowAtIndexPath
, but you will know the exact height of the image now.
Define an array where you will store the fetched images in your ViewController
.
private var images: [UIImage] = []
Now when creating the cell you will either pass that image to the cell, or you will lunch a download task with a callback that will notify the TableView to reload a specific row.
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "YourCell") as? YourCell
if images.count > indexPath.row {
// We have the image, load it
cell?.setupContentWith(image: images[indexPath.row])
} else {
// We do not have the image, download it
cell?.setupContent(url: URL(string: imageUrls[indexPath.row]), completion: { [weak self] image in
self?.images.append(image)
tableView.reloadRows(at: [indexPath], with: .none)
})
}
return cell ?? UITableViewCell()
}
The functions inside the TableViewCell could look something like this:
private func setupContent(url: URL?, completion: @escaping (UIImage) -> Void) {
guard let url = url else { return }
yourImageView?.downloaded(from: url, completion: completion)
}
private func setupContentWith(image: UIImage) {
yourImageView?.image = image
}
最后,当你不具备的图像,你可以返回一些默认的高度,你认为是恰当的。而如果你有图像,返回它的高度。
func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
if images.count > indexPath.row {
// We have the image, return it's height
return images[indexPath.row].size.height
} else {
// We do not have the image, return some default height
return 50 // Or some height you find approriate
}
}
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句