我使用的是CATiledLayer支持的NSView(Mac不是iOS),并且根据Apple文档https://developer.apple.com/reference/quartzcore/catiledlayer,我希望在多个线程上以异步方式调用此方法以提高性能,但是似乎只能在主线程上调用它。

我正在用drawLayer(layer: CALayer, inContext ctx: CGContext)进行工作

我已经在NSView上启用了canDrawConcurrently,并确保窗口将allowsConcurrentViewDrawing设置为true(默认值),但是它仍然始终在主线程上为每个图块rect调用。

在显示之前,我需要先进行一些图像处理,具体取决于需要显示的矩形区域,并且在主线程上运行会影响性能。

有什么想法我可以强制它在后台线程上调用吗?

我尝试将图像编码到后台线程上的操作,然后使用以下命令调出主队列,但显示空白:

backgroundQueue.addOperationWithBlock({ [ weak self ] in
    guard let strongSelf = self else { return }

    // ** This is the part I nee to do in background that can take some time
    guard let image = strongSelf.imageForTileRect(layerBounds, imageSize: imageSize) else { return }
    // ** End background bit

    var rect = layerBounds
    let rectImageRef = image.CGImageForProposedRect(&rect, context: nil, hints: nil)

    if (rectImageRef != nil) {
        NSOperationQueue.mainQueue().addOperationWithBlock({
            CGContextDrawImage(ctx, rect, rectImageRef)
        })
    }
})

最佳答案

当CATiledLayer作为主要层时,我们实际上从未设法使其正常工作,我不确定为什么它不起作用,而且我们也从未从Apple Bug中得到答案。

但是,我们通过将主要图层设为标准CALayer,然后将CATiledLayer作为子图层添加到该主要图层中,从而完成了背景渲染工作,类似于下面的代码。

我们还注意到,如果将CATiledLayer托管在NSView中,它将按预期工作

希望这可以帮助...

class HostingLayer : CALayer {

    var tiledLayer : CATiledLayer!

    override init() {
        super.init()

        self.tiledLayer = CATiledLayer.init()

        self.addSublayer(tiledLayer!)
    }
}

关于macos - CATiledLayer drawLayer :inContext always being called on Main thread - MacOS El Capitan,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/39564717/

10-10 19:38