uitableviewcontroller 구조에서 드릴 다운에서 사용자-위치를 복원하는 방법은 무엇입니까?
-
18-09-2019 - |
문제
다시 어린이를 포함 할 수있는 레벨이 포함 된 Coredata 모델이 있습니다.
나는 각 레벨을 a로 나타냅니다 UITableViewController
모든 어린이 목록. 사용자가 행을 탭하면 새 UITableViewController
is pushed onto the navigationController
. 여기에 문제가 없습니다.
이 테이블 구조 내에 사용자 위치를 저장하는 방법은 어떻게해야합니까? 이를위한 모범 사례가 있습니까? 구조의 깊이가 알려져 있다면이 작업에 아무런 문제가 없지만, 어떻게 든 정의되지 않은 깊이 로이 접근 방법에 대한 견해를 느꼈습니다.
내가 저장해야한다 NSIndexPath
사용자에 의해 배열에 탭하여 디스크에 작성 하시겠습니까?
해결책 2
사용자가 탭한 nsindexpaths를 사용하는 대신 나는 훨씬 더 안전한 기본 nsmanagedobjects와 함께 갔다.
나는 UinavigationController를 서브 클래스하고 다음을 수행했습니다.
레벨을 위해 새 tableViewController를 푸시 할 때 (저장 parentLevel
) userDefaults의 배열에 이것을 추가합니다.
- (void)pushViewController:(UIViewController *)viewController animated:(BOOL)animated {
[super pushViewController:viewController animated:animated];
if([viewController isKindOfClass:[LevelTableViewController class]]){
NSMutableArray *array = [NSMutableArray arrayWithArray:[[NSUserDefaults standardUserDefaults] objectForKey:LevelTablesPersistentKey]];
NSManagedObject *obj = [(LevelTableViewController*)viewController parentLevel];
if(obj!=nil){
[array addObject:[[obj objectID].URIRepresentation absoluteString]];
}
[[NSUserDefaults standardUserDefaults] setObject:[NSArray arrayWithArray:array] objectForKey:LevelTablesPersistentKey];
}
}
ViewController를 팝하면 해당 배열에서 마지막 항목을 제거합니다.
- (UIViewController *) popViewControllerAnimated:(BOOL)animated{
UIViewController *vc = [super popViewControllerAnimated:animated];
// remove last object
if([vc isKindOfClass:[LevelTableViewController class]]){
NSMutableArray *array = [NSMutableArray arrayWithArray:[[NSUserDefaults standardUserDefaults] objectForKey:LevelTablesPersistentKey]];
[array removeLastObject];
[[NSUserDefaults standardUserDefaults] setObject:[NSArray arrayWithArray:array] objectForKey:LevelTablesPersistentKey];
}
return vc;
}
그런 다음 앱이 다음에 트리를 재건하기 시작했을 때 NavigationController를 초기화 할 때이 배열을 사용할 수 있습니다.
- (LevelNavigationController*) initWithRootViewController:(LevelTableViewController*)vc {
if(self = [super initWithRootViewController:vc]){
// Recreate structure from UserDefaults
NSArray *array = [NSArray arrayWithArray:[[NSUserDefaults standardUserDefaults] objectForKey:LevelTablesPersistentKey]];
[[NSUserDefaults standardUserDefaults] setObject:nil forKey:LevelTablesPersistentKey]; // set the array to nil -> will be rebuild when pushing viewcontrollers onto navigation stack
NSPersistentStoreCoordinator *persistentStoreCoordinator = ...; // pointer to coordinator
NSManagedObjectContext * managedObjectContext = ...; // pointer to your context
for (NSString *objId in array) {
NSManagedObjectID *mobjId=[persistentStoreCoordinator managedObjectIDForURIRepresentation:[NSURL URLWithString:objId]];
if(mobjId!=nil){
NSManagedObject *obj = nil;
NSError **err = nil;
obj = [managedObjectContext objectWithID:mobjId];
if(err==nil && obj){
if([obj.entity.name isEqualToString:@"Level"]){
// push level
LevelTableViewController *nextLevel = [[LevelTableViewController alloc] initWithStyle:UITableViewStylePlain];
nextLevel.parentLevel = (Level*)obj;
[self pushViewController:nextLevel animated:NO];
[nextLevel release];
}
}
}
}
}
return self;
}
다른 팁
사용 NSIndexPath
당신의 상태와 끈기를 위해 그것을 저축/복원하는 것은 나에게 의미가 있습니다.
또한 PLIST (Property List)로 저장된 NSARRAY를 사용하려는 접근 방식은 매우 간단해야합니다.
나는 내 자신의 앱을 위해 이것을 시작할 준비가되었고 여기에 계획이 있습니다. UIViewController가 새로운보기를로드 할 때마다 NSUSERDEFAULTS에서 해당 새로운보기 (개방 된 위치, 인구가있는 데이터 등)에 대한 정보를 제공하는 값을 생성합니다. 하위 뷰가 반환되면보기 컨트롤러 가이 값을 제거합니다. UIViewController에 초기로드가 있으면 기본값을 확인하여 이전에 값을 저장한지 확인하는 경우 해당 하위 뷰를 다시로드하는 데 적절한 조치가 필요합니다. 프로세스는 내비게이션 체인을 계속합니다.
NSIndexPath 대신 에이 작업을 수행 한 이유는 기본보기 계층 외에도 보조 뷰 (추가, 제거, 편집 등)가 많이 있기 때문입니다. 메인 내비게이션 외부에 존재하는 이러한 뷰의 개방을 기록해야 할뿐만 아니라 저장하는 데 필요한 많은 상태 세부 정보가 있습니다 (선택된 옵션, 부분적으로 입력 된 텍스트 등).
나는 여기로 돌아와서 똥 계획으로 판명되면 이것을 다운 투표 할 것입니다.