2011-01-06 11 views
0

Ich habe einen Tab-Controller mit 4 Tabs. Jede Registerkarte hat ihren eigenen View-Controller und ein UIWebView.Zugriff auf eine Instanzmethode in einem anderen View-Controller

Angenommen, ich habe eine Schaltfläche (button1) in vc1 und eine Instanzmethode onClick1. In vc2 habe ich eine Methode namens reload. Meine Frage ist, wie kann ich auf die spezifische Instanzmethode, onClick1 in vc2, von vc1 zugreifen?

Für weitere Details, ich versuche tatsächlich, ein einfaches Shopping-Dienstprogramm für das iPhone zu programmieren. Wenn ein Benutzer einen Artikel aus der Durchsuchen-Ansicht zum Einkaufswagen hinzufügt, möchte ich die Warenkorbansicht automatisch neu laden können.

Im Folgenden sind einige Beispiele dafür, was ich meine. Dieses Problem war schwieriger als ich dachte. Ich bin mir nicht sicher, ob ich meine Anwendung umgestaltet habe oder was. Vielleicht gehören sowohl vc1 als auch vc2 zu einer Unterklasse von vcmain und haben sie Bezug auf jeden von ihnen? Aber wenn ich das tue, wie verweise ich sie dann auf ihre entsprechende .xib? Danke Leute!

@implementation viewController 1 

//Reloads vc2 
-(IBAction) onClick1: (id) sender { 

//Calls vc2 reload 
[vc2 reload]; 
} 

@end 

@implementation viewController 2 

//Reload View 
-(void)reload { 
    [webView reload]; 
} 

@end 

Antwort

0

Ich denke, Sie schon so etwas wie eine Basis haben sollte UIViewController (nennen wir es MyTabBars), die eine UITabBarController *tabBarController enthält alle Tab Bar View-Controller hat. Wenn Ihnen das bekannt vorkommt, benötigen Sie eine Methode in MyTabBars namens -(void)reloadCart. reloadCart wird das Array von tabBarController.viewControllers gehen. Auf jeder viewController können Sie eine respondsToSelector:@selector(reload) durchführen und wenn die spezifische viewController qualifiziert dann ruft es diese Selektor-Methode.

Um dies zu tun, möchten Sie wahrscheinlich alle Ihre vc1, vc2, ... Dateien haben eine id delegate definiert und synthetisiert. Wenn MyTabBars die verschiedenen Registerkarten erstellt, werden die vc1 und vc2 delegate auf self festgelegt.

@implementation MyTabBars 

//Reload Cart View 
-(void)reloadCart { 
    for (UIViewController *thisUIViewController in tabBarController.viewControllers){ 
    if ([thisUIViewController respondsToSelector:@selector(reload)]) { 
     [thisUIViewController reload]; 
    } 
    } 
} 

@end 

Angenommen, Sie wissen, wie ein Delegierter von MyTabBars in Ihre VC1 und VC2 passieren, dann können Sie jetzt den folgenden Code in VC1 haben:

@implementation viewController1 

//Reloads vc2 
-(IBAction) onClick1: (id) sender { 

//Calls MyTabBars reloadCart which will look for all tab bar view controllers 
//that have the 'reload' method 
[delegate reloadCart]; 
} 

@end 

Diese Lösung Idee verursacht MyTabBars jeder auslösen reload Methode gefunden in einem unserer Tab-Leiste View-Controller. Seien Sie daher vorsichtig bei der Benennung einer solchen Methode in Ihren vc1, vc2, usw. Dateien. Diese Lösung löst je nach Namenskonvention eine eindeutige vc-Methode oder mehrere vcs mit derselben Methode aus.

Hoffe, das hilft.

1

Sie haben grundsätzlich drei Ansätze, von denen jeder Plus und Minus hat. Ich werde Ihnen einen Überblick auf hoher Ebene geben und Sie auf die recht umfassende Dokumentation von Apple für Details verweisen. Hoffentlich kann ich Ihnen die richtigen Bedingungen geben, um nach spezifischerer Hilfe zu googlen.

Der Ansatz, der @dredful ziemlich ausführliche Details ist , um ein Handle zu den "anderen" View-Controller (s) und Call-Methoden auf ihnen direkt. Das funktioniert gut, aber es kann verwirrend und umständlich sein, Zeiger auf all Ihre Controller herumzugeben, und das Durchqueren der Ansichtshierarchie, um den gewünschten Controller zu bekommen, kann in der Tat sehr schwierig sein.

Der zweite Ansatz ist Key-Value Observing. Sie können einen View-Controller registrieren, um einen bestimmten Schlüssel (benannte Eigenschaft) eines anderen View-Controllers zu "beobachten" und einen bestimmten Selektor auszulösen, wenn verschiedene Dinge damit passieren.Das ist irgendwie magisch und nett, obwohl man irgendwann Zeiger auf beide Controller gleichzeitig haben muss, was den Nachteil der oben genannten Methode "Call it direct" nicht ganz aufhebt. Es ist auch eine Art unglückliche Kopplung von Ansichtssteuerung und Daten, Art von Breaks MVC. Der dritte Ansatz ist mit NSNotificationCenter. Eine Klasse kann eine Benachrichtigung bereitstellen, und jedes andere Objekt, das sich selbst registriert, um auf diese Art von Benachrichtigung zu warten, kann ausgelöst werden, wenn dies geschieht. Es ist schön, weil Sie möglicherweise viele verschiedene Objekte haben, die Gegenstände zum Warenkorb hinzufügen, und sie können einfach eine Notiz in das Benachrichtigungszentrum schießen (sogar wenn Sie ein Objekt oder beliebige Daten übergeben), und die Warenkorbansicht kann diese Benachrichtigungen konsumieren, fange die übergelaufenen Gegenstände auf und tue ihre Sache, kümmere dich nicht besonders darum, wer mit ihr spricht. Es hält separate Teile Ihrer Anwendung schön entkoppelt. Der Nachteil ist, dass es ein bisschen Overhead hat, und was auch immer Selector die notification-konsumierende Klasse ausführt passiert synchron, so dass Sie nicht Netzwerkaktivität oder einen anderen langen Prozess dort verstecken können.

Verwandte Themen