1/*
2 * Copyright 2018 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8#include "include/core/SkSurfaceCharacterization.h"
9
10#if SK_SUPPORT_GPU
11#include "src/gpu/GrCaps.h"
12#include "src/gpu/GrContextThreadSafeProxyPriv.h"
13
14#ifdef SK_DEBUG
15void SkSurfaceCharacterization::validate() const {
16 const GrCaps* caps = fContextInfo->priv().caps();
17
18 GrColorType grCT = SkColorTypeToGrColorType(this->colorType());
19 SkASSERT(fSampleCnt && caps->isFormatAsColorTypeRenderable(grCT, fBackendFormat, fSampleCnt));
20
21 SkASSERT(caps->areColorTypeAndFormatCompatible(grCT, fBackendFormat));
22}
23#endif
24
25
26bool SkSurfaceCharacterization::operator==(const SkSurfaceCharacterization& other) const {
27 if (!this->isValid() || !other.isValid()) {
28 return false;
29 }
30
31 if (fContextInfo != other.fContextInfo) {
32 return false;
33 }
34
35 return fCacheMaxResourceBytes == other.fCacheMaxResourceBytes &&
36 fOrigin == other.fOrigin &&
37 fImageInfo == other.fImageInfo &&
38 fBackendFormat == other.fBackendFormat &&
39 fSampleCnt == other.fSampleCnt &&
40 fIsTextureable == other.fIsTextureable &&
41 fIsMipMapped == other.fIsMipMapped &&
42 fUsesGLFBO0 == other.fUsesGLFBO0 &&
43 fVulkanSecondaryCBCompatible == other.fVulkanSecondaryCBCompatible &&
44 fIsProtected == other.fIsProtected &&
45 fSurfaceProps == other.fSurfaceProps;
46}
47
48SkSurfaceCharacterization SkSurfaceCharacterization::createResized(int width, int height) const {
49 const GrCaps* caps = fContextInfo->priv().caps();
50 if (!caps) {
51 return SkSurfaceCharacterization();
52 }
53
54 if (width <= 0 || height <= 0 || width > caps->maxRenderTargetSize() ||
55 height > caps->maxRenderTargetSize()) {
56 return SkSurfaceCharacterization();
57 }
58
59 return SkSurfaceCharacterization(fContextInfo, fCacheMaxResourceBytes,
60 fImageInfo.makeWH(width, height), fBackendFormat, fOrigin,
61 fSampleCnt, fIsTextureable, fIsMipMapped, fUsesGLFBO0,
62 fVulkanSecondaryCBCompatible, fIsProtected, fSurfaceProps);
63}
64
65SkSurfaceCharacterization SkSurfaceCharacterization::createColorSpace(
66 sk_sp<SkColorSpace> cs) const {
67 if (!this->isValid()) {
68 return SkSurfaceCharacterization();
69 }
70
71 return SkSurfaceCharacterization(fContextInfo, fCacheMaxResourceBytes,
72 fImageInfo.makeColorSpace(std::move(cs)), fBackendFormat,
73 fOrigin, fSampleCnt, fIsTextureable, fIsMipMapped, fUsesGLFBO0,
74 fVulkanSecondaryCBCompatible, fIsProtected, fSurfaceProps);
75}
76
77SkSurfaceCharacterization SkSurfaceCharacterization::createBackendFormat(
78 SkColorType colorType,
79 const GrBackendFormat& backendFormat) const {
80 if (!this->isValid()) {
81 return SkSurfaceCharacterization();
82 }
83
84 SkImageInfo newII = fImageInfo.makeColorType(colorType);
85
86 return SkSurfaceCharacterization(fContextInfo, fCacheMaxResourceBytes, newII, backendFormat,
87 fOrigin, fSampleCnt, fIsTextureable, fIsMipMapped, fUsesGLFBO0,
88 fVulkanSecondaryCBCompatible, fIsProtected, fSurfaceProps);
89}
90
91SkSurfaceCharacterization SkSurfaceCharacterization::createFBO0(bool usesGLFBO0) const {
92 if (!this->isValid()) {
93 return SkSurfaceCharacterization();
94 }
95
96 return SkSurfaceCharacterization(fContextInfo, fCacheMaxResourceBytes,
97 fImageInfo, fBackendFormat,
98 fOrigin, fSampleCnt, fIsTextureable, fIsMipMapped,
99 usesGLFBO0 ? UsesGLFBO0::kYes : UsesGLFBO0::kNo,
100 fVulkanSecondaryCBCompatible, fIsProtected, fSurfaceProps);
101}
102
103bool SkSurfaceCharacterization::isCompatible(const GrBackendTexture& backendTex) const {
104 if (!this->isValid() || !backendTex.isValid()) {
105 return false;
106 }
107
108 if (fBackendFormat != backendTex.getBackendFormat()) {
109 return false;
110 }
111
112 if (this->usesGLFBO0()) {
113 // It is a backend texture so can't be wrapping FBO0
114 return false;
115 }
116
117 if (this->vulkanSecondaryCBCompatible()) {
118 return false;
119 }
120
121 if (this->isMipMapped() && !backendTex.hasMipMaps()) {
122 // backend texture is allowed to have mipmaps even if the characterization doesn't require
123 // them.
124 return false;
125 }
126
127 if (this->width() != backendTex.width() || this->height() != backendTex.height()) {
128 return false;
129 }
130
131 if (this->isProtected() != GrProtected(backendTex.isProtected())) {
132 return false;
133 }
134
135 return true;
136}
137
138
139#endif
140