Flutter Engine
The Flutter Engine
Enumerations | Functions
skgpu::ganesh::DashOp Namespace Reference

Enumerations

enum class  AAMode { kNone , kCoverage , kCoverageWithMSAA }
 

Functions

GrOp::Owner MakeDashLineOp (GrRecordingContext *context, GrPaint &&paint, const SkMatrix &viewMatrix, const SkPoint pts[2], AAMode aaMode, const GrStyle &style, const GrUserStencilSettings *stencilSettings)
 
bool CanDrawDashLine (const SkPoint pts[2], const GrStyle &style, const SkMatrix &viewMatrix)
 

Enumeration Type Documentation

◆ AAMode

enum class skgpu::ganesh::DashOp::AAMode
strong
Enumerator
kNone 
kCoverage 
kCoverageWithMSAA 

Definition at line 21 of file DashOp.h.

Function Documentation

◆ CanDrawDashLine()

bool skgpu::ganesh::DashOp::CanDrawDashLine ( const SkPoint  pts[2],
const GrStyle style,
const SkMatrix viewMatrix 
)

Definition at line 1190 of file DashOp.cpp.

1190 {
1191 // Pts must be either horizontal or vertical in src space
1192 if (pts[0].fX != pts[1].fX && pts[0].fY != pts[1].fY) {
1193 return false;
1194 }
1195
1196 // May be able to relax this to include skew. As of now cannot do perspective
1197 // because of the non uniform scaling of bloating a rect
1198 if (!viewMatrix.preservesRightAngles()) {
1199 return false;
1200 }
1201
1202 if (!style.isDashed() || 2 != style.dashIntervalCnt()) {
1203 return false;
1204 }
1205
1206 const SkScalar* intervals = style.dashIntervals();
1207 if (0 == intervals[0] && 0 == intervals[1]) {
1208 return false;
1209 }
1210
1211 SkPaint::Cap cap = style.strokeRec().getCap();
1212 if (SkPaint::kRound_Cap == cap) {
1213 // Current we don't support round caps unless the on interval is zero
1214 if (intervals[0] != 0.f) {
1215 return false;
1216 }
1217 // If the width of the circle caps in greater than the off interval we will pick up unwanted
1218 // segments of circles at the start and end of the dash line.
1219 if (style.strokeRec().getWidth() > intervals[1]) {
1220 return false;
1221 }
1222 }
1223
1224 return true;
1225}
bool isDashed() const
Definition: GrStyle.h:126
const SkScalar * dashIntervals() const
Definition: GrStyle.h:135
int dashIntervalCnt() const
Definition: GrStyle.h:131
const SkStrokeRec & strokeRec() const
Definition: GrStyle.h:140
bool preservesRightAngles(SkScalar tol=SK_ScalarNearlyZero) const
Definition: SkMatrix.cpp:209
@ kRound_Cap
adds circle
Definition: SkPaint.h:335
SkScalar getWidth() const
Definition: SkStrokeRec.h:42
SkPaint::Cap getCap() const
Definition: SkStrokeRec.h:44
float SkScalar
Definition: extension.cpp:12

◆ MakeDashLineOp()

GrOp::Owner skgpu::ganesh::DashOp::MakeDashLineOp ( GrRecordingContext context,
GrPaint &&  paint,
const SkMatrix viewMatrix,
const SkPoint  pts[2],
AAMode  aaMode,
const GrStyle style,
const GrUserStencilSettings stencilSettings 
)

Definition at line 1130 of file DashOp.cpp.

1136 {
1137 SkASSERT(CanDrawDashLine(pts, style, viewMatrix));
1138 const SkScalar* intervals = style.dashIntervals();
1139 SkScalar phase = style.dashPhase();
1140
1141 SkPaint::Cap cap = style.strokeRec().getCap();
1142
1143 DashOpImpl::LineData lineData;
1144 lineData.fSrcStrokeWidth = style.strokeRec().getWidth();
1145
1146 // the phase should be normalized to be [0, sum of all intervals)
1147 SkASSERT(phase >= 0 && phase < intervals[0] + intervals[1]);
1148
1149 // Rotate the src pts so they are aligned horizontally with pts[0].fX < pts[1].fX
1150 if (pts[0].fY != pts[1].fY || pts[0].fX > pts[1].fX) {
1151 SkMatrix rotMatrix;
1152 align_to_x_axis(pts, &rotMatrix, lineData.fPtsRot);
1153 if (!rotMatrix.invert(&lineData.fSrcRotInv)) {
1154 SkDebugf("Failed to create invertible rotation matrix!\n");
1155 return nullptr;
1156 }
1157 } else {
1158 lineData.fSrcRotInv.reset();
1159 memcpy(lineData.fPtsRot, pts, 2 * sizeof(SkPoint));
1160 }
1161
1162 // Scale corrections of intervals and stroke from view matrix
1163 calc_dash_scaling(&lineData.fParallelScale, &lineData.fPerpendicularScale, viewMatrix, pts);
1164 if (SkScalarNearlyZero(lineData.fParallelScale) ||
1165 SkScalarNearlyZero(lineData.fPerpendicularScale)) {
1166 return nullptr;
1167 }
1168
1169 SkScalar offInterval = intervals[1] * lineData.fParallelScale;
1170 SkScalar strokeWidth = lineData.fSrcStrokeWidth * lineData.fPerpendicularScale;
1171
1172 if (SkPaint::kSquare_Cap == cap && 0 != lineData.fSrcStrokeWidth) {
1173 // add cap to on interval and remove from off interval
1174 offInterval -= strokeWidth;
1175 }
1176
1177 // TODO we can do a real rect call if not using fulldash(ie no off interval, not using AA)
1178 bool fullDash = offInterval > 0.f || aaMode != AAMode::kNone;
1179
1180 lineData.fViewMatrix = viewMatrix;
1181 lineData.fPhase = phase;
1182 lineData.fIntervals[0] = intervals[0];
1183 lineData.fIntervals[1] = intervals[1];
1184
1185 return DashOpImpl::Make(context, std::move(paint), lineData, cap, aaMode, fullDash,
1186 stencilSettings);
1187}
static const int strokeWidth
Definition: BlurTest.cpp:60
#define SkASSERT(cond)
Definition: SkAssert.h:116
void SK_SPI SkDebugf(const char format[],...) SK_PRINTF_LIKE(1
static bool SkScalarNearlyZero(SkScalar x, SkScalar tolerance=SK_ScalarNearlyZero)
Definition: SkScalar.h:101
SkScalar dashPhase() const
Definition: GrStyle.h:127
bool invert(SkMatrix *inverse) const
Definition: SkMatrix.h:1206
@ kSquare_Cap
adds square
Definition: SkPaint.h:336
const Paint & paint
Definition: color_source.cc:38
SK_API sk_sp< SkDocument > Make(SkWStream *dst, const SkSerialProcs *=nullptr, std::function< void(const SkPicture *)> onEndPage=nullptr)
bool CanDrawDashLine(const SkPoint pts[2], const GrStyle &style, const SkMatrix &viewMatrix)
Definition: DashOp.cpp:1190