iOS崩溃:轮换后MTLRenderPassDescriptor为null

时间:2016-11-05 10:22:14

标签: ios swift metal

我正在使用Metal编写iOS应用程序。在MTKViewDelegate绘图期间的某个时刻,我创建了一个渲染过程描述符并在屏幕上渲染,

let encoder = commandBuffer.makeRenderCommandEncoder(descriptor: renderPassDescriptor)
encoder.setViewport(camera.viewport)
encoder.setScissorRect(camera.scissorRect)

在我绘制函数的开头,我有一个信号量,在Xcode中找到的Metal游戏模板中找到相同的代码,然后检查以验证视图的大小没有改变。如果有,我重新创建我的缓冲区,

    let w = _gBuffer?.width ?? 0
    let h = _gBuffer?.height ?? 0
    if let metalLayer = view.layer as? CAMetalLayer {
        let size = metalLayer.drawableSize
        if w != Int(size.width) || h != Int(size.height ){
            _gBuffer = GBuffer(device: device, size: size)
        }
    }

一切正常,我的iPhone6上的旋转工作正常。但是,当我尝试使用iPad Pro时,它会在我尝试旋转设备时始终生成SIGABRT。调试器告诉我编码器为空。我也在控制台中得到了这个例外,

MTLDebugRenderCommandEncoder.mm:2028: failed assertion `(rect.x(1024) + rect.width(1024))(2048) must be <= 1536'

必须发生异常,因为我正在更新mtkView中的“camera”,

func mtkView(_ view: MTKView, drawableSizeWillChange size: CGSize) {
    camera.setBounds(view.bounds)
}

当我在没有附加调试器的情况下运行时,它不会崩溃。 我想mtkView是异步调用的,我应该做些什么来在调用mtkView时中途停止渲染,但互斥锁应该在库中,而不是在我的代码中?虽然draw和mtkView都是从同一个线程调用的(调试器中的线程1)...如果我在draw和mtkView中逐步调试断点,看起来我手动同步并且它不会崩溃。我有点失落......

完整的源代码在这里:https://github.com/endavid/VidEngine

有什么想法吗?

2 个答案:

答案 0 :(得分:0)

异常消息是提示。编码器为空,我分心了。我猜它会在抛出异常后变为null,但问题不在编码器中。

camera.setBounds(view.bounds)中的代码未更新scissorRect ... 我有一个CADisplayLink以不同的速率更新CPU对象,并且scissorRect在检测到更改时正在更新。

我已经在mtkView()中添加了对完整相机更新的调用,现在崩溃了:)

答案 1 :(得分:0)

我可以解决这个问题,取消选中&#34; Debug可执行文件&#34;在方案enter image description here