OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2006 The Android Open Source Project | 2 * Copyright 2006 The Android Open Source Project |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 #include "SkBlurMaskFilter.h" | 8 #include "SkBlurMaskFilter.h" |
9 #include "SkBlurMask.h" | 9 #include "SkBlurMask.h" |
10 #include "SkGpuBlurUtils.h" | 10 #include "SkGpuBlurUtils.h" |
(...skipping 1063 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1074 | 1074 |
1075 virtual ~GrRRectBlurEffect() {}; | 1075 virtual ~GrRRectBlurEffect() {}; |
1076 const char* name() const override { return "GrRRectBlur"; } | 1076 const char* name() const override { return "GrRRectBlur"; } |
1077 | 1077 |
1078 const SkRRect& getRRect() const { return fRRect; } | 1078 const SkRRect& getRRect() const { return fRRect; } |
1079 float getSigma() const { return fSigma; } | 1079 float getSigma() const { return fSigma; } |
1080 | 1080 |
1081 private: | 1081 private: |
1082 GrGLSLFragmentProcessor* onCreateGLSLInstance() const override; | 1082 GrGLSLFragmentProcessor* onCreateGLSLInstance() const override; |
1083 | 1083 |
1084 GrRRectBlurEffect(float sigma, const SkRRect&, GrTexture* profileTexture); | 1084 GrRRectBlurEffect(float xformedSigma, const SkRRect& devRRect, GrTexture* ma
sk); |
1085 | 1085 |
1086 virtual void onGetGLSLProcessorKey(const GrGLSLCaps& caps, | 1086 virtual void onGetGLSLProcessorKey(const GrGLSLCaps& caps, |
1087 GrProcessorKeyBuilder* b) const override; | 1087 GrProcessorKeyBuilder* b) const override; |
1088 | 1088 |
1089 bool onIsEqual(const GrFragmentProcessor& other) const override; | 1089 bool onIsEqual(const GrFragmentProcessor& other) const override; |
1090 | 1090 |
1091 void onComputeInvariantOutput(GrInvariantOutput* inout) const override; | 1091 void onComputeInvariantOutput(GrInvariantOutput* inout) const override; |
1092 | 1092 |
1093 SkRRect fRRect; | 1093 SkRRect fRRect; |
1094 float fSigma; | 1094 float fSigma; |
(...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1185 if (!ninePatchable) { | 1185 if (!ninePatchable) { |
1186 return nullptr; | 1186 return nullptr; |
1187 } | 1187 } |
1188 | 1188 |
1189 sk_sp<GrTexture> mask(find_or_create_rrect_blur_mask(context, rrectToDraw, s
ize, | 1189 sk_sp<GrTexture> mask(find_or_create_rrect_blur_mask(context, rrectToDraw, s
ize, |
1190 xformedSigma, true)); | 1190 xformedSigma, true)); |
1191 if (!mask) { | 1191 if (!mask) { |
1192 return nullptr; | 1192 return nullptr; |
1193 } | 1193 } |
1194 | 1194 |
1195 return sk_sp<GrFragmentProcessor>(new GrRRectBlurEffect(xformedSigma, | 1195 return sk_sp<GrFragmentProcessor>(new GrRRectBlurEffect(xformedSigma, devRRe
ct, mask.get())); |
1196 devRRect, | |
1197 mask.get())); | |
1198 } | 1196 } |
1199 | 1197 |
1200 void GrRRectBlurEffect::onComputeInvariantOutput(GrInvariantOutput* inout) const
{ | 1198 void GrRRectBlurEffect::onComputeInvariantOutput(GrInvariantOutput* inout) const
{ |
1201 inout->mulByUnknownSingleComponent(); | 1199 inout->mulByUnknownSingleComponent(); |
1202 } | 1200 } |
1203 | 1201 |
1204 GrRRectBlurEffect::GrRRectBlurEffect(float sigma, const SkRRect& rrect, GrTextur
e *ninePatchTexture) | 1202 GrRRectBlurEffect::GrRRectBlurEffect(float xformedSigma, |
1205 : fRRect(rrect), | 1203 const SkRRect& devRRect, |
1206 fSigma(sigma), | 1204 GrTexture *ninePatchTexture) |
1207 fNinePatchAccess(ninePatchTexture) { | 1205 : fRRect(devRRect) |
| 1206 , fSigma(xformedSigma) |
| 1207 , fNinePatchAccess(ninePatchTexture) { |
1208 this->initClassID<GrRRectBlurEffect>(); | 1208 this->initClassID<GrRRectBlurEffect>(); |
1209 this->addTextureAccess(&fNinePatchAccess); | 1209 this->addTextureAccess(&fNinePatchAccess); |
1210 this->setWillReadFragmentPosition(); | 1210 this->setWillReadFragmentPosition(); |
1211 } | 1211 } |
1212 | 1212 |
1213 bool GrRRectBlurEffect::onIsEqual(const GrFragmentProcessor& other) const { | 1213 bool GrRRectBlurEffect::onIsEqual(const GrFragmentProcessor& other) const { |
1214 const GrRRectBlurEffect& rrbe = other.cast<GrRRectBlurEffect>(); | 1214 const GrRRectBlurEffect& rrbe = other.cast<GrRRectBlurEffect>(); |
1215 return fRRect.getSimpleRadii().fX == rrbe.fRRect.getSimpleRadii().fX && | 1215 return fRRect.getSimpleRadii().fX == rrbe.fRRect.getSimpleRadii().fX && |
1216 fSigma == rrbe.fSigma && | 1216 fSigma == rrbe.fSigma && |
1217 fRRect.rect() == rrbe.fRRect.rect(); | 1217 fRRect.rect() == rrbe.fRRect.rect(); |
(...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1344 if (fBlurStyle != kNormal_SkBlurStyle) { | 1344 if (fBlurStyle != kNormal_SkBlurStyle) { |
1345 return false; | 1345 return false; |
1346 } | 1346 } |
1347 | 1347 |
1348 if (!strokeRec.isFillStyle()) { | 1348 if (!strokeRec.isFillStyle()) { |
1349 return false; | 1349 return false; |
1350 } | 1350 } |
1351 | 1351 |
1352 SkScalar xformedSigma = this->computeXformedSigma(viewMatrix); | 1352 SkScalar xformedSigma = this->computeXformedSigma(viewMatrix); |
1353 | 1353 |
| 1354 GrPaint newPaint(*grp); |
| 1355 newPaint.setAntiAlias(false); |
| 1356 |
1354 if (devRRect.isCircle()) { | 1357 if (devRRect.isCircle()) { |
1355 sk_sp<GrFragmentProcessor> fp(GrCircleBlurFragmentProcessor::Make( | 1358 sk_sp<GrFragmentProcessor> fp(GrCircleBlurFragmentProcessor::Make( |
1356 context-
>textureProvider(), | 1359 context-
>textureProvider(), |
1357 devRRect
.rect(), | 1360 devRRect
.rect(), |
1358 xformedS
igma)); | 1361 xformedS
igma)); |
1359 if (!fp) { | 1362 if (!fp) { |
1360 return false; | 1363 return false; |
1361 } | 1364 } |
1362 | 1365 |
1363 GrPaint newPaint(*grp); | |
1364 newPaint.addCoverageFragmentProcessor(std::move(fp)); | 1366 newPaint.addCoverageFragmentProcessor(std::move(fp)); |
1365 newPaint.setAntiAlias(false); | |
1366 | 1367 |
1367 SkRect srcProxyRect = srcRRect.rect(); | 1368 SkRect srcProxyRect = srcRRect.rect(); |
1368 srcProxyRect.outset(3.0f*fSigma, 3.0f*fSigma); | 1369 srcProxyRect.outset(3.0f*fSigma, 3.0f*fSigma); |
1369 | 1370 |
1370 drawContext->drawRect(clip, newPaint, viewMatrix, srcProxyRect); | 1371 drawContext->drawRect(clip, newPaint, viewMatrix, srcProxyRect); |
1371 return true; | 1372 return true; |
1372 } | 1373 } |
1373 | 1374 |
1374 sk_sp<GrFragmentProcessor> fp(GrRRectBlurEffect::Make(context, fSigma, xform
edSigma, | 1375 SkRRect maskSpaceRRectToDraw; |
1375 srcRRect, devRRect)); | 1376 SkISize maskSize; |
1376 if (!fp) { | 1377 SkScalar rectXs[SkBlurMaskFilter::kMaxDivisions], rectYs[SkBlurMaskFilter::k
MaxDivisions]; |
| 1378 SkScalar texXs[SkBlurMaskFilter::kMaxDivisions], texYs[SkBlurMaskFilter::kMa
xDivisions]; |
| 1379 int numX, numY; |
| 1380 uint32_t skipMask; |
| 1381 |
| 1382 bool ninePatchable = SkBlurMaskFilter::ComputeBlurredRRectParams(srcRRect, d
evRRect, fOccluder, |
| 1383 fSigma, xfo
rmedSigma, |
| 1384 &maskSpaceR
RectToDraw, |
| 1385 &maskSize, |
| 1386 rectXs, rec
tYs, texXs, texYs, |
| 1387 &numX, &num
Y, &skipMask); |
| 1388 if (!ninePatchable) { |
1377 return false; | 1389 return false; |
1378 } | 1390 } |
1379 | 1391 |
1380 GrPaint newPaint(*grp); | 1392 if (!this->ignoreXform()) { |
1381 newPaint.addCoverageFragmentProcessor(std::move(fp)); | 1393 sk_sp<GrTexture> mask(find_or_create_rrect_blur_mask(context, |
1382 newPaint.setAntiAlias(false); | 1394 maskSpaceRRectToDra
w, maskSize, |
| 1395 xformedSigma, true)
); |
| 1396 if (!mask) { |
| 1397 return false; |
| 1398 } |
1383 | 1399 |
1384 if (!this->ignoreXform()) { | 1400 SkMatrix texMatrix; |
1385 SkRect srcProxyRect = srcRRect.rect(); | 1401 texMatrix.setIDiv(mask->width(), mask->height()); |
1386 srcProxyRect.outset(3.0f*fSigma, 3.0f*fSigma); | |
1387 | 1402 |
1388 SkPoint points[8]; | 1403 GrTextureParams params; |
1389 uint16_t indices[24]; | 1404 params.reset(SkShader::kClamp_TileMode, GrTextureParams::kBilerp_FilterM
ode); |
1390 int numPoints, numIndices; | |
1391 | 1405 |
1392 SkRect temp = fOccluder; | 1406 sk_sp<GrFragmentProcessor> fp = GrSimpleTextureEffect::Make(mask.get(),
nullptr, |
| 1407 texMatrix, p
arams); |
| 1408 if (!fp) { |
| 1409 return false; |
| 1410 } |
1393 | 1411 |
1394 if (!temp.isEmpty() && (srcProxyRect.contains(temp) || temp.intersect(sr
cProxyRect))) { | 1412 newPaint.addColorFragmentProcessor(std::move(fp)); |
1395 srcProxyRect.toQuad(points); | |
1396 temp.toQuad(&points[4]); | |
1397 numPoints = 8; | |
1398 | 1413 |
1399 static const uint16_t ringI[24] = { 0, 1, 5, 5, 4, 0, | 1414 uint32_t checkBit = 0x1; |
1400 1, 2, 6, 6, 5, 1, | 1415 for (int y = 0; y < numY-1; ++y) { |
1401 2, 3, 7, 7, 6, 2, | 1416 for (int x = 0; x < numX-1; ++x) { |
1402 3, 0, 4, 4, 7, 3 }; | 1417 if (skipMask & checkBit) { |
1403 memcpy(indices, ringI, sizeof(ringI)); | 1418 checkBit <<= 1; |
1404 numIndices = 24; | 1419 continue; |
1405 } else { | 1420 } |
1406 // full rect case | 1421 drawContext->fillRectToRect( |
1407 srcProxyRect.toQuad(points); | 1422 clip, newPaint, viewMatrix, |
1408 numPoints = 4; | 1423 SkRect::MakeLTRB(rectXs[x], rectYs[y], rectXs[x+1],
rectYs[y+1]), // dst |
| 1424 SkRect::MakeLTRB(texXs[x], texYs[y], texXs[x+1], tex
Ys[y+1])); // src |
| 1425 checkBit <<= 1; |
| 1426 } |
| 1427 } |
| 1428 } else { |
| 1429 sk_sp<GrFragmentProcessor> fp(GrRRectBlurEffect::Make(context, |
| 1430 fSigma, xformedSig
ma, |
| 1431 srcRRect, devRRect
)); |
| 1432 if (!fp) { |
| 1433 return false; |
| 1434 } |
1409 | 1435 |
1410 static const uint16_t fullI[6] = { 0, 1, 2, 0, 2, 3 }; | 1436 newPaint.addCoverageFragmentProcessor(std::move(fp)); |
1411 memcpy(indices, fullI, sizeof(fullI)); | |
1412 numIndices = 6; | |
1413 } | |
1414 | 1437 |
1415 drawContext->drawVertices(clip, newPaint, viewMatrix, kTriangles_GrPrimi
tiveType, | |
1416 numPoints, points, nullptr, nullptr, indices,
numIndices); | |
1417 | |
1418 } else { | |
1419 SkMatrix inverse; | 1438 SkMatrix inverse; |
1420 if (!viewMatrix.invert(&inverse)) { | 1439 if (!viewMatrix.invert(&inverse)) { |
1421 return false; | 1440 return false; |
1422 } | 1441 } |
1423 | 1442 |
1424 float extra=3.f*SkScalarCeilToScalar(xformedSigma-1/6.0f); | 1443 float extra=3.f*SkScalarCeilToScalar(xformedSigma-1/6.0f); |
1425 SkRect proxyRect = devRRect.rect(); | 1444 SkRect proxyRect = devRRect.rect(); |
1426 proxyRect.outset(extra, extra); | 1445 proxyRect.outset(extra, extra); |
1427 | 1446 |
1428 | 1447 |
(...skipping 121 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1550 } else { | 1569 } else { |
1551 str->append("None"); | 1570 str->append("None"); |
1552 } | 1571 } |
1553 str->append("))"); | 1572 str->append("))"); |
1554 } | 1573 } |
1555 #endif | 1574 #endif |
1556 | 1575 |
1557 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_START(SkBlurMaskFilter) | 1576 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_START(SkBlurMaskFilter) |
1558 SK_DEFINE_FLATTENABLE_REGISTRAR_ENTRY(SkBlurMaskFilterImpl) | 1577 SK_DEFINE_FLATTENABLE_REGISTRAR_ENTRY(SkBlurMaskFilterImpl) |
1559 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_END | 1578 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_END |
OLD | NEW |