2013-10-06 7 views
10

Qui è il mio codice sorgenteUICollectionView metodi origine dati non ottenere chiamato, ma vengono impostato nel init

- (id)initWithCollectionView:(UICollectionView *)collectionView 
{ 
self = [super init]; 

if (self) 
{ 
    self.collectionView = collectionView; 
    self.collectionView.dataSource = self; 
    self.collectionView.delegate = self; 
    [self.collectionView registerClass:[TWNTweetCell class] forCellWithReuseIdentifier:kCell]; 
    self.collectionViewLayout = self.collectionView.collectionViewLayout; 



    self.tweetArray = @[]; 
    self.tweetTextArray = @[]; 

    self.twitter = [STTwitterAPI twitterAPIOSWithFirstAccount]; 
} 

return self; 
} 

#pragma mark - CollectionView 
#pragma mark DataSource 

-(NSInteger)numberOfSectionsInCollectionView:(UICollectionView *)collectionView 
{ 
return 1; 
} 

- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:  (NSInteger)section 
{ 
return [self.tweetArray count]; 
} 

- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath 
{ 
TWNTweetCell *cell = (TWNTweetCell *)[collectionView dequeueReusableCellWithReuseIdentifier:kCell forIndexPath:indexPath]; 

NSDictionary *status = [self.tweetArray objectAtIndex:indexPath.row]; 

NSString *text = [status valueForKey:@"text"]; 

cell.usernameLabel.text = screenName; 
// cell.createdAtLabel.text = dateString; 

cell.autoresizingMask = UIViewAutoresizingFlexibleWidth; 

UITextView *textView = [self.tweetTextArray objectAtIndex:indexPath.row]; 
[cell setTweet:text withTweetTextView:textView]; 

return cell; 
} 

Tutti i metodi non vengono interupted affatto da punti di interruzione. I tweet vengono caricati nel log quindi so che tutto il resto va bene, il suo solo non riconosce la vista della collezione. E sì, ho impostato il

Qualcuno ha qualche idea che sta succedendo?

+1

stai chiamando il metodo init corretta? Hai un set di breakpoint lì? A proposito, anche il tuo tweetArray sembra essere vuoto. – Tim

risposta

2

Un paio di cose:

1) a (e solo in) il metodo di "init", utilizzare la variabile di istanza di fondo per la vostra @property. Cioè,

_collectionView = collectionView; 
_collectionView.dataSource = self; 
_collectionView.delegate = self; 

Questo si chiama "accesso diretto", and more information can be seen in this related question.

2) nel file .h, accertarsi di dichiarare che il proprio oggetto è conforme ai protocolli delegati dell'origine dati &. PER ESEMPIO.

@interface JustinViewController : UIViewController <UICollectionViewDelegate, UICollectionViewDataSource> 
+0

dichiarando esplicitamente che i protocolli non cambiano molto in fase di esecuzione. –

+0

Ho intenzione di provare questo e tornerò a voi –

0

chiamata [collectionView reloadData] alla fine del tuo metodo init. La vista raccolta deve essere detta per popolare. Presumo che lo UICollectionViewController lo faccia internamente, ma non sembra che tu stia usando UICollectionViewController (o almeno non nel solito modo).

+1

Questo non è corretto, non è necessario chiamare reloadData per un carico iniziale. Quando si impostano il delegato e l'origine dati, questo è il momento in cui verranno chiamati i metodi. – Tim

+1

@Tim Sì, hai assolutamente ragione. –

2

Alcuni suggerimenti:

  • fare tutto il vostro UICollectionView installazione e la configurazione in viewDidLoad.
  • Assicurarsi di chiamare il creare init metodo dalla tua altra classe
  • tuo tweetArray è vuota, per cui se il numero di metodo di elementi viene chiamato, verrà restituito nulla e gli altri metodi non sarà chiamato
+0

Mi dispiace per colpa mia, non mostro tutto il mio codice ma l'array tweet è popolato. –

1

Aggiungi la collectionView a una gerarchia di viste.

Nel metodo init si imposta la proprietà (self.collectionView) ma non si aggiunge il collectionView a una gerarchia di viste. Quindi collectionView non chiamerà alcun metodo dataSource o delegate.

29

Non è il tuo caso, potrebbe essere utile per gli altri che verranno qui avendo problemi con i metodi di origine dati non vengono chiamati. Si potrebbe assegnando origine dati come:

collectionView.dataSource = MyDataSource() 

che è sbagliato come dataSource è un riferimento debole in modo che deve essere memorizzato da un forte riferimento essere vivo dopo averlo creato. Aggiunta una proprietà privata in un ViewController per mantenere il riferimento forte, inizializzarlo e quindi assegnarlo risolve il problema.

+0

grazie mille –

+0

Questo è un ottimo punto. Grazie. –

0

Ho creato la vista di raccolta nello storyboard e collegato l'origine dati e delegato ma non sono stati richiamati in Xcode 8.0 con Swift 3.0. Ho provato molte cose, ma la soluzione era dichiarare il delegato e l'origine dati nella riga di dichiarazione della classe:

classe ViewController: UIViewController, UICollectionViewDelegate, UICollectionViewDataSource { ... }

In precedenza, quando abbiamo collegato delegato e origine dati attraverso storyboard non era necessario, può essere un bug :)

Problemi correlati