我有一个使用自定义 NSCell 子类来绘制 NSProgressIndicator 的 NSOutlineView。每个 NSCell 都有一个refreshing
由 NSOutlineView 委托方法设置的属性willDisplayCell:forItem:
,如下所示:
- (void)outlineView:(NSOutlineView *)outlineView willDisplayCell:(id)cell forTableColumn:(NSTableColumn *)tableColumn item:(id)item
{
cell.refreshing = item.refreshing;
}
每个项目实例都包含一个 NSProgressIndicator,它的启动和停止取决于该特定项目是否正在刷新。
- (NSProgressIndicator *)startProgressIndicator
{
if(!self.progressIndicator)
{
self.progressIndicator = [[[NSProgressIndicator alloc] initWithFrame:NSMakeRect(0, 0, 16.0f, 16.0f)] autorelease];
[self.progressIndicator setControlSize:NSSmallControlSize];
[self.progressIndicator setStyle:NSProgressIndicatorSpinningStyle];
[self.progressIndicator setDisplayedWhenStopped:YES];
[self.progressIndicator setUsesThreadedAnimation:YES];
[self.progressIndicator startAnimation:self];
}
return self.progressIndicator;
}
- (void)stopProgressIndicator
{
if(self.progressIndicator != nil)
{
NSInteger row = [sourceList rowForItem:self];
[self.progressIndicator setDisplayedWhenStopped:NO];
[self.progressIndicator stopAnimation:self];
[[self.progressIndicator superview] setNeedsDisplayInRect:[sourceList rectOfRow:row]];
[self.progressIndicator removeFromSuperviewWithoutNeedingDisplay];
self.progressIndicator = nil;
}
for(ProjectListItem *node in self.children)
{
[node stopProgressIndicator];
}
}
项目 NSProgressIndicator 实例在我的 NSCelldrawInteriorWithFrame:inView:
类中停止和启动,如下所示:
- (void)drawInteriorWithFrame:(NSRect)cellFrame inView:(NSView *)controlView
{
if(self.refreshing)
{
NSProgressIndicator *progressIndicator = [item progressIndicator];
if (!progressIndicator)
{
progressIndicator = [item startProgressIndicator];
}
// Set the progress indicators frame here ...
if ([progressIndicator superview] != controlView)
[controlView addSubview:progressIndicator];
if (!NSEqualRects([progressIndicator frame], progressIndicatorFrame)) {
[progressIndicator setFrame:progressIndicatorFrame];
}
}
else
{
[item stopProgressIndicator];
}
[super drawInteriorWithFrame:cellFrame inView:controlView];
}
我遇到的问题是,尽管正确告知 NSProgressIndicators 停止,但对 stopProgressIndicator 的调用无效。这是未能触发刷新相关 NSOutlineView 行的代码。我已经手动检查了调用 rectOfRow 返回的 NSRect 并且可以确认该值是正确的。
[self.progressIndicator setDisplayedWhenStopped:NO];
[self.progressIndicator stopAnimation:self];
[[self.progressIndicator superview] setNeedsDisplayInRect:[sourceList rectOfRow:row]];
[self.progressIndicator removeFromSuperviewWithoutNeedingDisplay];
self.progressIndicator = nil;
当 NSOutlineView 完成刷新它的所有项目时,它会触发一个reloadData:
调用。这是唯一似乎可靠地更新所有有问题的单元格的东西,最终删除了 NSProgressIndicators。
我在这里做错了什么?