6
votes

Comment faire des contrôleurs de visualiseurs UITABBARCONTROLLER BAZILY?

J'ai un uitabbarcontroller créé programmaticaly qui gère 4 sous-classes d'UIViewController. Quelque chose comme: xxx

est un moyen de dire à l'uitabbarcontroller de charger les contrôleurs de vue paresseusement? EJ, lorsque l'utilisateur clique sur l'une des éléments de barre d'onglets ou lorsque TabbarController SetSelectedex est appelé?


0 commentaires

5 Réponses :


3
votes

Un uitabbarcontroller nécessite que les contrôleurs de vue réels soient définis pour son ViewControlers Propriété - il n'y a pas de chargement paresseux disponible dans les frameworks d'Apple. Le contrôleur de barre d'onglets s'appuie sur certains aspects des contrôleurs qu'elle charge pour ses propriétés. Cependant, il n'appelle pas ViewDidLoad jusqu'à ce que l'onglet soit enfoncé pour la première fois.

Ce que vous pouvez faire à la place est de créer votre propre contrôleur d'affichage "espace réservé" qui, dans son ViewDidLoadLoad ou ViewWillappappear Méthodes, remplace lui-même dans le contrôleur de barre d'onglets avec son réel Voir le contrôleur. De cette façon, vous pouvez minimiser la mémoire utilisée par les contrôleurs de vue tenus par le contrôleur de barre d'onglets jusqu'à ce que vous chargiez un contrôleur d'affichage de certains onglets et remplacez-le par votre contrôleur plus intensif de mémoire et de processeur.

Note latérale: Vous voudrez modifier directement la propriété CoverController de la barre d'onglets, plutôt que d'utiliser le SetViewControlers: animé: méthode, de sorte que vos utilisateurs ne font pas ' T voir une animation chaque fois que vous chargez un nouveau contrôleur.


0 commentaires

0
votes

Vous ne pouvez toujours pas utiliser d'uitabbarcontroller et gérer la barre d'onglets urself, lorsque quelqu'un sélectionne un onglet U appuyez sur la vue ViewControlers dans la méthode DidSelecindex


0 commentaires

5
votes

Qu'est-ce que vous essayez de charger paresseusement?

