web-dev-qa-db-ja.com

UICollectionViewは、非nilレイアウトパラメーターで初期化する必要があります

私はUICollectionViewが初めてで、Webで見つけたチュートリアルに従っていますが、理解できないエラーが発生しています。コンテキストの一部を次に示します。

デバッガーでは、次のことが起こっていることがわかります。

  • numberOfSectionsInCollectionView:が呼び出され、1を返します
  • collectionView:numberOfItemsInSection:が呼び出され、モデルのサイズを返します(20)
  • collectionView:layout:sizeForItemAtIndexPath:は、モデル内の各アイテムに対して1回呼び出されます
  • collectionView:layout:insetForSectionAtIndex:が呼び出されます
  • collectionView:cellForItemAtIndexPath:が呼び出され、この行でクラッシュします...

    UICollectionViewCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"MyCell" forIndexPath:indexPath];
    

このエラーで...

*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'UICollectionView must be initialized with a non-nil layout parameter'

その行で実行を一時停止してコンソールを確認すると、レイアウトがあるように見えます...

(lldb) po collectionView.collectionViewLayout
(UICollectionViewLayout *) $4 = 0x07180fd0 <UICollectionViewFlowLayout: 0x7180fd0>

UICollectionViewは、ストーリーボードの唯一無二のシーンの一部です。 viewController.mには、他の方法で作成されたUICollectionViewsはありません。

誰にもアイデアはありますか?

23
Murray Sagal

結局のところ、問題はregisterClass:。私はこれを持っていました:

[self.collectionView registerClass:[UICollectionView class] 
        forCellWithReuseIdentifier:@"MyCell"];

しかし、これは次のようになっているはずです。

[self.collectionView registerClass:[UICollectionViewCell class] 
        forCellWithReuseIdentifier:@"MyCell"];

したがって、デキューメソッドはUICollectionViewではなくUICollectionViewCellを作成していました。

18
Murray Sagal

これは私のために働いた:

UICollectionViewFlowLayout *aFlowLayout = [[UICollectionViewFlowLayout alloc] init];
    [aFlowLayout setItemSize:CGSizeMake(200, 140)];
    [aFlowLayout setScrollDirection:UICollectionViewScrollDirectionHorizontal];
myCollectionViewController = [[MyCollectionViewController alloc]initWithCollectionViewLayout:flowLayout];

プログラムでUICollectionViewを作成する場合、レイアウトが必要です。

31
Maz Naiini

UICollectionViewControllerでコレクションビューコントローラーをプログラムで作成する場合は、UICollectionViewController initメソッドが[super init]ではなく[super initWithCollectionViewLayout]を使用することを確認してください。

-(id) initWithImages:(NSArray *)pImages {
    UICollectionViewFlowLayout *layout = [[UICollectionViewFlowLayout alloc] init];
    [layout setMinimumInteritemSpacing:0.0f];
    [layout setMinimumLineSpacing:0.0f];
    layout.scrollDirection = UICollectionViewScrollDirectionVertical;
    if (self = [super initWithCollectionViewLayout:layout]) {
        _images= [[NSArray alloc] initWithArray:pImages];
    }
    return self;
}

From: ICollectionViewController Class Reference:Overview

8
jki

私は同じ問題を抱えていて、私のものを使って解決しました

UICollectionViewFlowLayout *myLayout = [[UICollectionViewFlowLayout alloc]init];
[myLayout setScrollDirection:UICollectionViewScrollDirectionVertical];
[myLayout setMinimumInteritemSpacing:0.0f];
[myLayout setMinimumLineSpacing:0.0f];
UICollectionView *myCollectionView = [[UICollectionView alloc]initWithFrame:viewfame collectionViewLayout:myLayout];

の代わりに

UICollectionView *myCollectionView = [[UICollectionView alloc]initWithFrame:self.view.frame];
[myLayout setScrollDirection:UICollectionViewScrollDirectionVertical];
[myLayout setMinimumInteritemSpacing:0.0f];
[myLayout setMinimumLineSpacing:0.0f];
[myCollectionView setCollectionViewLayout:myLayout];
3
Shabeer Ali

クラスがUICollectionViewControllerから継承している場合、またはプログラムでUICollectionViewを作成している場合は、クラスをプッシュするときに、collectionViewLayoutを以下のように設定できます

let homeViewController = HomeViewContoller(collectionViewLayout:UICollectionViewLayout())
1
GSK

ビューが初期化される前にself.view.boundsに等しいitemSizeでUICollectionViewLayoutオブジェクトを返すときに、この問題に直面していました。

0
brendan