2010-02-15 4 views
1

내가보기 컨트롤러 클래스에서AppDelegate : ViewController에서 값 가져 오기?

- (void)applicationWillTerminate:(UIApplication *)application 

에서 변수를 좀하고 싶습니다. 나는 tabbar 응용 프로그램을 빌드하고 appdelegate에만 tabbar 컨트롤러를 추가했습니다.

[window addSubview:tabBarController.view]; 

은 어떻게 TestViewController에서 변수를 얻을 수 있습니다 : 당신이 요청하지만, 여기에 추측 무엇

#import <UIKit/UIKit.h> 
#import <AVFoundation/AVFoundation.h> 

@interface TestViewController : UIViewController { 
    IBOutlet UILabel *testLabel; 
    NSString *currentString; //Value that i want to save at applicationWillTerminate 
} 

@property (nonatomic, retain) UILabel* testLabel; 
@property (nonatomic, retain) NSString* currentString; 

@end 

답변

2

그것은 TestViewController 당신이 applicationWillTerminate가 도달 시간 dealloc'd되지 않았 음을 다소 우발적 - 그것은 당신의 응용 프로그램에서 수준 높은 그 값을 저장하는 데 적합 할 수 있습니다. 나중에 페치 할 필요가 없도록 그 접근 방법은 항상 UIApplicationDelegate에 currentString를 저장하는 것입니다 :

@implementation TestViewController 
- (void)setCurrentString:(NSString *)currentString { 
    ((MyAppDelegate *)[[UIApplication sharedApplication] delegate]).currentString = currentString; 
} 
@end 
+0

고맙습니다.이 작동하지만, currentString 값이 매초마다 변경됩니다. 이게 괜찮습니까? 아니면 매 초마다 currentString을 AppDelegate로 설정하는 것이 좋지 않습니까? – x2on

+2

아마도 이상적이지는 않습니다. UIApplicationDelegate이기 때문에가 아니라 매초 세 개의 메시지를 보내는 것이 비싸기 때문입니다 (sharedApplication, delegate, setCurrentString). TestViewController가 close에서 currentString을 사용하여 수행해야하는 작업을 수행 할 수 있다면 UIApplicationWillTerminateNotification에이를 등록 할 수 있습니다. – dstnbrkr

+0

좋아요. 코드를 다시 작성 했으므로 UIApplicationWillTerminateNotification을 등록하고 거기에서 작업을 수행 할 수 있습니다. 이 힌트를 가져 주셔서 감사합니다! – x2on

0

100 % 확인 :
UITabBarController가의 모든 반환 속성이라고 viewControllers가 tabbar와 관련된보기 컨트롤러. 나중에 TabBar의에서 다른 위치로 TestViewController를 이동하기로 결정하는 경우이 휴식 것이

- (void)applicationWillTerminate:(UIApplication *)application { 
    TestViewController* test_view_controller = [tabBarController.viewControllers objectAtIndex:0] ; 
    NSString* value = test_view_controller.currentString ; 
} 

참고 : TestViewController 당신이하여 얻을 수있는 첫 번째 탭 이었다는 것을 가정

.

- 편집 - 모든 컨트롤러를 확인하고 유형이 TestViewController 인 컨트롤러에서 문자열을 가져옵니다.

NSString* value = nil ; 
for (id unknownController in tabBarController.viewControllers) { 
    if ([unknownController isKindOfClass:[TestViewController class]]) { 
    value = ((TestViewController*)unknownController).currentString ; 
    } 
} 
// value should be the value of the string. 
+0

그게 내가 아니야,하지만 난 애플 리케이션을 닫을 때 나는 folowing 오류를 얻을 때 : *** - [UINavigationController currentString] : 인식 할 수없는 셀렉터를 인스턴스 0x4313b80에 보냄 *** 앱 종료 중 uncaught 예외 'NSInvalidArgumentException'으로 인해, 이유 : '*** - [UINavigationController currentString] : 인스턴스 0x4313b80에 전송 된 인식 할 수없는 선택자' – x2on

+0

다른 탭 인덱스에있을 수 있습니다. 당신은 그들 모두를 반복 할 수 있고 TestViewController 타입인지를 체크 할 수 있습니다. NSString * 값; 각 컨트롤러에 대해 tabview if ([unknownController isKindOfClass : [TestViewController class]]) { value = ((TestViewController *) unknownController) .currentString; } – Eld

1

dbarker의 대답에 확장 그것은 당신이 정말로에 currentString 값을 저장하는 것입니다 필요 같은 소리, 당신의 데이터 모델. 이를 수행하기위한 적절한 위치는 viewController 자체에 있습니다.

데이터 모델이 하나의 문자열 일 경우 앱 대표자에게 속성을 만들어 보관할 수 있습니다. 그런 다음 viewController는 currentString 값이 뷰에서 변경되거나 뷰가 닫힐 때 해당 값이 변경 될 때마다 앱 위임 등록 정보에 기록합니다.

이렇게하면 열어 본 조회수에 관계없이 앱이 종료 될 때 데이터 (앱의 전체 지점)가 항상 유지됩니다.

정보를 인터페이스에서 데이터 모델로 이동하는 것이 컨트롤러의 적절한 역할입니다. 엄밀히 말하면, viewController는 인터페이스 자체가 필요로하는 것 이상의 데이터를 저장해서는 안됩니다. 이는 viewController가 인터페이스에서 가져온 값을 사용하여 데이터 모델 객체에 메시지를 보내서 설정 한 데이터 모델의 속성입니다.

이 경우,보기 컨트롤러에는 currentString 속성이 없습니다. 대신 그들은 데이터 모델의 currentString 속성에 대한 참조 일 뿐인 속성을 갖게됩니다. 뷰 컨트롤러는 계속해서 해당 속성을 업데이트하지만 아무것도 저장하지 않습니다.

이 디자인의 장점은 분명합니다. 앱의 어느 곳에서나 가치를 원한다면 하나의 위치와 하나의 호출로 얻을 수 있습니다. 앱의 어떤 부분도 데이터 모델을 위해 저장 한 앱의 다른 부분의 존재를 알 필요가 없습니다.