Ceci est une jolie mise en œuvre standard uitabbarcontroller. J'en ai un très similaire dans une application que j'écris. Dans mon code, la liste ViewDiDload (la méthode appelée après qu'un contrôleur a chargé ses vues associées en mémoire) n'est pas appelée tant que l'onglet est touché.

Je crois que la façon dont vous avez codé (à part tous les objets automatiques) est la méthode préférée de créer ce type d'interface utilisateur.


3 commentaires

Libère-t-il préféré à l'autoraération? pourquoi donc?


Libérer un objet libère la mémoire immédiatement, tandis qu'un objet Autorélied doit attendre que la piscine s'écoule. Sur un ordinateur de bureau, cela pourrait ne pas être un problème, mais dans le monde de la mémoire iPhone est une marchandise limitée. L'une des vidéos de la WWDC '09 sur la mémoire de la mémoire recommande spécifiquement de l'utilisation de l'autorelease dans des situations comme celle-ci où il n'y a aucune raison autre que le code raccourci du code.


@Lounges Je suis nouveau au développement iOS ... Pouvez-vous s'il vous plaît expliquer comment ce contrôleur d'onglets fonctionne réellement? comment et quand il charge ses vues sur la mémoire et combien de temps il reste en mémoire



12
votes

Je fais cette chose même dans l'une de mes applications. L'astuce consiste à rendre votre contrôleur de vue ne pas être une sous-classe d'UitabbarController, mais plutôt UIViewController et implémentez Uitabbardelegate. J'ai créé la vue pour cela dans IB, posant la barre d'onglets (avec le numéro correct des boutons, des images, des tags, etc.) et un espace d'emploi uIView qui est utilisé pour placer correctement les sous-espions qui sont échangés et sortis. Voir la commutation Happen sur Tabbar: DisSelecteCitem: Cela ressemble à ceci:

// MyTabBarController.h
@class MyFirstViewController;
@class MySecondViewController;
@class MyThirdViewController;

@interface MyTabBarController : UIViewController <UITabBarDelegate> {
    IBOutlet UIView *placeholderView;
    IBOutlet UITabBar *tabBar;
    MyFirstViewController *firstViewController;
    MySecondViewController *secondViewController;
    MyThirdViewController *thirdViewController;
    UIViewController *currentViewController;
}
@property (nonatomic, retain) MyFirstViewController *firstViewController;
@property (nonatomic, retain) MySecondViewController *secondViewController;
@property (nonatomic, retain) MyThirdViewController *thirdViewController;

- (void) switchToView:(UIViewController*)aViewController;
@end


//  MyTabBarController.m
#import "MyTabBarController.h"
#import "MyFirstViewController.h"
#import "MySecondViewController.h"
#import "MyThirdViewController.h"

enum {
    kView_First = 1,
    kView_Second,
    kView_Third
};

@implementation MyTabBarController

@synthesize firstViewController, secondViewController, thirdViewController;

- (void) viewDidLoad {
    // Default to first view.
    tabBar.selectedItem = [tabBar.items objectAtIndex:0];
    MyFirstViewController *viewController = [[MyFirstViewController alloc] initWithNibName:@"FirstView" bundle:nil];
    self.firstViewController = viewController;
    [viewController release];
    [self switchToView:firstViewController];
}

- (void)viewWillAppear:(BOOL)animated {
    // Tell our subview.
    if( currentViewController != nil ) {
        [currentViewController viewWillAppear:animated];
    }
}

- (void)tabBar:(UITabBar *)tabBar didSelectItem:(UITabBarItem *)item {
    switch (item.tag) {
        case kView_First: {
            if (firstViewController == nil) {
                MyFirstViewController *viewController = [[MyFirstViewController alloc]
                    initWithNibName:@"FirstView" bundle:nil];
                self.firstViewController = viewController;
                [viewController release];
            }

            [self switchToView:firstViewController];
        }
        break;

        case kView_Second:
            if (secondViewController == nil) {
                MySecondViewController *viewController = [[MySecondViewController alloc]
                initWithNibName:@"SecondView" bundle:nil];
                self.secondViewController = viewController;
                [viewController release];
            }

            [self switchToView:secondViewController];
            break;

        case kView_Third: {
            if (timesViewController == nil) {
                MyThirdViewController *viewController = [[MyThirdViewController alloc]
                initWithNibName:@"ThirdView" bundle:nil];
                self.thirdViewController = viewController;
                [viewController release];
            }

            [self switchToView:thirdViewController];
        }
        break;              
    }
}

- (void) switchToView:(UIViewController*)aViewController {
    if( aViewController == currentViewController ) return;

    UIView *aView= aViewController.view;                
    [aViewController viewWillAppear:NO];
    if( currentViewController != nil ) {
        [currentViewController viewWillDisappear:NO];
        [currentViewController.view removeFromSuperview];       
    }
    aView.frame = placeholderView.frame;
    [self.view insertSubview:aView aboveSubview:placeholderView];
    if( currentViewController != nil ) {
        [currentViewController viewDidDisappear:NO];
    }
    [aViewController viewDidAppear:NO];
    currentViewController = aViewController;
}
@end


4 commentaires

J'ai eu le même problème que l'OP et ce code a fonctionné parfaitement pour moi. Merci!! J'ai pu apporter mon heure de démarrage de l'application par 2 secondes complètes.


En fait, je fais plus de travail et je fais des tests avec cela et je rencontre un problème. Si je présente un contrôleur d'affichage modal, puis renvoyez ce modal, lorsque je revenons au contrôleur de tabulation, son interface est tout blassée. Mon uitabbar est déplacé, l'UIView qui est la sous-vision du contrôleur de barre d'onglets personnalisée a été étirée pour remplir plus d'écran. Avez-vous rencontré des problèmes comme celui-ci et si oui, avez-vous trouvé une solution?


@Kenny Wyland, je n'ai eu aucun problème comme celui-ci, mais je ne pense pas avoir jamais essayé d'afficher une vue modale sur elle. Je ne peux penser à aucune raison de partir en haut de ma tête que cela se conduirait mal comme ça, cependant.


+1 Je dois faire rouler mon propre contrôleur root uitabbarcontroller pour un projet et je ne savais pas comment gérer les sous-visualistes, cela me donne assez de plaisir pour aller aller merci!



0
votes

Dans la méthode Custom UitabbarController de UITABBARCONTROLLER, vous devez simplement faire ce appel:

[self setSelectedViewController :[self.viewControllers objectAtIndex:0]];


0 commentaires