Commit e356ce28 authored by Laszlo Agocs's avatar Laszlo Agocs

Evolve the api, introduce finish()

parent 969214c6
......@@ -108,9 +108,10 @@ int main(int argc, char **argv)
r->readback(cb, rb, &rbResult);
qDebug("Submit and wait");
r->endAndWaitOffscreenFrame();
r->endOffscreenFrame();
// here it's simple, no need to bother with the completed callback of rbResult
// No finish() or waiting for the completed callback is needed here
// since the endOffscreenFrame() implies a wait for completion.
qDebug() << rbResult.data.size();
}
......
......@@ -420,9 +420,19 @@ QRhi::FrameOpResult QRhi::beginOffscreenFrame(QRhiCommandBuffer **cb)
return d->beginOffscreenFrame(cb);
}
QRhi::FrameOpResult QRhi::endAndWaitOffscreenFrame()
QRhi::FrameOpResult QRhi::endOffscreenFrame()
{
return d->endAndWaitOffscreenFrame();
return d->endOffscreenFrame();
}
void QRhi::readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result)
{
d->readback(cb, rb, result);
}
QRhi::FrameOpResult QRhi::finish()
{
return d->finish();
}
void QRhi::beginPass(QRhiRenderTarget *rt,
......@@ -487,11 +497,6 @@ void QRhi::drawIndexed(QRhiCommandBuffer *cb, quint32 indexCount,
d->drawIndexed(cb, indexCount, instanceCount, firstIndex, vertexOffset, firstInstance);
}
void QRhi::readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result)
{
d->readback(cb, rb, result);
}
QVector<int> QRhi::supportedSampleCounts() const
{
return d->supportedSampleCounts();
......
......@@ -986,21 +986,35 @@ public:
FrameOpResult endFrame(QRhiSwapChain *swapChain);
/*
Rendering without a swapchain is possible as well. This is synchronous in
the sense that end will wait for completion of the submitted commands.
The typical use case is to use it in completely offscreen applications,
e.g. to generate image sequences by rendering and reading back without
ever showing a window.
Rendering without a swapchain is possible as well. The typical use case
is to use it in completely offscreen applications, e.g. to generate image
sequences by rendering and reading back without ever showing a window.
Usage in on-screen applications (so beginFrame, endFrame,
beginOffscreenFrame, endOffscreenFrame, beginFrame, ...) is possible too but
it does break parallelism so should be done only infrequently.
QRhiReadbackResult rbResult;
QRhiCommandBuffer *cb; // not owned
beginOffscreenFrame(&cb);
// ... the usual, set up a QRhiTextureRenderTarget, beginPass-endPass, etc.
readback(cb, rb, &rbResult);
endAndWaitOffscreenFrame();
endOffscreenFrame();
// image data available in rbResult
*/
FrameOpResult beginOffscreenFrame(QRhiCommandBuffer **cb);
FrameOpResult endAndWaitOffscreenFrame();
FrameOpResult endOffscreenFrame();
// Cannot be inside a pass.
void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result);
// Waits for any work on the graphics queue (where applicable) to complete,
// then forcibly executes all deferred operations, like completing
// readbacks and resource releases. This should _not_ be used in practice,
// except in infrequent special cases, like when the results of a readback
// are needed right away. Can be called inside and outside of a frame, but
// not inside a pass. Inside a frame it implies submitting any work on the
// command buffer. Unnecessary in combination with begin/endOffscreenFrame
// because ending an offscreen frame implies waiting for completion.
QRhi::FrameOpResult finish();
// Returns an instance to which updates can be queued. Batch instances are
// pooled and never owned by the application. An instance is returned to
......@@ -1049,9 +1063,6 @@ public:
quint32 instanceCount = 1, quint32 firstIndex = 0,
qint32 vertexOffset = 0, quint32 firstInstance = 0);
// Cannot be mixed with beginPass-endPass.
void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result);
QVector<int> supportedSampleCounts() const;
int ubufAlignment() const;
......
......@@ -84,7 +84,9 @@ public:
virtual QRhi::FrameOpResult beginFrame(QRhiSwapChain *swapChain) = 0;
virtual QRhi::FrameOpResult endFrame(QRhiSwapChain *swapChain) = 0;
virtual QRhi::FrameOpResult beginOffscreenFrame(QRhiCommandBuffer **cb) = 0;
virtual QRhi::FrameOpResult endAndWaitOffscreenFrame() = 0;
virtual QRhi::FrameOpResult endOffscreenFrame() = 0;
virtual void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result) = 0;
virtual QRhi::FrameOpResult finish() = 0;
virtual void beginPass(QRhiRenderTarget *rt,
QRhiCommandBuffer *cb,
......@@ -113,8 +115,6 @@ public:
quint32 instanceCount, quint32 firstIndex,
qint32 vertexOffset, quint32 firstInstance) = 0;
virtual void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result) = 0;
virtual QVector<int> supportedSampleCounts() const = 0;
virtual int ubufAlignment() const = 0;
virtual bool isYUpInFramebuffer() const = 0;
......
......@@ -453,13 +453,6 @@ void QRhiD3D11::drawIndexed(QRhiCommandBuffer *cb, quint32 indexCount,
cbD->commands.append(cmd);
}
void QRhiD3D11::readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result)
{
Q_UNUSED(cb);
Q_UNUSED(rb);
Q_UNUSED(result);
}
QRhi::FrameOpResult QRhiD3D11::beginFrame(QRhiSwapChain *swapChain)
{
Q_ASSERT(!inFrame);
......@@ -510,11 +503,27 @@ QRhi::FrameOpResult QRhiD3D11::beginOffscreenFrame(QRhiCommandBuffer **cb)
return QRhi::FrameOpError;
}
QRhi::FrameOpResult QRhiD3D11::endAndWaitOffscreenFrame()
QRhi::FrameOpResult QRhiD3D11::endOffscreenFrame()
{
return QRhi::FrameOpError;
}
void QRhiD3D11::readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result)
{
Q_UNUSED(cb);
Q_UNUSED(rb);
Q_UNUSED(result);
Q_ASSERT(inFrame && !inPass);
}
QRhi::FrameOpResult QRhiD3D11::finish()
{
Q_ASSERT(!inPass);
return QRhi::FrameOpSuccess;
}
static inline bool isCompressedFormat(QRhiTexture::Format format)
{
return format >= QRhiTexture::BC1 && format <= QRhiTexture::BC7;
......
......@@ -375,7 +375,9 @@ public:
QRhi::FrameOpResult beginFrame(QRhiSwapChain *swapChain) override;
QRhi::FrameOpResult endFrame(QRhiSwapChain *swapChain) override;
QRhi::FrameOpResult beginOffscreenFrame(QRhiCommandBuffer **cb) override;
QRhi::FrameOpResult endAndWaitOffscreenFrame() override;
QRhi::FrameOpResult endOffscreenFrame() override;
void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result) override;
QRhi::FrameOpResult finish() override;
void beginPass(QRhiRenderTarget *rt,
QRhiCommandBuffer *cb,
......@@ -405,8 +407,6 @@ public:
quint32 instanceCount, quint32 firstIndex,
qint32 vertexOffset, quint32 firstInstance) override;
void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result) override;
QVector<int> supportedSampleCounts() const override;
int ubufAlignment() const override;
bool isYUpInFramebuffer() const override;
......
......@@ -366,13 +366,6 @@ void QRhiGles2::drawIndexed(QRhiCommandBuffer *cb, quint32 indexCount,
cbD->commands.append(cmd);
}
void QRhiGles2::readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result)
{
Q_UNUSED(cb);
Q_UNUSED(rb);
Q_UNUSED(result);
}
QRhi::FrameOpResult QRhiGles2::beginFrame(QRhiSwapChain *swapChain)
{
Q_ASSERT(!inFrame);
......@@ -412,11 +405,27 @@ QRhi::FrameOpResult QRhiGles2::beginOffscreenFrame(QRhiCommandBuffer **cb)
return QRhi::FrameOpError;
}
QRhi::FrameOpResult QRhiGles2::endAndWaitOffscreenFrame()
QRhi::FrameOpResult QRhiGles2::endOffscreenFrame()
{
return QRhi::FrameOpError;
}
void QRhiGles2::readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result)
{
Q_UNUSED(cb);
Q_UNUSED(rb);
Q_UNUSED(result);
Q_ASSERT(inFrame && !inPass);
}
QRhi::FrameOpResult QRhiGles2::finish()
{
Q_ASSERT(!inPass);
return QRhi::FrameOpSuccess;
}
void QRhiGles2::commitResourceUpdates(QRhiResourceUpdateBatch *resourceUpdates)
{
QRhiResourceUpdateBatchPrivate *ud = QRhiResourceUpdateBatchPrivate::get(resourceUpdates);
......
......@@ -333,7 +333,9 @@ public:
QRhi::FrameOpResult beginFrame(QRhiSwapChain *swapChain) override;
QRhi::FrameOpResult endFrame(QRhiSwapChain *swapChain) override;
QRhi::FrameOpResult beginOffscreenFrame(QRhiCommandBuffer **cb) override;
QRhi::FrameOpResult endAndWaitOffscreenFrame() override;
QRhi::FrameOpResult endOffscreenFrame() override;
void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result) override;
QRhi::FrameOpResult finish() override;
void beginPass(QRhiRenderTarget *rt,
QRhiCommandBuffer *cb,
......@@ -363,8 +365,6 @@ public:
quint32 instanceCount, quint32 firstIndex,
qint32 vertexOffset, quint32 firstInstance) override;
void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result) override;
QVector<int> supportedSampleCounts() const override;
int ubufAlignment() const override;
bool isYUpInFramebuffer() const override;
......
......@@ -496,13 +496,6 @@ void QRhiMetal::drawIndexed(QRhiCommandBuffer *cb, quint32 indexCount,
baseInstance: firstInstance];
}
void QRhiMetal::readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result)
{
Q_UNUSED(cb);
Q_UNUSED(rb);
Q_UNUSED(result);
}
QRhi::FrameOpResult QRhiMetal::beginFrame(QRhiSwapChain *swapChain)
{
Q_ASSERT(!inFrame);
......@@ -570,11 +563,27 @@ QRhi::FrameOpResult QRhiMetal::beginOffscreenFrame(QRhiCommandBuffer **cb)
return QRhi::FrameOpError;
}
QRhi::FrameOpResult QRhiMetal::endAndWaitOffscreenFrame()
QRhi::FrameOpResult QRhiMetal::endOffscreenFrame()
{
return QRhi::FrameOpError;
}
void QRhiMetal::readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result)
{
Q_UNUSED(cb);
Q_UNUSED(rb);
Q_UNUSED(result);
Q_ASSERT(inFrame && !inPass);
}
QRhi::FrameOpResult QRhiMetal::finish()
{
Q_ASSERT(!inPass);
return QRhi::FrameOpSuccess;
}
MTLRenderPassDescriptor *QRhiMetalData::createDefaultRenderPass(bool hasDepthStencil,
const QRhiColorClearValue &colorClearValue,
const QRhiDepthStencilClearValue &depthStencilClearValue)
......
......@@ -264,7 +264,9 @@ public:
QRhi::FrameOpResult beginFrame(QRhiSwapChain *swapChain) override;
QRhi::FrameOpResult endFrame(QRhiSwapChain *swapChain) override;
QRhi::FrameOpResult beginOffscreenFrame(QRhiCommandBuffer **cb) override;
QRhi::FrameOpResult endAndWaitOffscreenFrame() override;
QRhi::FrameOpResult endOffscreenFrame() override;
void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result) override;
QRhi::FrameOpResult finish() override;
void beginPass(QRhiRenderTarget *rt,
QRhiCommandBuffer *cb,
......@@ -294,8 +296,6 @@ public:
quint32 instanceCount, quint32 firstIndex,
qint32 vertexOffset, quint32 firstInstance) override;
void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result) override;
QVector<int> supportedSampleCounts() const override;
int ubufAlignment() const override;
bool isYUpInFramebuffer() const override;
......
This diff is collapsed.
......@@ -326,7 +326,9 @@ public:
QRhi::FrameOpResult beginFrame(QRhiSwapChain *swapChain) override;
QRhi::FrameOpResult endFrame(QRhiSwapChain *swapChain) override;
QRhi::FrameOpResult beginOffscreenFrame(QRhiCommandBuffer **cb) override;
QRhi::FrameOpResult endAndWaitOffscreenFrame() override;
QRhi::FrameOpResult endOffscreenFrame() override;
void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result) override;
QRhi::FrameOpResult finish() override;
void beginPass(QRhiRenderTarget *rt,
QRhiCommandBuffer *cb,
......@@ -356,8 +358,6 @@ public:
quint32 instanceCount, quint32 firstIndex,
qint32 vertexOffset, quint32 firstInstance) override;
void readback(QRhiCommandBuffer *cb, const QRhiReadbackDescription &rb, QRhiReadbackResult *result) override;
QVector<int> supportedSampleCounts() const override;
int ubufAlignment() const override;
bool isYUpInFramebuffer() const override;
......@@ -394,10 +394,13 @@ public:
QRhi::FrameOpResult beginWrapperFrame(QRhiSwapChain *swapChain);
QRhi::FrameOpResult endWrapperFrame(QRhiSwapChain *swapChain);
QRhi::FrameOpResult startCommandBuffer(VkCommandBuffer *cb);
QRhi::FrameOpResult endAndSubmitCommandBuffer(VkCommandBuffer cb, VkFence cmdFence,
VkSemaphore *waitSem, VkSemaphore *signalSem);
QRhi::FrameOpResult beginNonWrapperFrame(QRhiSwapChain *swapChain);
QRhi::FrameOpResult endNonWrapperFrame(QRhiSwapChain *swapChain);
void prepareNewFrame(QRhiCommandBuffer *cb);
void finishFrame();
void prepareFrameEnd();
void commitResourceUpdates(QRhiCommandBuffer *cb, QRhiResourceUpdateBatch *resourceUpdates);
void executeBufferHostWritesForCurrentFrame(QVkBuffer *bufD);
void activateTextureRenderTarget(QRhiCommandBuffer *cb, QRhiTextureRenderTarget *rt);
......@@ -457,9 +460,11 @@ public:
bool inFrame = false;
int finishedFrameCount = 0;
bool inPass = false;
QVkSwapChain *currentSwapChain = nullptr;
struct OffscreenFrame {
OffscreenFrame(QRhiImplementation *rhi) : cbWrapper(rhi) { }
bool active = false;
QVkCommandBuffer cbWrapper;
VkFence cmdFence = VK_NULL_HANDLE;
} ofr;
......
gl, mtl: compressed textures
gl, mtl: srgb (tex, swapchain buf)
rhi without a window, fully offscreen
readbacks
some wait-gpu stuff for waiting for readback results inside a begin-endFrame f.ex.?
readback api
some wait-gpu stuff for waiting for readback results inside a begin-endFrame f.ex.
vk: implement finish()
vk: readback
mtl, d3d, gl: rhi without a window
mtl, d3d, gl: implement finish()
mtl, d3d, gl: readback
multi window? (multi swapchain) -> trouble
vk: rendering hangs sometimes when minimize and back on some systems?
mtl: cubemaps
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment