OLD | NEW |
1 | 1 |
2 /* | 2 /* |
3 * Copyright 2011 Google Inc. | 3 * Copyright 2011 Google Inc. |
4 * | 4 * |
5 * Use of this source code is governed by a BSD-style license that can be | 5 * Use of this source code is governed by a BSD-style license that can be |
6 * found in the LICENSE file. | 6 * found in the LICENSE file. |
7 */ | 7 */ |
8 | 8 |
9 #include "GrContext.h" | 9 #include "GrContext.h" |
10 | 10 |
(...skipping 386 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
397 | 397 |
398 class StrokeRectBatch : public GrBatch { | 398 class StrokeRectBatch : public GrBatch { |
399 public: | 399 public: |
400 struct Geometry { | 400 struct Geometry { |
401 GrColor fColor; | 401 GrColor fColor; |
402 SkMatrix fViewMatrix; | 402 SkMatrix fViewMatrix; |
403 SkRect fRect; | 403 SkRect fRect; |
404 SkScalar fStrokeWidth; | 404 SkScalar fStrokeWidth; |
405 }; | 405 }; |
406 | 406 |
407 static GrBatch* Create(const Geometry& geometry) { | 407 static GrBatch* Create(const Geometry& geometry, bool snapToPixelCenters) { |
408 return SkNEW_ARGS(StrokeRectBatch, (geometry)); | 408 return SkNEW_ARGS(StrokeRectBatch, (geometry, snapToPixelCenters)); |
409 } | 409 } |
410 | 410 |
411 const char* name() const override { return "StrokeRectBatch"; } | 411 const char* name() const override { return "StrokeRectBatch"; } |
412 | 412 |
413 void getInvariantOutputColor(GrInitInvariantOutput* out) const override { | 413 void getInvariantOutputColor(GrInitInvariantOutput* out) const override { |
414 // When this is called on a batch, there is only one geometry bundle | 414 // When this is called on a batch, there is only one geometry bundle |
415 out->setKnownFourComponents(fGeoData[0].fColor); | 415 out->setKnownFourComponents(fGeoData[0].fColor); |
416 } | 416 } |
417 | 417 |
418 void getInvariantOutputCoverage(GrInitInvariantOutput* out) const override { | 418 void getInvariantOutputCoverage(GrInitInvariantOutput* out) const override { |
(...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
494 } | 494 } |
495 | 495 |
496 GrVertices vertices; | 496 GrVertices vertices; |
497 vertices.init(primType, vertexBuffer, firstVertex, vertexCount); | 497 vertices.init(primType, vertexBuffer, firstVertex, vertexCount); |
498 batchTarget->draw(vertices); | 498 batchTarget->draw(vertices); |
499 } | 499 } |
500 | 500 |
501 SkSTArray<1, Geometry, true>* geoData() { return &fGeoData; } | 501 SkSTArray<1, Geometry, true>* geoData() { return &fGeoData; } |
502 | 502 |
503 private: | 503 private: |
504 StrokeRectBatch(const Geometry& geometry) { | 504 StrokeRectBatch(const Geometry& geometry, bool snapToPixelCenters) { |
505 this->initClassID<StrokeRectBatch>(); | 505 this->initClassID<StrokeRectBatch>(); |
506 | 506 |
507 fBatch.fHairline = geometry.fStrokeWidth == 0; | 507 fBatch.fHairline = geometry.fStrokeWidth == 0; |
508 | 508 |
509 fGeoData.push_back(geometry); | 509 fGeoData.push_back(geometry); |
510 | 510 |
511 // setup bounds | 511 // setup bounds |
512 fBounds = geometry.fRect; | 512 fBounds = geometry.fRect; |
513 SkScalar rad = SkScalarHalf(geometry.fStrokeWidth); | 513 SkScalar rad = SkScalarHalf(geometry.fStrokeWidth); |
514 fBounds.outset(rad, rad); | 514 fBounds.outset(rad, rad); |
515 geometry.fViewMatrix.mapRect(&fBounds); | 515 geometry.fViewMatrix.mapRect(&fBounds); |
| 516 |
| 517 // If our caller snaps to pixel centers then we have to round out the bo
unds |
| 518 if (snapToPixelCenters) { |
| 519 fBounds.roundOut(); |
| 520 } |
516 } | 521 } |
517 | 522 |
518 /* create a triangle strip that strokes the specified rect. There are 8 | 523 /* create a triangle strip that strokes the specified rect. There are 8 |
519 unique vertices, but we repeat the last 2 to close up. Alternatively we | 524 unique vertices, but we repeat the last 2 to close up. Alternatively we |
520 could use an indices array, and then only send 8 verts, but not sure that | 525 could use an indices array, and then only send 8 verts, but not sure that |
521 would be faster. | 526 would be faster. |
522 */ | 527 */ |
523 void setStrokeRectStrip(SkPoint verts[10], const SkRect& rect, SkScalar widt
h) { | 528 void setStrokeRectStrip(SkPoint verts[10], const SkRect& rect, SkScalar widt
h) { |
524 const SkScalar rad = SkScalarHalf(width); | 529 const SkScalar rad = SkScalarHalf(width); |
525 // TODO we should be able to enable this assert, but we'd have to filter
these draws | 530 // TODO we should be able to enable this assert, but we'd have to filter
these draws |
(...skipping 128 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
654 return; | 659 return; |
655 } | 660 } |
656 | 661 |
657 if (width >= 0) { | 662 if (width >= 0) { |
658 StrokeRectBatch::Geometry geometry; | 663 StrokeRectBatch::Geometry geometry; |
659 geometry.fViewMatrix = viewMatrix; | 664 geometry.fViewMatrix = viewMatrix; |
660 geometry.fColor = color; | 665 geometry.fColor = color; |
661 geometry.fRect = rect; | 666 geometry.fRect = rect; |
662 geometry.fStrokeWidth = width; | 667 geometry.fStrokeWidth = width; |
663 | 668 |
664 SkAutoTUnref<GrBatch> batch(StrokeRectBatch::Create(geometry)); | 669 // Non-AA hairlines are snapped to pixel centers to make which pixels ar
e hit deterministic |
| 670 bool snapToPixelCenters = (0 == width && !rt->isMultisampled()); |
| 671 SkAutoTUnref<GrBatch> batch(StrokeRectBatch::Create(geometry, snapToPixe
lCenters)); |
665 | 672 |
666 // Depending on sub-pixel coordinates and the particular GPU, we may los
e a corner of | 673 // Depending on sub-pixel coordinates and the particular GPU, we may los
e a corner of |
667 // hairline rects. We jam all the vertices to pixel centers to avoid thi
s, but not when MSAA | 674 // hairline rects. We jam all the vertices to pixel centers to avoid thi
s, but not when MSAA |
668 // is enabled because it can cause ugly artifacts. | 675 // is enabled because it can cause ugly artifacts. |
669 pipelineBuilder.setState(GrPipelineBuilder::kSnapVerticesToPixelCenters_
Flag, | 676 pipelineBuilder.setState(GrPipelineBuilder::kSnapVerticesToPixelCenters_
Flag, |
670 0 == width && !rt->isMultisampled()); | 677 snapToPixelCenters); |
671 target->drawBatch(&pipelineBuilder, batch); | 678 target->drawBatch(&pipelineBuilder, batch); |
672 } else { | 679 } else { |
673 // filled BW rect | 680 // filled BW rect |
674 target->drawSimpleRect(&pipelineBuilder, color, viewMatrix, rect); | 681 target->drawSimpleRect(&pipelineBuilder, color, viewMatrix, rect); |
675 } | 682 } |
676 } | 683 } |
677 | 684 |
678 void GrContext::drawNonAARectToRect(GrRenderTarget* rt, | 685 void GrContext::drawNonAARectToRect(GrRenderTarget* rt, |
679 const GrClip& clip, | 686 const GrClip& clip, |
680 const GrPaint& paint, | 687 const GrPaint& paint, |
(...skipping 320 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1001 | 1008 |
1002 // TODO clients should give us bounds | 1009 // TODO clients should give us bounds |
1003 SkRect bounds; | 1010 SkRect bounds; |
1004 if (!bounds.setBoundsCheck(positions, vertexCount)) { | 1011 if (!bounds.setBoundsCheck(positions, vertexCount)) { |
1005 SkDebugf("drawVertices call empty bounds\n"); | 1012 SkDebugf("drawVertices call empty bounds\n"); |
1006 return; | 1013 return; |
1007 } | 1014 } |
1008 | 1015 |
1009 viewMatrix.mapRect(&bounds); | 1016 viewMatrix.mapRect(&bounds); |
1010 | 1017 |
| 1018 // If we don't have AA then we outset for a half pixel in each direction to
account for |
| 1019 // snapping |
| 1020 if (!paint.isAntiAlias()) { |
| 1021 bounds.outset(0.5f, 0.5f); |
| 1022 } |
| 1023 |
1011 DrawVerticesBatch::Geometry geometry; | 1024 DrawVerticesBatch::Geometry geometry; |
1012 geometry.fColor = paint.getColor(); | 1025 geometry.fColor = paint.getColor(); |
1013 SkAutoTUnref<GrBatch> batch(DrawVerticesBatch::Create(geometry, primitiveTyp
e, viewMatrix, | 1026 SkAutoTUnref<GrBatch> batch(DrawVerticesBatch::Create(geometry, primitiveTyp
e, viewMatrix, |
1014 positions, vertexCount
, indices, | 1027 positions, vertexCount
, indices, |
1015 indexCount, colors, te
xCoords, | 1028 indexCount, colors, te
xCoords, |
1016 bounds)); | 1029 bounds)); |
1017 | 1030 |
1018 target->drawBatch(&pipelineBuilder, batch); | 1031 target->drawBatch(&pipelineBuilder, batch); |
1019 } | 1032 } |
1020 | 1033 |
(...skipping 851 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1872 | 1885 |
1873 #ifdef GR_TEST_UTILS | 1886 #ifdef GR_TEST_UTILS |
1874 | 1887 |
1875 BATCH_TEST_DEFINE(StrokeRect) { | 1888 BATCH_TEST_DEFINE(StrokeRect) { |
1876 StrokeRectBatch::Geometry geometry; | 1889 StrokeRectBatch::Geometry geometry; |
1877 geometry.fViewMatrix = GrTest::TestMatrix(random); | 1890 geometry.fViewMatrix = GrTest::TestMatrix(random); |
1878 geometry.fColor = GrRandomColor(random); | 1891 geometry.fColor = GrRandomColor(random); |
1879 geometry.fRect = GrTest::TestRect(random); | 1892 geometry.fRect = GrTest::TestRect(random); |
1880 geometry.fStrokeWidth = random->nextBool() ? 0.0f : 1.0f; | 1893 geometry.fStrokeWidth = random->nextBool() ? 0.0f : 1.0f; |
1881 | 1894 |
1882 return StrokeRectBatch::Create(geometry); | 1895 return StrokeRectBatch::Create(geometry, random->nextBool()); |
1883 } | 1896 } |
1884 | 1897 |
1885 static uint32_t seed_vertices(GrPrimitiveType type) { | 1898 static uint32_t seed_vertices(GrPrimitiveType type) { |
1886 switch (type) { | 1899 switch (type) { |
1887 case kTriangles_GrPrimitiveType: | 1900 case kTriangles_GrPrimitiveType: |
1888 case kTriangleStrip_GrPrimitiveType: | 1901 case kTriangleStrip_GrPrimitiveType: |
1889 case kTriangleFan_GrPrimitiveType: | 1902 case kTriangleFan_GrPrimitiveType: |
1890 return 3; | 1903 return 3; |
1891 case kPoints_GrPrimitiveType: | 1904 case kPoints_GrPrimitiveType: |
1892 return 1; | 1905 return 1; |
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1987 geometry.fColor = GrRandomColor(random); | 2000 geometry.fColor = GrRandomColor(random); |
1988 return DrawVerticesBatch::Create(geometry, type, viewMatrix, | 2001 return DrawVerticesBatch::Create(geometry, type, viewMatrix, |
1989 positions.begin(), vertexCount, | 2002 positions.begin(), vertexCount, |
1990 indices.begin(), hasIndices ? vertexCount :
0, | 2003 indices.begin(), hasIndices ? vertexCount :
0, |
1991 colors.begin(), | 2004 colors.begin(), |
1992 texCoords.begin(), | 2005 texCoords.begin(), |
1993 bounds); | 2006 bounds); |
1994 } | 2007 } |
1995 | 2008 |
1996 #endif | 2009 #endif |
OLD | NEW |