Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 /* | 1 /* |
| 2 * Copyright 2006 The Android Open Source Project | 2 * Copyright 2006 The Android Open Source Project |
| 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 "SkScanPriv.h" | 8 #include "SkScanPriv.h" |
| 9 #include "SkBlitter.h" | 9 #include "SkBlitter.h" |
| 10 #include "SkEdge.h" | 10 #include "SkEdge.h" |
| (...skipping 541 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 552 | 552 |
| 553 SkIRect limitR; | 553 SkIRect limitR; |
| 554 limitR.set(-limit, -limit, limit, limit); | 554 limitR.set(-limit, -limit, limit, limit); |
| 555 if (limitR.contains(orig.getBounds())) { | 555 if (limitR.contains(orig.getBounds())) { |
| 556 return false; | 556 return false; |
| 557 } | 557 } |
| 558 reduced->op(orig, limitR, SkRegion::kIntersect_Op); | 558 reduced->op(orig, limitR, SkRegion::kIntersect_Op); |
| 559 return true; | 559 return true; |
| 560 } | 560 } |
| 561 | 561 |
| 562 /** | |
| 563 * Variant of SkScalarRoundToInt, identical to SkDScalarRoundToInt except when the input fraction | |
| 564 * is 0.5. In this case only, round the value down. This is used to round the t op and left | |
| 565 * of a rectangle, and corresponds to the way the scan converter treats the top and left edges. | |
| 566 */ | |
| 567 static inline int round_down_to_int(SkScalar x) { | |
| 568 double xx = x; | |
| 569 xx += 0.5; | |
| 570 double floorXX = floor(xx); | |
| 571 return (int)floorXX - (xx == floorXX); | |
| 572 } | |
| 573 | |
| 574 /** | |
| 575 * Variant of SkRect::round() that explicitly performs the rounding step (i.e. floor(x + 0.5)) | |
| 576 * using double instead of SkScalar (float). It does this by calling SkDScalar RoundToInt(), | |
| 577 * which may be slower than calling SkScalarRountToInt(), but gives slightly m ore accurate | |
| 578 * results. | |
| 579 * | |
| 580 * e.g. | |
| 581 * SkScalar x = 0.49999997f; | |
|
reed1
2016/01/04 19:43:39
I think the comment block needs to be expanded, no
caryclark
2016/01/04 20:58:42
Done.
| |
| 582 * int ix = SkScalarRoundToInt(x); | |
| 583 * SkASSERT(0 == ix); // <--- fails | |
| 584 * ix = SkDScalarRoundToInt(x); | |
| 585 * SkASSERT(0 == ix); // <--- succeeds | |
| 586 */ | |
| 587 static void round_out(const SkRect& src, SkIRect* dst) { | |
|
reed1
2016/01/04 19:43:39
SkRect uses "out" to mean we floor/ceiling the val
caryclark
2016/01/04 20:58:42
Done.
| |
| 588 SkASSERT(dst); | |
| 589 dst->set(round_down_to_int(src.fLeft), round_down_to_int(src.fTop), | |
| 590 SkDScalarRoundToInt(src.fRight), SkDScalarRoundToInt(src.fBottom)); | |
| 591 } | |
| 592 | |
| 562 void SkScan::FillPath(const SkPath& path, const SkRegion& origClip, | 593 void SkScan::FillPath(const SkPath& path, const SkRegion& origClip, |
| 563 SkBlitter* blitter) { | 594 SkBlitter* blitter) { |
| 564 if (origClip.isEmpty()) { | 595 if (origClip.isEmpty()) { |
| 565 return; | 596 return; |
| 566 } | 597 } |
| 567 | 598 |
| 568 // Our edges are fixed-point, and don't like the bounds of the clip to | 599 // Our edges are fixed-point, and don't like the bounds of the clip to |
| 569 // exceed that. Here we trim the clip just so we don't overflow later on | 600 // exceed that. Here we trim the clip just so we don't overflow later on |
| 570 const SkRegion* clipPtr = &origClip; | 601 const SkRegion* clipPtr = &origClip; |
| 571 SkRegion finiteClip; | 602 SkRegion finiteClip; |
| 572 if (clip_to_limit(origClip, &finiteClip)) { | 603 if (clip_to_limit(origClip, &finiteClip)) { |
| 573 if (finiteClip.isEmpty()) { | 604 if (finiteClip.isEmpty()) { |
| 574 return; | 605 return; |
| 575 } | 606 } |
| 576 clipPtr = &finiteClip; | 607 clipPtr = &finiteClip; |
| 577 } | 608 } |
| 578 // don't reference "origClip" any more, just use clipPtr | 609 // don't reference "origClip" any more, just use clipPtr |
| 579 | 610 |
| 580 SkIRect ir; | 611 SkIRect ir; |
| 581 // We deliberately call dround() instead of round(), since we can't afford t o generate a | 612 // We deliberately call dround() instead of round(), since we can't afford t o generate a |
| 582 // bounds that is tighter than the corresponding SkEdges. The edge code basi cally converts | 613 // bounds that is tighter than the corresponding SkEdges. The edge code basi cally converts |
| 583 // the floats to fixed, and then "rounds". If we called round() instead of d round() here, | 614 // the floats to fixed, and then "rounds". If we called round() instead of d round() here, |
| 584 // we could generate the wrong ir for values like 0.4999997. | 615 // we could generate the wrong ir for values like 0.4999997. |
| 585 path.getBounds().dround(&ir); | 616 round_out(path.getBounds(), &ir); |
| 586 if (ir.isEmpty()) { | 617 if (ir.isEmpty()) { |
| 587 if (path.isInverseFillType()) { | 618 if (path.isInverseFillType()) { |
| 588 blitter->blitRegion(*clipPtr); | 619 blitter->blitRegion(*clipPtr); |
| 589 } | 620 } |
| 590 return; | 621 return; |
| 591 } | 622 } |
| 592 | 623 |
| 593 SkScanClipper clipper(blitter, clipPtr, ir, path.isInverseFillType()); | 624 SkScanClipper clipper(blitter, clipPtr, ir, path.isInverseFillType()); |
| 594 | 625 |
| 595 blitter = clipper.getBlitter(); | 626 blitter = clipper.getBlitter(); |
| (...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 700 clipRgn = &wrap.getRgn(); | 731 clipRgn = &wrap.getRgn(); |
| 701 blitter = wrap.getBlitter(); | 732 blitter = wrap.getBlitter(); |
| 702 } | 733 } |
| 703 | 734 |
| 704 SkScanClipper clipper(blitter, clipRgn, ir); | 735 SkScanClipper clipper(blitter, clipRgn, ir); |
| 705 blitter = clipper.getBlitter(); | 736 blitter = clipper.getBlitter(); |
| 706 if (blitter) { | 737 if (blitter) { |
| 707 sk_fill_triangle(pts, clipper.getClipRect(), blitter, ir); | 738 sk_fill_triangle(pts, clipper.getClipRect(), blitter, ir); |
| 708 } | 739 } |
| 709 } | 740 } |
| OLD | NEW |