Gunakan metode ini untuk menyetel lebar tinggi sel khusus.
Pastikan untuk menambahkan protokol ini
UICollectionViewDelegate
UICollectionViewDataSource
UICollectionViewDelegateFlowLayout
Jika Anda menggunakan cepat 5 atau Xcode 11 dan kemudian Anda perlu set Estimate Size
untuk none
menggunakan storyboard untuk membuatnya bekerja dengan baik. Jika Anda tidak mengatur bahwa kode di bawah ini tidak akan bekerja seperti yang diharapkan.
Swift 4 atau Nanti
extension YourViewController: UICollectionViewDelegate {
}
extension YourViewController: UICollectionViewDataSource {
}
extension YourViewController: UICollectionViewDelegateFlowLayout {
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
return CGSize(width: screenWidth, height: screenWidth)
}
}
Objective-C
@interface YourViewController : UIViewController<UICollectionViewDelegate,UICollectionViewDataSource,UICollectionViewDelegateFlowLayout>
- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath
{
return CGSizeMake(CGRectGetWidth(collectionView.frame), (CGRectGetHeight(collectionView.frame)));
}
Pastikan untuk menambahkan protokol
UICollectionViewDelegateFlowLayout
diclass
deklarasi Andaclass MyCollectionViewController: UICollectionViewController, UICollectionViewDelegateFlowLayout { //MARK: - UICollectionViewDelegateFlowLayout func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize { return CGSize(width: 100.0, height: 100.0) } }
sumber
Jika seseorang menggunakan storyboard dan menimpa UICollectionViewDelegateFlowLayout maka di swift 5 dan Xcode 11 juga atur Estimate size menjadi None
sumber
UICollectionViewFlowLayout
tampaknya defaultestimatedItemSize
untukUICollectionViewFlowLayout.automaticSize
saat menggunakan IB meskipun dokumentasi mengatakan itu harus default keCGSizeZero
. Seperti yang dinyatakan Apple,automaticSize
"mengaktifkan sel ukuran sendiri untuk tampilan koleksi Anda." Itu sebabnya perubahan ukuran lain di IB tidak melakukan apa-apa.Akhirnya mendapat jawabannya. Anda harus memperpanjang
UICollectionViewDelegateFlowLayout
Ini harus bekerja dengan jawaban di atas.
sumber
Anda memiliki 2 cara untuk mengubah ukuran CollectionView.
Cara pertama -> tambahkan protokol ini UICollectionViewDelegateFlowLayout
untuk Dalam kasus saya, saya ingin membagi sel menjadi 3 bagian dalam satu baris. Saya melakukan kode ini di bawah
extension ViewController: UICollectionViewDelegate, UICollectionViewDataSource ,UICollectionViewDelegateFlowLayout{ func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize { // In this function is the code you must implement to your code project if you want to change size of Collection view let width = (view.frame.width-20)/3 return CGSize(width: width, height: width) } func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int { return collectionData.count } func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell { let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "CollectionViewCell", for: indexPath) if let label = cell.viewWithTag(100) as? UILabel { label.text = collectionData[indexPath.row] } return cell } }
Cara kedua -> Anda tidak perlu menambahkan UICollectionViewDelegateFlowLayout tetapi Anda harus menulis beberapa kode dalam fungsi viewDidload sebagai gantinya seperti kode di bawah ini
class ViewController: UIViewController { @IBOutlet weak var collectionView1: UICollectionView! var collectionData = ["1.", "2.", "3.", "4.", "5.", "6.", "7.", "8.", "9.", "10.", "11.", "12."] override func viewDidLoad() { super.viewDidLoad() let width = (view.frame.width-20)/3 let layout = collectionView.collectionViewLayout as! UICollectionViewFlowLayout layout.itemSize = CGSize(width: width, height: width) } }
extension ViewController: UICollectionViewDelegate, UICollectionViewDataSource { func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int { return collectionData.count } func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell { let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "CollectionViewCell", for: indexPath) if let label = cell.viewWithTag(100) as? UILabel { label.text = collectionData[indexPath.row] } return cell } }
Apapun yang Anda tulis kode sebagai cara pertama atau kedua Anda akan mendapatkan hasil yang sama seperti di atas. Saya menulisnya. Itu berhasil untuk saya
sumber
Rasio ukuran menurut ukuran iPhone:
Inilah yang dapat Anda lakukan untuk memiliki lebar dan tinggi yang berbeda untuk sel sehubungan dengan ukuran iPhone:
func collectionView(collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAtIndexPath indexPath: NSIndexPath) -> CGSize { let width = (self.view.frame.size.width - 12 * 3) / 3 //some width let height = width * 1.5 //ratio return CGSize(width: width, height: height) }
Dan mungkin Anda juga harus menonaktifkan batasan AutoLayout pada sel agar jawaban ini berfungsi.
sumber
Tampilan koleksi memiliki objek tata letak . Dalam kasus Anda, ini mungkin adalah tata letak aliran ( UICollectionViewFlowLayout ). Setel
itemSize
properti tata letak aliran .sumber
di Swift3 dan Swift4 Anda bisa mengubah ukuran sel dengan menambahkan UICollectionViewDelegateFlowLayout dan mengimplementasikannya seperti ini:
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize { return CGSize(width: 100, height: 100) }
atau jika membuat UICollectionView secara terprogram, Anda dapat melakukannya seperti ini:
let layout = UICollectionViewFlowLayout() layout.scrollDirection = .horizontal //this is for direction layout.minimumInteritemSpacing = 0 // this is for spacing between cells layout.itemSize = CGSize(width: view.frame.width, height: view.frame.height) //this is for cell size let collectionView = UICollectionView(frame: self.view.bounds, collectionViewLayout: layout)
sumber
swift4 swift 4 ios collection view collectionview contoh xcode contoh kode kerja terbaru
Tambahkan ini di bagian Delegasi di atas
UICollectionViewDelegateFlowLayout
dan gunakan fungsi ini
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize { let width = (self.view.frame.size.width - 20) / 3 //some width let height = width * 1.5 //ratio return CGSize(width: width, height: height) }
///// contoh kode lengkap
buat pada tampilan koleksi dan sel tampilan koleksi di storyboard memberikan referensi ke koleksi sebagai
@IBOutlet weak var cvContent: UICollectionView!
tempel ini di View controller
import UIKit class ViewController: UIViewController, UICollectionViewDelegate, UICollectionViewDataSource, UICollectionViewDelegateFlowLayout { var arrVeg = [String]() var arrFruits = [String]() var arrCurrent = [String]() @IBOutlet weak var cvContent: UICollectionView! override func viewDidLoad() { super.viewDidLoad() arrVeg = ["Carrot","Potato", "Tomato","Carrot","Potato", "Tomato","Carrot","Potato", "Tomato","Carrot","Potato", "Tomato"] arrVeg = ["Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange","Mango","Papaya","Orange"] arrCurrent = arrVeg } //MARK: - CollectionView func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize { let width = (self.view.frame.size.width - 20) / 3 //some width let height = width * 1.5 //ratio return CGSize(width: width, height: height) } func numberOfSections(in collectionView: UICollectionView) -> Int { return 1 } func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int { return arrCurrent.count } func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell { let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "cell", for: indexPath) as! ContentCollectionViewCell cell.backgroundColor = UIColor.green return cell } }
sumber
Coba metode di bawah ini
func collectionView(collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAtIndexPath indexPath: NSIndexPath) -> CGSize { return CGSize(width: 100.0, height: 100.0) }
sumber
Swift 5 Secara terprogram
lazy var collectionView: UICollectionView = { let layout = UICollectionViewFlowLayout() layout.scrollDirection = .horizontal //Provide Width and Height According to your need let cellWidth = UIScreen.main.bounds.width / 10 let cellHeight = UIScreen.main.bounds.height / 10 layout.itemSize = CGSize(width: cellWidth, height: cellHeight) //You can also provide estimated Height and Width layout.estimatedItemSize = CGSize(width: cellWidth, height: cellHeight) //For Setting the Spacing between cells layout.minimumInteritemSpacing = 0 layout.minimumLineSpacing = 0 return UICollectionView(frame: self.view.frame, collectionViewLayout: layout) }()
sumber
**Swift 5** To make this work you have to do the following. Add these protocols - UICollectionViewDelegate - UICollectionViewDataSource - UICollectionViewDelegateFlowLayout Your code will then look like this extension YourViewController: UICollectionViewDelegate { //Write Delegate Code Here } extension YourViewController: UICollectionViewDataSource { //Write DataSource Code Here } extension YourViewController: UICollectionViewDelegateFlowLayout { func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize { return CGSize(width: screenWidth, height: screenWidth) } } Now the final and crucial step to see this take effect is to go to your viedDidLoad function inside your Viewcontroller. override func viewDidLoad() { super.viewDidLoad() collection.dataSource = self // Add this collection.delegate = self // Add this // Do any additional setup after loading the view. } Without telling your view which class the delegate is it won't work.
sumber
#Cara yang benar-benar sederhana:
class YourCollection: UIViewController, UICollectionViewDelegate, UICollectionViewDataSource {
#Anda harus menambahkan "UICollectionViewDelegateFlowLayout" atau, tidak ada pelengkapan otomatis:
class YourCollection: UIViewController, UICollectionViewDelegate, UICollectionViewDataSource, UICollectionViewDelegateFlowLayout {
#Type "sizeForItemAt ...". Kamu sudah selesai!
class YourCollection: UIViewController, UICollectionViewDelegate, UICollectionViewDataSource, UICollectionViewDelegateFlowLayout { func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize { return CGSize(width: 37, height: 63) }
Itu dia.
Contoh, jika Anda ingin "setiap sel mengisi seluruh tampilan koleksi":
guard let b = view.superview?.bounds else { .. } return CGSize(width: b.width, height: b.height)
sumber
Cara lain adalah dengan menyetel nilai secara langsung di tata letak aliran
let layout = collectionView.collectionViewLayout as! UICollectionViewFlowLayout layout.itemSize = CGSize(width: size, height: size)
sumber
Jadi, Anda perlu menyetel dari storyboard untuk atribut untuk collectionView di bagian sel, memperkirakan Ukuran ke tidak ada, dan di ViewController Anda perlu memiliki metode delegasi untuk mengimplementasikan metode ini:
optional func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize
sumber
Coba gunakan metode UICollectionViewDelegateFlowLayout. Di Xcode 11 atau lebih baru, Anda perlu mengatur Perkiraan Ukuran ke tidak ada dari storyboard.
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize { let padding: CGFloat = 170 let collectionViewSize = advertCollectionView.frame.size.width - padding return CGSize(width: collectionViewSize/2, height: collectionViewSize/2) }
sumber
Cara sederhana:
Jika Anda hanya membutuhkan ukuran tetap sederhana :
class SizedCollectionView: UIICollectionView { override func common() { super.common() let l = UICollectionViewFlowLayout() l.itemSize = CGSize(width: 42, height: 42) collectionViewLayout = l } }
Itu saja yang ada untuk itu.
Di storyboard, ubah saja kelas dari UICollectionView ke SizedCollectionView.
Tapi !!!
Perhatikan kelas dasar ada "UI 'I' CollectionView". 'I' untuk Penginisialisasi.
Tidak mudah menambahkan penginisialisasi ke tampilan koleksi. Berikut pendekatan yang umum:
Tampilan koleksi ... dengan penginisialisasi:
import UIKit class UIICollectionView: UICollectionView { private var commoned: Bool = false override func didMoveToWindow() { super.didMoveToWindow() if window != nil && !commoned { commoned = true common() } } internal func common() { } }
Di sebagian besar proyek, Anda memerlukan "tampilan koleksi dengan penginisialisasi". Jadi Anda mungkin tetap akan memiliki
UIICollectionView
(perhatikan I ekstra untuk Penginisialisasi!) Dalam proyek Anda.sumber
Swift 5, pengaturan Programmatic UICollectionView Lebar dan tinggi sel
// MARK: MyViewController final class MyViewController: UIViewController, UICollectionViewDataSource, UICollectionViewDelegateFlowLayout { private lazy var collectionViewLayout: UICollectionViewFlowLayout = { let layout = UICollectionViewFlowLayout() let spacing: CGFloat = 1 let numOfColumns: CGFloat = 3 let itemSize: CGFloat = (UIScreen.main.bounds.width - (numOfColumns - spacing) - 2) / 3 layout.itemSize = CGSize(width: itemSize, height: itemSize) layout.minimumInteritemSpacing = spacing layout.minimumLineSpacing = spacing layout.sectionInset = UIEdgeInsets(top: spacing, left: spacing, bottom: spacing, right: spacing) return layout }() private lazy var collectionView: UICollectionView = { let collectionView = UICollectionView(frame: view.bounds, collectionViewLayout: collectionViewLayout) collectionView.backgroundColor = .white collectionView.dataSource = self collectionView.delegate = self collectionView.translatesAutoresizingMaskIntoConstraints = false return collectionView }() override func viewDidLoad() { super.viewDidLoad() configureCollectionView() } private func configureCollectionView() { view.addSubview(collectionView) NSLayoutConstraint.activate([ collectionView.topAnchor.constraint(equalTo: view.safeAreaLayoutGuide.topAnchor), collectionView.bottomAnchor.constraint(equalTo: view.safeAreaLayoutGuide.bottomAnchor), collectionView.leadingAnchor.constraint(equalTo: view.safeAreaLayoutGuide.leadingAnchor), collectionView.trailingAnchor.constraint(equalTo: view.safeAreaLayoutGuide.trailingAnchor) ]) collectionView.register(PhotoCell.self, forCellWithReuseIdentifier: "PhotoCell") } // MARK: UICollectionViewDataSource func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int { return 20 } func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell { let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "PhotoCell", for: indexPath) as! PhotoCell cell.backgroundColor = .red return cell } } // MARK: PhotoCell final class PhotoCell: UICollectionViewCell { lazy var imageView: UIImageView = { let imageView = UIImageView() imageView.contentMode = .scaleAspectFill imageView.translatesAutoresizingMaskIntoConstraints = false imageView.layer.masksToBounds = true return imageView }() override init(frame: CGRect) { super.init(frame: frame) setupViews() } required init?(coder aDecoder: NSCoder) { fatalError("init?(coder:) not implemented") } func setupViews() { addSubview(imageView) NSLayoutConstraint.activate([ topAnchor.constraint(equalTo: topAnchor), bottomAnchor.constraint(equalTo: bottomAnchor), leadingAnchor.constraint(equalTo: leadingAnchor), trailingAnchor.constraint(equalTo: trailingAnchor) ]) } }
sumber
Jika, seperti saya, Anda perlu menjaga tata letak aliran kustom Anda yang
itemSize
dinamis diperbarui berdasarkan lebar koleksi pandangan Anda, Anda harus menimpa AndaUICollectionViewFlowLayout
'sprepare()
metode. Berikut adalah video WWDC yang mendemonstrasikan teknik ini .class MyLayout: UICollectionViewFlowLayout { override func prepare() { super.prepare() guard let collectionView = collectionView else { return } itemSize = CGSize(width: ..., height: ...) } }
sumber
Ini adalah versi saya, temukan rasio yang sesuai untuk mendapatkan ukuran sel sesuai kebutuhan Anda.
- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath { return CGSizeMake(CGRectGetWidth(collectionView.frame)/4, CGRectGetHeight(collectionView.frame)/4); }
sumber