我的应用程序在第一帧上执行多个渲染操作(我使用的是 Metal,尽管我认为这同样适用于 GLES)。例如,它渲染到在后续帧中使用的目标,但之后不会更新。我正在尝试从这些渲染操作中调试一些绘制调用,并且我想使用“GPU 捕获帧”功能来执行此操作。我过去用它来进行按需 GPU 帧调试,它非常有用。
不幸的是,我似乎找不到捕捉第一帧的方法。例如,此选项在调试器中中断时不可用(在第一帧之前设置断点)。一旦调试开始,Xcode 行为似乎也不允许捕获帧。在 Metal API 或 CAMetalLayer 中似乎甚至没有用于执行 GPU 捕获的 API。
有人成功过吗?
最佳答案
我又遇到了这个问题,现在已经弄明白了。我会将其添加为单独的答案,因为它与我的其他答案完全不同。
首先,一些背景。捕获 GPU 帧包含三个组成部分:
- 告诉 Xcode 您想要捕获 GPU 帧。在典型的记录使用中,您可以通过单击 Xcode 中的 GPU Frame Capture“相机”按钮手动执行此操作。
- 指示要捕获的下一帧的开始。通常,这发生在
MTLCommandBuffer presentDrawable:
的下 出现时,它被调用以将帧缓冲区呈现给底层 View 。 - 指示正在捕获的帧的结束。通常,这发生在 next-but-one 出现
MTLCommandBuffer presentDrawable:
时。
在捕获第一个 帧或第一帧之前 的事件时,只有第三个可用,因此我们需要备用执行前两项的方法:
要告诉 Xcode 开始捕获帧,请在 Xcode 中的某行代码的某行添加一个断点之前您要开始捕获帧的点。右键单击断点,从弹出菜单中选择Edit Breakpoint...,然后向断点添加一个Capture GPU Frame操作:
要指示要捕获的帧的开始,在第一次出现
MTLCommandBuffer presentDrawable:
之前,您可以使用MTLCommandQueue insertDebugCaptureBoundary
方法。例如,您可以在实例化MTLCommandQueue
后立即调用此方法,以立即开始捕获提交到队列的所有内容。确保在调用此代码之前触发第 1 项中的断点。要指示捕获帧的结束,您可以依赖
MTLCommandBuffer presentDrawable:
的第一次正常出现,或者您可以添加MTLCommandQueue insertDebugCaptureBoundary< 的第二次调用
.
最后,MTLCommandQueue insertDebugCaptureBoundary
方法实际上不会导致帧被捕获。它只是标记了一个边界点,因此您可以将其保留在代码中以供将来调试使用。如果您希望它从生产代码中消失,请将其包装在 DEBUG
编译条件中。
关于ios - iOS 应用程序的“捕获 GPU 帧”第一帧,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32719796/