Question

Je ne prévois pas d'écrire des applications sans IB, je suis en train d'essayer d'en apprendre davantage sur la programmation.

Comment puis-je obtenir une seule instance de ma classe AppController au démarrage? (Il est normalement chargé depuis la pointe.) Et pouvez-vous clarifier l'utilisation de + initialize et de -init ? Si je comprends bien, + initialize est appelé sur toutes les classes au démarrage. Comment puis-je l'utiliser pour créer une instance de mon AppController avec des variables d'instance qui constituent mon interface?

J'espère que cela a du sens et merci pour votre aide.

Était-ce utile?

La solution

+ initalize est envoyé à une classe la première fois que cette classe ou l'une de ses sous-classes reçoit un message pour la première fois. Alors, quand vous faites:

instance = [[[YourClass alloc] init] autorelease];

Ce message alloc déclenche initialize .

Si vous faites la même chose avec une sous-classe:

instance = [[[SubclassOfYourClass alloc] init] autorelease];

Ce message alloc déclenchera + [YourClass initialize] de la même manière que l'autre (avant de déclencher également + [SubclassOfYourClass initialize] . Mais un seul d'entre eux le fera: chaque initialize de chaque classe n'est jamais appelé plus d'une fois (à moins que vous ne l'appeliez vous-même avec [super initialize] ou [SomeClass initialize] - ne le faites pas, car la méthode ne l'attend pas.)

-init , d’autre part, initialise une nouvelle instance. Dans l'expression [[YourClass alloc] init] , vous envoyez personnellement le message directement à l'instance. Vous pouvez également l'appeler indirectement, via un autre initialiseur ( [[[YourClass alloc]] initWithSomethingElse: bar] ) ou une fabrique de commodité ( [Instance YourClass] ).

Contrairement à initialize , vous devez toujours envoyer init (ou un autre initialiseur, le cas échéant) dans votre superclasse. La plupart des méthodes init ressemblent à ceci:

- (id) init {
    if ((self = [super init])) {
        framistan = [[Framistan alloc] init];
    }
    return self;
}

Les détails diffèrent (cette méthode, celle de la superclasse ou les deux peuvent prendre des arguments, et certaines personnes préfèrent self = [super init] sur sa propre ligne et Wil Shipley n'attribue pas du tout à self ), mais la base L’idée est la même: appelez [super init [Avec quelque chose:…]] , assurez-vous qu’il n’a pas renvoyé nil , configurez l’instance si elle ne l’a pas été, et retourne quelle que soit la superclasse retournée.

Cela implique que vous puissiez retourner nil à partir de init , et vous le pouvez. Si vous faites cela, vous devriez [auto-libérer] , afin de ne pas laisser fuir l'objet en échec. (Pour détecter les valeurs d'argument non valides, une alternative est NSParameterAssert , qui lève une exception en cas d'échec de l'assertion. Les mérites relatifs de chacune d'elles dépassent le cadre de cette question.)

  

Comment puis-je utiliser cela pour créer une instance de mon AppController avec des variables d'instance qui constituent mon interface?

Le meilleur moyen est de tout faire dans main :

int main(int argc, char **argv) {
    NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];

    AppController *controller = [[[AppController alloc] init] autorelease];
    [[NSApplication sharedApplication] setDelegate:controller]; //Assuming you want it as your app delegate, which is likely
    int status = NSApplicationMain(argc, argv);

    [pool drain];
    return status;
}

Vous effectuerez toute autre configuration dans les méthodes de délégation de votre application dans AppController .

Vous le savez déjà, mais pour tous ceux qui liront ceci: Les plumes sont votre ami. Interface Builder est votre ami. Ne combattez pas le framework, travaillez-le et construisez votre interface graphiquement. Votre application en sera meilleure.

Autres conseils

Un ensemble de cartes d'interface réseau semble ne pas constituer une réponse satisfaisante, même lorsqu'il est représenté au format XML (XIB), car il n'existe pas de moyen facile de les comparer ou de les fusionner avec des outils standard de type subversion ou SCM. Les informations encodées sont fragiles et ne sont pas destinées à être éditées par de simples humains. Comment les modifications seraient-elles représentées par une interface graphique? Est-ce que je passerais en revue chaque attribut de chaque contrôle et les visuellement?

Cependant, si le comportement de l'application est écrit dans le code, il y a une chance que je puisse comprendre ce qui se passe, même si je dois garder de nombreux détails à portée de main en même temps.

Une solution proposée: utilisez une NIB de niveau supérieur codée par l'architecte principal, puis codez le reste de l'application de manière explicite.

Quelqu'un a-t-il une meilleure idée?

Autre solution au problème du lancement d'une application sans nib.

Au lieu d'allouer votre propre contrôleur, utilisez simplement les paramètres supplémentaires de la méthode NSApplicationMain () :

int retVal = NSApplicationMain(argc, argv, @"UIApplication", @"MyAppDelegate");

Ceci prend en charge tous les liens appropriés dont on aurait besoin.

Ensuite, la seule chose dont vous devez vous souvenir est de créer votre propre fenêtre et de la rendre visible.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top