58 votes

Quel devrais-je utiliser, -awakeFromNib ou -viewDidLoad?

Récemment, j'ai rencontré un problème dans mon application où certaines sous-vues que je créais dans la méthode -awakeFromNib d'une sous-classe de UIViewController disparaissaient de la vue. Après avoir fait quelques recherches, j'ai découvert que le déplacement du code que j'avais mis dans -awakeFromNib vers -viewDidLoad résolvait le problème. Il semblerait que -awakeFromNib ne soit appelé qu'une seule fois lorsque le UIViewController est désarchivé à partir du nib, et que -viewDidLoad soit appelé chaque fois que la vue est désarchivée.

Alors, quelle est la meilleure pratique? Il semblerait que la méthode -awakeFromNib de UIViewController ne devrait pas ajouter de vues à la vue, ce genre de choses devrait être fait dans -viewDidLoad. Est-ce que je comprends bien? Ou suis-je plus confus que je ne le pensais?

6 votes

Souviens-toi, viewDidLoad s'applique uniquement aux CONTRÔLEURS DE VUE, et non aux vues en tant que telles. awakeFromNib s'applique en réalité à "tout" car il fait partie de NSObject. Et souviens-toi, si tu travailles avec une vue, NE lance PAS, par exemple, d'animations dans awakeFromNib car la vue est très probablement en train d'être animée vers sa position, etc.

67voto

Kevin Ballard Points 88866

awakeFromNib est appelé lorsque le contrôleur lui-même est désarchivé à partir d'un nib. viewDidLoad est appelé lorsque la vue est créée/désarchivée. Cette distinction est particulièrement importante lorsque la vue du contrôleur est stockée dans un fichier nib séparé.

8 votes

0 votes

Dans la spécification de awakeFromNib, "il est garanti que toutes ses connexions d'outlet et d'action sont déjà établies", donc quel est cet outlet? Est-ce l'outlet de la vue?

1 votes

Quelle est la différence entre créé et non archivé? Est-ce que non archivé fait référence aux fichiers créés de manière non-programmatique (c'est-à-dire par le storyboard et le xib) et créé fait référence à une création purement programmatique?

24voto

Prcela Points 1736

Il est également important de noter que la fonction awakeFromNib ne sera jamais appelée après une récupération d'un avertissement de mémoire. Cependant, la fonction viewDidLoad sera appelée.

3 votes

Est-ce encore valide en 2016 ?

4 votes

@khunshan Non, les vues ne sont plus déchargées automatiquement par iOS comme elles l'étaient auparavant.

12voto

Mehrdad Afshari Points 204872

Oui, c'est correct. Vous ne devriez pas vraiment vous fier à awakeFromNib pour ce type de tâches.

awakeFromNib est similaire à un événement qui est appelé après la désérialisation en .NET. viewDidLoad est similaire à l'événement Load en .NET.

Si vous êtes familier avec les concepts de .NET, cela devrait suffire, je pense.

7voto

hrchen Points 395

Je vais essayer de répondre en donnant un exemple :

Si vous définissez la classe customCell et le fichier customCell.xib, puis chargez la cellule en utilisant
- (NSArray *)loadNibNamed:(NSString *)name owner:(id)owner options:(NSDictionary *)options, awakeFromNib est appelé lorsque les objets dans le xib sont désarchivés.

Si vous définissez un customViewController, alors lorsque le customViewController est créé en utilisant - (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil, viewDidLoad sera appelé lorsqu'il est chargé dans la hiérarchie des vues.

Quelques méthodes connexes et potentiellement confuses :

  • (void)loadView : C'est ici que les sous-classes devraient créer leur hiérarchie de vue personnalisée si elles n'utilisent pas de fichier xib. Si vous ne spécifiez pas de nom de xib, alors loadView tentera de charger un xib dont le nom est le même que celui de la classe de votre contrôleur de vue. Si un tel xib n'existe pas, vous devez soit appeler -setView: avant que -view ne soit invoqué, soit remplacer la méthode -loadView pour configurer vos vues de manière programmatique. -loadView ne devrait jamais être appelé directement.

  • (void)viewDidLoad : Appelé après le chargement de la vue. Pour les contrôleurs de vue créés en code, c'est après -loadView. Pour les contrôleurs de vue désarchivés à partir d'un xib, c'est après l'initialisation de la vue.

-1voto

andreskwan Points 487

Pour un ViewController, les IBOutlets sont disponibles dans viewDidLoad()

Ici stackView représente un IBOutlet dans un ViewController, stackView est nil dans awakeFromNib, mais il a été instancié lorsque viewDidLoad() est appelé.

État des IBOutlets dans awakeFromNib() vs État des IBOutlet dans viewDidLoad()

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X