Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(55)

Side by Side Diff: src/gpu/GrOvalRenderer.cpp

Issue 815553003: Move ViewMatrix off of drawstate (Closed) Base URL: https://skia.googlesource.com/skia.git@remove-fragment-stage
Patch Set: more cleaning Created 5 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/gpu/GrOvalRenderer.h ('k') | src/gpu/GrPathRenderer.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 "GrProcessor.h" 10 #include "GrProcessor.h"
(...skipping 157 matching lines...) Expand 10 before | Expand all | Expand 10 after
168 const BatchTracker& mine = m.cast<BatchTracker>(); 168 const BatchTracker& mine = m.cast<BatchTracker>();
169 const BatchTracker& theirs = t.cast<BatchTracker>(); 169 const BatchTracker& theirs = t.cast<BatchTracker>();
170 return CanCombineLocalMatrices(*this, mine.fUsesLocalCoords, 170 return CanCombineLocalMatrices(*this, mine.fUsesLocalCoords,
171 that, theirs.fUsesLocalCoords) && 171 that, theirs.fUsesLocalCoords) &&
172 CanCombineOutput(mine.fInputColorType, mine.fColor, 172 CanCombineOutput(mine.fInputColorType, mine.fColor,
173 theirs.fInputColorType, theirs.fColor); 173 theirs.fInputColorType, theirs.fColor);
174 } 174 }
175 175
176 private: 176 private:
177 CircleEdgeEffect(GrColor color, bool stroke, const SkMatrix& localMatrix) 177 CircleEdgeEffect(GrColor color, bool stroke, const SkMatrix& localMatrix)
178 : INHERITED(color, false, localMatrix) { 178 : INHERITED(color, SkMatrix::I(), localMatrix) {
179 this->initClassID<CircleEdgeEffect>(); 179 this->initClassID<CircleEdgeEffect>();
180 fInPosition = &this->addVertexAttrib(GrAttribute("inPosition", kVec2f_Gr VertexAttribType)); 180 fInPosition = &this->addVertexAttrib(GrAttribute("inPosition", kVec2f_Gr VertexAttribType));
181 fInCircleEdge = &this->addVertexAttrib(GrAttribute("inCircleEdge", 181 fInCircleEdge = &this->addVertexAttrib(GrAttribute("inCircleEdge",
182 kVec4f_GrVertexAttrib Type)); 182 kVec4f_GrVertexAttrib Type));
183 fStroke = stroke; 183 fStroke = stroke;
184 } 184 }
185 185
186 virtual bool onIsEqual(const GrGeometryProcessor& other) const SK_OVERRIDE { 186 virtual bool onIsEqual(const GrGeometryProcessor& other) const SK_OVERRIDE {
187 const CircleEdgeEffect& cee = other.cast<CircleEdgeEffect>(); 187 const CircleEdgeEffect& cee = other.cast<CircleEdgeEffect>();
188 return cee.fStroke == fStroke; 188 return cee.fStroke == fStroke;
(...skipping 17 matching lines...) Expand all
206 206
207 typedef GrGeometryProcessor INHERITED; 207 typedef GrGeometryProcessor INHERITED;
208 }; 208 };
209 209
210 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(CircleEdgeEffect); 210 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(CircleEdgeEffect);
211 211
212 GrGeometryProcessor* CircleEdgeEffect::TestCreate(SkRandom* random, 212 GrGeometryProcessor* CircleEdgeEffect::TestCreate(SkRandom* random,
213 GrContext* context, 213 GrContext* context,
214 const GrDrawTargetCaps&, 214 const GrDrawTargetCaps&,
215 GrTexture* textures[]) { 215 GrTexture* textures[]) {
216 return CircleEdgeEffect::Create(GrRandomColor(random), random->nextBool(), 216 return CircleEdgeEffect::Create(GrRandomColor(random),
217 random->nextBool(),
217 GrProcessorUnitTest::TestMatrix(random)); 218 GrProcessorUnitTest::TestMatrix(random));
218 } 219 }
219 220
220 /////////////////////////////////////////////////////////////////////////////// 221 ///////////////////////////////////////////////////////////////////////////////
221 222
222 /** 223 /**
223 * The output of this effect is a modulation of the input color and coverage for an axis-aligned 224 * The output of this effect is a modulation of the input color and coverage for an axis-aligned
224 * ellipse, specified as a 2D offset from center, and the reciprocals of the out er and inner radii, 225 * ellipse, specified as a 2D offset from center, and the reciprocals of the out er and inner radii,
225 * in both x and y directions. 226 * in both x and y directions.
226 * 227 *
(...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after
356 const BatchTracker& mine = m.cast<BatchTracker>(); 357 const BatchTracker& mine = m.cast<BatchTracker>();
357 const BatchTracker& theirs = t.cast<BatchTracker>(); 358 const BatchTracker& theirs = t.cast<BatchTracker>();
358 return CanCombineLocalMatrices(*this, mine.fUsesLocalCoords, 359 return CanCombineLocalMatrices(*this, mine.fUsesLocalCoords,
359 that, theirs.fUsesLocalCoords) && 360 that, theirs.fUsesLocalCoords) &&
360 CanCombineOutput(mine.fInputColorType, mine.fColor, 361 CanCombineOutput(mine.fInputColorType, mine.fColor,
361 theirs.fInputColorType, theirs.fColor); 362 theirs.fInputColorType, theirs.fColor);
362 } 363 }
363 364
364 private: 365 private:
365 EllipseEdgeEffect(GrColor color, bool stroke, const SkMatrix& localMatrix) 366 EllipseEdgeEffect(GrColor color, bool stroke, const SkMatrix& localMatrix)
366 : INHERITED(color, false, localMatrix) { 367 : INHERITED(color, SkMatrix::I(), localMatrix) {
367 this->initClassID<EllipseEdgeEffect>(); 368 this->initClassID<EllipseEdgeEffect>();
368 fInPosition = &this->addVertexAttrib(GrAttribute("inPosition", kVec2f_Gr VertexAttribType)); 369 fInPosition = &this->addVertexAttrib(GrAttribute("inPosition", kVec2f_Gr VertexAttribType));
369 fInEllipseOffset = &this->addVertexAttrib(GrAttribute("inEllipseOffset", 370 fInEllipseOffset = &this->addVertexAttrib(GrAttribute("inEllipseOffset",
370 kVec2f_GrVertexAtt ribType)); 371 kVec2f_GrVertexAtt ribType));
371 fInEllipseRadii = &this->addVertexAttrib(GrAttribute("inEllipseRadii", 372 fInEllipseRadii = &this->addVertexAttrib(GrAttribute("inEllipseRadii",
372 kVec4f_GrVertexAttr ibType)); 373 kVec4f_GrVertexAttr ibType));
373 fStroke = stroke; 374 fStroke = stroke;
374 } 375 }
375 376
376 virtual bool onIsEqual(const GrGeometryProcessor& other) const SK_OVERRIDE { 377 virtual bool onIsEqual(const GrGeometryProcessor& other) const SK_OVERRIDE {
(...skipping 20 matching lines...) Expand all
397 398
398 typedef GrGeometryProcessor INHERITED; 399 typedef GrGeometryProcessor INHERITED;
399 }; 400 };
400 401
401 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(EllipseEdgeEffect); 402 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(EllipseEdgeEffect);
402 403
403 GrGeometryProcessor* EllipseEdgeEffect::TestCreate(SkRandom* random, 404 GrGeometryProcessor* EllipseEdgeEffect::TestCreate(SkRandom* random,
404 GrContext* context, 405 GrContext* context,
405 const GrDrawTargetCaps&, 406 const GrDrawTargetCaps&,
406 GrTexture* textures[]) { 407 GrTexture* textures[]) {
407 return EllipseEdgeEffect::Create(GrRandomColor(random), random->nextBool(), 408 return EllipseEdgeEffect::Create(GrRandomColor(random),
409 random->nextBool(),
408 GrProcessorUnitTest::TestMatrix(random)); 410 GrProcessorUnitTest::TestMatrix(random));
409 } 411 }
410 412
411 /////////////////////////////////////////////////////////////////////////////// 413 ///////////////////////////////////////////////////////////////////////////////
412 414
413 /** 415 /**
414 * The output of this effect is a modulation of the input color and coverage for an ellipse, 416 * The output of this effect is a modulation of the input color and coverage for an ellipse,
415 * specified as a 2D offset from center for both the outer and inner paths (if s troked). The 417 * specified as a 2D offset from center for both the outer and inner paths (if s troked). The
416 * implict equation used is for a unit circle (x^2 + y^2 - 1 = 0) and the edge c orrected by 418 * implict equation used is for a unit circle (x^2 + y^2 - 1 = 0) and the edge c orrected by
417 * using differentials. 419 * using differentials.
418 * 420 *
419 * The result is device-independent and can be used with any affine matrix. 421 * The result is device-independent and can be used with any affine matrix.
420 */ 422 */
421 423
422 class DIEllipseEdgeEffect : public GrGeometryProcessor { 424 class DIEllipseEdgeEffect : public GrGeometryProcessor {
423 public: 425 public:
424 enum Mode { kStroke = 0, kHairline, kFill }; 426 enum Mode { kStroke = 0, kHairline, kFill };
425 427
426 static GrGeometryProcessor* Create(GrColor color, Mode mode) { 428 static GrGeometryProcessor* Create(GrColor color, const SkMatrix& viewMatrix , Mode mode) {
427 return SkNEW_ARGS(DIEllipseEdgeEffect, (color, mode)); 429 return SkNEW_ARGS(DIEllipseEdgeEffect, (color, viewMatrix, mode));
428 } 430 }
429 431
430 virtual ~DIEllipseEdgeEffect() {} 432 virtual ~DIEllipseEdgeEffect() {}
431 433
432 virtual const char* name() const SK_OVERRIDE { return "DIEllipseEdge"; } 434 virtual const char* name() const SK_OVERRIDE { return "DIEllipseEdge"; }
433 435
434 const GrAttribute* inPosition() const { return fInPosition; } 436 const GrAttribute* inPosition() const { return fInPosition; }
435 const GrAttribute* inEllipseOffsets0() const { return fInEllipseOffsets0; } 437 const GrAttribute* inEllipseOffsets0() const { return fInEllipseOffsets0; }
436 const GrAttribute* inEllipseOffsets1() const { return fInEllipseOffsets1; } 438 const GrAttribute* inEllipseOffsets1() const { return fInEllipseOffsets1; }
437 439
(...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after
564 const GrBatchTracker& t) const SK_OVERRIDE { 566 const GrBatchTracker& t) const SK_OVERRIDE {
565 const BatchTracker& mine = m.cast<BatchTracker>(); 567 const BatchTracker& mine = m.cast<BatchTracker>();
566 const BatchTracker& theirs = t.cast<BatchTracker>(); 568 const BatchTracker& theirs = t.cast<BatchTracker>();
567 return CanCombineLocalMatrices(*this, mine.fUsesLocalCoords, 569 return CanCombineLocalMatrices(*this, mine.fUsesLocalCoords,
568 that, theirs.fUsesLocalCoords) && 570 that, theirs.fUsesLocalCoords) &&
569 CanCombineOutput(mine.fInputColorType, mine.fColor, 571 CanCombineOutput(mine.fInputColorType, mine.fColor,
570 theirs.fInputColorType, theirs.fColor); 572 theirs.fInputColorType, theirs.fColor);
571 } 573 }
572 574
573 private: 575 private:
574 DIEllipseEdgeEffect(GrColor color, Mode mode) : INHERITED(color) { 576 DIEllipseEdgeEffect(GrColor color, const SkMatrix& viewMatrix, Mode mode)
577 : INHERITED(color, viewMatrix) {
575 this->initClassID<DIEllipseEdgeEffect>(); 578 this->initClassID<DIEllipseEdgeEffect>();
576 fInPosition = &this->addVertexAttrib(GrAttribute("inPosition", kVec2f_Gr VertexAttribType)); 579 fInPosition = &this->addVertexAttrib(GrAttribute("inPosition", kVec2f_Gr VertexAttribType));
577 fInEllipseOffsets0 = &this->addVertexAttrib(GrAttribute("inEllipseOffset s0", 580 fInEllipseOffsets0 = &this->addVertexAttrib(GrAttribute("inEllipseOffset s0",
578 kVec2f_GrVertexA ttribType)); 581 kVec2f_GrVertexA ttribType));
579 fInEllipseOffsets1 = &this->addVertexAttrib(GrAttribute("inEllipseOffset s1", 582 fInEllipseOffsets1 = &this->addVertexAttrib(GrAttribute("inEllipseOffset s1",
580 kVec2f_GrVertexA ttribType)); 583 kVec2f_GrVertexA ttribType));
581 fMode = mode; 584 fMode = mode;
582 } 585 }
583 586
584 virtual bool onIsEqual(const GrGeometryProcessor& other) const SK_OVERRIDE { 587 virtual bool onIsEqual(const GrGeometryProcessor& other) const SK_OVERRIDE {
(...skipping 20 matching lines...) Expand all
605 608
606 typedef GrGeometryProcessor INHERITED; 609 typedef GrGeometryProcessor INHERITED;
607 }; 610 };
608 611
609 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(DIEllipseEdgeEffect); 612 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(DIEllipseEdgeEffect);
610 613
611 GrGeometryProcessor* DIEllipseEdgeEffect::TestCreate(SkRandom* random, 614 GrGeometryProcessor* DIEllipseEdgeEffect::TestCreate(SkRandom* random,
612 GrContext* context, 615 GrContext* context,
613 const GrDrawTargetCaps&, 616 const GrDrawTargetCaps&,
614 GrTexture* textures[]) { 617 GrTexture* textures[]) {
615 return DIEllipseEdgeEffect::Create(GrRandomColor(random), (Mode)(random->nex tRangeU(0,2))); 618 return DIEllipseEdgeEffect::Create(GrRandomColor(random),
619 GrProcessorUnitTest::TestMatrix(random),
620 (Mode)(random->nextRangeU(0,2)));
616 } 621 }
617 622
618 /////////////////////////////////////////////////////////////////////////////// 623 ///////////////////////////////////////////////////////////////////////////////
619 624
620 void GrOvalRenderer::reset() { 625 void GrOvalRenderer::reset() {
621 SkSafeSetNull(fRRectIndexBuffer); 626 SkSafeSetNull(fRRectIndexBuffer);
622 SkSafeSetNull(fStrokeRRectIndexBuffer); 627 SkSafeSetNull(fStrokeRRectIndexBuffer);
623 } 628 }
624 629
625 bool GrOvalRenderer::drawOval(GrDrawTarget* target, 630 bool GrOvalRenderer::drawOval(GrDrawTarget* target,
626 GrDrawState* drawState, 631 GrDrawState* drawState,
627 GrColor color, 632 GrColor color,
633 const SkMatrix& viewMatrix,
628 bool useAA, 634 bool useAA,
629 const SkRect& oval, 635 const SkRect& oval,
630 const SkStrokeRec& stroke) 636 const SkStrokeRec& stroke)
631 { 637 {
632 bool useCoverageAA = useAA && 638 bool useCoverageAA = useAA &&
633 !drawState->getRenderTarget()->isMultisampled() && 639 !drawState->getRenderTarget()->isMultisampled() &&
634 drawState->canUseFracCoveragePrimProc(color, *target->caps()); 640 drawState->canUseFracCoveragePrimProc(color, *target->caps());
635 641
636 if (!useCoverageAA) { 642 if (!useCoverageAA) {
637 return false; 643 return false;
638 } 644 }
639 645
640 const SkMatrix& vm = drawState->getViewMatrix();
641
642 // we can draw circles 646 // we can draw circles
643 if (SkScalarNearlyEqual(oval.width(), oval.height()) 647 if (SkScalarNearlyEqual(oval.width(), oval.height()) && circle_stays_circle( viewMatrix)) {
644 && circle_stays_circle(vm)) { 648 this->drawCircle(target, drawState, color, viewMatrix, useCoverageAA, ov al, stroke);
645 this->drawCircle(target, drawState, color, useCoverageAA, oval, stroke);
646 // if we have shader derivative support, render as device-independent 649 // if we have shader derivative support, render as device-independent
647 } else if (target->caps()->shaderDerivativeSupport()) { 650 } else if (target->caps()->shaderDerivativeSupport()) {
648 return this->drawDIEllipse(target, drawState, color, useCoverageAA, oval , stroke); 651 return this->drawDIEllipse(target, drawState, color, viewMatrix, useCove rageAA, oval,
652 stroke);
649 // otherwise axis-aligned ellipses only 653 // otherwise axis-aligned ellipses only
650 } else if (vm.rectStaysRect()) { 654 } else if (viewMatrix.rectStaysRect()) {
651 return this->drawEllipse(target, drawState, color, useCoverageAA, oval, stroke); 655 return this->drawEllipse(target, drawState, color, viewMatrix, useCovera geAA, oval, stroke);
652 } else { 656 } else {
653 return false; 657 return false;
654 } 658 }
655 659
656 return true; 660 return true;
657 } 661 }
658 662
659 /////////////////////////////////////////////////////////////////////////////// 663 ///////////////////////////////////////////////////////////////////////////////
660 664
661 void GrOvalRenderer::drawCircle(GrDrawTarget* target, 665 void GrOvalRenderer::drawCircle(GrDrawTarget* target,
662 GrDrawState* drawState, 666 GrDrawState* drawState,
663 GrColor color, 667 GrColor color,
668 const SkMatrix& viewMatrix,
664 bool useCoverageAA, 669 bool useCoverageAA,
665 const SkRect& circle, 670 const SkRect& circle,
666 const SkStrokeRec& stroke) 671 const SkStrokeRec& stroke) {
667 {
668 const SkMatrix& vm = drawState->getViewMatrix();
669 SkPoint center = SkPoint::Make(circle.centerX(), circle.centerY()); 672 SkPoint center = SkPoint::Make(circle.centerX(), circle.centerY());
670 vm.mapPoints(&center, 1); 673 viewMatrix.mapPoints(&center, 1);
671 SkScalar radius = vm.mapRadius(SkScalarHalf(circle.width())); 674 SkScalar radius = viewMatrix.mapRadius(SkScalarHalf(circle.width()));
672 SkScalar strokeWidth = vm.mapRadius(stroke.getWidth()); 675 SkScalar strokeWidth = viewMatrix.mapRadius(stroke.getWidth());
673 676
674 SkMatrix invert; 677 SkMatrix invert;
675 if (!vm.invert(&invert)) { 678 if (!viewMatrix.invert(&invert)) {
676 return; 679 return;
677 } 680 }
678 681
679 GrDrawState::AutoViewMatrixRestore avmr(drawState);
680
681 SkStrokeRec::Style style = stroke.getStyle(); 682 SkStrokeRec::Style style = stroke.getStyle();
682 bool isStrokeOnly = SkStrokeRec::kStroke_Style == style || 683 bool isStrokeOnly = SkStrokeRec::kStroke_Style == style ||
683 SkStrokeRec::kHairline_Style == style; 684 SkStrokeRec::kHairline_Style == style;
684 bool hasStroke = isStrokeOnly || SkStrokeRec::kStrokeAndFill_Style == style; 685 bool hasStroke = isStrokeOnly || SkStrokeRec::kStrokeAndFill_Style == style;
685 686
686 SkScalar innerRadius = 0.0f; 687 SkScalar innerRadius = 0.0f;
687 SkScalar outerRadius = radius; 688 SkScalar outerRadius = radius;
688 SkScalar halfWidth = 0; 689 SkScalar halfWidth = 0;
689 if (hasStroke) { 690 if (hasStroke) {
690 if (SkScalarNearlyZero(strokeWidth)) { 691 if (SkScalarNearlyZero(strokeWidth)) {
691 halfWidth = SK_ScalarHalf; 692 halfWidth = SK_ScalarHalf;
692 } else { 693 } else {
693 halfWidth = SkScalarHalf(strokeWidth); 694 halfWidth = SkScalarHalf(strokeWidth);
694 } 695 }
695 696
696 outerRadius += halfWidth; 697 outerRadius += halfWidth;
697 if (isStrokeOnly) { 698 if (isStrokeOnly) {
698 innerRadius = radius - halfWidth; 699 innerRadius = radius - halfWidth;
699 } 700 }
700 } 701 }
701 702
702 SkAutoTUnref<GrGeometryProcessor> gp( 703 SkAutoTUnref<GrGeometryProcessor> gp(
703 CircleEdgeEffect::Create(color, isStrokeOnly && innerRadius > 0, inv ert)); 704 CircleEdgeEffect::Create(color, isStrokeOnly && innerRadius > 0,inve rt));
704 705
705 GrDrawTarget::AutoReleaseGeometry geo(target, 4, gp->getVertexStride(), 0); 706 GrDrawTarget::AutoReleaseGeometry geo(target, 4, gp->getVertexStride(), 0);
706 SkASSERT(gp->getVertexStride() == sizeof(CircleVertex)); 707 SkASSERT(gp->getVertexStride() == sizeof(CircleVertex));
707 if (!geo.succeeded()) { 708 if (!geo.succeeded()) {
708 SkDebugf("Failed to get space for vertices!\n"); 709 SkDebugf("Failed to get space for vertices!\n");
709 return; 710 return;
710 } 711 }
711 712
712 CircleVertex* verts = reinterpret_cast<CircleVertex*>(geo.vertices()); 713 CircleVertex* verts = reinterpret_cast<CircleVertex*>(geo.vertices());
713 714
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
750 target->setIndexSourceToBuffer(fGpu->getQuadIndexBuffer()); 751 target->setIndexSourceToBuffer(fGpu->getQuadIndexBuffer());
751 target->drawIndexedInstances(drawState, gp, kTriangles_GrPrimitiveType, 1, 4 , 6, &bounds); 752 target->drawIndexedInstances(drawState, gp, kTriangles_GrPrimitiveType, 1, 4 , 6, &bounds);
752 target->resetIndexSource(); 753 target->resetIndexSource();
753 } 754 }
754 755
755 /////////////////////////////////////////////////////////////////////////////// 756 ///////////////////////////////////////////////////////////////////////////////
756 757
757 bool GrOvalRenderer::drawEllipse(GrDrawTarget* target, 758 bool GrOvalRenderer::drawEllipse(GrDrawTarget* target,
758 GrDrawState* drawState, 759 GrDrawState* drawState,
759 GrColor color, 760 GrColor color,
761 const SkMatrix& viewMatrix,
760 bool useCoverageAA, 762 bool useCoverageAA,
761 const SkRect& ellipse, 763 const SkRect& ellipse,
762 const SkStrokeRec& stroke) 764 const SkStrokeRec& stroke) {
763 {
764 #ifdef SK_DEBUG 765 #ifdef SK_DEBUG
765 { 766 {
766 // we should have checked for this previously 767 // we should have checked for this previously
767 bool isAxisAlignedEllipse = drawState->getViewMatrix().rectStaysRect(); 768 bool isAxisAlignedEllipse = viewMatrix.rectStaysRect();
768 SkASSERT(useCoverageAA && isAxisAlignedEllipse); 769 SkASSERT(useCoverageAA && isAxisAlignedEllipse);
769 } 770 }
770 #endif 771 #endif
771 772
772 // do any matrix crunching before we reset the draw state for device coords 773 // do any matrix crunching before we reset the draw state for device coords
773 const SkMatrix& vm = drawState->getViewMatrix();
774 SkPoint center = SkPoint::Make(ellipse.centerX(), ellipse.centerY()); 774 SkPoint center = SkPoint::Make(ellipse.centerX(), ellipse.centerY());
775 vm.mapPoints(&center, 1); 775 viewMatrix.mapPoints(&center, 1);
776 SkScalar ellipseXRadius = SkScalarHalf(ellipse.width()); 776 SkScalar ellipseXRadius = SkScalarHalf(ellipse.width());
777 SkScalar ellipseYRadius = SkScalarHalf(ellipse.height()); 777 SkScalar ellipseYRadius = SkScalarHalf(ellipse.height());
778 SkScalar xRadius = SkScalarAbs(vm[SkMatrix::kMScaleX]*ellipseXRadius + 778 SkScalar xRadius = SkScalarAbs(viewMatrix[SkMatrix::kMScaleX]*ellipseXRadius +
779 vm[SkMatrix::kMSkewY]*ellipseYRadius); 779 viewMatrix[SkMatrix::kMSkewY]*ellipseYRadius) ;
780 SkScalar yRadius = SkScalarAbs(vm[SkMatrix::kMSkewX]*ellipseXRadius + 780 SkScalar yRadius = SkScalarAbs(viewMatrix[SkMatrix::kMSkewX]*ellipseXRadius +
781 vm[SkMatrix::kMScaleY]*ellipseYRadius); 781 viewMatrix[SkMatrix::kMScaleY]*ellipseYRadius );
782 782
783 // do (potentially) anisotropic mapping of stroke 783 // do (potentially) anisotropic mapping of stroke
784 SkVector scaledStroke; 784 SkVector scaledStroke;
785 SkScalar strokeWidth = stroke.getWidth(); 785 SkScalar strokeWidth = stroke.getWidth();
786 scaledStroke.fX = SkScalarAbs(strokeWidth*(vm[SkMatrix::kMScaleX] + vm[SkMat rix::kMSkewY])); 786 scaledStroke.fX = SkScalarAbs(strokeWidth*(viewMatrix[SkMatrix::kMScaleX] +
787 scaledStroke.fY = SkScalarAbs(strokeWidth*(vm[SkMatrix::kMSkewX] + vm[SkMatr ix::kMScaleY])); 787 viewMatrix[SkMatrix::kMSkewY]));
788 scaledStroke.fY = SkScalarAbs(strokeWidth*(viewMatrix[SkMatrix::kMSkewX] +
789 viewMatrix[SkMatrix::kMScaleY]));
788 790
789 SkStrokeRec::Style style = stroke.getStyle(); 791 SkStrokeRec::Style style = stroke.getStyle();
790 bool isStrokeOnly = SkStrokeRec::kStroke_Style == style || 792 bool isStrokeOnly = SkStrokeRec::kStroke_Style == style ||
791 SkStrokeRec::kHairline_Style == style; 793 SkStrokeRec::kHairline_Style == style;
792 bool hasStroke = isStrokeOnly || SkStrokeRec::kStrokeAndFill_Style == style; 794 bool hasStroke = isStrokeOnly || SkStrokeRec::kStrokeAndFill_Style == style;
793 795
794 SkScalar innerXRadius = 0; 796 SkScalar innerXRadius = 0;
795 SkScalar innerYRadius = 0; 797 SkScalar innerYRadius = 0;
796 if (hasStroke) { 798 if (hasStroke) {
797 if (SkScalarNearlyZero(scaledStroke.length())) { 799 if (SkScalarNearlyZero(scaledStroke.length())) {
(...skipping 18 matching lines...) Expand all
816 if (isStrokeOnly) { 818 if (isStrokeOnly) {
817 innerXRadius = xRadius - scaledStroke.fX; 819 innerXRadius = xRadius - scaledStroke.fX;
818 innerYRadius = yRadius - scaledStroke.fY; 820 innerYRadius = yRadius - scaledStroke.fY;
819 } 821 }
820 822
821 xRadius += scaledStroke.fX; 823 xRadius += scaledStroke.fX;
822 yRadius += scaledStroke.fY; 824 yRadius += scaledStroke.fY;
823 } 825 }
824 826
825 SkMatrix invert; 827 SkMatrix invert;
826 if (!vm.invert(&invert)) { 828 if (!viewMatrix.invert(&invert)) {
827 return false; 829 return false;
828 } 830 }
829 831
830 GrDrawState::AutoViewMatrixRestore avmr(drawState);
831
832 SkAutoTUnref<GrGeometryProcessor> gp( 832 SkAutoTUnref<GrGeometryProcessor> gp(
833 EllipseEdgeEffect::Create(color, isStrokeOnly && innerXRadius > 0 && innerYRadius > 0, 833 EllipseEdgeEffect::Create(color,
834 isStrokeOnly && innerXRadius > 0 && innerY Radius > 0,
834 invert)); 835 invert));
835 836
836 GrDrawTarget::AutoReleaseGeometry geo(target, 4, gp->getVertexStride(), 0); 837 GrDrawTarget::AutoReleaseGeometry geo(target, 4, gp->getVertexStride(), 0);
837 SkASSERT(gp->getVertexStride() == sizeof(EllipseVertex)); 838 SkASSERT(gp->getVertexStride() == sizeof(EllipseVertex));
838 if (!geo.succeeded()) { 839 if (!geo.succeeded()) {
839 SkDebugf("Failed to get space for vertices!\n"); 840 SkDebugf("Failed to get space for vertices!\n");
840 return false; 841 return false;
841 } 842 }
842 843
843 EllipseVertex* verts = reinterpret_cast<EllipseVertex*>(geo.vertices()); 844 EllipseVertex* verts = reinterpret_cast<EllipseVertex*>(geo.vertices());
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
884 target->setIndexSourceToBuffer(fGpu->getQuadIndexBuffer()); 885 target->setIndexSourceToBuffer(fGpu->getQuadIndexBuffer());
885 target->drawIndexedInstances(drawState, gp, kTriangles_GrPrimitiveType, 1, 4 , 6, &bounds); 886 target->drawIndexedInstances(drawState, gp, kTriangles_GrPrimitiveType, 1, 4 , 6, &bounds);
886 target->resetIndexSource(); 887 target->resetIndexSource();
887 888
888 return true; 889 return true;
889 } 890 }
890 891
891 bool GrOvalRenderer::drawDIEllipse(GrDrawTarget* target, 892 bool GrOvalRenderer::drawDIEllipse(GrDrawTarget* target,
892 GrDrawState* drawState, 893 GrDrawState* drawState,
893 GrColor color, 894 GrColor color,
895 const SkMatrix& viewMatrix,
894 bool useCoverageAA, 896 bool useCoverageAA,
895 const SkRect& ellipse, 897 const SkRect& ellipse,
896 const SkStrokeRec& stroke) 898 const SkStrokeRec& stroke) {
897 {
898 const SkMatrix& vm = drawState->getViewMatrix();
899
900 SkPoint center = SkPoint::Make(ellipse.centerX(), ellipse.centerY()); 899 SkPoint center = SkPoint::Make(ellipse.centerX(), ellipse.centerY());
901 SkScalar xRadius = SkScalarHalf(ellipse.width()); 900 SkScalar xRadius = SkScalarHalf(ellipse.width());
902 SkScalar yRadius = SkScalarHalf(ellipse.height()); 901 SkScalar yRadius = SkScalarHalf(ellipse.height());
903 902
904 SkStrokeRec::Style style = stroke.getStyle(); 903 SkStrokeRec::Style style = stroke.getStyle();
905 DIEllipseEdgeEffect::Mode mode = (SkStrokeRec::kStroke_Style == style) ? 904 DIEllipseEdgeEffect::Mode mode = (SkStrokeRec::kStroke_Style == style) ?
906 DIEllipseEdgeEffect::kStroke : 905 DIEllipseEdgeEffect::kStroke :
907 (SkStrokeRec::kHairline_Style == style) ? 906 (SkStrokeRec::kHairline_Style == style) ?
908 DIEllipseEdgeEffect::kHairline : DIEllipseEd geEffect::kFill; 907 DIEllipseEdgeEffect::kHairline : DIEllipseEd geEffect::kFill;
909 908
(...skipping 29 matching lines...) Expand all
939 xRadius += strokeWidth; 938 xRadius += strokeWidth;
940 yRadius += strokeWidth; 939 yRadius += strokeWidth;
941 } 940 }
942 if (DIEllipseEdgeEffect::kStroke == mode) { 941 if (DIEllipseEdgeEffect::kStroke == mode) {
943 mode = (innerXRadius > 0 && innerYRadius > 0) ? DIEllipseEdgeEffect::kSt roke : 942 mode = (innerXRadius > 0 && innerYRadius > 0) ? DIEllipseEdgeEffect::kSt roke :
944 DIEllipseEdgeEffect::kFi ll; 943 DIEllipseEdgeEffect::kFi ll;
945 } 944 }
946 SkScalar innerRatioX = SkScalarDiv(xRadius, innerXRadius); 945 SkScalar innerRatioX = SkScalarDiv(xRadius, innerXRadius);
947 SkScalar innerRatioY = SkScalarDiv(yRadius, innerYRadius); 946 SkScalar innerRatioY = SkScalarDiv(yRadius, innerYRadius);
948 947
949 SkAutoTUnref<GrGeometryProcessor> gp(DIEllipseEdgeEffect::Create(color, mode )); 948 SkAutoTUnref<GrGeometryProcessor> gp(DIEllipseEdgeEffect::Create(color, view Matrix, mode));
950 949
951 GrDrawTarget::AutoReleaseGeometry geo(target, 4, gp->getVertexStride(), 0); 950 GrDrawTarget::AutoReleaseGeometry geo(target, 4, gp->getVertexStride(), 0);
952 SkASSERT(gp->getVertexStride() == sizeof(DIEllipseVertex)); 951 SkASSERT(gp->getVertexStride() == sizeof(DIEllipseVertex));
953 if (!geo.succeeded()) { 952 if (!geo.succeeded()) {
954 SkDebugf("Failed to get space for vertices!\n"); 953 SkDebugf("Failed to get space for vertices!\n");
955 return false; 954 return false;
956 } 955 }
957 956
958 DIEllipseVertex* verts = reinterpret_cast<DIEllipseVertex*>(geo.vertices()); 957 DIEllipseVertex* verts = reinterpret_cast<DIEllipseVertex*>(geo.vertices());
959 958
960 // This expands the outer rect so that after CTM we end up with a half-pixel border 959 // This expands the outer rect so that after CTM we end up with a half-pixel border
961 SkScalar a = vm[SkMatrix::kMScaleX]; 960 SkScalar a = viewMatrix[SkMatrix::kMScaleX];
962 SkScalar b = vm[SkMatrix::kMSkewX]; 961 SkScalar b = viewMatrix[SkMatrix::kMSkewX];
963 SkScalar c = vm[SkMatrix::kMSkewY]; 962 SkScalar c = viewMatrix[SkMatrix::kMSkewY];
964 SkScalar d = vm[SkMatrix::kMScaleY]; 963 SkScalar d = viewMatrix[SkMatrix::kMScaleY];
965 SkScalar geoDx = SkScalarDiv(SK_ScalarHalf, SkScalarSqrt(a*a + c*c)); 964 SkScalar geoDx = SkScalarDiv(SK_ScalarHalf, SkScalarSqrt(a*a + c*c));
966 SkScalar geoDy = SkScalarDiv(SK_ScalarHalf, SkScalarSqrt(b*b + d*d)); 965 SkScalar geoDy = SkScalarDiv(SK_ScalarHalf, SkScalarSqrt(b*b + d*d));
967 // This adjusts the "radius" to include the half-pixel border 966 // This adjusts the "radius" to include the half-pixel border
968 SkScalar offsetDx = SkScalarDiv(geoDx, xRadius); 967 SkScalar offsetDx = SkScalarDiv(geoDx, xRadius);
969 SkScalar offsetDy = SkScalarDiv(geoDy, yRadius); 968 SkScalar offsetDy = SkScalarDiv(geoDy, yRadius);
970 969
971 SkRect bounds = SkRect::MakeLTRB( 970 SkRect bounds = SkRect::MakeLTRB(
972 center.fX - xRadius - geoDx, 971 center.fX - xRadius - geoDx,
973 center.fY - yRadius - geoDy, 972 center.fY - yRadius - geoDy,
974 center.fX + xRadius + geoDx, 973 center.fX + xRadius + geoDx,
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after
1039 kNumRRectsInInd exBuffer, 1038 kNumRRectsInInd exBuffer,
1040 kVertsPerRRect) ; 1039 kVertsPerRRect) ;
1041 } 1040 }
1042 return fRRectIndexBuffer; 1041 return fRRectIndexBuffer;
1043 } 1042 }
1044 } 1043 }
1045 1044
1046 bool GrOvalRenderer::drawDRRect(GrDrawTarget* target, 1045 bool GrOvalRenderer::drawDRRect(GrDrawTarget* target,
1047 GrDrawState* drawState, 1046 GrDrawState* drawState,
1048 GrColor color, 1047 GrColor color,
1048 const SkMatrix& viewMatrix,
1049 bool useAA, 1049 bool useAA,
1050 const SkRRect& origOuter, 1050 const SkRRect& origOuter,
1051 const SkRRect& origInner) { 1051 const SkRRect& origInner) {
1052 bool applyAA = useAA && 1052 bool applyAA = useAA &&
1053 !drawState->getRenderTarget()->isMultisampled() && 1053 !drawState->getRenderTarget()->isMultisampled() &&
1054 drawState->canUseFracCoveragePrimProc(color, *target->caps()) ; 1054 drawState->canUseFracCoveragePrimProc(color, *target->caps()) ;
1055 GrDrawState::AutoRestoreEffects are; 1055 GrDrawState::AutoRestoreEffects are;
1056 if (!origInner.isEmpty()) { 1056 if (!origInner.isEmpty()) {
1057 SkTCopyOnFirstWrite<SkRRect> inner(origInner); 1057 SkTCopyOnFirstWrite<SkRRect> inner(origInner);
1058 if (!drawState->getViewMatrix().isIdentity()) { 1058 if (!viewMatrix.isIdentity()) {
1059 if (!origInner.transform(drawState->getViewMatrix(), inner.writable( ))) { 1059 if (!origInner.transform(viewMatrix, inner.writable())) {
1060 return false; 1060 return false;
1061 } 1061 }
1062 } 1062 }
1063 GrPrimitiveEdgeType edgeType = applyAA ? 1063 GrPrimitiveEdgeType edgeType = applyAA ?
1064 kInverseFillAA_GrProcessorEdgeType : 1064 kInverseFillAA_GrProcessorEdgeType :
1065 kInverseFillBW_GrProcessorEdgeType; 1065 kInverseFillBW_GrProcessorEdgeType;
1066 // TODO this needs to be a geometry processor 1066 // TODO this needs to be a geometry processor
1067 GrFragmentProcessor* fp = GrRRectEffect::Create(edgeType, *inner); 1067 GrFragmentProcessor* fp = GrRRectEffect::Create(edgeType, *inner);
1068 if (NULL == fp) { 1068 if (NULL == fp) {
1069 return false; 1069 return false;
1070 } 1070 }
1071 are.set(drawState); 1071 are.set(drawState);
1072 drawState->addCoverageProcessor(fp)->unref(); 1072 drawState->addCoverageProcessor(fp)->unref();
1073 } 1073 }
1074 1074
1075 SkStrokeRec fillRec(SkStrokeRec::kFill_InitStyle); 1075 SkStrokeRec fillRec(SkStrokeRec::kFill_InitStyle);
1076 if (this->drawRRect(target, drawState, color, useAA, origOuter, fillRec)) { 1076 if (this->drawRRect(target, drawState, color, viewMatrix, useAA, origOuter, fillRec)) {
1077 return true; 1077 return true;
1078 } 1078 }
1079 1079
1080 SkASSERT(!origOuter.isEmpty()); 1080 SkASSERT(!origOuter.isEmpty());
1081 SkTCopyOnFirstWrite<SkRRect> outer(origOuter); 1081 SkTCopyOnFirstWrite<SkRRect> outer(origOuter);
1082 if (!drawState->getViewMatrix().isIdentity()) { 1082 if (!viewMatrix.isIdentity()) {
1083 if (!origOuter.transform(drawState->getViewMatrix(), outer.writable())) { 1083 if (!origOuter.transform(viewMatrix, outer.writable())) {
1084 return false; 1084 return false;
1085 } 1085 }
1086 } 1086 }
1087 GrPrimitiveEdgeType edgeType = applyAA ? kFillAA_GrProcessorEdgeType : 1087 GrPrimitiveEdgeType edgeType = applyAA ? kFillAA_GrProcessorEdgeType :
1088 kFillBW_GrProcessorEdgeType; 1088 kFillBW_GrProcessorEdgeType;
1089 GrFragmentProcessor* effect = GrRRectEffect::Create(edgeType, *outer); 1089 GrFragmentProcessor* effect = GrRRectEffect::Create(edgeType, *outer);
1090 if (NULL == effect) { 1090 if (NULL == effect) {
1091 return false; 1091 return false;
1092 } 1092 }
1093 if (!are.isSet()) { 1093 if (!are.isSet()) {
1094 are.set(drawState); 1094 are.set(drawState);
1095 } 1095 }
1096 1096
1097 SkMatrix invert; 1097 SkMatrix invert;
1098 if (!drawState->getViewMatrix().invert(&invert)) { 1098 if (!viewMatrix.invert(&invert)) {
1099 return false; 1099 return false;
1100 } 1100 }
1101 1101
1102 GrDrawState::AutoViewMatrixRestore avmr(drawState);
1103 drawState->addCoverageProcessor(effect)->unref(); 1102 drawState->addCoverageProcessor(effect)->unref();
1104 SkRect bounds = outer->getBounds(); 1103 SkRect bounds = outer->getBounds();
1105 if (applyAA) { 1104 if (applyAA) {
1106 bounds.outset(SK_ScalarHalf, SK_ScalarHalf); 1105 bounds.outset(SK_ScalarHalf, SK_ScalarHalf);
1107 } 1106 }
1108 target->drawRect(drawState, color, bounds, NULL, &invert); 1107 target->drawRect(drawState, color, SkMatrix::I(), bounds, NULL, &invert);
1109 return true; 1108 return true;
1110 } 1109 }
1111 1110
1112 bool GrOvalRenderer::drawRRect(GrDrawTarget* target, 1111 bool GrOvalRenderer::drawRRect(GrDrawTarget* target,
1113 GrDrawState* drawState, 1112 GrDrawState* drawState,
1114 GrColor color, 1113 GrColor color,
1114 const SkMatrix& viewMatrix,
1115 bool useAA, 1115 bool useAA,
1116 const SkRRect& rrect, 1116 const SkRRect& rrect,
1117 const SkStrokeRec& stroke) { 1117 const SkStrokeRec& stroke) {
1118 if (rrect.isOval()) { 1118 if (rrect.isOval()) {
1119 return this->drawOval(target, drawState, color, useAA, rrect.getBounds() , stroke); 1119 return this->drawOval(target, drawState, color, viewMatrix, useAA, rrect .getBounds(),
1120 stroke);
1120 } 1121 }
1121 1122
1122 bool useCoverageAA = useAA && 1123 bool useCoverageAA = useAA &&
1123 !drawState->getRenderTarget()->isMultisampled() && 1124 !drawState->getRenderTarget()->isMultisampled() &&
1124 drawState->canUseFracCoveragePrimProc(color, *target->caps()); 1125 drawState->canUseFracCoveragePrimProc(color, *target->caps());
1125 1126
1126 // only anti-aliased rrects for now 1127 // only anti-aliased rrects for now
1127 if (!useCoverageAA) { 1128 if (!useCoverageAA) {
1128 return false; 1129 return false;
1129 } 1130 }
1130 1131
1131 const SkMatrix& vm = drawState->getViewMatrix(); 1132 if (!viewMatrix.rectStaysRect() || !rrect.isSimple()) {
1132
1133 if (!vm.rectStaysRect() || !rrect.isSimple()) {
1134 return false; 1133 return false;
1135 } 1134 }
1136 1135
1137 // do any matrix crunching before we reset the draw state for device coords 1136 // do any matrix crunching before we reset the draw state for device coords
1138 const SkRect& rrectBounds = rrect.getBounds(); 1137 const SkRect& rrectBounds = rrect.getBounds();
1139 SkRect bounds; 1138 SkRect bounds;
1140 vm.mapRect(&bounds, rrectBounds); 1139 viewMatrix.mapRect(&bounds, rrectBounds);
1141 1140
1142 SkVector radii = rrect.getSimpleRadii(); 1141 SkVector radii = rrect.getSimpleRadii();
1143 SkScalar xRadius = SkScalarAbs(vm[SkMatrix::kMScaleX]*radii.fX + 1142 SkScalar xRadius = SkScalarAbs(viewMatrix[SkMatrix::kMScaleX]*radii.fX +
1144 vm[SkMatrix::kMSkewY]*radii.fY); 1143 viewMatrix[SkMatrix::kMSkewY]*radii.fY);
1145 SkScalar yRadius = SkScalarAbs(vm[SkMatrix::kMSkewX]*radii.fX + 1144 SkScalar yRadius = SkScalarAbs(viewMatrix[SkMatrix::kMSkewX]*radii.fX +
1146 vm[SkMatrix::kMScaleY]*radii.fY); 1145 viewMatrix[SkMatrix::kMScaleY]*radii.fY);
1147 1146
1148 SkStrokeRec::Style style = stroke.getStyle(); 1147 SkStrokeRec::Style style = stroke.getStyle();
1149 1148
1150 // do (potentially) anisotropic mapping of stroke 1149 // do (potentially) anisotropic mapping of stroke
1151 SkVector scaledStroke; 1150 SkVector scaledStroke;
1152 SkScalar strokeWidth = stroke.getWidth(); 1151 SkScalar strokeWidth = stroke.getWidth();
1153 1152
1154 bool isStrokeOnly = SkStrokeRec::kStroke_Style == style || 1153 bool isStrokeOnly = SkStrokeRec::kStroke_Style == style ||
1155 SkStrokeRec::kHairline_Style == style; 1154 SkStrokeRec::kHairline_Style == style;
1156 bool hasStroke = isStrokeOnly || SkStrokeRec::kStrokeAndFill_Style == style; 1155 bool hasStroke = isStrokeOnly || SkStrokeRec::kStrokeAndFill_Style == style;
1157 1156
1158 if (hasStroke) { 1157 if (hasStroke) {
1159 if (SkStrokeRec::kHairline_Style == style) { 1158 if (SkStrokeRec::kHairline_Style == style) {
1160 scaledStroke.set(1, 1); 1159 scaledStroke.set(1, 1);
1161 } else { 1160 } else {
1162 scaledStroke.fX = SkScalarAbs(strokeWidth*(vm[SkMatrix::kMScaleX] + 1161 scaledStroke.fX = SkScalarAbs(strokeWidth*(viewMatrix[SkMatrix::kMSc aleX] +
1163 vm[SkMatrix::kMSkewY])); 1162 viewMatrix[SkMatrix::kMSk ewY]));
1164 scaledStroke.fY = SkScalarAbs(strokeWidth*(vm[SkMatrix::kMSkewX] + 1163 scaledStroke.fY = SkScalarAbs(strokeWidth*(viewMatrix[SkMatrix::kMSk ewX] +
1165 vm[SkMatrix::kMScaleY])); 1164 viewMatrix[SkMatrix::kMSc aleY]));
1166 } 1165 }
1167 1166
1168 // if half of strokewidth is greater than radius, we don't handle that r ight now 1167 // if half of strokewidth is greater than radius, we don't handle that r ight now
1169 if (SK_ScalarHalf*scaledStroke.fX > xRadius || SK_ScalarHalf*scaledStrok e.fY > yRadius) { 1168 if (SK_ScalarHalf*scaledStroke.fX > xRadius || SK_ScalarHalf*scaledStrok e.fY > yRadius) {
1170 return false; 1169 return false;
1171 } 1170 }
1172 } 1171 }
1173 1172
1174 // The way the effect interpolates the offset-to-ellipse/circle-center attri bute only works on 1173 // The way the effect interpolates the offset-to-ellipse/circle-center attri bute only works on
1175 // the interior of the rrect if the radii are >= 0.5. Otherwise, the inner r ect of the nine- 1174 // the interior of the rrect if the radii are >= 0.5. Otherwise, the inner r ect of the nine-
1176 // patch will have fractional coverage. This only matters when the interior is actually filled. 1175 // patch will have fractional coverage. This only matters when the interior is actually filled.
1177 // We could consider falling back to rect rendering here, since a tiny radiu s is 1176 // We could consider falling back to rect rendering here, since a tiny radiu s is
1178 // indistinguishable from a square corner. 1177 // indistinguishable from a square corner.
1179 if (!isStrokeOnly && (SK_ScalarHalf > xRadius || SK_ScalarHalf > yRadius)) { 1178 if (!isStrokeOnly && (SK_ScalarHalf > xRadius || SK_ScalarHalf > yRadius)) {
1180 return false; 1179 return false;
1181 } 1180 }
1182 1181
1183 // reset to device coordinates 1182 // reset to device coordinates
1184 SkMatrix invert; 1183 SkMatrix invert;
1185 if (!vm.invert(&invert)) { 1184 if (!viewMatrix.invert(&invert)) {
1186 SkDebugf("Failed to invert\n"); 1185 SkDebugf("Failed to invert\n");
1187 return false; 1186 return false;
1188 } 1187 }
1189 1188
1190 GrDrawState::AutoViewMatrixRestore avmr(drawState);
1191
1192 GrIndexBuffer* indexBuffer = this->rRectIndexBuffer(isStrokeOnly); 1189 GrIndexBuffer* indexBuffer = this->rRectIndexBuffer(isStrokeOnly);
1193 if (NULL == indexBuffer) { 1190 if (NULL == indexBuffer) {
1194 SkDebugf("Failed to create index buffer!\n"); 1191 SkDebugf("Failed to create index buffer!\n");
1195 return false; 1192 return false;
1196 } 1193 }
1197 1194
1198 // if the corners are circles, use the circle renderer 1195 // if the corners are circles, use the circle renderer
1199 if ((!hasStroke || scaledStroke.fX == scaledStroke.fY) && xRadius == yRadius ) { 1196 if ((!hasStroke || scaledStroke.fX == scaledStroke.fY) && xRadius == yRadius ) {
1200 SkScalar innerRadius = 0.0f; 1197 SkScalar innerRadius = 0.0f;
1201 SkScalar outerRadius = xRadius; 1198 SkScalar outerRadius = xRadius;
1202 SkScalar halfWidth = 0; 1199 SkScalar halfWidth = 0;
1203 if (hasStroke) { 1200 if (hasStroke) {
1204 if (SkScalarNearlyZero(scaledStroke.fX)) { 1201 if (SkScalarNearlyZero(scaledStroke.fX)) {
1205 halfWidth = SK_ScalarHalf; 1202 halfWidth = SK_ScalarHalf;
1206 } else { 1203 } else {
1207 halfWidth = SkScalarHalf(scaledStroke.fX); 1204 halfWidth = SkScalarHalf(scaledStroke.fX);
1208 } 1205 }
1209 1206
1210 if (isStrokeOnly) { 1207 if (isStrokeOnly) {
1211 innerRadius = xRadius - halfWidth; 1208 innerRadius = xRadius - halfWidth;
1212 } 1209 }
1213 outerRadius += halfWidth; 1210 outerRadius += halfWidth;
1214 bounds.outset(halfWidth, halfWidth); 1211 bounds.outset(halfWidth, halfWidth);
1215 } 1212 }
1216 1213
1217 isStrokeOnly = (isStrokeOnly && innerRadius >= 0); 1214 isStrokeOnly = (isStrokeOnly && innerRadius >= 0);
1218 1215
1219 SkAutoTUnref<GrGeometryProcessor> effect(CircleEdgeEffect::Create(color, isStrokeOnly, 1216 SkAutoTUnref<GrGeometryProcessor> effect(CircleEdgeEffect::Create(color,
1217 isStro keOnly,
1220 invert )); 1218 invert ));
1221 1219
1222 GrDrawTarget::AutoReleaseGeometry geo(target, 16, effect->getVertexStrid e(), 0); 1220 GrDrawTarget::AutoReleaseGeometry geo(target, 16, effect->getVertexStrid e(), 0);
1223 SkASSERT(effect->getVertexStride() == sizeof(CircleVertex)); 1221 SkASSERT(effect->getVertexStride() == sizeof(CircleVertex));
1224 if (!geo.succeeded()) { 1222 if (!geo.succeeded()) {
1225 SkDebugf("Failed to get space for vertices!\n"); 1223 SkDebugf("Failed to get space for vertices!\n");
1226 return false; 1224 return false;
1227 } 1225 }
1228 CircleVertex* verts = reinterpret_cast<CircleVertex*>(geo.vertices()); 1226 CircleVertex* verts = reinterpret_cast<CircleVertex*>(geo.vertices());
1229 1227
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after
1309 innerYRadius = yRadius - scaledStroke.fY; 1307 innerYRadius = yRadius - scaledStroke.fY;
1310 } 1308 }
1311 1309
1312 xRadius += scaledStroke.fX; 1310 xRadius += scaledStroke.fX;
1313 yRadius += scaledStroke.fY; 1311 yRadius += scaledStroke.fY;
1314 bounds.outset(scaledStroke.fX, scaledStroke.fY); 1312 bounds.outset(scaledStroke.fX, scaledStroke.fY);
1315 } 1313 }
1316 1314
1317 isStrokeOnly = (isStrokeOnly && innerXRadius >= 0 && innerYRadius >= 0); 1315 isStrokeOnly = (isStrokeOnly && innerXRadius >= 0 && innerYRadius >= 0);
1318 1316
1319 SkAutoTUnref<GrGeometryProcessor> effect(EllipseEdgeEffect::Create(color , isStrokeOnly, 1317 SkAutoTUnref<GrGeometryProcessor> effect(EllipseEdgeEffect::Create(color ,
1318 isStr okeOnly,
1320 inver t)); 1319 inver t));
1321 1320
1322 GrDrawTarget::AutoReleaseGeometry geo(target, 16, effect->getVertexStrid e(), 0); 1321 GrDrawTarget::AutoReleaseGeometry geo(target, 16, effect->getVertexStrid e(), 0);
1323 SkASSERT(effect->getVertexStride() == sizeof(EllipseVertex)); 1322 SkASSERT(effect->getVertexStride() == sizeof(EllipseVertex));
1324 if (!geo.succeeded()) { 1323 if (!geo.succeeded()) {
1325 SkDebugf("Failed to get space for vertices!\n"); 1324 SkDebugf("Failed to get space for vertices!\n");
1326 return false; 1325 return false;
1327 } 1326 }
1328 1327
1329 EllipseVertex* verts = reinterpret_cast<EllipseVertex*>(geo.vertices()); 1328 EllipseVertex* verts = reinterpret_cast<EllipseVertex*>(geo.vertices());
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after
1384 int indexCnt = isStrokeOnly ? SK_ARRAY_COUNT(gRRectIndices) - 6 : 1383 int indexCnt = isStrokeOnly ? SK_ARRAY_COUNT(gRRectIndices) - 6 :
1385 SK_ARRAY_COUNT(gRRectIndices); 1384 SK_ARRAY_COUNT(gRRectIndices);
1386 target->setIndexSourceToBuffer(indexBuffer); 1385 target->setIndexSourceToBuffer(indexBuffer);
1387 target->drawIndexedInstances(drawState, effect, kTriangles_GrPrimitiveTy pe, 1, 16, indexCnt, 1386 target->drawIndexedInstances(drawState, effect, kTriangles_GrPrimitiveTy pe, 1, 16, indexCnt,
1388 &bounds); 1387 &bounds);
1389 } 1388 }
1390 1389
1391 target->resetIndexSource(); 1390 target->resetIndexSource();
1392 return true; 1391 return true;
1393 } 1392 }
OLDNEW
« no previous file with comments | « src/gpu/GrOvalRenderer.h ('k') | src/gpu/GrPathRenderer.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698