0

I have two separate view controllers.

In ViewController1, I have a CollectionView1 and a cell that works fine. I set up the cell using storyboard with ReuseIdentifier "Cell1".

In ViewController2, I have another CollectionView2 and a different cell that works fine. I set up the cell also using storyboard with ReuseIdentifier "Cell2".

Both cells have custom cell classes, UserCell1 and UserCell2, and work fine within their separate CollectionViews.

Now, for the 2nd cell in the CollectionView2, I want to use the cell from the first collection view (ie. IndexPath(row: 1, section: 0)).

In CollectionView2, I want:

IndexPath(row: 0, section: 0) -> "Cell1"
IndexPath(row: 1, section: 0) -> "Cell2"

On ViewController2, within the cellForItemAt, I have tried using formula that indicates which cell to dequeue at each index. However, it is telling me that the cell from the first ViewController is not registered... but that same cell is working within its home CollectionView, so the ReuseIdentifier is clearly working.

Within cellForItemAt (numberOfRowsInSection = 2):

if indexPath == IndexPath(row: 0, section: 0) {
                guard let cell1 = collectionView.dequeueReusableCell(withReuseIdentifier: "Cell1", for: indexPath) as? UserCell1 else { return UICollectionViewCell() }
                cell1.configure(user: selectedUser)
                return cell1
            } else if indexPath == IndexPath(row: 1, section: 0) {
                guard let cell2 = collectionView.dequeueReusableCell(withReuseIdentifier: "Cell2", for: indexPath) as? UserCell2 else { return UICollectionViewCell() }
                cell2.configure(user: selectedUser)
                return cell2
            } else {
            return UICollectionViewCell()
            }

The error I'm getting is:

Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'could not dequeue a view of kind: UICollectionElementKindCell with identifier Cell1 - must register a nib or a class for the identifier or connect a prototype cell in a storyboard'

Thanks in advance!!!! This is driving me crazy :(

PGDev
  • 23,751
  • 6
  • 34
  • 88
nicksarno
  • 3,850
  • 1
  • 13
  • 33
  • each cell needs to be registered for each table/collectionview. If you plan on using 2 cells in one collectionview. Both need to be registered – arvidurs May 23 '19 at 23:49

2 Answers2

0

the good practice to your code is to define each cell in XIB not in storyboard, this will help you to reuse both of cells in any collection view by registering them from code, you can see example here:

How to load custom cell ( xib) in UICollectionView cell using swift

if you need to define the cell in storyboard for some reason, then you need to declare two prototype cell in each collectionView2

see the following screen, we have one collection view with number of items = 2 and we should give unique ReuseIdentifier for each cell

enter image description here

omartarek32
  • 179
  • 6
0

To use a UICollectionViewCell in a UICollectionView, you must first register the cell with collectionView.

Why Cell1 is working in CollectionView1 and not in CollectionView2?

Incase you've created the cell in the same collectionView you're using, the registering cell part can be skipped. But if you want to use it in some other collectionView, registering the cell is mandatory to get that working. This is the reason Cell1 is working perfectly in CollectionView1 and not in CollectionView2.

Since you want to use both Cell1 and Cell2 in CollectionView2, so both the cells must be registered with it.

But the issue is you've created Cell1 in the CollectionView1 itself inside the storyboard.

  1. So first you need to create a .xib file and move Cell1 into it. Let's name the .xib file as Cell1.xib.

Suggestion: You must create custom UICollectionViewCell inside .xib file so you can use it elsewhere as well.

  1. Next you need to register Cell1 with CollectionView1 in ViewController1 and CollectionView2 in ViewController2 in viewDidLoad() itself.

In ViewController1:

override func viewDidLoad() {
    super.viewDidLoad()
    CollectionView1.register(UINib(nibName: "Cell1", bundle: nil), forCellWithReuseIdentifier: "Cell1")
}

In ViewController2:

override func viewDidLoad() {
    super.viewDidLoad()
    CollectionView2.register(UINib(nibName: "Cell1", bundle: nil), forCellWithReuseIdentifier: "Cell1")
}

Similarly you can register other type of cells with collectionView as well. Try implementing this and let me know in case you still face any issues.

PGDev
  • 23,751
  • 6
  • 34
  • 88