我使用D3DImage作为我的WPF用户控件的一部分。在呈现时,D3DImage.TryLock很少会失败。
到目前为止,我还没有找到任何关于为什么D3D.TryLock会失败的文档。有人知道为什么会发生这种事吗?
发布于 2014-02-21 20:23:00
备注部分中的看看这个。它指出:
有时,前端缓冲区变得不可用。这种缺乏可用性可能是由屏幕锁定、全屏专用Direct3D应用程序、用户切换或其他系统活动造成的。当发生这种情况时,通过处理IsFrontBufferAvailableChanged事件通知WPF应用程序。
它表示这与Unlock方法有关,该方法将后台缓冲区内容推送到frontbuffer。但是,我设想如果您获得一个锁并调用Unlock,此时它会失败,因为它由于任何原因不能写入frontbuffer,那么锁可能会被保留,直到它成功地解除锁定,这时对TryLock的调用将失败。我想是这样的:
image.TryLock
// image gets written to
image.Unlock // fails for one of the listed reasons, lock is retained
// loop
image.TryLock // fails because lock is already acquired
image.Unlock // succeeds because the previously successful lock is still in
// place and the issue that caused the previous failure of Unlock
// has since subsided.我已经看到这个问题出现在一些本机DirectX开发中,当不正确地使用BeginDraw和EndDraw时,所以它可能是您的解决方案。我就只有这些了。希望能帮上忙!
正如在该块注释中所述,您可以通过向IsFrontBufferAvailableChanged事件添加一个事件来检查是否是这种情况。如果不是,您可以通过不调用TryLock/Unlock组合来适当地处理这个问题,实质上是在前端缓冲区不可用时跳过呈现。有关此事件处理程序的更多信息可以找到这里。此页上的备注提供了有关引发此事件时如何更好地处理该事件的进一步信息。它指出:
SetBackBuffer方法具有一个重载,该重载接受一个参数,该参数指定WPF是否返回到软件呈现。
发布于 2018-10-12 13:56:32
请注意,即使TryLock失败,也必须调用Unlock。MSDN文档没有明确提到这一点。参见源代码D3DImage.TryLock,它调用LockImpl,该方法总是增加内部引用计数.
https://stackoverflow.com/questions/21834735
复制相似问题