我有一个用户界面,其中NSCollectionViewItem
的视图内容是通过CALayers以编程方式绘制的。我在调整大小时使用CAConstraintLayoutManager
来保持子层的布局一致,但是这样做时我的表现非常糟糕。似乎调整窗口大小,导致调整两个CATextLayer
的大小以使它们适合根层的宽度,并重新定位一个CATextLayer
以使其保持右对齐,从而导致应用程序花大部分时间执行CGSScanConvolveAndIntegrateRGB
功能(我使用过Time Profiler仪器)。
最“昂贵”的图层(即使是显示的唯一图片也会造成最多的结果)是一条包裹的多线CATextLayer
。我完全不知道如何获得更好的性能(我已经尝试过不使用CAConstraintLayoutManager
并使用图层对齐,但我得到了同样的东西)。有谁有这个问题?有办法吗?
PS:我已经将布局管理器子类化,并在执行- (void)layoutSublayersOfLayer:(CALayer *)layer
期间禁用了所有动画,方法是在kCATransactionDisableActions
中设置为CATransaction
,但似乎没有帮助。
编辑:我已经为文本图层禁用了字体平滑,性能提升了一点点(非常少),但它在_ZL9view_drawP7_CAViewdPK11CVTimeStampb中花费了大量时间(这是被调用的东西)我认为,通过ATI Radeon驱动程序的一个主题。
答案 0 :(得分:1)
我解决了。的种类。它对我来说似乎仍然是一个肮脏的黑客,但我无法找到如何使setNeedsDisplayInRect
工作,所以我最终这样做:
在NSWindow代表:
- (void)windowWillStartLiveResize:(NSNotification *)通知 { [[NSNotificationCenter defaultCenter] postNotificationName:@" beginResize"对象:无]; }
- (void)windowDidEndLiveResize:(NSNotification *)通知
{
[[NSNotificationCenter defaultCenter] postNotificationName:@" endResize"对象:无];
}
在我的自定义视图中,这两个通知分别称为-(void)beginResize
和-(void)endResize
选择器。第一个将BOOL inLiveResize变量设置为YES,而第二个将其设置为NO并再次使用新帧大小调用setFrameSize。
我覆盖了(被覆盖?不是母语为英语的人,对不起)这样的-(void)setFrameSize:(NSSize)newSize
方法:
-(void)setFrameSize:(NSSize)newSize
{
if (inLiveResize) {
NSRect scrollFrame = [[[self superview] enclosingScrollView] documentVisibleRect];
BOOL condition1 = (self.frame.origin.y > (scrollFrame.origin.y - self.frame.size.height));
BOOL condition2 = (self.frame.origin.y < (scrollFrame.origin.y + scrollFrame.size.height + self.frame.size.height));
if (condition1 && condition2)
[super setFrameSize:newSize];
}
else {
[super setFrameSize:newSize]; }}
那就是它。这样,只有可见视图会随窗口一起调整大小,而其他视图会在操作结束时重新绘制。它有效,但我不喜欢肮脏的&#39;是的,我确信使用setNeedsDisplayInRect
方法可以实现更优雅,内置(ish)的方法。我会研究更多。