| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright 2011 Google Inc. | 2 * Copyright 2011 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 "GrAAHairLinePathRenderer.h" | 8 #include "GrAAHairLinePathRenderer.h" |
| 9 | 9 |
| 10 #include "GrContext.h" | 10 #include "GrContext.h" |
| (...skipping 153 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 164 | 164 |
| 165 #define PREALLOC_PTARRAY(N) SkSTArray<(N),SkPoint, true> | 165 #define PREALLOC_PTARRAY(N) SkSTArray<(N),SkPoint, true> |
| 166 | 166 |
| 167 // Takes 178th time of logf on Z600 / VC2010 | 167 // Takes 178th time of logf on Z600 / VC2010 |
| 168 int get_float_exp(float x) { | 168 int get_float_exp(float x) { |
| 169 GR_STATIC_ASSERT(sizeof(int) == sizeof(float)); | 169 GR_STATIC_ASSERT(sizeof(int) == sizeof(float)); |
| 170 #if GR_DEBUG | 170 #if GR_DEBUG |
| 171 static bool tested; | 171 static bool tested; |
| 172 if (!tested) { | 172 if (!tested) { |
| 173 tested = true; | 173 tested = true; |
| 174 GrAssert(get_float_exp(0.25f) == -2); | 174 SkASSERT(get_float_exp(0.25f) == -2); |
| 175 GrAssert(get_float_exp(0.3f) == -2); | 175 SkASSERT(get_float_exp(0.3f) == -2); |
| 176 GrAssert(get_float_exp(0.5f) == -1); | 176 SkASSERT(get_float_exp(0.5f) == -1); |
| 177 GrAssert(get_float_exp(1.f) == 0); | 177 SkASSERT(get_float_exp(1.f) == 0); |
| 178 GrAssert(get_float_exp(2.f) == 1); | 178 SkASSERT(get_float_exp(2.f) == 1); |
| 179 GrAssert(get_float_exp(2.5f) == 1); | 179 SkASSERT(get_float_exp(2.5f) == 1); |
| 180 GrAssert(get_float_exp(8.f) == 3); | 180 SkASSERT(get_float_exp(8.f) == 3); |
| 181 GrAssert(get_float_exp(100.f) == 6); | 181 SkASSERT(get_float_exp(100.f) == 6); |
| 182 GrAssert(get_float_exp(1000.f) == 9); | 182 SkASSERT(get_float_exp(1000.f) == 9); |
| 183 GrAssert(get_float_exp(1024.f) == 10); | 183 SkASSERT(get_float_exp(1024.f) == 10); |
| 184 GrAssert(get_float_exp(3000000.f) == 21); | 184 SkASSERT(get_float_exp(3000000.f) == 21); |
| 185 } | 185 } |
| 186 #endif | 186 #endif |
| 187 const int* iptr = (const int*)&x; | 187 const int* iptr = (const int*)&x; |
| 188 return (((*iptr) & 0x7f800000) >> 23) - 127; | 188 return (((*iptr) & 0x7f800000) >> 23) - 127; |
| 189 } | 189 } |
| 190 | 190 |
| 191 // Uses the max curvature function for quads to estimate | 191 // Uses the max curvature function for quads to estimate |
| 192 // where to chop the conic. If the max curvature is not | 192 // where to chop the conic. If the max curvature is not |
| 193 // found along the curve segment it will return 1 and | 193 // found along the curve segment it will return 1 and |
| 194 // dst[0] is the original conic. If it returns 2 the dst[0] | 194 // dst[0] is the original conic. If it returns 2 the dst[0] |
| (...skipping 190 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 385 int n = SkChopQuadAtMaxCurvature(pathPts, choppedPts); | 385 int n = SkChopQuadAtMaxCurvature(pathPts, choppedPts); |
| 386 for (int i = 0; i < n; ++i) { | 386 for (int i = 0; i < n; ++i) { |
| 387 SkPoint* quadPts = choppedPts + i * 2; | 387 SkPoint* quadPts = choppedPts + i * 2; |
| 388 m.mapPoints(devPts, quadPts, 3); | 388 m.mapPoints(devPts, quadPts, 3); |
| 389 bounds.setBounds(devPts, 3); | 389 bounds.setBounds(devPts, 3); |
| 390 bounds.outset(SK_Scalar1, SK_Scalar1); | 390 bounds.outset(SK_Scalar1, SK_Scalar1); |
| 391 bounds.roundOut(&ibounds); | 391 bounds.roundOut(&ibounds); |
| 392 | 392 |
| 393 if (SkIRect::Intersects(devClipBounds, ibounds)) { | 393 if (SkIRect::Intersects(devClipBounds, ibounds)) { |
| 394 int subdiv = num_quad_subdivs(devPts); | 394 int subdiv = num_quad_subdivs(devPts); |
| 395 GrAssert(subdiv >= -1); | 395 SkASSERT(subdiv >= -1); |
| 396 if (-1 == subdiv) { | 396 if (-1 == subdiv) { |
| 397 SkPoint* pts = lines->push_back_n(4); | 397 SkPoint* pts = lines->push_back_n(4); |
| 398 pts[0] = devPts[0]; | 398 pts[0] = devPts[0]; |
| 399 pts[1] = devPts[1]; | 399 pts[1] = devPts[1]; |
| 400 pts[2] = devPts[1]; | 400 pts[2] = devPts[1]; |
| 401 pts[3] = devPts[2]; | 401 pts[3] = devPts[2]; |
| 402 } else { | 402 } else { |
| 403 // when in perspective keep quads in src space | 403 // when in perspective keep quads in src space |
| 404 SkPoint* qPts = persp ? quadPts : devPts; | 404 SkPoint* qPts = persp ? quadPts : devPts; |
| 405 SkPoint* pts = quads->push_back_n(3); | 405 SkPoint* pts = quads->push_back_n(3); |
| (...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 441 bounds.setBounds(devPts, 3); | 441 bounds.setBounds(devPts, 3); |
| 442 qInDevSpace = devPts; | 442 qInDevSpace = devPts; |
| 443 } else { | 443 } else { |
| 444 bounds.setBounds(&q[i], 3); | 444 bounds.setBounds(&q[i], 3); |
| 445 qInDevSpace = &q[i]; | 445 qInDevSpace = &q[i]; |
| 446 } | 446 } |
| 447 bounds.outset(SK_Scalar1, SK_Scalar1); | 447 bounds.outset(SK_Scalar1, SK_Scalar1); |
| 448 bounds.roundOut(&ibounds); | 448 bounds.roundOut(&ibounds); |
| 449 if (SkIRect::Intersects(devClipBounds, ibounds)) { | 449 if (SkIRect::Intersects(devClipBounds, ibounds)) { |
| 450 int subdiv = num_quad_subdivs(qInDevSpace); | 450 int subdiv = num_quad_subdivs(qInDevSpace); |
| 451 GrAssert(subdiv >= -1); | 451 SkASSERT(subdiv >= -1); |
| 452 if (-1 == subdiv) { | 452 if (-1 == subdiv) { |
| 453 SkPoint* pts = lines->push_back_n(4); | 453 SkPoint* pts = lines->push_back_n(4); |
| 454 // lines should always be in device coords | 454 // lines should always be in device coords |
| 455 pts[0] = qInDevSpace[0]; | 455 pts[0] = qInDevSpace[0]; |
| 456 pts[1] = qInDevSpace[1]; | 456 pts[1] = qInDevSpace[1]; |
| 457 pts[2] = qInDevSpace[1]; | 457 pts[2] = qInDevSpace[1]; |
| 458 pts[3] = qInDevSpace[2]; | 458 pts[3] = qInDevSpace[2]; |
| 459 } else { | 459 } else { |
| 460 SkPoint* pts = quads->push_back_n(3); | 460 SkPoint* pts = quads->push_back_n(3); |
| 461 // q is already in src space when there is no | 461 // q is already in src space when there is no |
| (...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 520 | 520 |
| 521 void set_uv_quad(const SkPoint qpts[3], BezierVertex verts[kVertsPerQuad]) { | 521 void set_uv_quad(const SkPoint qpts[3], BezierVertex verts[kVertsPerQuad]) { |
| 522 // this should be in the src space, not dev coords, when we have perspective | 522 // this should be in the src space, not dev coords, when we have perspective |
| 523 GrPathUtils::QuadUVMatrix DevToUV(qpts); | 523 GrPathUtils::QuadUVMatrix DevToUV(qpts); |
| 524 DevToUV.apply<kVertsPerQuad, sizeof(BezierVertex), sizeof(GrPoint)>(verts); | 524 DevToUV.apply<kVertsPerQuad, sizeof(BezierVertex), sizeof(GrPoint)>(verts); |
| 525 } | 525 } |
| 526 | 526 |
| 527 void bloat_quad(const SkPoint qpts[3], const SkMatrix* toDevice, | 527 void bloat_quad(const SkPoint qpts[3], const SkMatrix* toDevice, |
| 528 const SkMatrix* toSrc, BezierVertex verts[kVertsPerQuad], | 528 const SkMatrix* toSrc, BezierVertex verts[kVertsPerQuad], |
| 529 SkRect* devBounds) { | 529 SkRect* devBounds) { |
| 530 GrAssert(!toDevice == !toSrc); | 530 SkASSERT(!toDevice == !toSrc); |
| 531 // original quad is specified by tri a,b,c | 531 // original quad is specified by tri a,b,c |
| 532 SkPoint a = qpts[0]; | 532 SkPoint a = qpts[0]; |
| 533 SkPoint b = qpts[1]; | 533 SkPoint b = qpts[1]; |
| 534 SkPoint c = qpts[2]; | 534 SkPoint c = qpts[2]; |
| 535 | 535 |
| 536 if (toDevice) { | 536 if (toDevice) { |
| 537 toDevice->mapPoints(&a, 1); | 537 toDevice->mapPoints(&a, 1); |
| 538 toDevice->mapPoints(&b, 1); | 538 toDevice->mapPoints(&b, 1); |
| 539 toDevice->mapPoints(&c, 1); | 539 toDevice->mapPoints(&c, 1); |
| 540 } | 540 } |
| (...skipping 16 matching lines...) Expand all Loading... |
| 557 BezierVertex& c1 = verts[4]; | 557 BezierVertex& c1 = verts[4]; |
| 558 | 558 |
| 559 SkVector ab = b; | 559 SkVector ab = b; |
| 560 ab -= a; | 560 ab -= a; |
| 561 SkVector ac = c; | 561 SkVector ac = c; |
| 562 ac -= a; | 562 ac -= a; |
| 563 SkVector cb = b; | 563 SkVector cb = b; |
| 564 cb -= c; | 564 cb -= c; |
| 565 | 565 |
| 566 // We should have already handled degenerates | 566 // We should have already handled degenerates |
| 567 GrAssert(ab.length() > 0 && cb.length() > 0); | 567 SkASSERT(ab.length() > 0 && cb.length() > 0); |
| 568 | 568 |
| 569 ab.normalize(); | 569 ab.normalize(); |
| 570 SkVector abN; | 570 SkVector abN; |
| 571 abN.setOrthog(ab, SkVector::kLeft_Side); | 571 abN.setOrthog(ab, SkVector::kLeft_Side); |
| 572 if (abN.dot(ac) > 0) { | 572 if (abN.dot(ac) > 0) { |
| 573 abN.negate(); | 573 abN.negate(); |
| 574 } | 574 } |
| 575 | 575 |
| 576 cb.normalize(); | 576 cb.normalize(); |
| 577 SkVector cbN; | 577 SkVector cbN; |
| (...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 622 k[1] = p[0].fX - p[2].fX; | 622 k[1] = p[0].fX - p[2].fX; |
| 623 k[2] = (p[2].fX - p[0].fX) * p[0].fY - (p[2].fY - p[0].fY) * p[0].fX; | 623 k[2] = (p[2].fX - p[0].fX) * p[0].fY - (p[2].fY - p[0].fY) * p[0].fX; |
| 624 | 624 |
| 625 // scale the max absolute value of coeffs to 10 | 625 // scale the max absolute value of coeffs to 10 |
| 626 SkScalar scale = 0.0f; | 626 SkScalar scale = 0.0f; |
| 627 for (int i = 0; i < 3; ++i) { | 627 for (int i = 0; i < 3; ++i) { |
| 628 scale = SkMaxScalar(scale, SkScalarAbs(k[i])); | 628 scale = SkMaxScalar(scale, SkScalarAbs(k[i])); |
| 629 scale = SkMaxScalar(scale, SkScalarAbs(l[i])); | 629 scale = SkMaxScalar(scale, SkScalarAbs(l[i])); |
| 630 scale = SkMaxScalar(scale, SkScalarAbs(m[i])); | 630 scale = SkMaxScalar(scale, SkScalarAbs(m[i])); |
| 631 } | 631 } |
| 632 GrAssert(scale > 0); | 632 SkASSERT(scale > 0); |
| 633 scale /= 10.0f; | 633 scale /= 10.0f; |
| 634 k[0] /= scale; | 634 k[0] /= scale; |
| 635 k[1] /= scale; | 635 k[1] /= scale; |
| 636 k[2] /= scale; | 636 k[2] /= scale; |
| 637 l[0] /= scale; | 637 l[0] /= scale; |
| 638 l[1] /= scale; | 638 l[1] /= scale; |
| 639 l[2] /= scale; | 639 l[2] /= scale; |
| 640 m[0] /= scale; | 640 m[0] /= scale; |
| 641 m[1] /= scale; | 641 m[1] /= scale; |
| 642 m[2] /= scale; | 642 m[2] /= scale; |
| (...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 674 set_conic_coeffs(p, *vert, weight); | 674 set_conic_coeffs(p, *vert, weight); |
| 675 *vert += kVertsPerQuad; | 675 *vert += kVertsPerQuad; |
| 676 } | 676 } |
| 677 | 677 |
| 678 void add_quads(const SkPoint p[3], | 678 void add_quads(const SkPoint p[3], |
| 679 int subdiv, | 679 int subdiv, |
| 680 const SkMatrix* toDevice, | 680 const SkMatrix* toDevice, |
| 681 const SkMatrix* toSrc, | 681 const SkMatrix* toSrc, |
| 682 BezierVertex** vert, | 682 BezierVertex** vert, |
| 683 SkRect* devBounds) { | 683 SkRect* devBounds) { |
| 684 GrAssert(subdiv >= 0); | 684 SkASSERT(subdiv >= 0); |
| 685 if (subdiv) { | 685 if (subdiv) { |
| 686 SkPoint newP[5]; | 686 SkPoint newP[5]; |
| 687 SkChopQuadAtHalf(p, newP); | 687 SkChopQuadAtHalf(p, newP); |
| 688 add_quads(newP + 0, subdiv-1, toDevice, toSrc, vert, devBounds); | 688 add_quads(newP + 0, subdiv-1, toDevice, toSrc, vert, devBounds); |
| 689 add_quads(newP + 2, subdiv-1, toDevice, toSrc, vert, devBounds); | 689 add_quads(newP + 2, subdiv-1, toDevice, toSrc, vert, devBounds); |
| 690 } else { | 690 } else { |
| 691 bloat_quad(p, toDevice, toSrc, *vert, devBounds); | 691 bloat_quad(p, toDevice, toSrc, *vert, devBounds); |
| 692 set_uv_quad(p, *vert); | 692 set_uv_quad(p, *vert); |
| 693 *vert += kVertsPerQuad; | 693 *vert += kVertsPerQuad; |
| 694 } | 694 } |
| (...skipping 313 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1008 | 1008 |
| 1009 const SkMatrix& viewM = drawState->getViewMatrix(); | 1009 const SkMatrix& viewM = drawState->getViewMatrix(); |
| 1010 | 1010 |
| 1011 *devBounds = path.getBounds(); | 1011 *devBounds = path.getBounds(); |
| 1012 viewM.mapRect(devBounds); | 1012 viewM.mapRect(devBounds); |
| 1013 devBounds->outset(SK_Scalar1, SK_Scalar1); | 1013 devBounds->outset(SK_Scalar1, SK_Scalar1); |
| 1014 | 1014 |
| 1015 int vertCnt = kVertsPerLineSeg * lineCnt; | 1015 int vertCnt = kVertsPerLineSeg * lineCnt; |
| 1016 | 1016 |
| 1017 target->drawState()->setVertexAttribs<gHairlineLineAttribs>(SK_ARRAY_COUNT(g
HairlineLineAttribs)); | 1017 target->drawState()->setVertexAttribs<gHairlineLineAttribs>(SK_ARRAY_COUNT(g
HairlineLineAttribs)); |
| 1018 GrAssert(sizeof(LineVertex) == target->getDrawState().getVertexSize()); | 1018 SkASSERT(sizeof(LineVertex) == target->getDrawState().getVertexSize()); |
| 1019 | 1019 |
| 1020 if (!arg->set(target, vertCnt, 0)) { | 1020 if (!arg->set(target, vertCnt, 0)) { |
| 1021 return false; | 1021 return false; |
| 1022 } | 1022 } |
| 1023 | 1023 |
| 1024 LineVertex* verts = reinterpret_cast<LineVertex*>(arg->vertices()); | 1024 LineVertex* verts = reinterpret_cast<LineVertex*>(arg->vertices()); |
| 1025 | 1025 |
| 1026 const SkMatrix* toSrc = NULL; | 1026 const SkMatrix* toSrc = NULL; |
| 1027 SkMatrix ivm; | 1027 SkMatrix ivm; |
| 1028 | 1028 |
| (...skipping 28 matching lines...) Expand all Loading... |
| 1057 // All the vertices that we compute are within 1 of path control points with
the exception of | 1057 // All the vertices that we compute are within 1 of path control points with
the exception of |
| 1058 // one of the bounding vertices for each quad. The add_quads() function will
update the bounds | 1058 // one of the bounding vertices for each quad. The add_quads() function will
update the bounds |
| 1059 // for each quad added. | 1059 // for each quad added. |
| 1060 *devBounds = path.getBounds(); | 1060 *devBounds = path.getBounds(); |
| 1061 viewM.mapRect(devBounds); | 1061 viewM.mapRect(devBounds); |
| 1062 devBounds->outset(SK_Scalar1, SK_Scalar1); | 1062 devBounds->outset(SK_Scalar1, SK_Scalar1); |
| 1063 | 1063 |
| 1064 int vertCnt = kVertsPerQuad * quadCnt + kVertsPerQuad * conicCnt; | 1064 int vertCnt = kVertsPerQuad * quadCnt + kVertsPerQuad * conicCnt; |
| 1065 | 1065 |
| 1066 target->drawState()->setVertexAttribs<gHairlineBezierAttribs>(SK_ARRAY_COUNT
(gHairlineBezierAttribs)); | 1066 target->drawState()->setVertexAttribs<gHairlineBezierAttribs>(SK_ARRAY_COUNT
(gHairlineBezierAttribs)); |
| 1067 GrAssert(sizeof(BezierVertex) == target->getDrawState().getVertexSize()); | 1067 SkASSERT(sizeof(BezierVertex) == target->getDrawState().getVertexSize()); |
| 1068 | 1068 |
| 1069 if (!arg->set(target, vertCnt, 0)) { | 1069 if (!arg->set(target, vertCnt, 0)) { |
| 1070 return false; | 1070 return false; |
| 1071 } | 1071 } |
| 1072 | 1072 |
| 1073 BezierVertex* verts = reinterpret_cast<BezierVertex*>(arg->vertices()); | 1073 BezierVertex* verts = reinterpret_cast<BezierVertex*>(arg->vertices()); |
| 1074 | 1074 |
| 1075 const SkMatrix* toDevice = NULL; | 1075 const SkMatrix* toDevice = NULL; |
| 1076 const SkMatrix* toSrc = NULL; | 1076 const SkMatrix* toSrc = NULL; |
| 1077 SkMatrix ivm; | 1077 SkMatrix ivm; |
| 1078 | 1078 |
| 1079 if (viewM.hasPerspective()) { | 1079 if (viewM.hasPerspective()) { |
| 1080 if (viewM.invert(&ivm)) { | 1080 if (viewM.invert(&ivm)) { |
| 1081 toDevice = &viewM; | 1081 toDevice = &viewM; |
| 1082 toSrc = &ivm; | 1082 toSrc = &ivm; |
| 1083 } | 1083 } |
| 1084 } | 1084 } |
| 1085 | 1085 |
| 1086 int unsubdivQuadCnt = quads.count() / 3; | 1086 int unsubdivQuadCnt = quads.count() / 3; |
| 1087 for (int i = 0; i < unsubdivQuadCnt; ++i) { | 1087 for (int i = 0; i < unsubdivQuadCnt; ++i) { |
| 1088 GrAssert(qSubdivs[i] >= 0); | 1088 SkASSERT(qSubdivs[i] >= 0); |
| 1089 add_quads(&quads[3*i], qSubdivs[i], toDevice, toSrc, &verts, devBounds); | 1089 add_quads(&quads[3*i], qSubdivs[i], toDevice, toSrc, &verts, devBounds); |
| 1090 } | 1090 } |
| 1091 | 1091 |
| 1092 // Start Conics | 1092 // Start Conics |
| 1093 for (int i = 0; i < conicCnt; ++i) { | 1093 for (int i = 0; i < conicCnt; ++i) { |
| 1094 add_conics(&conics[3*i], cWeights[i], toDevice, toSrc, &verts, devBounds
); | 1094 add_conics(&conics[3*i], cWeights[i], toDevice, toSrc, &verts, devBounds
); |
| 1095 } | 1095 } |
| 1096 return true; | 1096 return true; |
| 1097 } | 1097 } |
| 1098 | 1098 |
| (...skipping 180 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1279 &devBounds); | 1279 &devBounds); |
| 1280 conics += n; | 1280 conics += n; |
| 1281 } | 1281 } |
| 1282 } | 1282 } |
| 1283 } | 1283 } |
| 1284 | 1284 |
| 1285 target->resetIndexSource(); | 1285 target->resetIndexSource(); |
| 1286 | 1286 |
| 1287 return true; | 1287 return true; |
| 1288 } | 1288 } |
| OLD | NEW |