[graphite] Implement convex wedge tessellating renderer

Cq-Include-Trybots: luci.skia.skia.primary:Test-Mac12-Clang-MacBookPro16.2-GPU-IntelIrisPlus-x86_64-Debug-All-Graphite,Test-Mac11-Clang-MacMini9.1-GPU-AppleM1-arm64-Release-All-Graphite,Test-Mac11-Clang-MacMini9.1-GPU-AppleM1-arm64-Debug-All-ASAN_Graphite,Test-Mac10.15.7-Clang-MacBookPro11.5-GPU-RadeonHD8870M-x86_64-Debug-All-Graphite,Perf-Mac11-Clang-MacMini9.1-GPU-AppleM1-arm64-Release-All-Graphite,Perf-Mac10.15.7-Clang-MacBookPro11.5-GPU-RadeonHD8870M-x86_64-Release-All-Graphite,Build-Mac-Clang-x86_64-Release-Graphite,Build-Mac-Clang-x86_64-Debug-Graphite,Build-Mac-Clang-arm64-Release-iOS_Graphite,Build-Mac-Clang-arm64-Release-Graphite,Build-Mac-Clang-arm64-Debug-iOS_Graphite,Build-Mac-Clang-arm64-Debug-Graphite_NoGpu,Build-Mac-Clang-arm64-Debug-Graphite,Build-Mac-Clang-arm64-Debug-ASAN_Graphite
Bug: skia:12703
Change-Id: If00b6b40ed40be42c4337f3c8ffe504c9f6e667f
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/522097
Reviewed-by: Greg Daniel <egdaniel@google.com>
Commit-Queue: Michael Ludwig <michaelludwig@google.com>
This commit is contained in:
Michael Ludwig 2022-03-21 15:55:57 -04:00 committed by SkCQ
parent 10258645fc
commit 86781bd10c
7 changed files with 50 additions and 27 deletions

View File

