【问题标题】:NSOutlineView reloadItem: has no effectNSOutlineView reloadItem:没有效果
【发布时间】:2013-11-13 19:51:12
【问题描述】:

我正在尝试释放基于视图的NSOutlineView 的一些压力,为此我更改了单个项目属性,并且最初使用[myOutlineView reloadData] 重新加载它就好了。

我尝试了[myOutlineView reloadItem: myOutlineViewItem],但它从不调用- (NSView *)outlineView:(NSOutlineView *)ov viewForTableColumn:(NSTableColumn *)tableColumn item:(id)item,因此数据没有更新。

-(void)reloadOutlineViewObject
{
    //[myOutlineView reloadData];   //Reload data just fines but is ressource-hungry
    NSLog(@"%d",[myOutlineView rowForItem:myOutlineViewItem]; //Making sure my object is an item of the outlineView, which it is !
    [myOutlineView reloadItem:myOutlineViewItem];   
}

我在这里错过了什么吗?

更新

正如 cmets 中所指出的,我的 outlineView 是基于视图的。

更新 2

尝试了一些东西让我意识到我正在重新加载的对象是一个二级对象(cf 对象树)并且调用 reloadItem:firstLevelObject reloadChildren:YES 确实有效。

是否有可能我们只能在第一级对象上调用 reloadItem: ?在我的情况下,这将是非常低效的(我只有一个二级项目和很多二级项目)!

nil ->firstLevelA ->secondLevel1
                  ->secondLevel2
    ->firstLevelB ->secondLevel3
                  ->secondLevel4

同时尝试继承 NSOutlineView 并重写 reloadItem:

更新 3

我查看了NSOutlineView in Cocotron 以开始并觉得我需要编写的覆盖reloadItem 的代码会很繁重。有人要确认吗?

【问题讨论】:

  • 表格是基于视图的,不是基于单元格的,是吗?
  • 确实如此。有关系吗?
  • 我也遇到了这个问题。你找到解决办法了吗?
  • 不幸的是,我没有。您认为是否值得将其提交给 Apple 支持?

标签: cocoa nstableview nsoutlineview


【解决方案1】:

我在基于视图的大纲视图中遇到了同样的问题,调用-reloadItem: 似乎什么也没做。这绝对看起来像是一个大错误,尽管文档没有明确说明 reloadItem 将重新获取该行的视图。

我的解决方法是改为调用NSTableView-reloadDataForRowIndexes:columnIndexes:,这似乎按预期工作,触发了对该项目的-outlineView:viewForTableColumn:item: 委托方法的调用。您可以通过调用-rowForItem: 并传入您要重新加载的项目来获取需要重新加载的行。

【讨论】:

  • 也只是尝试在项目的父项上调用-reloadItem:reloadChildren:,只要您为 reloadChildren 传递 YES,这似乎就可以工作。但是,这当然会重新加载 所有 子项,而不仅仅是一项。
  • 谢谢!你可以想象,我现在与项目完全不同步,我可能需要一些时间来验证答案;)
  • 看到这个后我非常乐观,但不幸的是它对我也不起作用。
  • 我也遇到了这个问题。截至 2015 年 1 月仍然是一个问题。只有 -reloadRowIndexes:columnIndexes: 为我工作。几乎认为它不是因为我传入了错误的行索引(提示:确保确保你询问-rowForItem:的大纲视图 - 呃!:-))。
  • 啊,方法名打错了:其实是-reloadDataForRowIndexes:columnIndexes:。现在在答案中修复。
【解决方案2】:

这真的不是错误 - 这是我明确设计的。我的想法是 reloadItem (等)应该只重新加载大纲视图项目属性,而不是该项目的表格单元格,因为它没有携带关于重新加载内容的足够具体信息(例如您可能想要重新加载的特定单元格)。我原本打算让人们使用 reloadDataForRowIndexes:columnIndexes: 重新加载基于特定视图的 tableview 单元格;当基类只需几行代码就可以轻松完成相同的事情时,我们通常不提供覆盖方法。

不过,话虽如此,我知道很多人对此感到困惑,并且大多数人都希望它也会重新加载单元格。

请记录一个错误,请求 Apple 更改此设置。

谢谢, -corbin

【讨论】:

    【解决方案3】:

    Apple 似乎已经“修复”了它。

    WWDC 2016,演示 203“可可的新功能”,视频中的 30:35:

    "NSOutlineView

    • 在调用 reloadItem() 时重新加载与“项目”关联的单元格视图”

    【讨论】:

      【解决方案4】:

      reloadItem: 仅适用于 macOS 10.12。

      来自发行说明: https://developer.apple.com/library/content/releasenotes/AppKit/RN-AppKit/

      NSOutlineView 现在将重新加载与“项目”关联的单元格视图 当 [outlineView reloadItem:] 被调用时。该方法只是调用 [outlineView reloadDataForRowIndexes:columnIndexes:] 传递 要重新加载的特定行和所有列。为了 兼容性,这仅适用于链接到的应用程序 10.12 SDK。

      因此,如果您想在早期系统上重新加载行,您应该使用-reloadDataForRowIndexes:columnIndexes:。 类似的东西:

      let index = outlineView.row(forItem: obj)
      let rowIndex = IndexSet(integer: index)
      
      let cols = IndexSet(0 ... outlineView.numberOfColumns) 
      
      outlineView.reloadData(forRowIndexes: rowIndex, columnIndexes: cols)
      

      【讨论】:

      • 多么可怕,但这是真的,所以确实是 MacOs 部署目标决定了行为......
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-10-30
      • 2018-05-21
      • 2018-07-28
      • 2018-05-15
      • 1970-01-01
      相关资源
      最近更新 更多