129 lines
5.8 KiB
C++
129 lines
5.8 KiB
C++
/*
|
|
* Copyright 2019 Google Inc.
|
|
*
|
|
* Use of this source code is governed by a BSD-style license that can be
|
|
* found in the LICENSE file.
|
|
*/
|
|
|
|
#ifndef GrVkSecondaryCBDrawContext_DEFINED
|
|
#define GrVkSecondaryCBDrawContext_DEFINED
|
|
|
|
#include "include/core/SkRefCnt.h"
|
|
#include "include/core/SkSurfaceProps.h"
|
|
#include "include/core/SkTypes.h"
|
|
|
|
#include <memory>
|
|
|
|
class GrBackendSemaphore;
|
|
class GrRecordingContext;
|
|
struct GrVkDrawableInfo;
|
|
namespace skgpu::v1 { class Device; }
|
|
class SkCanvas;
|
|
class SkDeferredDisplayList;
|
|
struct SkImageInfo;
|
|
class SkSurfaceCharacterization;
|
|
class SkSurfaceProps;
|
|
|
|
/**
|
|
* This class is a private header that is intended to only be used inside of Chromium. This requires
|
|
* Chromium to burrow in and include this specifically since it is not part of skia's public include
|
|
* directory.
|
|
*/
|
|
|
|
/**
|
|
* This class is used to draw into an external Vulkan secondary command buffer that is imported
|
|
* by the client. The secondary command buffer that gets imported must already have had begin called
|
|
* on it with VK_COMMAND_BUFFER_USAGE_RENDER_PASS_CONTINUE_BIT. Thus any draws to the imported
|
|
* command buffer cannot require changing the render pass. This requirement means that certain types
|
|
* of draws will not be supported when using a GrVkSecondaryCBDrawContext. This includes:
|
|
* Draws that require a dst copy for blending will be dropped
|
|
* Text draws will be dropped (these may require intermediate uploads of text data)
|
|
* Read and Write pixels will not work
|
|
* Any other draw that requires a copy will fail (this includes using backdrop filter with save
|
|
* layer).
|
|
* Stenciling is also disabled, but that should not restrict any actual draws from working.
|
|
*
|
|
* While using a GrVkSecondaryCBDrawContext, the client can also draw into normal SkSurfaces and
|
|
* then draw those SkSufaces (as SkImages) into the GrVkSecondaryCBDrawContext. If any of the
|
|
* previously mentioned unsupported draws are needed by the client, they can draw them into an
|
|
* offscreen surface, and then draw that into the GrVkSecondaryCBDrawContext.
|
|
*
|
|
* After all drawing to the GrVkSecondaryCBDrawContext has been done, the client must call flush()
|
|
* on the GrVkSecondaryCBDrawContext to actually fill in the secondary VkCommandBuffer with the
|
|
* draws.
|
|
*
|
|
* Additionally, the client must keep the GrVkSecondaryCBDrawContext alive until the secondary
|
|
* VkCommandBuffer has been submitted and all work finished on the GPU. Before deleting the
|
|
* GrVkSecondaryCBDrawContext, the client must call releaseResources() so that Skia can cleanup
|
|
* any internal objects that were created for the draws into the secondary command buffer.
|
|
*/
|
|
class SK_SPI GrVkSecondaryCBDrawContext : public SkRefCnt {
|
|
public:
|
|
static sk_sp<GrVkSecondaryCBDrawContext> Make(GrRecordingContext*,
|
|
const SkImageInfo&,
|
|
const GrVkDrawableInfo&,
|
|
const SkSurfaceProps* props);
|
|
|
|
~GrVkSecondaryCBDrawContext() override;
|
|
|
|
SkCanvas* getCanvas();
|
|
|
|
// Records all the draws to the imported secondary command buffer and sets any dependent
|
|
// offscreen draws to the GPU.
|
|
void flush();
|
|
|
|
/** Inserts a list of GPU semaphores that Skia will have the driver wait on before executing
|
|
commands for this secondary CB. The wait semaphores will get added to the VkCommandBuffer
|
|
owned by this GrContext when flush() is called, and not the command buffer which the
|
|
Secondary CB is from. This will guarantee that the driver waits on the semaphores before
|
|
the secondary command buffer gets executed. If this call returns false, then the GPU
|
|
back end will not wait on any passed in semaphores, and the client will still own the
|
|
semaphores, regardless of the value of deleteSemaphoresAfterWait.
|
|
|
|
If deleteSemaphoresAfterWait is false then Skia will not delete the semaphores. In this case
|
|
it is the client's responsibility to not destroy or attempt to reuse the semaphores until it
|
|
knows that Skia has finished waiting on them. This can be done by using finishedProcs
|
|
on flush calls.
|
|
|
|
@param numSemaphores size of waitSemaphores array
|
|
@param waitSemaphores array of semaphore containers
|
|
@paramm deleteSemaphoresAfterWait who owns and should delete the semaphores
|
|
@return true if GPU is waiting on semaphores
|
|
*/
|
|
bool wait(int numSemaphores,
|
|
const GrBackendSemaphore waitSemaphores[],
|
|
bool deleteSemaphoresAfterWait = true);
|
|
|
|
// This call will release all resources held by the draw context. The client must call
|
|
// releaseResources() before deleting the drawing context. However, the resources also include
|
|
// any Vulkan resources that were created and used for draws. Therefore the client must only
|
|
// call releaseResources() after submitting the secondary command buffer, and waiting for it to
|
|
// finish on the GPU. If it is called earlier then some vulkan objects may be deleted while they
|
|
// are still in use by the GPU.
|
|
void releaseResources();
|
|
|
|
const SkSurfaceProps& props() const { return fProps; }
|
|
|
|
// TODO: Fill out these calls to support DDL
|
|
bool characterize(SkSurfaceCharacterization* characterization) const;
|
|
|
|
#ifndef SK_DDL_IS_UNIQUE_POINTER
|
|
bool draw(sk_sp<const SkDeferredDisplayList> deferredDisplayList);
|
|
#else
|
|
bool draw(const SkDeferredDisplayList* deferredDisplayList);
|
|
#endif
|
|
|
|
bool isCompatible(const SkSurfaceCharacterization& characterization) const;
|
|
|
|
private:
|
|
explicit GrVkSecondaryCBDrawContext(sk_sp<skgpu::v1::Device>, const SkSurfaceProps*);
|
|
|
|
sk_sp<skgpu::v1::Device> fDevice;
|
|
std::unique_ptr<SkCanvas> fCachedCanvas;
|
|
const SkSurfaceProps fProps;
|
|
|
|
using INHERITED = SkRefCnt;
|
|
};
|
|
|
|
#endif
|