Add createBackendFormat and createFBO0 helper methods to SkSurfaceCharacterization
These make it easier for clients to create new surface characterizations that differ only a little from an existing surface characterization.
Change-Id: Iebd0b32ae941d3f91427927108d092cb5864b09f
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/270444
Commit-Queue: Robert Phillips <robertphillips@google.com>
Reviewed-by: Brian Salomon <bsalomon@google.com>
diff --git a/RELEASE_NOTES.txt b/RELEASE_NOTES.txt
index 0b923df..7907549 100644
--- a/RELEASE_NOTES.txt
+++ b/RELEASE_NOTES.txt
@@ -7,6 +7,10 @@
Milestone 82
<Insert new notes here- top is most recent.>
+ * Added two new helper methods to SkSurfaceCharacterization: createBackendFormat and
+ createFBO0. These make it easier for clients to create new surface characterizations that
+ differ only a little from an existing surface characterization.
+
* Removed SkTMax and SkTMin.
* Removed SkTClamp and SkClampMax.
* Removed SkScalarClampMax and SkScalarPin.
diff --git a/include/core/SkSurfaceCharacterization.h b/include/core/SkSurfaceCharacterization.h
index f259fed..c2cb589 100644
--- a/include/core/SkSurfaceCharacterization.h
+++ b/include/core/SkSurfaceCharacterization.h
@@ -11,13 +11,15 @@
#include "include/gpu/GrTypes.h"
#include "include/core/SkColorSpace.h"
+#include "include/core/SkImageInfo.h"
#include "include/core/SkRefCnt.h"
#include "include/core/SkSurfaceProps.h"
class SkColorSpace;
-#if SK_SUPPORT_GPU
#include "include/gpu/GrBackendSurface.h"
+
+#if SK_SUPPORT_GPU
// TODO: remove the GrContext.h include once Flutter is updated
#include "include/gpu/GrContext.h"
#include "include/gpu/GrContextThreadSafeProxy.h"
@@ -70,6 +72,18 @@
*/
SkSurfaceCharacterization createColorSpace(sk_sp<SkColorSpace>) const;
+ /*
+ * Return a new surface characterization with the backend format replaced. A colorType
+ * must also be supplied to indicate the interpretation of the new format.
+ */
+ SkSurfaceCharacterization createBackendFormat(SkColorType colorType,
+ const GrBackendFormat& backendFormat) const;
+
+ /*
+ * Return a new surface characterization with just a different use of FBO0 (in GL)
+ */
+ SkSurfaceCharacterization createFBO0(bool usesGLFBO0) const;
+
GrContextThreadSafeProxy* contextInfo() const { return fContextInfo.get(); }
sk_sp<GrContextThreadSafeProxy> refContextInfo() const { return fContextInfo; }
size_t cacheMaxResourceBytes() const { return fCacheMaxResourceBytes; }
@@ -200,6 +214,14 @@
return *this;
}
+ SkSurfaceCharacterization createBackendFormat(SkColorType, const GrBackendFormat&) const {
+ return *this;
+ }
+
+ SkSurfaceCharacterization createFBO0(bool usesGLFBO0) const {
+ return *this;
+ }
+
bool operator==(const SkSurfaceCharacterization& other) const { return false; }
bool operator!=(const SkSurfaceCharacterization& other) const {
return !(*this == other);
diff --git a/include/gpu/GrBackendSurface.h b/include/gpu/GrBackendSurface.h
index 6102ac7..f5c56b2 100644
--- a/include/gpu/GrBackendSurface.h
+++ b/include/gpu/GrBackendSurface.h
@@ -36,6 +36,12 @@
#if !SK_SUPPORT_GPU
+// SkSurfaceCharacterization always needs a minimal version of this
+class SK_API GrBackendFormat {
+public:
+ bool isValid() const { return false; }
+};
+
// SkSurface and SkImage rely on a minimal version of these always being available
class SK_API GrBackendTexture {
public:
diff --git a/src/core/SkSurfaceCharacterization.cpp b/src/core/SkSurfaceCharacterization.cpp
index 0d9b5e8..6080fed 100644
--- a/src/core/SkSurfaceCharacterization.cpp
+++ b/src/core/SkSurfaceCharacterization.cpp
@@ -74,6 +74,31 @@
fVulkanSecondaryCBCompatible, fIsProtected, fSurfaceProps);
}
+SkSurfaceCharacterization SkSurfaceCharacterization::createBackendFormat(
+ SkColorType colorType,
+ const GrBackendFormat& backendFormat) const {
+ if (!this->isValid()) {
+ return SkSurfaceCharacterization();
+ }
+
+ SkImageInfo newII = fImageInfo.makeColorType(colorType);
+
+ return SkSurfaceCharacterization(fContextInfo, fCacheMaxResourceBytes, newII, backendFormat,
+ fOrigin, fSampleCnt, fIsTextureable, fIsMipMapped, fUsesGLFBO0,
+ fVulkanSecondaryCBCompatible, fIsProtected, fSurfaceProps);
+}
+
+SkSurfaceCharacterization SkSurfaceCharacterization::createFBO0(bool usesGLFBO0) const {
+ if (!this->isValid()) {
+ return SkSurfaceCharacterization();
+ }
+
+ return SkSurfaceCharacterization(fContextInfo, fCacheMaxResourceBytes,
+ fImageInfo, fBackendFormat,
+ fOrigin, fSampleCnt, fIsTextureable, fIsMipMapped,
+ usesGLFBO0 ? UsesGLFBO0::kYes : UsesGLFBO0::kNo,
+ fVulkanSecondaryCBCompatible, fIsProtected, fSurfaceProps);
+}
bool SkSurfaceCharacterization::isCompatible(const GrBackendTexture& backendTex) const {
if (!this->isValid() || !backendTex.isValid()) {
diff --git a/tests/DeferredDisplayListTest.cpp b/tests/DeferredDisplayListTest.cpp
index d31fcb6..743f1a6 100644
--- a/tests/DeferredDisplayListTest.cpp
+++ b/tests/DeferredDisplayListTest.cpp
@@ -547,6 +547,78 @@
s = nullptr;
params.cleanUpBackEnd(context, backend);
}
+
+ // Exercise the createBackendFormat method
+ {
+ SurfaceParameters params(context);
+ GrBackendTexture backend;
+
+ sk_sp<SkSurface> s = params.make(context, &backend);
+ if (!s) {
+ return;
+ }
+
+ SkSurfaceCharacterization char0;
+ SkAssertResult(s->characterize(&char0));
+
+ // The default params create a renderable RGBA8 surface
+ auto originalBackendFormat = context->defaultBackendFormat(kRGBA_8888_SkColorType,
+ GrRenderable::kYes);
+ REPORTER_ASSERT(reporter, originalBackendFormat.isValid());
+ REPORTER_ASSERT(reporter, char0.backendFormat() == originalBackendFormat);
+
+ auto newBackendFormat = context->defaultBackendFormat(kRGB_565_SkColorType,
+ GrRenderable::kYes);
+
+ if (newBackendFormat.isValid()) {
+ SkSurfaceCharacterization char1 = char0.createBackendFormat(kRGB_565_SkColorType,
+ newBackendFormat);
+ REPORTER_ASSERT(reporter, char1.isValid());
+ REPORTER_ASSERT(reporter, char1.backendFormat() == newBackendFormat);
+
+ SkSurfaceCharacterization invalid;
+ REPORTER_ASSERT(reporter, !invalid.isValid());
+ auto stillInvalid = invalid.createBackendFormat(kRGB_565_SkColorType,
+ newBackendFormat);
+ REPORTER_ASSERT(reporter, !stillInvalid.isValid());
+ }
+
+ s = nullptr;
+ params.cleanUpBackEnd(context, backend);
+ }
+
+ // Exercise the createFBO0 method
+ if (context->backend() == GrBackendApi::kOpenGL) {
+ SurfaceParameters params(context);
+ GrBackendTexture backend;
+
+ sk_sp<SkSurface> s = params.make(context, &backend);
+ if (!s) {
+ return;
+ }
+
+ SkSurfaceCharacterization char0;
+ SkAssertResult(s->characterize(&char0));
+
+ // The default params create a non-FBO0 surface
+ REPORTER_ASSERT(reporter, !char0.usesGLFBO0());
+
+ {
+ SkSurfaceCharacterization char1 = char0.createFBO0(true);
+ REPORTER_ASSERT(reporter, char1.isValid());
+ REPORTER_ASSERT(reporter, char1.usesGLFBO0());
+ }
+
+ {
+ SkSurfaceCharacterization invalid;
+ REPORTER_ASSERT(reporter, !invalid.isValid());
+ SkSurfaceCharacterization stillInvalid = invalid.createFBO0(true);
+ REPORTER_ASSERT(reporter, !stillInvalid.isValid());
+ }
+
+ s = nullptr;
+ params.cleanUpBackEnd(context, backend);
+ }
}
DEF_GPUTEST_FOR_RENDERING_CONTEXTS(DDLSurfaceCharacterizationTest, reporter, ctxInfo) {