Cocoa NSOutlineView和对象持久性异常行为

Cocoa NSOutlineView和对象持久性异常行为,cocoa,nsoutlineview,Cocoa,Nsoutlineview,这件事让我很难受。当涉及到基于视图的NSOutlineView的对象持久性时,我有一个非常奇怪的行为。目前,我有一个包含object1数组的对象,该数组包含object2数组,该数组包含object3数组,等等。。。每个类(对象)都有一个isEqual:方法和一个isEqualToObject:方法。我一次又一次地修改这些,它们工作得很好 现在,当我展开一个项目时,它会保存到默认的plist,并且我已经选中了它,保存的项目数是正确的 然而,当我再次打开文档时;有时所有的行都会像我离开时一样展开,

这件事让我很难受。当涉及到基于视图的NSOutlineView的对象持久性时,我有一个非常奇怪的行为。目前,我有一个包含object1数组的对象,该数组包含object2数组,该数组包含object3数组,等等。。。每个类(对象)都有一个isEqual:方法和一个isEqualToObject:方法。我一次又一次地修改这些,它们工作得很好

现在,当我展开一个项目时,它会保存到默认的plist,并且我已经选中了它,保存的项目数是正确的

然而,当我再次打开文档时;有时所有的行都会像我离开时一样展开,有时没有一行展开,有时NSOutlineView会展开一些行,但不会展开其他行

注意,我没有使用NSTreeController。我正在使用NSOutlineView数据源和委托。下面的方法是这样实现的。此外,还会设置大纲视图的自动保存名称

- (id)outlineView:(NSOutlineView *)outlineView persistentObjectForItem:(id)item {
        return [NSKeyedArchiver archivedDataWithRootObject:item];
    }

- (id)outlineView:(NSOutlineView *)outlineView itemForPersistentObject:(id)object {
        return [NSKeyedUnarchiver unarchiveObjectWithData:object];

}
基本上,有时有效,有时一半有效,有时完全无效。这是非常随机的


奇怪的是,我放置了NSLog,每个条目都找到了匹配项,但是。。。大纲视图没有展开它

我成功了。因此,我最终要做的是搜索我拥有的每个数组中的对象,并返回匹配的对象(不是persistentObject,而是已经是我数据一部分的对象)。换句话说

- (id)outlineView:(NSOutlineView *)outlineView itemForPersistentObject:(id)object {

    id persistentObject =[NSKeyedUnarchiver unarchiveObjectWithData:object];

    for (Class * a in dataArray) {
        if ([a isEqual:persistentObject]) {
            return a;  //instead of returning persistentObject
        }
    }
}

这就成功了。我已经搜索了很长时间,希望有人能发现它有用。

我认为你应该使用
[item representedObject]
来获取模型中的底层对象aka。此外,在检查我的代码时,我发现我调用了文档类
[self.groupView setAutosaveExpandedItems:YES]的
awakeFromNib
。我记得读到你必须手动调用它。我想您也设置了自动保存名称?我已经设置了自动保存名称。[item representedObject]仅在我使用的不是NSTreeController的情况下才起作用。您能再解释一下您的设置吗?我在这方面遇到了麻烦,听起来你的模型和我的相似,但我不确定。基本上,我有一个“组”对象数组(即使用
HeaderCell
标识符作为视图的项)。在每个组中,我都有可以嵌套或不嵌套的项。基本上,这是:
groups=@[itemArray,itemArray,itemArray]在这些项目数组中,有“项目”,有些有子项;有些没有。我只是被你的
for
循环弄糊涂了。你到底在储蓄什么?另外,我的所有数据模型对象都符合NSCoding。@BenStock我不保存任何内容。我正在返回数组中的对象。您的示例应该类似于
-(id)outlineView:(NSOutlineView*)outlineView PersistentObject ForItem:(id)item{return[nsKeyedArchivedDataWithRootObject:item];}-(id)outlineView:(NSOutlineView*)outlineView itemForPersistentObject:(id)object{id item=[nsKeyedUnarchiveDataWithData:object];for(NSArray*数组在组中){for(id testItem在数组中){if([item isEqual:testItem]){return testItem;}}}
好的,我明白你的意思。为什么不能只返回未归档的对象?我在其他地方读到,在自定义模型对象中,必须实现
-isEqual:
方法,从你所写的来看,情况似乎是这样。P.S.很抱歉问你在保存什么。我的意思是:你到底在归档什么ng/取消归档?整个对象、标识符、索引集等,但我现在可以看到它是项。很酷。谢谢你的帮助。因为计算机是从内存的角度考虑的。你已经分配的对象占用的内存空间与取消归档的对象不同。因此,你必须在每个对象和对象中实现相等另一种方法是为每个对象创建一个UUID,对其进行归档,然后取消归档,在对象中搜索匹配的UUID并返回该对象。您的方法是正确的。