| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright 2013 Google Inc. | 2 * Copyright 2013 Google Inc. |
| 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 "GrOvalRenderer.h" | 8 #include "GrOvalRenderer.h" |
| 9 | 9 |
| 10 #include "GrBatch.h" | 10 #include "GrBatch.h" |
| (...skipping 584 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 595 const GrCaps&, | 595 const GrCaps&, |
| 596 GrTexture* textures[]) { | 596 GrTexture* textures[]) { |
| 597 return DIEllipseEdgeEffect::Create(GrRandomColor(random), | 597 return DIEllipseEdgeEffect::Create(GrRandomColor(random), |
| 598 GrTest::TestMatrix(random), | 598 GrTest::TestMatrix(random), |
| 599 (Mode)(random->nextRangeU(0,2)), | 599 (Mode)(random->nextRangeU(0,2)), |
| 600 random->nextBool()); | 600 random->nextBool()); |
| 601 } | 601 } |
| 602 | 602 |
| 603 /////////////////////////////////////////////////////////////////////////////// | 603 /////////////////////////////////////////////////////////////////////////////// |
| 604 | 604 |
| 605 bool GrOvalRenderer::drawOval(GrDrawTarget* target, | 605 bool GrOvalRenderer::DrawOval(GrDrawTarget* target, |
| 606 GrPipelineBuilder* pipelineBuilder, | 606 GrPipelineBuilder* pipelineBuilder, |
| 607 GrColor color, | 607 GrColor color, |
| 608 const SkMatrix& viewMatrix, | 608 const SkMatrix& viewMatrix, |
| 609 bool useAA, | 609 bool useAA, |
| 610 const SkRect& oval, | 610 const SkRect& oval, |
| 611 const SkStrokeRec& stroke) | 611 const SkStrokeRec& stroke) |
| 612 { | 612 { |
| 613 bool useCoverageAA = useAA && !pipelineBuilder->getRenderTarget()->isMultisa
mpled(); | 613 bool useCoverageAA = useAA && !pipelineBuilder->getRenderTarget()->isMultisa
mpled(); |
| 614 | 614 |
| 615 if (!useCoverageAA) { | 615 if (!useCoverageAA) { |
| 616 return false; | 616 return false; |
| 617 } | 617 } |
| 618 | 618 |
| 619 // we can draw circles | 619 // we can draw circles |
| 620 if (SkScalarNearlyEqual(oval.width(), oval.height()) && circle_stays_circle(
viewMatrix)) { | 620 if (SkScalarNearlyEqual(oval.width(), oval.height()) && circle_stays_circle(
viewMatrix)) { |
| 621 this->drawCircle(target, pipelineBuilder, color, viewMatrix, useCoverage
AA, oval, stroke); | 621 DrawCircle(target, pipelineBuilder, color, viewMatrix, useCoverageAA, ov
al, stroke); |
| 622 // if we have shader derivative support, render as device-independent | 622 // if we have shader derivative support, render as device-independent |
| 623 } else if (target->caps()->shaderCaps()->shaderDerivativeSupport()) { | 623 } else if (target->caps()->shaderCaps()->shaderDerivativeSupport()) { |
| 624 return this->drawDIEllipse(target, pipelineBuilder, color, viewMatrix, u
seCoverageAA, oval, | 624 return DrawDIEllipse(target, pipelineBuilder, color, viewMatrix, useCove
rageAA, oval, |
| 625 stroke); | 625 stroke); |
| 626 // otherwise axis-aligned ellipses only | 626 // otherwise axis-aligned ellipses only |
| 627 } else if (viewMatrix.rectStaysRect()) { | 627 } else if (viewMatrix.rectStaysRect()) { |
| 628 return this->drawEllipse(target, pipelineBuilder, color, viewMatrix, use
CoverageAA, oval, | 628 return DrawEllipse(target, pipelineBuilder, color, viewMatrix, useCovera
geAA, oval, |
| 629 stroke); | 629 stroke); |
| 630 } else { | 630 } else { |
| 631 return false; | 631 return false; |
| 632 } | 632 } |
| 633 | 633 |
| 634 return true; | 634 return true; |
| 635 } | 635 } |
| 636 | 636 |
| 637 /////////////////////////////////////////////////////////////////////////////// | 637 /////////////////////////////////////////////////////////////////////////////// |
| 638 | 638 |
| 639 class CircleBatch : public GrBatch { | 639 class CircleBatch : public GrBatch { |
| (...skipping 187 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 827 geometry.fColor = color; | 827 geometry.fColor = color; |
| 828 geometry.fInnerRadius = innerRadius; | 828 geometry.fInnerRadius = innerRadius; |
| 829 geometry.fOuterRadius = outerRadius; | 829 geometry.fOuterRadius = outerRadius; |
| 830 geometry.fStroke = isStrokeOnly && innerRadius > 0; | 830 geometry.fStroke = isStrokeOnly && innerRadius > 0; |
| 831 geometry.fDevBounds = SkRect::MakeLTRB(center.fX - outerRadius, center.fY -
outerRadius, | 831 geometry.fDevBounds = SkRect::MakeLTRB(center.fX - outerRadius, center.fY -
outerRadius, |
| 832 center.fX + outerRadius, center.fY +
outerRadius); | 832 center.fX + outerRadius, center.fY +
outerRadius); |
| 833 | 833 |
| 834 return CircleBatch::Create(geometry); | 834 return CircleBatch::Create(geometry); |
| 835 } | 835 } |
| 836 | 836 |
| 837 void GrOvalRenderer::drawCircle(GrDrawTarget* target, | 837 void GrOvalRenderer::DrawCircle(GrDrawTarget* target, |
| 838 GrPipelineBuilder* pipelineBuilder, | 838 GrPipelineBuilder* pipelineBuilder, |
| 839 GrColor color, | 839 GrColor color, |
| 840 const SkMatrix& viewMatrix, | 840 const SkMatrix& viewMatrix, |
| 841 bool useCoverageAA, | 841 bool useCoverageAA, |
| 842 const SkRect& circle, | 842 const SkRect& circle, |
| 843 const SkStrokeRec& stroke) { | 843 const SkStrokeRec& stroke) { |
| 844 SkAutoTUnref<GrBatch> batch(create_circle_batch(color, viewMatrix, useCovera
geAA, circle, | 844 SkAutoTUnref<GrBatch> batch(create_circle_batch(color, viewMatrix, useCovera
geAA, circle, |
| 845 stroke)); | 845 stroke)); |
| 846 target->drawBatch(pipelineBuilder, batch); | 846 target->drawBatch(pipelineBuilder, batch); |
| 847 } | 847 } |
| (...skipping 236 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1084 geometry.fYRadius = yRadius; | 1084 geometry.fYRadius = yRadius; |
| 1085 geometry.fInnerXRadius = innerXRadius; | 1085 geometry.fInnerXRadius = innerXRadius; |
| 1086 geometry.fInnerYRadius = innerYRadius; | 1086 geometry.fInnerYRadius = innerYRadius; |
| 1087 geometry.fStroke = isStrokeOnly && innerXRadius > 0 && innerYRadius > 0; | 1087 geometry.fStroke = isStrokeOnly && innerXRadius > 0 && innerYRadius > 0; |
| 1088 geometry.fDevBounds = SkRect::MakeLTRB(center.fX - xRadius, center.fY - yRad
ius, | 1088 geometry.fDevBounds = SkRect::MakeLTRB(center.fX - xRadius, center.fY - yRad
ius, |
| 1089 center.fX + xRadius, center.fY + yRad
ius); | 1089 center.fX + xRadius, center.fY + yRad
ius); |
| 1090 | 1090 |
| 1091 return EllipseBatch::Create(geometry); | 1091 return EllipseBatch::Create(geometry); |
| 1092 } | 1092 } |
| 1093 | 1093 |
| 1094 bool GrOvalRenderer::drawEllipse(GrDrawTarget* target, | 1094 bool GrOvalRenderer::DrawEllipse(GrDrawTarget* target, |
| 1095 GrPipelineBuilder* pipelineBuilder, | 1095 GrPipelineBuilder* pipelineBuilder, |
| 1096 GrColor color, | 1096 GrColor color, |
| 1097 const SkMatrix& viewMatrix, | 1097 const SkMatrix& viewMatrix, |
| 1098 bool useCoverageAA, | 1098 bool useCoverageAA, |
| 1099 const SkRect& ellipse, | 1099 const SkRect& ellipse, |
| 1100 const SkStrokeRec& stroke) { | 1100 const SkStrokeRec& stroke) { |
| 1101 SkAutoTUnref<GrBatch> batch(create_ellipse_batch(color, viewMatrix, useCover
ageAA, ellipse, | 1101 SkAutoTUnref<GrBatch> batch(create_ellipse_batch(color, viewMatrix, useCover
ageAA, ellipse, |
| 1102 stroke)); | 1102 stroke)); |
| 1103 if (!batch) { | 1103 if (!batch) { |
| 1104 return false; | 1104 return false; |
| (...skipping 225 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1330 geometry.fGeoDy = geoDy; | 1330 geometry.fGeoDy = geoDy; |
| 1331 geometry.fMode = mode; | 1331 geometry.fMode = mode; |
| 1332 geometry.fBounds = SkRect::MakeLTRB(center.fX - xRadius - geoDx, center.fY -
yRadius - geoDy, | 1332 geometry.fBounds = SkRect::MakeLTRB(center.fX - xRadius - geoDx, center.fY -
yRadius - geoDy, |
| 1333 center.fX + xRadius + geoDx, center.fY +
yRadius + geoDy); | 1333 center.fX + xRadius + geoDx, center.fY +
yRadius + geoDy); |
| 1334 | 1334 |
| 1335 SkRect devBounds = geometry.fBounds; | 1335 SkRect devBounds = geometry.fBounds; |
| 1336 viewMatrix.mapRect(&devBounds); | 1336 viewMatrix.mapRect(&devBounds); |
| 1337 return DIEllipseBatch::Create(geometry, devBounds); | 1337 return DIEllipseBatch::Create(geometry, devBounds); |
| 1338 } | 1338 } |
| 1339 | 1339 |
| 1340 bool GrOvalRenderer::drawDIEllipse(GrDrawTarget* target, | 1340 bool GrOvalRenderer::DrawDIEllipse(GrDrawTarget* target, |
| 1341 GrPipelineBuilder* pipelineBuilder, | 1341 GrPipelineBuilder* pipelineBuilder, |
| 1342 GrColor color, | 1342 GrColor color, |
| 1343 const SkMatrix& viewMatrix, | 1343 const SkMatrix& viewMatrix, |
| 1344 bool useCoverageAA, | 1344 bool useCoverageAA, |
| 1345 const SkRect& ellipse, | 1345 const SkRect& ellipse, |
| 1346 const SkStrokeRec& stroke) { | 1346 const SkStrokeRec& stroke) { |
| 1347 SkAutoTUnref<GrBatch> batch(create_diellipse_batch(color, viewMatrix, useCov
erageAA, ellipse, | 1347 SkAutoTUnref<GrBatch> batch(create_diellipse_batch(color, viewMatrix, useCov
erageAA, ellipse, |
| 1348 stroke)); | 1348 stroke)); |
| 1349 if (!batch) { | 1349 if (!batch) { |
| 1350 return false; | 1350 return false; |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1389 gRRectIndices, kIndicesPerStrokeRRect, kNumRRectsInIndexBuffer, kVer
tsPerRRect, | 1389 gRRectIndices, kIndicesPerStrokeRRect, kNumRRectsInIndexBuffer, kVer
tsPerRRect, |
| 1390 gStrokeRRectOnlyIndexBufferKey); | 1390 gStrokeRRectOnlyIndexBufferKey); |
| 1391 } else { | 1391 } else { |
| 1392 return resourceProvider->refOrCreateInstancedIndexBuffer( | 1392 return resourceProvider->refOrCreateInstancedIndexBuffer( |
| 1393 gRRectIndices, kIndicesPerRRect, kNumRRectsInIndexBuffer, kVertsPerR
Rect, | 1393 gRRectIndices, kIndicesPerRRect, kNumRRectsInIndexBuffer, kVertsPerR
Rect, |
| 1394 gRRectOnlyIndexBufferKey); | 1394 gRRectOnlyIndexBufferKey); |
| 1395 | 1395 |
| 1396 } | 1396 } |
| 1397 } | 1397 } |
| 1398 | 1398 |
| 1399 bool GrOvalRenderer::drawDRRect(GrDrawTarget* target, | 1399 bool GrOvalRenderer::DrawDRRect(GrDrawTarget* target, |
| 1400 GrPipelineBuilder* pipelineBuilder, | 1400 GrPipelineBuilder* pipelineBuilder, |
| 1401 GrColor color, | 1401 GrColor color, |
| 1402 const SkMatrix& viewMatrix, | 1402 const SkMatrix& viewMatrix, |
| 1403 bool useAA, | 1403 bool useAA, |
| 1404 const SkRRect& origOuter, | 1404 const SkRRect& origOuter, |
| 1405 const SkRRect& origInner) { | 1405 const SkRRect& origInner) { |
| 1406 bool applyAA = useAA && | 1406 bool applyAA = useAA && |
| 1407 !pipelineBuilder->getRenderTarget()->isMultisampled(); | 1407 !pipelineBuilder->getRenderTarget()->isMultisampled(); |
| 1408 GrPipelineBuilder::AutoRestoreFragmentProcessors arfp; | 1408 GrPipelineBuilder::AutoRestoreFragmentProcessors arfp; |
| 1409 if (!origInner.isEmpty()) { | 1409 if (!origInner.isEmpty()) { |
| 1410 SkTCopyOnFirstWrite<SkRRect> inner(origInner); | 1410 SkTCopyOnFirstWrite<SkRRect> inner(origInner); |
| 1411 if (!viewMatrix.isIdentity()) { | 1411 if (!viewMatrix.isIdentity()) { |
| 1412 if (!origInner.transform(viewMatrix, inner.writable())) { | 1412 if (!origInner.transform(viewMatrix, inner.writable())) { |
| 1413 return false; | 1413 return false; |
| 1414 } | 1414 } |
| 1415 } | 1415 } |
| 1416 GrPrimitiveEdgeType edgeType = applyAA ? | 1416 GrPrimitiveEdgeType edgeType = applyAA ? |
| 1417 kInverseFillAA_GrProcessorEdgeType : | 1417 kInverseFillAA_GrProcessorEdgeType : |
| 1418 kInverseFillBW_GrProcessorEdgeType; | 1418 kInverseFillBW_GrProcessorEdgeType; |
| 1419 // TODO this needs to be a geometry processor | 1419 // TODO this needs to be a geometry processor |
| 1420 GrFragmentProcessor* fp = GrRRectEffect::Create(edgeType, *inner); | 1420 GrFragmentProcessor* fp = GrRRectEffect::Create(edgeType, *inner); |
| 1421 if (NULL == fp) { | 1421 if (NULL == fp) { |
| 1422 return false; | 1422 return false; |
| 1423 } | 1423 } |
| 1424 arfp.set(pipelineBuilder); | 1424 arfp.set(pipelineBuilder); |
| 1425 pipelineBuilder->addCoverageProcessor(fp)->unref(); | 1425 pipelineBuilder->addCoverageProcessor(fp)->unref(); |
| 1426 } | 1426 } |
| 1427 | 1427 |
| 1428 SkStrokeRec fillRec(SkStrokeRec::kFill_InitStyle); | 1428 SkStrokeRec fillRec(SkStrokeRec::kFill_InitStyle); |
| 1429 if (this->drawRRect(target, pipelineBuilder, color, viewMatrix, useAA, origO
uter, fillRec)) { | 1429 if (DrawRRect(target, pipelineBuilder, color, viewMatrix, useAA, origOuter,
fillRec)) { |
| 1430 return true; | 1430 return true; |
| 1431 } | 1431 } |
| 1432 | 1432 |
| 1433 SkASSERT(!origOuter.isEmpty()); | 1433 SkASSERT(!origOuter.isEmpty()); |
| 1434 SkTCopyOnFirstWrite<SkRRect> outer(origOuter); | 1434 SkTCopyOnFirstWrite<SkRRect> outer(origOuter); |
| 1435 if (!viewMatrix.isIdentity()) { | 1435 if (!viewMatrix.isIdentity()) { |
| 1436 if (!origOuter.transform(viewMatrix, outer.writable())) { | 1436 if (!origOuter.transform(viewMatrix, outer.writable())) { |
| 1437 return false; | 1437 return false; |
| 1438 } | 1438 } |
| 1439 } | 1439 } |
| (...skipping 10 matching lines...) Expand all Loading... |
| 1450 SkMatrix invert; | 1450 SkMatrix invert; |
| 1451 if (!viewMatrix.invert(&invert)) { | 1451 if (!viewMatrix.invert(&invert)) { |
| 1452 return false; | 1452 return false; |
| 1453 } | 1453 } |
| 1454 | 1454 |
| 1455 pipelineBuilder->addCoverageProcessor(effect)->unref(); | 1455 pipelineBuilder->addCoverageProcessor(effect)->unref(); |
| 1456 SkRect bounds = outer->getBounds(); | 1456 SkRect bounds = outer->getBounds(); |
| 1457 if (applyAA) { | 1457 if (applyAA) { |
| 1458 bounds.outset(SK_ScalarHalf, SK_ScalarHalf); | 1458 bounds.outset(SK_ScalarHalf, SK_ScalarHalf); |
| 1459 } | 1459 } |
| 1460 target->drawRect(pipelineBuilder, color, SkMatrix::I(), bounds, NULL, &inver
t); | 1460 target->drawBWRect(pipelineBuilder, color, SkMatrix::I(), bounds, NULL, &inv
ert); |
| 1461 return true; | 1461 return true; |
| 1462 } | 1462 } |
| 1463 | 1463 |
| 1464 ////////////////////////////////////////////////////////////////////////////////
/////////////////// | 1464 ////////////////////////////////////////////////////////////////////////////////
/////////////////// |
| 1465 | 1465 |
| 1466 class RRectCircleRendererBatch : public GrBatch { | 1466 class RRectCircleRendererBatch : public GrBatch { |
| 1467 public: | 1467 public: |
| 1468 struct Geometry { | 1468 struct Geometry { |
| 1469 GrColor fColor; | 1469 GrColor fColor; |
| 1470 SkMatrix fViewMatrix; | 1470 SkMatrix fViewMatrix; |
| (...skipping 488 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1959 geometry.fYRadius = yRadius; | 1959 geometry.fYRadius = yRadius; |
| 1960 geometry.fInnerXRadius = innerXRadius; | 1960 geometry.fInnerXRadius = innerXRadius; |
| 1961 geometry.fInnerYRadius = innerYRadius; | 1961 geometry.fInnerYRadius = innerYRadius; |
| 1962 geometry.fStroke = isStrokeOnly; | 1962 geometry.fStroke = isStrokeOnly; |
| 1963 geometry.fDevBounds = bounds; | 1963 geometry.fDevBounds = bounds; |
| 1964 | 1964 |
| 1965 return RRectEllipseRendererBatch::Create(geometry); | 1965 return RRectEllipseRendererBatch::Create(geometry); |
| 1966 } | 1966 } |
| 1967 } | 1967 } |
| 1968 | 1968 |
| 1969 bool GrOvalRenderer::drawRRect(GrDrawTarget* target, | 1969 bool GrOvalRenderer::DrawRRect(GrDrawTarget* target, |
| 1970 GrPipelineBuilder* pipelineBuilder, | 1970 GrPipelineBuilder* pipelineBuilder, |
| 1971 GrColor color, | 1971 GrColor color, |
| 1972 const SkMatrix& viewMatrix, | 1972 const SkMatrix& viewMatrix, |
| 1973 bool useAA, | 1973 bool useAA, |
| 1974 const SkRRect& rrect, | 1974 const SkRRect& rrect, |
| 1975 const SkStrokeRec& stroke) { | 1975 const SkStrokeRec& stroke) { |
| 1976 if (rrect.isOval()) { | 1976 if (rrect.isOval()) { |
| 1977 return this->drawOval(target, pipelineBuilder, color, viewMatrix, useAA,
rrect.getBounds(), | 1977 return DrawOval(target, pipelineBuilder, color, viewMatrix, useAA, rrect
.getBounds(), |
| 1978 stroke); | 1978 stroke); |
| 1979 } | 1979 } |
| 1980 | 1980 |
| 1981 bool useCoverageAA = useAA && !pipelineBuilder->getRenderTarget()->isMultisa
mpled(); | 1981 bool useCoverageAA = useAA && !pipelineBuilder->getRenderTarget()->isMultisa
mpled(); |
| 1982 | 1982 |
| 1983 // only anti-aliased rrects for now | 1983 // only anti-aliased rrects for now |
| 1984 if (!useCoverageAA) { | 1984 if (!useCoverageAA) { |
| 1985 return false; | 1985 return false; |
| 1986 } | 1986 } |
| 1987 | 1987 |
| 1988 if (!viewMatrix.rectStaysRect() || !rrect.isSimple()) { | 1988 if (!viewMatrix.rectStaysRect() || !rrect.isSimple()) { |
| (...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2029 } | 2029 } |
| 2030 | 2030 |
| 2031 BATCH_TEST_DEFINE(RRectBatch) { | 2031 BATCH_TEST_DEFINE(RRectBatch) { |
| 2032 SkMatrix viewMatrix = GrTest::TestMatrixRectStaysRect(random); | 2032 SkMatrix viewMatrix = GrTest::TestMatrixRectStaysRect(random); |
| 2033 GrColor color = GrRandomColor(random); | 2033 GrColor color = GrRandomColor(random); |
| 2034 const SkRRect& rrect = GrTest::TestRRectSimple(random); | 2034 const SkRRect& rrect = GrTest::TestRRectSimple(random); |
| 2035 return create_rrect_batch(color, viewMatrix, rrect, GrTest::TestStrokeRec(ra
ndom)); | 2035 return create_rrect_batch(color, viewMatrix, rrect, GrTest::TestStrokeRec(ra
ndom)); |
| 2036 } | 2036 } |
| 2037 | 2037 |
| 2038 #endif | 2038 #endif |
| OLD | NEW |