OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2012 Google Inc. | 2 * Copyright 2012 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 "GrAARectRenderer.h" | 8 #include "GrAARectRenderer.h" |
9 #include "GrGpu.h" | 9 #include "GrGpu.h" |
10 #include "gl/GrGLEffect.h" | 10 #include "gl/GrGLEffect.h" |
(...skipping 237 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
248 GrEffect* GrRectEffect::TestCreate(SkRandom* random, | 248 GrEffect* GrRectEffect::TestCreate(SkRandom* random, |
249 GrContext* context, | 249 GrContext* context, |
250 const GrDrawTargetCaps&, | 250 const GrDrawTargetCaps&, |
251 GrTexture* textures[]) { | 251 GrTexture* textures[]) { |
252 return GrRectEffect::Create(); | 252 return GrRectEffect::Create(); |
253 } | 253 } |
254 | 254 |
255 /////////////////////////////////////////////////////////////////////////////// | 255 /////////////////////////////////////////////////////////////////////////////// |
256 | 256 |
257 namespace { | 257 namespace { |
258 | |
259 extern const GrVertexAttrib gAARectAttribs[] = { | 258 extern const GrVertexAttrib gAARectAttribs[] = { |
260 {kVec2f_GrVertexAttribType, 0, kPosition_Gr
VertexAttribBinding}, | 259 {kVec2f_GrVertexAttribType, 0, kPosition_Gr
VertexAttribBinding}, |
261 {kVec4ub_GrVertexAttribType, sizeof(SkPoint), kColor_GrVer
texAttribBinding}, | 260 {kVec4ub_GrVertexAttribType, sizeof(SkPoint), kColor_GrVer
texAttribBinding}, |
262 {kVec4ub_GrVertexAttribType, sizeof(SkPoint) + sizeof(SkColor), kCoverage_Gr
VertexAttribBinding}, | 261 {kVec4ub_GrVertexAttribType, sizeof(SkPoint) + sizeof(SkColor), kCoverage_Gr
VertexAttribBinding}, |
263 }; | 262 }; |
264 | 263 |
| 264 // Should the coverage be multiplied into the color attrib or use a separate att
rib. |
| 265 enum CoverageAttribType { |
| 266 kUseColor_CoverageAttribType, |
| 267 kUseCoverage_CoverageAttribType, |
| 268 }; |
| 269 } |
| 270 |
| 271 static CoverageAttribType set_rect_attribs(GrDrawState* drawState) { |
| 272 if (drawState->canTweakAlphaForCoverage()) { |
| 273 drawState->setVertexAttribs<gAARectAttribs>(2); |
| 274 return kUseColor_CoverageAttribType; |
| 275 } else { |
| 276 drawState->setVertexAttribs<gAARectAttribs>(3); |
| 277 return kUseCoverage_CoverageAttribType; |
| 278 } |
| 279 } |
| 280 |
265 static void set_inset_fan(SkPoint* pts, size_t stride, | 281 static void set_inset_fan(SkPoint* pts, size_t stride, |
266 const SkRect& r, SkScalar dx, SkScalar dy) { | 282 const SkRect& r, SkScalar dx, SkScalar dy) { |
267 pts->setRectFan(r.fLeft + dx, r.fTop + dy, | 283 pts->setRectFan(r.fLeft + dx, r.fTop + dy, |
268 r.fRight - dx, r.fBottom - dy, stride); | 284 r.fRight - dx, r.fBottom - dy, stride); |
269 } | 285 } |
270 | 286 |
271 }; | |
272 | |
273 void GrAARectRenderer::reset() { | 287 void GrAARectRenderer::reset() { |
274 SkSafeSetNull(fAAFillRectIndexBuffer); | 288 SkSafeSetNull(fAAFillRectIndexBuffer); |
275 SkSafeSetNull(fAAMiterStrokeRectIndexBuffer); | 289 SkSafeSetNull(fAAMiterStrokeRectIndexBuffer); |
276 SkSafeSetNull(fAABevelStrokeRectIndexBuffer); | 290 SkSafeSetNull(fAABevelStrokeRectIndexBuffer); |
277 } | 291 } |
278 | 292 |
279 static const uint16_t gFillAARectIdx[] = { | 293 static const uint16_t gFillAARectIdx[] = { |
280 0, 1, 5, 5, 4, 0, | 294 0, 1, 5, 5, 4, 0, |
281 1, 2, 6, 6, 5, 1, | 295 1, 2, 6, 6, 5, 1, |
282 2, 3, 7, 7, 6, 2, | 296 2, 3, 7, 7, 6, 2, |
(...skipping 154 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
437 | 451 |
438 void GrAARectRenderer::geometryFillAARect(GrGpu* gpu, | 452 void GrAARectRenderer::geometryFillAARect(GrGpu* gpu, |
439 GrDrawTarget* target, | 453 GrDrawTarget* target, |
440 const SkRect& rect, | 454 const SkRect& rect, |
441 const SkMatrix& combinedMatrix, | 455 const SkMatrix& combinedMatrix, |
442 const SkRect& devRect) { | 456 const SkRect& devRect) { |
443 GrDrawState* drawState = target->drawState(); | 457 GrDrawState* drawState = target->drawState(); |
444 | 458 |
445 GrColor color = drawState->getColor(); | 459 GrColor color = drawState->getColor(); |
446 | 460 |
447 drawState->setVertexAttribs<gAARectAttribs>(SK_ARRAY_COUNT(gAARectAttribs)); | 461 CoverageAttribType covAttribType = set_rect_attribs(drawState); |
448 if (GrColorIsOpaque(color)) { | 462 if (kUseCoverage_CoverageAttribType == covAttribType && GrColorIsOpaque(colo
r)) { |
449 drawState->setHint(GrDrawState::kVertexColorsAreOpaque_Hint, true); | 463 drawState->setHint(GrDrawState::kVertexColorsAreOpaque_Hint, true); |
450 } | 464 } |
451 | 465 |
452 GrDrawTarget::AutoReleaseGeometry geo(target, 8, 0); | 466 GrDrawTarget::AutoReleaseGeometry geo(target, 8, 0); |
453 if (!geo.succeeded()) { | 467 if (!geo.succeeded()) { |
454 GrPrintf("Failed to get space for vertices!\n"); | 468 GrPrintf("Failed to get space for vertices!\n"); |
455 return; | 469 return; |
456 } | 470 } |
457 | 471 |
458 GrIndexBuffer* indexBuffer = this->aaFillRectIndexBuffer(gpu); | 472 GrIndexBuffer* indexBuffer = this->aaFillRectIndexBuffer(gpu); |
459 if (NULL == indexBuffer) { | 473 if (NULL == indexBuffer) { |
460 GrPrintf("Failed to create index buffer!\n"); | 474 GrPrintf("Failed to create index buffer!\n"); |
461 return; | 475 return; |
462 } | 476 } |
463 | 477 |
464 intptr_t verts = reinterpret_cast<intptr_t>(geo.vertices()); | 478 intptr_t verts = reinterpret_cast<intptr_t>(geo.vertices()); |
465 size_t vsize = drawState->getVertexSize(); | 479 size_t vsize = drawState->getVertexSize(); |
466 SkASSERT(sizeof(SkPoint) + 2 * sizeof(GrColor) == vsize); | |
467 | 480 |
468 SkPoint* fan0Pos = reinterpret_cast<SkPoint*>(verts); | 481 SkPoint* fan0Pos = reinterpret_cast<SkPoint*>(verts); |
469 SkPoint* fan1Pos = reinterpret_cast<SkPoint*>(verts + 4 * vsize); | 482 SkPoint* fan1Pos = reinterpret_cast<SkPoint*>(verts + 4 * vsize); |
470 | 483 |
471 SkScalar inset = SkMinScalar(devRect.width(), SK_Scalar1); | 484 SkScalar inset = SkMinScalar(devRect.width(), SK_Scalar1); |
472 inset = SK_ScalarHalf * SkMinScalar(inset, devRect.height()); | 485 inset = SK_ScalarHalf * SkMinScalar(inset, devRect.height()); |
473 | 486 |
474 if (combinedMatrix.rectStaysRect()) { | 487 if (combinedMatrix.rectStaysRect()) { |
475 // Temporarily #if'ed out. We don't want to pass in the devRect but | 488 // Temporarily #if'ed out. We don't want to pass in the devRect but |
476 // right now it is computed in GrContext::apply_aa_to_rect and we don't | 489 // right now it is computed in GrContext::apply_aa_to_rect and we don't |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
516 *((SkPoint*)((intptr_t)fan0Pos + 2 * vsize)) += vec[0] + vec[1]; | 529 *((SkPoint*)((intptr_t)fan0Pos + 2 * vsize)) += vec[0] + vec[1]; |
517 // TR | 530 // TR |
518 *((SkPoint*)((intptr_t)fan1Pos + 3 * vsize)) = | 531 *((SkPoint*)((intptr_t)fan1Pos + 3 * vsize)) = |
519 *((SkPoint*)((intptr_t)fan0Pos + 3 * vsize)) - vec[0] + vec[1]; | 532 *((SkPoint*)((intptr_t)fan0Pos + 3 * vsize)) - vec[0] + vec[1]; |
520 *((SkPoint*)((intptr_t)fan0Pos + 3 * vsize)) += vec[0] - vec[1]; | 533 *((SkPoint*)((intptr_t)fan0Pos + 3 * vsize)) += vec[0] - vec[1]; |
521 } | 534 } |
522 | 535 |
523 // Make verts point to vertex color and then set all the color and coverage
vertex attrs values. | 536 // Make verts point to vertex color and then set all the color and coverage
vertex attrs values. |
524 verts += sizeof(SkPoint); | 537 verts += sizeof(SkPoint); |
525 for (int i = 0; i < 4; ++i) { | 538 for (int i = 0; i < 4; ++i) { |
526 *reinterpret_cast<GrColor*>(verts + i * vsize) = color; | 539 if (kUseCoverage_CoverageAttribType == covAttribType) { |
527 *reinterpret_cast<GrColor*>(verts + i * vsize + sizeof(GrColor)) = 0; | 540 *reinterpret_cast<GrColor*>(verts + i * vsize) = color; |
| 541 *reinterpret_cast<GrColor*>(verts + i * vsize + sizeof(GrColor)) = 0
; |
| 542 } else { |
| 543 *reinterpret_cast<GrColor*>(verts + i * vsize) = 0; |
| 544 } |
528 } | 545 } |
529 | 546 |
530 int scale; | 547 int scale; |
531 if (inset < SK_ScalarHalf) { | 548 if (inset < SK_ScalarHalf) { |
532 scale = SkScalarFloorToInt(512.0f * inset / (inset + SK_ScalarHalf)); | 549 scale = SkScalarFloorToInt(512.0f * inset / (inset + SK_ScalarHalf)); |
533 SkASSERT(scale >= 0 && scale <= 255); | 550 SkASSERT(scale >= 0 && scale <= 255); |
534 } else { | 551 } else { |
535 scale = 0xff; | 552 scale = 0xff; |
536 } | 553 } |
537 | 554 |
538 GrColor innerCoverage; | 555 GrColor innerCoverage; |
539 innerCoverage = GrColorPackRGBA(scale, scale, scale, scale); verts += 4 *
vsize; | 556 if (kUseCoverage_CoverageAttribType == covAttribType) { |
| 557 innerCoverage = GrColorPackRGBA(scale, scale, scale, scale); |
| 558 } else { |
| 559 innerCoverage = (0xff == scale) ? color : SkAlphaMulQ(color, scale); |
| 560 } |
| 561 verts += 4 * vsize; |
540 for (int i = 0; i < 4; ++i) { | 562 for (int i = 0; i < 4; ++i) { |
541 *reinterpret_cast<GrColor*>(verts + i * vsize) = color; | 563 if (kUseCoverage_CoverageAttribType == covAttribType) { |
542 *reinterpret_cast<GrColor*>(verts + i * vsize + sizeof(GrColor)) = inner
Coverage; | 564 *reinterpret_cast<GrColor*>(verts + i * vsize) = color; |
| 565 *reinterpret_cast<GrColor*>(verts + i * vsize + sizeof(GrColor)) = i
nnerCoverage; |
| 566 } else { |
| 567 *reinterpret_cast<GrColor*>(verts + i * vsize) = innerCoverage; |
| 568 } |
543 } | 569 } |
544 | 570 |
545 target->setIndexSourceToBuffer(indexBuffer); | 571 target->setIndexSourceToBuffer(indexBuffer); |
546 target->drawIndexedInstances(kTriangles_GrPrimitiveType, 1, | 572 target->drawIndexedInstances(kTriangles_GrPrimitiveType, 1, |
547 kVertsPerAAFillRect, | 573 kVertsPerAAFillRect, |
548 kIndicesPerAAFillRect); | 574 kIndicesPerAAFillRect); |
549 target->resetIndexSource(); | 575 target->resetIndexSource(); |
550 } | 576 } |
551 | 577 |
552 namespace { | 578 namespace { |
(...skipping 219 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
772 } | 798 } |
773 | 799 |
774 void GrAARectRenderer::geometryStrokeAARect(GrGpu* gpu, | 800 void GrAARectRenderer::geometryStrokeAARect(GrGpu* gpu, |
775 GrDrawTarget* target, | 801 GrDrawTarget* target, |
776 const SkRect& devOutside, | 802 const SkRect& devOutside, |
777 const SkRect& devOutsideAssist, | 803 const SkRect& devOutsideAssist, |
778 const SkRect& devInside, | 804 const SkRect& devInside, |
779 bool miterStroke) { | 805 bool miterStroke) { |
780 GrDrawState* drawState = target->drawState(); | 806 GrDrawState* drawState = target->drawState(); |
781 | 807 |
782 drawState->setVertexAttribs<gAARectAttribs>(SK_ARRAY_COUNT(gAARectAttribs)); | 808 CoverageAttribType covAttribType = set_rect_attribs(drawState); |
783 | 809 |
784 GrColor color = drawState->getColor(); | 810 GrColor color = drawState->getColor(); |
785 if (GrColorIsOpaque(color)) { | 811 if (kUseCoverage_CoverageAttribType == covAttribType && GrColorIsOpaque(colo
r)) { |
786 drawState->setHint(GrDrawState::kVertexColorsAreOpaque_Hint, true); | 812 drawState->setHint(GrDrawState::kVertexColorsAreOpaque_Hint, true); |
787 } | 813 } |
788 | 814 |
789 int innerVertexNum = 4; | 815 int innerVertexNum = 4; |
790 int outerVertexNum = miterStroke ? 4 : 8; | 816 int outerVertexNum = miterStroke ? 4 : 8; |
791 int totalVertexNum = (outerVertexNum + innerVertexNum) * 2; | 817 int totalVertexNum = (outerVertexNum + innerVertexNum) * 2; |
792 | 818 |
793 GrDrawTarget::AutoReleaseGeometry geo(target, totalVertexNum, 0); | 819 GrDrawTarget::AutoReleaseGeometry geo(target, totalVertexNum, 0); |
794 if (!geo.succeeded()) { | 820 if (!geo.succeeded()) { |
795 GrPrintf("Failed to get space for vertices!\n"); | 821 GrPrintf("Failed to get space for vertices!\n"); |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
848 // inner one of the inner two | 874 // inner one of the inner two |
849 set_inset_fan(fan2Pos, vsize, devInside, -inset, -inset); | 875 set_inset_fan(fan2Pos, vsize, devInside, -inset, -inset); |
850 // innermost | 876 // innermost |
851 set_inset_fan(fan3Pos, vsize, devInside, SK_ScalarHalf, SK_ScalarHalf
); | 877 set_inset_fan(fan3Pos, vsize, devInside, SK_ScalarHalf, SK_ScalarHalf
); |
852 } | 878 } |
853 | 879 |
854 // Make verts point to vertex color and then set all the color and coverage
vertex attrs values. | 880 // Make verts point to vertex color and then set all the color and coverage
vertex attrs values. |
855 // The outermost rect has 0 coverage | 881 // The outermost rect has 0 coverage |
856 verts += sizeof(SkPoint); | 882 verts += sizeof(SkPoint); |
857 for (int i = 0; i < outerVertexNum; ++i) { | 883 for (int i = 0; i < outerVertexNum; ++i) { |
858 *reinterpret_cast<GrColor*>(verts + i * vsize) = color; | 884 if (kUseCoverage_CoverageAttribType == covAttribType) { |
859 *reinterpret_cast<GrColor*>(verts + i * vsize + sizeof(GrColor)) = 0; | 885 *reinterpret_cast<GrColor*>(verts + i * vsize) = color; |
| 886 *reinterpret_cast<GrColor*>(verts + i * vsize + sizeof(GrColor)) = 0
; |
| 887 } else { |
| 888 *reinterpret_cast<GrColor*>(verts + i * vsize) = 0; |
| 889 } |
860 } | 890 } |
861 | 891 |
862 // scale is the coverage for the the inner two rects. | 892 // scale is the coverage for the the inner two rects. |
863 int scale; | 893 int scale; |
864 if (inset < SK_ScalarHalf) { | 894 if (inset < SK_ScalarHalf) { |
865 scale = SkScalarFloorToInt(512.0f * inset / (inset + SK_ScalarHalf)); | 895 scale = SkScalarFloorToInt(512.0f * inset / (inset + SK_ScalarHalf)); |
866 SkASSERT(scale >= 0 && scale <= 255); | 896 SkASSERT(scale >= 0 && scale <= 255); |
867 } else { | 897 } else { |
868 scale = 0xff; | 898 scale = 0xff; |
869 } | 899 } |
870 | 900 |
871 verts += outerVertexNum * vsize; | 901 verts += outerVertexNum * vsize; |
872 GrColor innerCoverage = GrColorPackRGBA(scale, scale, scale, scale); | 902 GrColor innerCoverage; |
| 903 if (kUseCoverage_CoverageAttribType == covAttribType) { |
| 904 innerCoverage = GrColorPackRGBA(scale, scale, scale, scale); |
| 905 } else { |
| 906 innerCoverage = (0xff == scale) ? color : SkAlphaMulQ(color, scale); |
| 907 } |
| 908 |
873 for (int i = 0; i < outerVertexNum + innerVertexNum; ++i) { | 909 for (int i = 0; i < outerVertexNum + innerVertexNum; ++i) { |
874 *reinterpret_cast<GrColor*>(verts + i * vsize) = color; | 910 if (kUseCoverage_CoverageAttribType == covAttribType) { |
875 *reinterpret_cast<GrColor*>(verts + i * vsize + sizeof(GrColor)) = inner
Coverage; | 911 *reinterpret_cast<GrColor*>(verts + i * vsize) = color; |
| 912 *reinterpret_cast<GrColor*>(verts + i * vsize + sizeof(GrColor)) = i
nnerCoverage; |
| 913 } else { |
| 914 *reinterpret_cast<GrColor*>(verts + i * vsize) = innerCoverage; |
| 915 } |
876 } | 916 } |
877 | 917 |
878 // The innermost rect has 0 coverage | 918 // The innermost rect has 0 coverage |
879 verts += (outerVertexNum + innerVertexNum) * vsize; | 919 verts += (outerVertexNum + innerVertexNum) * vsize; |
880 for (int i = 0; i < innerVertexNum; ++i) { | 920 for (int i = 0; i < innerVertexNum; ++i) { |
881 *reinterpret_cast<GrColor*>(verts + i * vsize) = color; | 921 if (kUseCoverage_CoverageAttribType == covAttribType) { |
882 *reinterpret_cast<GrColor*>(verts + i * vsize + sizeof(GrColor)) = 0; | 922 *reinterpret_cast<GrColor*>(verts + i * vsize) = color; |
| 923 *reinterpret_cast<GrColor*>(verts + i * vsize + sizeof(GrColor)) = 0
; |
| 924 } else { |
| 925 *reinterpret_cast<GrColor*>(verts + i * vsize) = 0; |
| 926 } |
883 } | 927 } |
884 | 928 |
885 target->setIndexSourceToBuffer(indexBuffer); | 929 target->setIndexSourceToBuffer(indexBuffer); |
886 target->drawIndexed(kTriangles_GrPrimitiveType, 0, 0, | 930 target->drawIndexed(kTriangles_GrPrimitiveType, 0, 0, |
887 totalVertexNum, aaStrokeRectIndexCount(miterStroke)); | 931 totalVertexNum, aaStrokeRectIndexCount(miterStroke)); |
888 } | 932 } |
889 | 933 |
890 void GrAARectRenderer::fillAANestedRects(GrGpu* gpu, | 934 void GrAARectRenderer::fillAANestedRects(GrGpu* gpu, |
891 GrDrawTarget* target, | 935 GrDrawTarget* target, |
892 const SkRect rects[2], | 936 const SkRect rects[2], |
893 const SkMatrix& combinedMatrix) { | 937 const SkMatrix& combinedMatrix) { |
894 SkASSERT(combinedMatrix.rectStaysRect()); | 938 SkASSERT(combinedMatrix.rectStaysRect()); |
895 SkASSERT(!rects[1].isEmpty()); | 939 SkASSERT(!rects[1].isEmpty()); |
896 | 940 |
897 SkRect devOutside, devOutsideAssist, devInside; | 941 SkRect devOutside, devOutsideAssist, devInside; |
898 combinedMatrix.mapRect(&devOutside, rects[0]); | 942 combinedMatrix.mapRect(&devOutside, rects[0]); |
899 // can't call mapRect for devInside since it calls sort | 943 // can't call mapRect for devInside since it calls sort |
900 combinedMatrix.mapPoints((SkPoint*)&devInside, (const SkPoint*)&rects[1], 2)
; | 944 combinedMatrix.mapPoints((SkPoint*)&devInside, (const SkPoint*)&rects[1], 2)
; |
901 | 945 |
902 if (devInside.isEmpty()) { | 946 if (devInside.isEmpty()) { |
903 this->fillAARect(gpu, target, devOutside, SkMatrix::I(), devOutside); | 947 this->fillAARect(gpu, target, devOutside, SkMatrix::I(), devOutside); |
904 return; | 948 return; |
905 } | 949 } |
906 | 950 |
907 this->geometryStrokeAARect(gpu, target, devOutside, devOutsideAssist, devIns
ide, true); | 951 this->geometryStrokeAARect(gpu, target, devOutside, devOutsideAssist, devIns
ide, true); |
908 } | 952 } |
OLD | NEW |