2012-10-08 11 views
16

Sto tentando di aggiungere un UICollectionView a un file .nib in IB. Ho lavorato con alcuni tutorial e non ho avuto problemi.UICollectionView non contiene UICollectionViewCell in IB

Nella mia app esistente, quando trascino una vista di raccolta in una vista in IB e quindi espandi l'oggetto, il layout di flusso di CollectionView è lì, ma non esiste una cella di visualizzazione della raccolta. Non riesco anche a trascinare e rilasciare una cella nella vista dell'insieme. Anche la vista raccolta viene visualizzata in modo diverso, mostrando un'immagine di una griglia di celle invece della normale casella bianca.

Ho provato a creare un nuovo controller di visualizzazione con pennino e ottengo gli stessi risultati quando aggiungo una collezioneView.

Questa applicazione si indirizzava a iOS 4.2, ma ho cambiato la destinazione di distribuzione per iOS 6.

In tutti i progetti di nuova creazione che non capisco questo comportamento.

+6

OK, sembra che si può impaginare solo UICollectionView completamente con IB all'interno di uno storyboard. In un .nib si ottiene il comportamento che ho descritto sopra. In uno storyboard, ottieni UICollectionViewCell con UICollectionView. Cosa succede con quello??? – Alpinista

+0

avendo anche questo stesso problema, piuttosto fastidioso – adit

+0

Anche nello storyboard, non è possibile scaricare e rilasciare la cella della vista di raccolta in un oggetto di visualizzazione insieme. Non so perché. – theiOSguy

risposta

3

Definisci la visualizzazione della cella in un file di pennino separato. La vista deve essere di tipo UICollectionViewCell o una sottoclasse.

Quindi, è necessario registrare il pennino con la vostra vista collezione:

- (void)viewDidLoad 
{ 
    UINib *cellNib = [UINib nibWithNibName:@"MyNib" bundle:nil]; 
    [self.collectionView registerNib:cellNib forCellWithReuseIdentifier:@"cell"]; 
} 
+2

per qualche motivo questo non funziona. quando si dequeue la cella, viene generata un'eccezione: "nib deve contenere esattamente un oggetto di livello superiore che deve essere un'istanza UICollectionReusableView". questo è davvero strano, poiché la documentazione afferma "Il file pennino deve contenere solo un oggetto di livello superiore e tale oggetto deve essere del tipo UICollectionViewCell". – DELUXEnized

+0

UICollectionViewCell eredita da UICollectionReusableView. –

8

Non posso dire perché non funziona, ma per me l'approccio sottoclasse da questo post del blog risolto il problema:

http://www.adoptioncurve.net/archives/2012/09/a-simple-uicollectionview-tutorial.php

ecco un breve riassunto:

  • creare un nuova classe MyViewCell che estende UICollectionViewCell e crea proprietà, azioni, punti vendita e metodi secondo necessità.

@interface MyViewCell : UICollectionViewCell

  • creare una visualizzazione (file XI ter) con una collezione guarda cellulare come oggetto root (ed eliminare l'oggetto che viene creato per impostazione predefinita).
  • negli attributi impostare la classe personalizzata di questa cella Vista raccolta alla classe estesa MyViewCell (anziché UICollectionViewCell predefinito).
  • negli attributi in Raccolta vista riutilizzabile definire un identificatore, ad es. myCell, ti servirà più tardi per registrare la tua chiamata.
  • tornare alla classe personalizzata e modificare il metodo inithWithFrame per caricare e utilizzare la vista creata.

    - (id)initWithFrame:(CGRect)frame 
    { 
        self = [super initWithFrame:frame]; 
        if (self) 
        { 
        // Initialization code 
        NSArray *arrayOfViews = [[NSBundle mainBundle] loadNibNamed:@"CVCell" owner:self options:nil]; 
    
        if ([arrayOfViews count] < 1) { return nil; } 
    
        if (![[arrayOfViews objectAtIndex:0] isKindOfClass:[UICollectionViewCell class]]) { return nil; } 
    
        self = [arrayOfViews objectAtIndex:0]; 
        } 
        return self; 
    } 
    
  • allora si può registrare questa classe per essere utilizzato dal CollectionView con

[self.collectionView registerClass:[MyViewCell class] forCellWithReuseIdentifier:@"myCell"];

+0

Sebbene ciò possa teoricamente rispondere alla domanda, [sarebbe preferibile] (http://meta.stackexchange.com/q/8259) includere qui le parti essenziali della risposta e fornire il link per riferimento. –

+0

Ho aggiunto più dettagli alla risposta. – DELUXEnized

+0

Fantastico! Non dimenticarti di registrare collectionView: [self.collectionView registerClass: [MyViewCell class] forCellWithReuseIdentifier: @ "myCell"]; – atulkhatri

0

Mentre queste risposte sono corrette, la causa del problema è molto sottile e Apple ha bisogno di aggiornare il loro messaggio di errore nel registro.Quando vedi:

Unknown class MyViewCell in Interface Builder file. 

Che cosa significa in realtà è che il codice sorgente non è presente la dichiarazione @implementation o che il file .m non è stato aggiunto al bersaglio. Quindi controllare il codice e assicurarsi di avere:

@implementation MyViewCell 

@end 

Questo è vero sia per UITableViewCell e UICollectionViewCell.

Discuto il problema ulteriormente a https://stackoverflow.com/a/12755891/539149 per il caso generale.

La cosa interessante è che se vi manca il @implementation e chiamare:

[self.myCollectionView registerClass:[MyViewCell class] forCellWithReuseIdentifier:@"MyViewCell"]; 

si vedrà:

Undefined symbols for architecture armv7: 
    "_OBJC_CLASS_$_MyViewCell", referenced from: 
     objc-class-ref in MyViewController.o 
ld: symbol(s) not found for architecture armv7 
clang: error: linker command failed with exit code 1 (use -v to see invocation) 

Così Apple sa circa il problema, hanno appena aren' t rilevandolo durante la compilazione. Ti consiglio di non inserire celle personalizzate in pennini separati o di chiamare registerClass: forCellWithReuseIdentifier :. È molto più pulito memorizzare la cella personalizzata all'interno del suo contenitore UICollectionView o UITableView in Interface Builder.

8

È passato un po 'di tempo da quando la domanda è stata fatta, ma ho affrontato lo stesso problema ultimamente.

Alla fine, ho trovato la risposta here.

In breve:

  • Non è possibile trascinare e rilasciare un UICollectionViewCell in un UICollectionView se ci si trova in un file .xib. Questo è possibile solo in uno storyboard.
  • La soluzione consiste nel creare un file .xib per il tuo cellulare personalizzato e registrare manualmente il cellulare in:

    [self.collectionView registerClass:[CollectionViewCell class] forCellWithReuseIdentifier:CELL_ID];

+0

Questo è ancora un problema su Xcode 8.2.1.Penso che dovremo usare la soluzione alternativa per sempre. –

+0

Per la soluzione alternativa, devo utilizzare registerNib oppure il dequeueReusableCell è solo una vista vuota, senza alcuna informazione configurata in xib. –

+0

Ancora lo stesso con Xcode 8.3. Perché... – Jonny

Problemi correlati