@ -487,20 +487,21 @@ void Device::recordDraw(const Transform& localToDevice,
// are large enough to exceed the fixed count tessellation limits.
const Renderer* renderer = nullptr;
// TODO: Combine this heuristic with what is used in PathStencilCoverOp to choose between wedges
// curves consistently in Graphite and Ganesh.
const bool preferWedges = (shape.isPath() && shape.path().countVerbs() < 50) ||
clip.drawBounds().area() <= (256 * 256);
// TODO: Route all filled shapes to stencil-and-cover for the sprint; convex will draw
// correctly but uses an unnecessary stencil step.
// if (shape.convex()) {
// renderer = Renderer::ConvexPath();
// } else {
if (preferWedges) {
renderer = &Renderer::StencilTessellatedWedges(shape.fillType());
if (shape.convex() && !shape.inverted()) {
// TODO: Ganesh doesn't have a curve+middle-out triangles option for convex paths, but it
// would be pretty trivial to spin up.
renderer = &Renderer::ConvexTessellatedWedges();
} else {
renderer = &Renderer::StencilTessellatedCurvesAndTris(shape.fillType());
// TODO: Combine this heuristic with what is used in PathStencilCoverOp to choose between
// wedges curves consistently in Graphite and Ganesh.
const bool preferWedges = (shape.isPath() && shape.path().countVerbs() < 50) ||
clip.drawBounds().area() <= (256 * 256);
if (preferWedges) {
renderer = &Renderer::StencilTessellatedWedges(shape.fillType());
} else {
renderer = &Renderer::StencilTessellatedCurvesAndTris(shape.fillType());
}
}
if (!renderer) {

View File

@ -209,8 +209,10 @@ public:
static const Renderer& StencilTessellatedCurvesAndTris(SkPathFillType);
static const Renderer& StencilTessellatedWedges(SkPathFillType);
static const Renderer& ConvexTessellatedWedges();
// TODO: Not on the immediate sprint target, but show what needs to be added for DrawList's API
// static const Renderer& FillConvexPath();
// static const Renderer& StrokePath();
// TODO: Will add more of these as primitive rendering etc. is fleshed out

View File

@ -23,6 +23,7 @@ namespace skgpu::mtl {
bool FormatIsDepthOrStencil(MTLPixelFormat format) {
switch (format) {
case MTLPixelFormatStencil8: // fallthrough
case MTLPixelFormatDepth32Float:
case MTLPixelFormatDepth32Float_Stencil8:
return true;
default:
@ -32,6 +33,7 @@ bool FormatIsDepthOrStencil(MTLPixelFormat format) {
bool FormatIsDepth(MTLPixelFormat format) {
switch (format) {
case MTLPixelFormatDepth32Float:
case MTLPixelFormatDepth32Float_Stencil8:
return true;
default:

View File

@ -103,7 +103,7 @@ constexpr DepthStencilSettings::Face kPassZero = {
// stencil buffer has been modified by either kWindingStencilPass or kEvenOddStencilPass.
constexpr DepthStencilSettings kRegularCoverPass = {
/*frontStencil=*/kPassNonZero,
/*frontStencil=*/kPassNonZero,
/*backStencil=*/ kPassNonZero,
/*refValue=*/ 0,
/*stencilTest=*/ true,
/*depthCompare=*/CompareOp::kAlways, // TODO: kGreater once steps know the right depth value
@ -115,7 +115,7 @@ constexpr DepthStencilSettings kRegularCoverPass = {
// stencil buffer has been modified by either kWindingStencilPass or kEvenOddStencilPass.
constexpr DepthStencilSettings kInverseCoverPass = {
/*frontStencil=*/kPassZero,
/*frontStencil=*/kPassZero,
/*backStencil=*/ kPassZero,
/*refValue=*/ 0,
/*stencilTest=*/ true,
/*depthCompare=*/CompareOp::kAlways, // TODO: kGreater once steps know the right depth value

View File

@ -9,6 +9,7 @@
#include "experimental/graphite/src/render/CoverBoundsRenderStep.h"
#include "experimental/graphite/src/render/MiddleOutFanRenderStep.h"
#include "experimental/graphite/src/render/StencilAndCoverDSS.h"
#include "experimental/graphite/src/render/TessellateCurvesRenderStep.h"
#include "experimental/graphite/src/render/TessellateWedgesRenderStep.h"
#include "include/core/SkPathTypes.h"
@ -27,6 +28,16 @@ const RenderStep* inverse_cover_step() {
return &kInverseFill;
}
static constexpr DepthStencilSettings kDirectShadingPass = {
/*frontStencil=*/{},
/*backStencil=*/ {},
/*refValue=*/ 0,
/*stencilTest=*/ false,
/*depthCompare=*/CompareOp::kAlways, // TODO: switch to greater
/*depthTest=*/ true,
/*depthWrite=*/ true
};
} // namespace
const Renderer& Renderer::StencilTessellatedCurvesAndTris(SkPathFillType fillType) {
@ -64,8 +75,8 @@ const Renderer& Renderer::StencilTessellatedCurvesAndTris(SkPathFillType fillTyp
}
const Renderer& Renderer::StencilTessellatedWedges(SkPathFillType fillType) {
static const TessellateWedgesRenderStep kWindingStencilWedges{false};
static const TessellateWedgesRenderStep kEvenOddStencilWedges{true};
static const TessellateWedgesRenderStep kWindingStencilWedges{"winding", kWindingStencilPass};
static const TessellateWedgesRenderStep kEvenOddStencilWedges{"even-odd", kEvenOddStencilPass};
static const Renderer kWindingRenderer{"StencilTessellatedWedges[winding]",
&kWindingStencilWedges,
@ -89,4 +100,10 @@ const Renderer& Renderer::StencilTessellatedWedges(SkPathFillType fillType) {
SkUNREACHABLE;
}
const Renderer& Renderer::ConvexTessellatedWedges() {
static const TessellateWedgesRenderStep kConvexWedges{"convex", kDirectShadingPass};
static const Renderer kConvexWedgeRenderer{"ConvexTessellatedWedges", &kConvexWedges};
return kConvexWedgeRenderer;
}
} // namespace skgpu

View File

@ -10,7 +10,6 @@
#include "experimental/graphite/src/DrawWriter.h"
#include "experimental/graphite/src/geom/Shape.h"
#include "experimental/graphite/src/geom/Transform_graphite.h"
#include "experimental/graphite/src/render/StencilAndCoverDSS.h"
#include "src/gpu/tessellate/AffineMatrix.h"
#include "src/gpu/tessellate/MidpointContourParser.h"
@ -67,13 +66,16 @@ size_t fixed_index_buffer_size() {
} // namespace
TessellateWedgesRenderStep::TessellateWedgesRenderStep(bool evenOdd)
TessellateWedgesRenderStep::TessellateWedgesRenderStep(std::string_view variantName,
DepthStencilSettings depthStencilSettings)
: RenderStep("TessellateWedgesRenderStep",
evenOdd ? "even-odd" : "winding",
Flags::kRequiresMSAA,
variantName,
Flags::kRequiresMSAA |
(depthStencilSettings.fDepthWriteEnabled ? Flags::kPerformsShading
: Flags::kNone),
/*uniforms=*/{},
PrimitiveType::kTriangles,
evenOdd ? kEvenOddStencilPass : kWindingStencilPass,
depthStencilSettings,
/*vertexAttrs=*/ {{"resolveLevel_and_idx",
VertexAttribType::kFloat2, SkSLType::kFloat2}},
/*instanceAttrs=*/{{"p01", VertexAttribType::kFloat4, SkSLType::kFloat4},

View File

@ -14,10 +14,8 @@ namespace skgpu {
class TessellateWedgesRenderStep final : public RenderStep {
public:
// TODO: If this takes DepthStencilSettings directly and a way to adjust the flags to specify
// that it performs shading, this RenderStep definition can be shared between the stencil and
// the convex rendering variants.
TessellateWedgesRenderStep(bool evenOdd);
TessellateWedgesRenderStep(std::string_view variantName,
DepthStencilSettings depthStencilSettings);
~TessellateWedgesRenderStep() override;
@ -30,6 +28,7 @@ public:
const SkIRect&,
const Transform&,
const Shape&) const override;
};
} // namespace skgpu