diff options
author | Brian Salomon <bsalomon@google.com> | 2018-05-01 18:49:38 +0000 |
---|---|---|
committer | Skia Commit-Bot <skia-commit-bot@chromium.org> | 2018-05-01 18:49:46 +0000 |
commit | 763abf01643cb738b81b66b8e1d296a7247b4af4 (patch) | |
tree | b50f2a8ce4e941c7e58ffe9604bb3bf806f27459 | |
parent | 101d56359a5a5dc3b8a2a4149ac171e25eb0bec0 (diff) |
Revert "Use a cached index buffer for triangle fans in GrDefaultPathRenderer."
This reverts commit ddff425b0a9cd4b178c74d7feee2c5c22e37c8d1.
Reason for revert: bad gms
Original change's description:
> Use a cached index buffer for triangle fans in GrDefaultPathRenderer.
>
> Change-Id: I3c3c8db6506c71e4b273c8bc7adcc68d3d768626
> Reviewed-on: https://skia-review.googlesource.com/124841
> Reviewed-by: Brian Osman <brianosman@google.com>
> Commit-Queue: Brian Salomon <bsalomon@google.com>
TBR=bsalomon@google.com,brianosman@google.com
Change-Id: I701b55f188c949c2ee39b39f9bbf5b233f80f174
No-Presubmit: true
No-Tree-Checks: true
No-Try: true
Reviewed-on: https://skia-review.googlesource.com/125040
Reviewed-by: Brian Salomon <bsalomon@google.com>
Commit-Queue: Brian Salomon <bsalomon@google.com>
-rw-r--r-- | src/gpu/GrResourceProvider.cpp | 42 | ||||
-rw-r--r-- | src/gpu/GrResourceProvider.h | 30 | ||||
-rw-r--r-- | src/gpu/ops/GrDefaultPathRenderer.cpp | 66 |
3 files changed, 33 insertions, 105 deletions
diff --git a/src/gpu/GrResourceProvider.cpp b/src/gpu/GrResourceProvider.cpp index 62e2675b79..2d2b3a7bc9 100644 --- a/src/gpu/GrResourceProvider.cpp +++ b/src/gpu/GrResourceProvider.cpp @@ -27,7 +27,6 @@ #include "SkMathPriv.h" GR_DECLARE_STATIC_UNIQUE_KEY(gQuadIndexBufferKey); -GR_DECLARE_STATIC_UNIQUE_KEY(gFanIndexBufferKey); const uint32_t GrResourceProvider::kMinScratchTextureSize = 16; @@ -60,9 +59,6 @@ GrResourceProvider::GrResourceProvider(GrGpu* gpu, GrResourceCache* cache, GrSin GR_DEFINE_STATIC_UNIQUE_KEY(gQuadIndexBufferKey); fQuadIndexBufferKey = gQuadIndexBufferKey; - - GR_DEFINE_STATIC_UNIQUE_KEY(gFanIndexBufferKey); - fFanIndexBufferKey = gFanIndexBufferKey; } sk_sp<GrTexture> GrResourceProvider::createTexture(const GrSurfaceDesc& desc, SkBudgeted budgeted, @@ -345,49 +341,13 @@ sk_sp<const GrBuffer> GrResourceProvider::createPatternedIndexBuffer(const uint1 static constexpr int kMaxQuads = 1 << 12; // max possible: (1 << 14) - 1; -int GrResourceProvider::QuadCountOfQuadBuffer() { return kMaxQuads; } - sk_sp<const GrBuffer> GrResourceProvider::createQuadIndexBuffer() { GR_STATIC_ASSERT(4 * kMaxQuads <= 65535); static const uint16_t kPattern[] = { 0, 1, 2, 2, 1, 3 }; return this->createPatternedIndexBuffer(kPattern, 6, kMaxQuads, 4, fQuadIndexBufferKey); } -// Don't make this maximally sized. It'd be way bigger than required for most cases. -static constexpr int kMaxFanTris = 1 << 12; - -int GrResourceProvider::TriCountOfFanBuffer() { return kMaxFanTris; } - -sk_sp<const GrBuffer> GrResourceProvider::createFanIndexBuffer() { - GR_STATIC_ASSERT(kMaxFanTris + 2 <= SK_MaxU16 + 1); - size_t numIndices = kMaxFanTris * 3; - size_t bufferSize = numIndices * sizeof(uint16_t); - sk_sp<GrBuffer> buffer(this->createBuffer(bufferSize, kIndex_GrBufferType, - kStatic_GrAccessPattern, kNoPendingIO_Flag)); - if (!buffer) { - return nullptr; - } - uint16_t* data = (uint16_t*)buffer->map(); - SkAutoTArray<uint16_t> temp; - if (!data) { - temp.reset(numIndices); - data = temp.get(); - } - for (int i = 0; i < kMaxFanTris; ++i) { - data[3 * i + 0] = 0; - data[3 * i + 1] = i + 1; - data[3 * i + 2] = i + 2; - } - if (temp.get()) { - if (!buffer->updateData(data, bufferSize)) { - return nullptr; - } - } else { - buffer->unmap(); - } - this->assignUniqueKeyToResource(fFanIndexBufferKey, buffer.get()); - return std::move(buffer); -} +int GrResourceProvider::QuadCountOfQuadBuffer() { return kMaxQuads; } sk_sp<GrPath> GrResourceProvider::createPath(const SkPath& path, const GrStyle& style) { if (this->isAbandoned()) { diff --git a/src/gpu/GrResourceProvider.h b/src/gpu/GrResourceProvider.h index e8f93b561f..a853f08ca3 100644 --- a/src/gpu/GrResourceProvider.h +++ b/src/gpu/GrResourceProvider.h @@ -150,9 +150,9 @@ public: /** * Returns an index buffer that can be used to render quads. * Six indices per quad: 0, 1, 2, 2, 1, 3, etc. - * The max number of quads is specified by QuadCountOfQuadBuffer(). + * The max number of quads is the buffer's index capacity divided by 6. * Draw with GrPrimitiveType::kTriangles - * @return the quad index buffer + * @ return the quad index buffer */ sk_sp<const GrBuffer> refQuadIndexBuffer() { if (auto buffer = this->findByUniqueKey<const GrBuffer>(fQuadIndexBufferKey)) { @@ -164,22 +164,6 @@ public: static int QuadCountOfQuadBuffer(); /** - * Returns an index buffer that can be used to render triangle fans. - * The buffer has the pattern 0, 1, 2, 0, 2, 3, 0, 3, 4 ... - * The max number of quads is specified by TriCountOfFanBuffer(). - * Draw with GrPrimitiveType::kTriangles - * @return the fan index buffer - */ - sk_sp<const GrBuffer> refFanIndexBuffer() { - if (auto buffer = this->findByUniqueKey<const GrBuffer>(fFanIndexBufferKey)) { - return buffer; - } - return this->createFanIndexBuffer(); - } - - static int TriCountOfFanBuffer(); - - /** * Factories for GrPath objects. It's an error to call these if path rendering * is not supported. */ @@ -311,14 +295,12 @@ private: const GrUniqueKey& key); sk_sp<const GrBuffer> createQuadIndexBuffer(); - sk_sp<const GrBuffer> createFanIndexBuffer(); - GrResourceCache* fCache; - GrGpu* fGpu; + GrResourceCache* fCache; + GrGpu* fGpu; sk_sp<const GrCaps> fCaps; - GrUniqueKey fQuadIndexBufferKey; - GrUniqueKey fFanIndexBufferKey; - bool fExplicitlyAllocateGPUResources; + GrUniqueKey fQuadIndexBufferKey; + bool fExplicitlyAllocateGPUResources; // In debug builds we guard against improper thread handling SkDEBUGCODE(mutable GrSingleOwner* fSingleOwner;) diff --git a/src/gpu/ops/GrDefaultPathRenderer.cpp b/src/gpu/ops/GrDefaultPathRenderer.cpp index 00e2b88087..1c5acb0a82 100644 --- a/src/gpu/ops/GrDefaultPathRenderer.cpp +++ b/src/gpu/ops/GrDefaultPathRenderer.cpp @@ -61,20 +61,17 @@ namespace { class PathGeoBuilder { public: - PathGeoBuilder(GrPrimitiveType primitiveType, bool useTriFanIndexBuffer, - GrMeshDrawOp::Target* target, GrGeometryProcessor* geometryProcessor, - const GrPipeline* pipeline) + PathGeoBuilder(GrPrimitiveType primitiveType, GrMeshDrawOp::Target* target, + GrGeometryProcessor* geometryProcessor, const GrPipeline* pipeline) : fMesh(primitiveType) , fTarget(target) , fVertexStride(sizeof(SkPoint)) , fGeometryProcessor(geometryProcessor) , fPipeline(pipeline) , fIndexBuffer(nullptr) - , fUseTriFanIndexBuffer(useTriFanIndexBuffer) , fFirstIndex(0) , fIndicesInChunk(0) , fIndices(nullptr) { - SkASSERT(!fUseTriFanIndexBuffer || GrPrimitiveType::kTriangles == primitiveType); this->allocNewBuffers(); } @@ -95,7 +92,7 @@ public: void addLine(const SkPoint& p) { needSpace(1, this->indexScale()); - if (this->isDynamicallyIndexed()) { + if (this->isIndexed()) { uint16_t prevIdx = this->currentIndex() - 1; appendCountourEdgeIndices(prevIdx); } @@ -111,7 +108,7 @@ public: uint16_t numPts = (uint16_t)GrPathUtils::generateQuadraticPoints( pts[0], pts[1], pts[2], srcSpaceTolSqd, &fCurVert, GrPathUtils::quadraticPointCount(pts, srcSpaceTol)); - if (this->isDynamicallyIndexed()) { + if (this->isIndexed()) { for (uint16_t i = 0; i < numPts; ++i) { appendCountourEdgeIndices(firstQPtIdx + i); } @@ -136,7 +133,7 @@ public: uint16_t numPts = (uint16_t) GrPathUtils::generateCubicPoints( pts[0], pts[1], pts[2], pts[3], srcSpaceTolSqd, &fCurVert, GrPathUtils::cubicPointCount(pts, srcSpaceTol)); - if (this->isDynamicallyIndexed()) { + if (this->isIndexed()) { for (uint16_t i = 0; i < numPts; ++i) { appendCountourEdgeIndices(firstCPtIdx + i); } @@ -197,9 +194,9 @@ private: * Derived properties * TODO: Cache some of these for better performance, rather than re-computing? */ - bool isDynamicallyIndexed() const { - return !fUseTriFanIndexBuffer && (GrPrimitiveType::kLines == fMesh.primitiveType() || - GrPrimitiveType::kTriangles == fMesh.primitiveType()); + bool isIndexed() const { + return GrPrimitiveType::kLines == fMesh.primitiveType() || + GrPrimitiveType::kTriangles == fMesh.primitiveType(); } bool isHairline() const { return GrPrimitiveType::kLines == fMesh.primitiveType() || @@ -226,7 +223,6 @@ private: // which have a worst-case of 1k points. static const int kMinVerticesPerChunk = GrPathUtils::kMaxPointsPerCurve + 2; static const int kFallbackVerticesPerChunk = 16384; - GR_STATIC_ASSERT(kFallbackVerticesPerChunk <= SK_MaxU16 + 1); fVertices = static_cast<SkPoint*>(fTarget->makeVertexSpaceAtLeast(fVertexStride, kMinVerticesPerChunk, @@ -235,7 +231,7 @@ private: &fFirstVertex, &fVerticesInChunk)); - if (this->isDynamicallyIndexed()) { + if (this->isIndexed()) { // Similar to above: Ensure we get enough indices for one worst-case quad/cubic. // No extra indices are needed for stitching, though. If we can't get that many, ask // for enough to match our large vertex request. @@ -269,25 +265,14 @@ private: SkASSERT(vertexCount <= fVerticesInChunk); SkASSERT(indexCount <= fIndicesInChunk); - if (fUseTriFanIndexBuffer) { - if (vertexCount >= 3) { - if (auto indexBuffer = fTarget->resourceProvider()->refFanIndexBuffer()) { - fMesh.setIndexed(indexBuffer.get(), 3 * (vertexCount - 2), 0, 0, - vertexCount - 1); - fMesh.setVertexData(fVertexBuffer, fFirstVertex); - fTarget->draw(fGeometryProcessor, fPipeline, fMesh); - } - } - } else { - if (this->isDynamicallyIndexed() ? SkToBool(indexCount) : SkToBool(vertexCount)) { - if (!this->isDynamicallyIndexed()) { - fMesh.setNonIndexedNonInstanced(vertexCount); - } else { - fMesh.setIndexed(fIndexBuffer, indexCount, fFirstIndex, 0, vertexCount - 1); - } - fMesh.setVertexData(fVertexBuffer, fFirstVertex); - fTarget->draw(fGeometryProcessor, fPipeline, fMesh); + if (this->isIndexed() ? SkToBool(indexCount) : SkToBool(vertexCount)) { + if (!this->isIndexed()) { + fMesh.setNonIndexedNonInstanced(vertexCount); + } else { + fMesh.setIndexed(fIndexBuffer, indexCount, fFirstIndex, 0, vertexCount - 1); } + fMesh.setVertexData(fVertexBuffer, fFirstVertex); + fTarget->draw(fGeometryProcessor, fPipeline, fMesh); } fTarget->putBackIndices((size_t)(fIndicesInChunk - indexCount)); @@ -333,7 +318,6 @@ private: SkPoint* fCurVert; const GrBuffer* fIndexBuffer; - bool fUseTriFanIndexBuffer; int fFirstIndex; int fIndicesInChunk; uint16_t* fIndices; @@ -414,25 +398,27 @@ private: SkASSERT(gp->getVertexStride() == sizeof(SkPoint)); - bool useFanIndexBuffer = false; - bool singleContour = - 1 == fPaths.count() && !PathGeoBuilder::PathHasMultipleSubpaths(fPaths[0].fPath); + int instanceCount = fPaths.count(); + + // We avoid indices when we have a single hairline contour. + bool isIndexed = !this->isHairline() || instanceCount > 1 || + PathGeoBuilder::PathHasMultipleSubpaths(fPaths[0].fPath); // determine primitiveType GrPrimitiveType primitiveType; if (this->isHairline()) { - primitiveType = singleContour ? GrPrimitiveType::kLineStrip : GrPrimitiveType::kLines; + primitiveType = isIndexed ? GrPrimitiveType::kLines : GrPrimitiveType::kLineStrip; } else { - useFanIndexBuffer = singleContour; primitiveType = GrPrimitiveType::kTriangles; } - PathGeoBuilder pathGeoBuilder(primitiveType, useFanIndexBuffer, target, gp.get(), + PathGeoBuilder pathGeoBuilder(primitiveType, target, gp.get(), fHelper.makePipeline(target)); // fill buffers - for (const auto& instance : fPaths) { - pathGeoBuilder.addPath(instance.fPath, instance.fTolerance); + for (int i = 0; i < instanceCount; i++) { + const PathData& args = fPaths[i]; + pathGeoBuilder.addPath(args.fPath, args.fTolerance); } } |