blob: ceda8be4838a285d31f388f45ff0fe7e68f456fc [file] [log] [blame]
/*
* Copyright 2015 Google Inc.
*
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
#ifndef GrSurfaceDrawContext_DEFINED
#define GrSurfaceDrawContext_DEFINED
#include "include/core/SkCanvas.h"
#include "include/core/SkDrawable.h"
#include "include/core/SkRefCnt.h"
#include "include/core/SkSurface.h"
#include "include/core/SkSurfaceProps.h"
#include "include/private/GrTypesPriv.h"
#include "src/core/SkGlyphRunPainter.h"
#include "src/gpu/GrOpsTask.h"
#include "src/gpu/GrPaint.h"
#include "src/gpu/GrRenderTargetProxy.h"
#include "src/gpu/GrSurfaceFillContext.h"
#include "src/gpu/GrSurfaceProxyView.h"
#include "src/gpu/GrXferProcessor.h"
#include "src/gpu/geometry/GrQuad.h"
#include "src/gpu/text/GrTextBlob.h"
class GrBackendSemaphore;
class GrClip;
class GrColorSpaceXform;
class GrCoverageCountingPathRenderer;
class GrDrawOp;
class GrOp;
class GrRenderTarget;
class GrStyledShape;
class GrStyle;
class GrTextureProxy;
struct GrUserStencilSettings;
struct SkDrawShadowRec;
class SkGlyphRunList;
struct SkIPoint;
struct SkIRect;
class SkLatticeIter;
class SkMatrixProvider;
class SkMatrix;
class SkPaint;
class SkPath;
struct SkPoint;
struct SkRect;
class SkRegion;
class SkRRect;
struct SkRSXform;
class SkRuntimeEffect;
class SkTextBlob;
class SkVertices;
/**
* A helper object to orchestrate commands (draws, etc...) for GrSurfaces that are GrRenderTargets.
*/
class GrSurfaceDrawContext : public GrSurfaceFillContext {
public:
static std::unique_ptr<GrSurfaceDrawContext> Make(GrRecordingContext*,
GrColorType,
sk_sp<SkColorSpace>,
sk_sp<GrSurfaceProxy>,
GrSurfaceOrigin,
const SkSurfaceProps*,
bool flushTimeOpsTask = false);
/* Uses the default texture format for the color type */
static std::unique_ptr<GrSurfaceDrawContext> Make(GrRecordingContext*,
GrColorType,
sk_sp<SkColorSpace>,
SkBackingFit,
SkISize dimensions,
int sampleCnt = 1,
GrMipmapped = GrMipmapped::kNo,
GrProtected = GrProtected::kNo,
GrSurfaceOrigin = kBottomLeft_GrSurfaceOrigin,
SkBudgeted = SkBudgeted::kYes,
const SkSurfaceProps* = nullptr);
/**
* Takes custom swizzles rather than determining swizzles from color type and format.
* It will have color type kUnknown.
*/
static std::unique_ptr<GrSurfaceDrawContext> Make(GrRecordingContext*,
sk_sp<SkColorSpace>,
SkBackingFit,
SkISize dimensions,
const GrBackendFormat&,
int sampleCnt,
GrMipmapped,
GrProtected,
GrSwizzle readSwizzle,
GrSwizzle writeSwizzle,
GrSurfaceOrigin,
SkBudgeted,
const SkSurfaceProps*);
// Same as previous factory but will try to use fallback GrColorTypes if the one passed in
// fails. The fallback GrColorType will have at least the number of channels and precision per
// channel as the passed in GrColorType. It may also swizzle the changes (e.g., BGRA -> RGBA).
// SRGB-ness will be preserved.
static std::unique_ptr<GrSurfaceDrawContext> MakeWithFallback(
GrRecordingContext*,
GrColorType,
sk_sp<SkColorSpace>,
SkBackingFit,
SkISize dimensions,
int sampleCnt = 1,
GrMipmapped = GrMipmapped::kNo,
GrProtected = GrProtected::kNo,
GrSurfaceOrigin = kBottomLeft_GrSurfaceOrigin,
SkBudgeted = SkBudgeted::kYes,
const SkSurfaceProps* = nullptr);
// These match the definitions in SkSurface & GrSurface.h, for whence they came
typedef void* ReleaseContext;
typedef void (*ReleaseProc)(ReleaseContext);
// Creates a GrSurfaceDrawContext that wraps the passed in GrBackendTexture.
static std::unique_ptr<GrSurfaceDrawContext> MakeFromBackendTexture(
GrRecordingContext*, GrColorType, sk_sp<SkColorSpace>, const GrBackendTexture&,
int sampleCnt, GrSurfaceOrigin, const SkSurfaceProps*,
sk_sp<GrRefCntedCallback> releaseHelper);
static std::unique_ptr<GrSurfaceDrawContext> MakeFromBackendRenderTarget(
GrRecordingContext*,
GrColorType,
sk_sp<SkColorSpace>,
const GrBackendRenderTarget&,
GrSurfaceOrigin,
const SkSurfaceProps*,
sk_sp<GrRefCntedCallback> releaseHelper);
static std::unique_ptr<GrSurfaceDrawContext> MakeFromVulkanSecondaryCB(
GrRecordingContext*, const SkImageInfo&, const GrVkDrawableInfo&,
const SkSurfaceProps*);
GrSurfaceDrawContext(GrRecordingContext*,
GrSurfaceProxyView readView,
GrSurfaceProxyView writeView,
GrColorType,
sk_sp<SkColorSpace>,
const SkSurfaceProps*,
bool flushTimeOpsTask = false);
~GrSurfaceDrawContext() override;
/**
* Draw everywhere (respecting the clip) with the paint.
*/
void drawPaint(const GrClip*, GrPaint&&, const SkMatrix& viewMatrix);
/**
* Draw the rect using a paint.
* @param paint describes how to color pixels.
* @param GrAA Controls whether rect is antialiased
* @param viewMatrix transformation matrix
* @param style The style to apply. Null means fill. Currently path effects are not
* allowed.
* The rects coords are used to access the paint (through texture matrix)
*/
void drawRect(const GrClip*,
GrPaint&& paint,
GrAA,
const SkMatrix& viewMatrix,
const SkRect&,
const GrStyle* style = nullptr);
/**
* Maps a rectangle of shader coordinates to a rectangle and fills that rectangle.
*
* @param paint describes how to color pixels.
* @param GrAA Controls whether rect is antialiased
* @param viewMatrix transformation matrix which applies to rectToDraw
* @param rectToDraw the rectangle to draw
* @param localRect the rectangle of shader coordinates applied to rectToDraw
*/
void fillRectToRect(const GrClip* clip,
GrPaint&& paint,
GrAA aa,
const SkMatrix& viewMatrix,
const SkRect& rectToDraw,
const SkRect& localRect) {
DrawQuad quad{GrQuad::MakeFromRect(rectToDraw, viewMatrix), GrQuad(localRect),
aa == GrAA::kYes ? GrQuadAAFlags::kAll : GrQuadAAFlags::kNone};
this->drawFilledQuad(clip, std::move(paint), aa, &quad);
}
/**
* Fills a rect with a paint and a localMatrix.
*/
void fillRectWithLocalMatrix(const GrClip* clip,
GrPaint&& paint,
GrAA aa,
const SkMatrix& viewMatrix,
const SkRect& rect,
const SkMatrix& localMatrix) {
DrawQuad quad{GrQuad::MakeFromRect(rect, viewMatrix),
GrQuad::MakeFromRect(rect, localMatrix),
aa == GrAA::kYes ? GrQuadAAFlags::kAll : GrQuadAAFlags::kNone};
this->drawFilledQuad(clip, std::move(paint), aa, &quad);
}
/**
* Creates an op that draws a fill rect with per-edge control over anti-aliasing.
*
* This is a specialized version of fillQuadWithEdgeAA, but is kept separate since knowing
* the geometry is a rectangle affords more optimizations.
*/
void fillRectWithEdgeAA(const GrClip* clip, GrPaint&& paint, GrAA aa, GrQuadAAFlags edgeAA,
const SkMatrix& viewMatrix, const SkRect& rect,
const SkRect* optionalLocalRect = nullptr) {
const SkRect& localRect = optionalLocalRect ? *optionalLocalRect : rect;
DrawQuad quad{GrQuad::MakeFromRect(rect, viewMatrix), GrQuad(localRect), edgeAA};
this->drawFilledQuad(clip, std::move(paint), aa, &quad);
}
/**
* Similar to fillRectWithEdgeAA but draws an arbitrary 2D convex quadrilateral transformed
* by 'viewMatrix', with per-edge control over anti-aliasing. The quad should follow the
* ordering used by SkRect::toQuad(), which determines how the edge AA is applied:
* - "top" = points [0] and [1]
* - "right" = points[1] and [2]
* - "bottom" = points[2] and [3]
* - "left" = points[3] and [0]
*
* The last argument, 'optionalLocalQuad', can be null if no separate local coordinates are
* necessary.
*/
void fillQuadWithEdgeAA(const GrClip* clip, GrPaint&& paint, GrAA aa, GrQuadAAFlags edgeAA,
const SkMatrix& viewMatrix, const SkPoint points[4],
const SkPoint optionalLocalPoints[4]) {
const SkPoint* localPoints = optionalLocalPoints ? optionalLocalPoints : points;
DrawQuad quad{GrQuad::MakeFromSkQuad(points, viewMatrix),
GrQuad::MakeFromSkQuad(localPoints, SkMatrix::I()), edgeAA};
this->drawFilledQuad(clip, std::move(paint), aa, &quad);
}
/** Used with drawQuadSet */
struct QuadSetEntry {
SkRect fRect;
SkPMColor4f fColor; // Overrides any color on the GrPaint
SkMatrix fLocalMatrix;
GrQuadAAFlags fAAFlags;
};
// TODO(michaelludwig) - remove if the bulk API is not useful for SkiaRenderer
void drawQuadSet(const GrClip* clip, GrPaint&& paint, GrAA aa, const SkMatrix& viewMatrix,
const QuadSetEntry[], int cnt);
/**
* Creates an op that draws a subrectangle of a texture. The passed color is modulated by the
* texture's color. 'srcRect' specifies the rectangle of the texture to draw. 'dstRect'
* specifies the rectangle to draw in local coords which will be transformed by 'viewMatrix' to
* device space.
*/
void drawTexture(const GrClip* clip,
GrSurfaceProxyView view,
SkAlphaType srcAlphaType,
GrSamplerState::Filter filter,
GrSamplerState::MipmapMode mm,
SkBlendMode mode,
const SkPMColor4f& color,
const SkRect& srcRect,
const SkRect& dstRect,
GrAA aa,
GrQuadAAFlags edgeAA,
SkCanvas::SrcRectConstraint constraint,
const SkMatrix& viewMatrix,
sk_sp<GrColorSpaceXform> texXform) {
const SkRect* subset = constraint == SkCanvas::kStrict_SrcRectConstraint ?
&srcRect : nullptr;
DrawQuad quad{GrQuad::MakeFromRect(dstRect, viewMatrix), GrQuad(srcRect), edgeAA};
this->drawTexturedQuad(clip, std::move(view), srcAlphaType, std::move(texXform), filter, mm,
color, mode, aa, &quad, subset);
}
/**
* Variant of drawTexture that instead draws the texture applied to 'dstQuad' transformed by
* 'viewMatrix', using the 'srcQuad' texture coordinates clamped to the optional 'subset'. If
* 'subset' is null, it's equivalent to using the fast src rect constraint. If 'subset' is
* provided, the strict src rect constraint is applied using 'subset'.
*/
void drawTextureQuad(const GrClip* clip,
GrSurfaceProxyView view,
GrColorType srcColorType,
SkAlphaType srcAlphaType,
GrSamplerState::Filter filter,
GrSamplerState::MipmapMode mm,
SkBlendMode mode,
const SkPMColor4f& color,
const SkPoint srcQuad[4],
const SkPoint dstQuad[4],
GrAA aa,
GrQuadAAFlags edgeAA,
const SkRect* subset,
const SkMatrix& viewMatrix,
sk_sp<GrColorSpaceXform> texXform) {
DrawQuad quad{GrQuad::MakeFromSkQuad(dstQuad, viewMatrix),
GrQuad::MakeFromSkQuad(srcQuad, SkMatrix::I()), edgeAA};
this->drawTexturedQuad(clip, std::move(view), srcAlphaType, std::move(texXform), filter, mm,
color, mode, aa, &quad, subset);
}
/** Used with drawTextureSet */
struct TextureSetEntry {
GrSurfaceProxyView fProxyView;
SkAlphaType fSrcAlphaType;
SkRect fSrcRect;
SkRect fDstRect;
const SkPoint* fDstClipQuad; // Must be null, or point to an array of 4 points
const SkMatrix* fPreViewMatrix; // If not null, entry's CTM is 'viewMatrix' * fPreViewMatrix
SkPMColor4f fColor; // {a,a,a,a} for rgb textures, {r,g,b,a} for alpha-only textures
GrQuadAAFlags fAAFlags;
};
/**
* Draws a set of textures with a shared filter, color, view matrix, color xform, and
* texture color xform. The textures must all have the same GrTextureType and GrConfig.
*
* If any entries provide a non-null fDstClip array, it will be read from immediately based on
* fDstClipCount, so the pointer can become invalid after this returns.
*
* 'proxRunCnt' is the number of proxy changes encountered in the entry array. Technically this
* can be inferred from the array within this function, but the information is already known
* by SkGpuDevice, so no need to incur another iteration over the array.
*/
void drawTextureSet(const GrClip*,
TextureSetEntry[],
int cnt,
int proxyRunCnt,
GrSamplerState::Filter,
GrSamplerState::MipmapMode,
SkBlendMode mode,
GrAA aa,
SkCanvas::SrcRectConstraint,
const SkMatrix& viewMatrix,
sk_sp<GrColorSpaceXform> texXform);
/**
* Draw a roundrect using a paint.
*
* @param paint describes how to color pixels.
* @param GrAA Controls whether rrect is antialiased.
* @param viewMatrix transformation matrix
* @param rrect the roundrect to draw
* @param style style to apply to the rrect. Currently path effects are not allowed.
*/
void drawRRect(const GrClip*,
GrPaint&&,
GrAA,
const SkMatrix& viewMatrix,
const SkRRect& rrect,
const GrStyle& style);
/**
* Use a fast method to render the ambient and spot shadows for a path.
* Will return false if not possible for the given path.
*
* @param viewMatrix transformation matrix
* @param path the path to shadow
* @param rec parameters for shadow rendering
*/
bool drawFastShadow(const GrClip*,
const SkMatrix& viewMatrix,
const SkPath& path,
const SkDrawShadowRec& rec);
/**
* Shortcut for filling a SkPath consisting of nested rrects using a paint. The result is
* undefined if outer does not contain inner.
*
* @param paint describes how to color pixels.
* @param GrAA Controls whether rrects edges are antialiased
* @param viewMatrix transformation matrix
* @param outer the outer roundrect
* @param inner the inner roundrect
*/
void drawDRRect(const GrClip*,
GrPaint&&,
GrAA,
const SkMatrix& viewMatrix,
const SkRRect& outer,
const SkRRect& inner);
/**
* Draws a path.
*
* @param paint describes how to color pixels.
* @param GrAA Controls whether the path is antialiased.
* @param viewMatrix transformation matrix
* @param path the path to draw
* @param style style to apply to the path.
*/
void drawPath(const GrClip*,
GrPaint&&,
GrAA,
const SkMatrix& viewMatrix,
const SkPath&,
const GrStyle&);
/**
* Draws a shape.
*
* @param paint describes how to color pixels.
* @param GrAA Controls whether the path is antialiased.
* @param viewMatrix transformation matrix
* @param shape the shape to draw
*/
void drawShape(const GrClip*,
GrPaint&&,
GrAA,
const SkMatrix& viewMatrix,
GrStyledShape&&);
/**
* Draws vertices with a paint.
*
* @param paint describes how to color pixels.
* @param viewMatrix transformation matrix
* @param vertices specifies the mesh to draw.
* @param overridePrimType primitive type to draw. If NULL, derive prim type from vertices.
* @param effect runtime effect that will handle custom vertex attributes.
*/
void drawVertices(const GrClip*,
GrPaint&& paint,
const SkMatrixProvider& matrixProvider,
sk_sp<SkVertices> vertices,
GrPrimitiveType* overridePrimType = nullptr,
const SkRuntimeEffect* effect = nullptr);
/**
* Draws textured sprites from an atlas with a paint. This currently does not support AA for the
* sprite rectangle edges.
*
* @param paint describes how to color pixels.
* @param viewMatrix transformation matrix
* @param spriteCount number of sprites.
* @param xform array of compressed transformation data, required.
* @param texRect array of texture rectangles used to access the paint.
* @param colors optional array of per-sprite colors, supercedes
* the paint's color field.
*/
void drawAtlas(const GrClip*,
GrPaint&& paint,
const SkMatrix& viewMatrix,
int spriteCount,
const SkRSXform xform[],
const SkRect texRect[],
const SkColor colors[]);
/**
* Draws a region.
*
* @param paint describes how to color pixels
* @param viewMatrix transformation matrix
* @param aa should the rects of the region be antialiased.
* @param region the region to be drawn
* @param style style to apply to the region
*/
void drawRegion(const GrClip*,
GrPaint&& paint,
GrAA aa,
const SkMatrix& viewMatrix,
const SkRegion& region,
const GrStyle& style,
const GrUserStencilSettings* ss = nullptr);
/**
* Draws an oval.
*
* @param paint describes how to color pixels.
* @param GrAA Controls whether the oval is antialiased.
* @param viewMatrix transformation matrix
* @param oval the bounding rect of the oval.
* @param style style to apply to the oval. Currently path effects are not allowed.
*/
void drawOval(const GrClip*,
GrPaint&& paint,
GrAA,
const SkMatrix& viewMatrix,
const SkRect& oval,
const GrStyle& style);
/**
* Draws a partial arc of an oval.
*
* @param paint describes how to color pixels.
* @param GrGrAA Controls whether the arc is antialiased.
* @param viewMatrix transformation matrix.
* @param oval the bounding rect of the oval.
* @param startAngle starting angle in degrees.
* @param sweepAngle angle to sweep in degrees. Must be in (-360, 360)
* @param useCenter true means that the implied path begins at the oval center, connects as
* a line to the point indicated by the start contains the arc indicated by
* the sweep angle. If false the line beginning at the center point is
* omitted.
* @param style style to apply to the oval.
*/
void drawArc(const GrClip*,
GrPaint&& paint,
GrAA,
const SkMatrix& viewMatrix,
const SkRect& oval,
SkScalar startAngle,
SkScalar sweepAngle,
bool useCenter,
const GrStyle& style);
/**
* Draw the image as a set of rects, specified by |iter|.
*/
void drawImageLattice(const GrClip*,
GrPaint&&,
const SkMatrix& viewMatrix,
GrSurfaceProxyView,
SkAlphaType alphaType,
sk_sp<GrColorSpaceXform>,
GrSamplerState::Filter,
std::unique_ptr<SkLatticeIter>,
const SkRect& dst);
/**
* Draw the text specified by the SkGlyphRunList.
*
* @param viewMatrix transformationMatrix
* @param glyphRunList text, text positions, and paint.
*/
void drawGlyphRunList(const GrClip*,
const SkMatrixProvider& viewMatrix,
const SkGlyphRunList& glyphRunList);
/**
* Adds the necessary signal and wait semaphores and adds the passed in SkDrawable to the
* command stream.
*/
void drawDrawable(std::unique_ptr<SkDrawable::GpuDrawHandler>, const SkRect& bounds);
// called to note the last clip drawn to the stencil buffer.
// TODO: remove after clipping overhaul.
void setLastClip(uint32_t clipStackGenID,
const SkIRect& devClipBounds,
int numClipAnalyticElements) {
GrOpsTask* opsTask = this->getOpsTask();
opsTask->fLastClipStackGenID = clipStackGenID;
opsTask->fLastDevClipBounds = devClipBounds;
opsTask->fLastClipNumAnalyticElements = numClipAnalyticElements;
}
// called to determine if we have to render the clip into SB.
// TODO: remove after clipping overhaul.
bool mustRenderClip(uint32_t clipStackGenID,
const SkIRect& devClipBounds,
int numClipAnalyticElements) {
GrOpsTask* opsTask = this->getOpsTask();
return opsTask->fLastClipStackGenID != clipStackGenID ||
!opsTask->fLastDevClipBounds.contains(devClipBounds) ||
opsTask->fLastClipNumAnalyticElements != numClipAnalyticElements;
}
void clearStencilClip(const SkIRect& scissor, bool insideStencilMask) {
this->internalStencilClear(&scissor, insideStencilMask);
}
// While this can take a general clip, since GrReducedClip relies on this function, it must take
// care to only provide hard clips or we could get stuck in a loop. The general clip is needed
// so that path renderers can use this function.
void stencilRect(const GrClip* clip,
const GrUserStencilSettings* ss,
GrPaint&& paint,
GrAA doStencilMSAA,
const SkMatrix& viewMatrix,
const SkRect& rect,
const SkMatrix* localMatrix = nullptr) {
// Since this provides stencil settings to drawFilledQuad, it performs a different AA type
// resolution compared to regular rect draws, which is the main reason it remains separate.
DrawQuad quad{GrQuad::MakeFromRect(rect, viewMatrix),
localMatrix ? GrQuad::MakeFromRect(rect, *localMatrix) : GrQuad(rect),
GrQuadAAFlags::kNone};
this->drawFilledQuad(clip, std::move(paint), doStencilMSAA, &quad, ss);
}
void stencilPath(const GrHardClip*,
GrAA doStencilMSAA,
const SkMatrix& viewMatrix,
sk_sp<const GrPath>);
/**
* Draws a path, either AA or not, and touches the stencil buffer with the user stencil settings
* for each color sample written.
*/
bool drawAndStencilPath(const GrHardClip*,
const GrUserStencilSettings*,
SkRegion::Op op,
bool invert,
GrAA doStencilMSAA,
const SkMatrix& viewMatrix,
const SkPath&);
SkBudgeted isBudgeted() const;
int maxWindowRectangles() const;
SkGlyphRunListPainter* glyphRunPainter() { return &fGlyphPainter; }
/*
* This unique ID will not change for a given RenderTargetContext. However, it is _NOT_
* guaranteed to match the uniqueID of the underlying GrRenderTarget - beware!
*/
GrSurfaceProxy::UniqueID uniqueID() const { return this->asSurfaceProxy()->uniqueID(); }
// Allows caller of addDrawOp to know which op list an op will be added to.
using WillAddOpFn = void(GrOp*, uint32_t opsTaskID);
// These perform processing specific to GrDrawOp-derived ops before recording them into an
// op list. Before adding the op to an op list the WillAddOpFn is called. Note that it
// will not be called in the event that the op is discarded. Moreover, the op may merge into
// another op after the function is called (either before addDrawOp returns or some time later).
//
// If the clip pointer is null, no clipping will be performed.
void addDrawOp(const GrClip*,
GrOp::Owner,
const std::function<WillAddOpFn>& = std::function<WillAddOpFn>());
void addDrawOp(GrOp::Owner op) { this->addDrawOp(nullptr, std::move(op)); }
bool refsWrappedObjects() const { return this->asRenderTargetProxy()->refsWrappedObjects(); }
/**
* The next time this GrSurfaceDrawContext is flushed, the gpu will wait on the passed in
* semaphores before executing any commands.
*/
bool waitOnSemaphores(int numSemaphores, const GrBackendSemaphore waitSemaphores[],
bool deleteSemaphoresAfterWait);
int numSamples() const { return this->asRenderTargetProxy()->numSamples(); }
const SkSurfaceProps& surfaceProps() const { return fSurfaceProps; }
bool wrapsVkSecondaryCB() const { return this->asRenderTargetProxy()->wrapsVkSecondaryCB(); }
GrMipmapped mipmapped() const;
// This entry point should only be called if the backing GPU object is known to be
// instantiated.
GrRenderTarget* accessRenderTarget() { return this->asSurfaceProxy()->peekRenderTarget(); }
GrSurfaceDrawContext* asRenderTargetContext() override { return this; }
#if GR_TEST_UTILS
void testingOnly_SetPreserveOpsOnFullClear() { fPreserveOpsOnFullClear_TestingOnly = true; }
#endif
private:
enum class QuadOptimization;
GrAAType chooseAAType(GrAA);
GrOpsTask::CanDiscardPreviousOps canDiscardPreviousOpsOnFullClear() const override;
void setNeedsStencil(bool useMixedSamplesIfNotMSAA);
void internalStencilClear(const SkIRect* scissor, bool insideStencilMask);
// Only consumes the GrPaint if successful.
bool drawFilledDRRect(const GrClip* clip,
GrPaint&& paint,
GrAA,
const SkMatrix& viewMatrix,
const SkRRect& origOuter,
const SkRRect& origInner);
// If the drawn quad's paint is a const blended color, provide it as a non-null pointer to
// 'constColor', which enables the draw-as-clear optimization. Otherwise it is assumed the paint
// requires some form of shading that invalidates using a clear op.
//
// The non-const pointers should be the original draw request on input, and will be updated as
// appropriate depending on the returned optimization level.
//
// 'stencilSettings' are provided merely for decision making purposes; When non-null,
// optimization strategies that submit special ops are avoided.
QuadOptimization attemptQuadOptimization(const GrClip* clip,
const SkPMColor4f* constColor,
const GrUserStencilSettings* stencilSettings,
GrAA* aa,
DrawQuad* quad);
// If stencil settings, 'ss', are non-null, AA controls MSAA or no AA. If they are null, then AA
// can choose between coverage, MSAA as per chooseAAType(). This will always attempt to apply
// quad optimizations, so all quad/rect public APIs should rely on this function for consistent
// clipping behavior. 'quad' will be modified in place to reflect final rendered geometry.
void drawFilledQuad(const GrClip* clip,
GrPaint&& paint,
GrAA aa,
DrawQuad* quad,
const GrUserStencilSettings* ss = nullptr);
// Like drawFilledQuad but does not require using a GrPaint or FP for texturing.
// 'quad' may be modified in place to reflect final geometry.
void drawTexturedQuad(const GrClip* clip,
GrSurfaceProxyView proxyView,
SkAlphaType alphaType,
sk_sp<GrColorSpaceXform> textureXform,
GrSamplerState::Filter filter,
GrSamplerState::MipmapMode,
const SkPMColor4f& color,
SkBlendMode blendMode,
GrAA aa,
DrawQuad* quad,
const SkRect* subset = nullptr);
void drawStrokedLine(const GrClip*, GrPaint&&, GrAA, const SkMatrix&, const SkPoint[2],
const SkStrokeRec&);
// Tries to detect if the given shape is a simple, and draws it without path rendering if
// we know how.
bool drawSimpleShape(const GrClip*, GrPaint*, GrAA, const SkMatrix&, const GrStyledShape&);
// If 'attemptDrawSimple' is true, of if the original shape is marked as having been simplfied,
// this will attempt to re-route through drawSimpleShape() to see if we can avoid path rendering
// one more time.
void drawShapeUsingPathRenderer(const GrClip*, GrPaint&&, GrAA, const SkMatrix&,
GrStyledShape&&, bool attemptDrawSimple = false);
// Makes a copy of the proxy if it is necessary for the draw and places the texture that should
// be used by GrXferProcessor to access the destination color in 'result'. If the return
// value is false then a texture copy could not be made.
//
// The op should have already had setClippedBounds called on it.
bool SK_WARN_UNUSED_RESULT setupDstProxyView(const GrOp& op,
GrXferProcessor::DstProxyView* result);
SkGlyphRunListPainter* glyphPainter() { return &fGlyphPainter; }
SkSurfaceProps fSurfaceProps;
int fNumStencilSamples = 0;
GrDstSampleType fDstSampleType = GrDstSampleType::kNone;
#if GR_TEST_UTILS
bool fPreserveOpsOnFullClear_TestingOnly = false;
#endif
SkGlyphRunListPainter fGlyphPainter;
using INHERITED = GrSurfaceFillContext;
};
#endif