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 "SkDraw.h" | 8 #include "SkDraw.h" |
9 #include "SkBlitter.h" | 9 #include "SkBlitter.h" |
10 #include "SkCanvas.h" | 10 #include "SkCanvas.h" |
(...skipping 1425 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1436 } | 1436 } |
1437 | 1437 |
1438 // disable warning : local variable used without having been initialized | 1438 // disable warning : local variable used without having been initialized |
1439 #if defined _WIN32 && _MSC_VER >= 1300 | 1439 #if defined _WIN32 && _MSC_VER >= 1300 |
1440 #pragma warning ( push ) | 1440 #pragma warning ( push ) |
1441 #pragma warning ( disable : 4701 ) | 1441 #pragma warning ( disable : 4701 ) |
1442 #endif | 1442 #endif |
1443 | 1443 |
1444 ////////////////////////////////////////////////////////////////////////////// | 1444 ////////////////////////////////////////////////////////////////////////////// |
1445 | 1445 |
1446 static void D1G_RectClip(const SkDraw1Glyph& state, SkFixed fx, SkFixed fy, cons
t SkGlyph& glyph) { | 1446 static void D1G_RectClip(const SkDraw1Glyph& state, Sk48Dot16 fx, Sk48Dot16 fy,
const SkGlyph& glyph) { |
1447 int left = SkFixedFloorToInt(fx); | 1447 int left = Sk48Dot16FloorToInt(fx); |
1448 int top = SkFixedFloorToInt(fy); | 1448 int top = Sk48Dot16FloorToInt(fy); |
1449 SkASSERT(glyph.fWidth > 0 && glyph.fHeight > 0); | 1449 SkASSERT(glyph.fWidth > 0 && glyph.fHeight > 0); |
1450 SkASSERT((NULL == state.fClip && state.fAAClip) || | 1450 SkASSERT((NULL == state.fClip && state.fAAClip) || |
1451 (state.fClip && NULL == state.fAAClip && state.fClip->isRect())); | 1451 (state.fClip && NULL == state.fAAClip && state.fClip->isRect())); |
1452 | 1452 |
1453 left += glyph.fLeft; | 1453 left += glyph.fLeft; |
1454 top += glyph.fTop; | 1454 top += glyph.fTop; |
1455 | 1455 |
1456 int right = left + glyph.fWidth; | 1456 int right = left + glyph.fWidth; |
1457 int bottom = top + glyph.fHeight; | 1457 int bottom = top + glyph.fHeight; |
1458 | 1458 |
(...skipping 18 matching lines...) Expand all Loading... |
1477 return; // can't rasterize glyph | 1477 return; // can't rasterize glyph |
1478 } | 1478 } |
1479 } | 1479 } |
1480 | 1480 |
1481 mask.fRowBytes = glyph.rowBytes(); | 1481 mask.fRowBytes = glyph.rowBytes(); |
1482 mask.fFormat = static_cast<SkMask::Format>(glyph.fMaskFormat); | 1482 mask.fFormat = static_cast<SkMask::Format>(glyph.fMaskFormat); |
1483 mask.fImage = aa; | 1483 mask.fImage = aa; |
1484 state.blitMask(mask, *bounds); | 1484 state.blitMask(mask, *bounds); |
1485 } | 1485 } |
1486 | 1486 |
1487 static void D1G_RgnClip(const SkDraw1Glyph& state, SkFixed fx, SkFixed fy, const
SkGlyph& glyph) { | 1487 static void D1G_RgnClip(const SkDraw1Glyph& state, Sk48Dot16 fx, Sk48Dot16 fy, c
onst SkGlyph& glyph) { |
1488 int left = SkFixedFloorToInt(fx); | 1488 int left = Sk48Dot16FloorToInt(fx); |
1489 int top = SkFixedFloorToInt(fy); | 1489 int top = Sk48Dot16FloorToInt(fy); |
1490 SkASSERT(glyph.fWidth > 0 && glyph.fHeight > 0); | 1490 SkASSERT(glyph.fWidth > 0 && glyph.fHeight > 0); |
1491 SkASSERT(!state.fClip->isRect()); | 1491 SkASSERT(!state.fClip->isRect()); |
1492 | 1492 |
1493 SkMask mask; | 1493 SkMask mask; |
1494 | 1494 |
1495 left += glyph.fLeft; | 1495 left += glyph.fLeft; |
1496 top += glyph.fTop; | 1496 top += glyph.fTop; |
1497 | 1497 |
1498 mask.fBounds.set(left, top, left + glyph.fWidth, top + glyph.fHeight); | 1498 mask.fBounds.set(left, top, left + glyph.fWidth, top + glyph.fHeight); |
1499 SkRegion::Cliperator clipper(*state.fClip, mask.fBounds); | 1499 SkRegion::Cliperator clipper(*state.fClip, mask.fBounds); |
(...skipping 27 matching lines...) Expand all Loading... |
1527 } | 1527 } |
1528 | 1528 |
1529 SkDraw1Glyph::Proc SkDraw1Glyph::init(const SkDraw* draw, SkBlitter* blitter, Sk
GlyphCache* cache, | 1529 SkDraw1Glyph::Proc SkDraw1Glyph::init(const SkDraw* draw, SkBlitter* blitter, Sk
GlyphCache* cache, |
1530 const SkPaint& pnt) { | 1530 const SkPaint& pnt) { |
1531 fDraw = draw; | 1531 fDraw = draw; |
1532 fBlitter = blitter; | 1532 fBlitter = blitter; |
1533 fCache = cache; | 1533 fCache = cache; |
1534 fPaint = &pnt; | 1534 fPaint = &pnt; |
1535 | 1535 |
1536 if (cache->isSubpixel()) { | 1536 if (cache->isSubpixel()) { |
1537 fHalfSampleX = fHalfSampleY = SkGlyph::kSubpixelRound; | 1537 fHalfSampleX = fHalfSampleY = SkFixedToScalar(SkGlyph::kSubpixelRound); |
1538 } else { | 1538 } else { |
1539 fHalfSampleX = fHalfSampleY = SK_FixedHalf; | 1539 fHalfSampleX = fHalfSampleY = SK_ScalarHalf; |
1540 } | 1540 } |
1541 | 1541 |
1542 if (hasCustomD1GProc(*draw)) { | 1542 if (hasCustomD1GProc(*draw)) { |
1543 // todo: fix this assumption about clips w/ custom | 1543 // todo: fix this assumption about clips w/ custom |
1544 fClip = draw->fClip; | 1544 fClip = draw->fClip; |
1545 fClipBounds = fClip->getBounds(); | 1545 fClipBounds = fClip->getBounds(); |
1546 return draw->fProcs->fD1GProc; | 1546 return draw->fProcs->fD1GProc; |
1547 } | 1547 } |
1548 | 1548 |
1549 if (draw->fRC->isBW()) { | 1549 if (draw->fRC->isBW()) { |
(...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1640 SkAutoKern autokern; | 1640 SkAutoKern autokern; |
1641 SkDraw1Glyph d1g; | 1641 SkDraw1Glyph d1g; |
1642 SkDraw1Glyph::Proc proc = d1g.init(this, blitter, cache, paint); | 1642 SkDraw1Glyph::Proc proc = d1g.init(this, blitter, cache, paint); |
1643 | 1643 |
1644 SkFixed fxMask = ~0; | 1644 SkFixed fxMask = ~0; |
1645 SkFixed fyMask = ~0; | 1645 SkFixed fyMask = ~0; |
1646 if (cache->isSubpixel()) { | 1646 if (cache->isSubpixel()) { |
1647 SkAxisAlignment baseline = SkComputeAxisAlignmentForHText(*fMatrix); | 1647 SkAxisAlignment baseline = SkComputeAxisAlignmentForHText(*fMatrix); |
1648 if (kX_SkAxisAlignment == baseline) { | 1648 if (kX_SkAxisAlignment == baseline) { |
1649 fyMask = 0; | 1649 fyMask = 0; |
1650 d1g.fHalfSampleY = SK_FixedHalf; | 1650 d1g.fHalfSampleY = SK_ScalarHalf; |
1651 } else if (kY_SkAxisAlignment == baseline) { | 1651 } else if (kY_SkAxisAlignment == baseline) { |
1652 fxMask = 0; | 1652 fxMask = 0; |
1653 d1g.fHalfSampleX = SK_FixedHalf; | 1653 d1g.fHalfSampleX = SK_ScalarHalf; |
1654 } | 1654 } |
1655 } | 1655 } |
1656 | 1656 |
1657 SkFixed fx = SkScalarToFixed(x) + d1g.fHalfSampleX; | 1657 Sk48Dot16 fx = SkScalarTo48Dot16(x + d1g.fHalfSampleX); |
1658 SkFixed fy = SkScalarToFixed(y) + d1g.fHalfSampleY; | 1658 Sk48Dot16 fy = SkScalarTo48Dot16(y + d1g.fHalfSampleY); |
1659 | 1659 |
1660 while (text < stop) { | 1660 while (text < stop) { |
1661 const SkGlyph& glyph = glyphCacheProc(cache, &text, fx & fxMask, fy & fy
Mask); | 1661 const SkGlyph& glyph = glyphCacheProc(cache, &text, fx & fxMask, fy & fy
Mask); |
1662 | 1662 |
1663 fx += autokern.adjust(glyph); | 1663 fx += autokern.adjust(glyph); |
1664 | 1664 |
1665 if (glyph.fWidth) { | 1665 if (glyph.fWidth) { |
1666 proc(d1g, fx, fy, glyph); | 1666 proc(d1g, fx, fy, glyph); |
1667 } | 1667 } |
1668 | 1668 |
(...skipping 16 matching lines...) Expand all Loading... |
1685 | 1685 |
1686 // Temporarily jam in kFill, so we only ever ask for the raw outline from th
e cache. | 1686 // Temporarily jam in kFill, so we only ever ask for the raw outline from th
e cache. |
1687 paint.setStyle(SkPaint::kFill_Style); | 1687 paint.setStyle(SkPaint::kFill_Style); |
1688 paint.setPathEffect(NULL); | 1688 paint.setPathEffect(NULL); |
1689 | 1689 |
1690 SkDrawCacheProc glyphCacheProc = paint.getDrawCacheProc(); | 1690 SkDrawCacheProc glyphCacheProc = paint.getDrawCacheProc(); |
1691 SkAutoGlyphCache autoCache(paint, NULL, NULL); | 1691 SkAutoGlyphCache autoCache(paint, NULL, NULL); |
1692 SkGlyphCache* cache = autoCache.getCache(); | 1692 SkGlyphCache* cache = autoCache.getCache(); |
1693 | 1693 |
1694 const char* stop = text + byteLength; | 1694 const char* stop = text + byteLength; |
1695 SkTextAlignProcScalar alignProc(paint.getTextAlign()); | 1695 SkTextAlignProc alignProc(paint.getTextAlign()); |
1696 SkTextMapStateProc tmsProc(SkMatrix::I(), offset, scalarsPerPosition); | 1696 SkTextMapStateProc tmsProc(SkMatrix::I(), offset, scalarsPerPosition); |
1697 | 1697 |
1698 // Now restore the original settings, so we "draw" with whatever style/strok
ing. | 1698 // Now restore the original settings, so we "draw" with whatever style/strok
ing. |
1699 paint.setStyle(origPaint.getStyle()); | 1699 paint.setStyle(origPaint.getStyle()); |
1700 paint.setPathEffect(origPaint.getPathEffect()); | 1700 paint.setPathEffect(origPaint.getPathEffect()); |
1701 | 1701 |
1702 while (text < stop) { | 1702 while (text < stop) { |
1703 const SkGlyph& glyph = glyphCacheProc(cache, &text, 0, 0); | 1703 const SkGlyph& glyph = glyphCacheProc(cache, &text, 0, 0); |
1704 if (glyph.fWidth) { | 1704 if (glyph.fWidth) { |
1705 const SkPath* path = cache->findPath(glyph); | 1705 const SkPath* path = cache->findPath(glyph); |
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1763 SkTextMapStateProc tmsProc(*fMatrix, offset, scalarsPerPosition); | 1763 SkTextMapStateProc tmsProc(*fMatrix, offset, scalarsPerPosition); |
1764 | 1764 |
1765 if (cache->isSubpixel()) { | 1765 if (cache->isSubpixel()) { |
1766 // maybe we should skip the rounding if linearText is set | 1766 // maybe we should skip the rounding if linearText is set |
1767 SkAxisAlignment baseline = SkComputeAxisAlignmentForHText(*fMatrix); | 1767 SkAxisAlignment baseline = SkComputeAxisAlignmentForHText(*fMatrix); |
1768 | 1768 |
1769 SkFixed fxMask = ~0; | 1769 SkFixed fxMask = ~0; |
1770 SkFixed fyMask = ~0; | 1770 SkFixed fyMask = ~0; |
1771 if (kX_SkAxisAlignment == baseline) { | 1771 if (kX_SkAxisAlignment == baseline) { |
1772 fyMask = 0; | 1772 fyMask = 0; |
1773 d1g.fHalfSampleY = SK_FixedHalf; | 1773 d1g.fHalfSampleY = SK_ScalarHalf; |
1774 } else if (kY_SkAxisAlignment == baseline) { | 1774 } else if (kY_SkAxisAlignment == baseline) { |
1775 fxMask = 0; | 1775 fxMask = 0; |
1776 d1g.fHalfSampleX = SK_FixedHalf; | 1776 d1g.fHalfSampleX = SK_ScalarHalf; |
1777 } | 1777 } |
1778 | 1778 |
1779 if (SkPaint::kLeft_Align == paint.getTextAlign()) { | 1779 if (SkPaint::kLeft_Align == paint.getTextAlign()) { |
1780 while (text < stop) { | 1780 while (text < stop) { |
1781 SkPoint tmsLoc; | 1781 SkPoint tmsLoc; |
1782 tmsProc(pos, &tmsLoc); | 1782 tmsProc(pos, &tmsLoc); |
1783 SkFixed fx = SkScalarToFixed(tmsLoc.fX) + d1g.fHalfSampleX; | |
1784 SkFixed fy = SkScalarToFixed(tmsLoc.fY) + d1g.fHalfSampleY; | |
1785 | 1783 |
1786 const SkGlyph& glyph = glyphCacheProc(cache, &text, | 1784 Sk48Dot16 fx = SkScalarTo48Dot16(tmsLoc.fX + d1g.fHalfSampleX); |
1787 fx & fxMask, fy & fyMask); | 1785 Sk48Dot16 fy = SkScalarTo48Dot16(tmsLoc.fY + d1g.fHalfSampleY); |
| 1786 |
| 1787 const SkGlyph& glyph = glyphCacheProc(cache, &text, fx & fxMask,
fy & fyMask); |
1788 | 1788 |
1789 if (glyph.fWidth) { | 1789 if (glyph.fWidth) { |
1790 proc(d1g, fx, fy, glyph); | 1790 proc(d1g, fx, fy, glyph); |
1791 } | 1791 } |
1792 pos += scalarsPerPosition; | 1792 pos += scalarsPerPosition; |
1793 } | 1793 } |
1794 } else { | 1794 } else { |
1795 while (text < stop) { | 1795 while (text < stop) { |
1796 const char* currentText = text; | 1796 const char* currentText = text; |
1797 const SkGlyph& metricGlyph = glyphCacheProc(cache, &text, 0, 0); | 1797 const SkGlyph& metricGlyph = glyphCacheProc(cache, &text, 0, 0); |
1798 | 1798 |
1799 if (metricGlyph.fWidth) { | 1799 if (metricGlyph.fWidth) { |
1800 SkDEBUGCODE(SkFixed prevAdvX = metricGlyph.fAdvanceX;) | 1800 SkDEBUGCODE(SkFixed prevAdvX = metricGlyph.fAdvanceX;) |
1801 SkDEBUGCODE(SkFixed prevAdvY = metricGlyph.fAdvanceY;) | 1801 SkDEBUGCODE(SkFixed prevAdvY = metricGlyph.fAdvanceY;) |
1802 SkPoint tmsLoc; | 1802 SkPoint tmsLoc; |
1803 tmsProc(pos, &tmsLoc); | 1803 tmsProc(pos, &tmsLoc); |
1804 SkIPoint fixedLoc; | |
1805 alignProc(tmsLoc, metricGlyph, &fixedLoc); | |
1806 | 1804 |
1807 SkFixed fx = fixedLoc.fX + d1g.fHalfSampleX; | 1805 SkPoint alignLoc; |
1808 SkFixed fy = fixedLoc.fY + d1g.fHalfSampleY; | 1806 alignProc(tmsLoc, metricGlyph, &alignLoc); |
| 1807 |
| 1808 Sk48Dot16 fx = SkScalarTo48Dot16(alignLoc.fX + d1g.fHalfSamp
leX); |
| 1809 Sk48Dot16 fy = SkScalarTo48Dot16(alignLoc.fY + d1g.fHalfSamp
leY); |
1809 | 1810 |
1810 // have to call again, now that we've been "aligned" | 1811 // have to call again, now that we've been "aligned" |
1811 const SkGlyph& glyph = glyphCacheProc(cache, ¤tText, | 1812 const SkGlyph& glyph = glyphCacheProc(cache, ¤tText, |
1812 fx & fxMask, fy & fyMa
sk); | 1813 fx & fxMask, fy & fyMa
sk); |
1813 // the assumption is that the metrics haven't changed | 1814 // the assumption is that the metrics haven't changed |
1814 SkASSERT(prevAdvX == glyph.fAdvanceX); | 1815 SkASSERT(prevAdvX == glyph.fAdvanceX); |
1815 SkASSERT(prevAdvY == glyph.fAdvanceY); | 1816 SkASSERT(prevAdvY == glyph.fAdvanceY); |
1816 SkASSERT(glyph.fWidth); | 1817 SkASSERT(glyph.fWidth); |
1817 | 1818 |
1818 proc(d1g, fx, fy, glyph); | 1819 proc(d1g, fx, fy, glyph); |
1819 } | 1820 } |
1820 pos += scalarsPerPosition; | 1821 pos += scalarsPerPosition; |
1821 } | 1822 } |
1822 } | 1823 } |
1823 } else { // not subpixel | 1824 } else { // not subpixel |
1824 if (SkPaint::kLeft_Align == paint.getTextAlign()) { | 1825 if (SkPaint::kLeft_Align == paint.getTextAlign()) { |
1825 while (text < stop) { | 1826 while (text < stop) { |
1826 // the last 2 parameters are ignored | 1827 // the last 2 parameters are ignored |
1827 const SkGlyph& glyph = glyphCacheProc(cache, &text, 0, 0); | 1828 const SkGlyph& glyph = glyphCacheProc(cache, &text, 0, 0); |
1828 | 1829 |
1829 if (glyph.fWidth) { | 1830 if (glyph.fWidth) { |
1830 SkPoint tmsLoc; | 1831 SkPoint tmsLoc; |
1831 tmsProc(pos, &tmsLoc); | 1832 tmsProc(pos, &tmsLoc); |
1832 | 1833 |
1833 proc(d1g, | 1834 proc(d1g, |
1834 SkScalarToFixed(tmsLoc.fX) + SK_FixedHalf, //d1g.fHalfS
ampleX, | 1835 SkScalarTo48Dot16(tmsLoc.fX + SK_ScalarHalf), //d1g.fHa
lfSampleX, |
1835 SkScalarToFixed(tmsLoc.fY) + SK_FixedHalf, //d1g.fHalfS
ampleY, | 1836 SkScalarTo48Dot16(tmsLoc.fY + SK_ScalarHalf), //d1g.fHa
lfSampleY, |
1836 glyph); | 1837 glyph); |
1837 } | 1838 } |
1838 pos += scalarsPerPosition; | 1839 pos += scalarsPerPosition; |
1839 } | 1840 } |
1840 } else { | 1841 } else { |
1841 while (text < stop) { | 1842 while (text < stop) { |
1842 // the last 2 parameters are ignored | 1843 // the last 2 parameters are ignored |
1843 const SkGlyph& glyph = glyphCacheProc(cache, &text, 0, 0); | 1844 const SkGlyph& glyph = glyphCacheProc(cache, &text, 0, 0); |
1844 | 1845 |
1845 if (glyph.fWidth) { | 1846 if (glyph.fWidth) { |
1846 SkPoint tmsLoc; | 1847 SkPoint tmsLoc; |
1847 tmsProc(pos, &tmsLoc); | 1848 tmsProc(pos, &tmsLoc); |
1848 | 1849 |
1849 SkIPoint fixedLoc; | 1850 SkPoint alignLoc; |
1850 alignProc(tmsLoc, glyph, &fixedLoc); | 1851 alignProc(tmsLoc, glyph, &alignLoc); |
1851 | 1852 |
1852 proc(d1g, | 1853 proc(d1g, |
1853 fixedLoc.fX + SK_FixedHalf, //d1g.fHalfSampleX, | 1854 SkScalarTo48Dot16(alignLoc.fX + SK_ScalarHalf), //d1g.f
HalfSampleX, |
1854 fixedLoc.fY + SK_FixedHalf, //d1g.fHalfSampleY, | 1855 SkScalarTo48Dot16(alignLoc.fY + SK_ScalarHalf), //d1g.f
HalfSampleY, |
1855 glyph); | 1856 glyph); |
1856 } | 1857 } |
1857 pos += scalarsPerPosition; | 1858 pos += scalarsPerPosition; |
1858 } | 1859 } |
1859 } | 1860 } |
1860 } | 1861 } |
1861 } | 1862 } |
1862 | 1863 |
1863 #if defined _WIN32 && _MSC_VER >= 1300 | 1864 #if defined _WIN32 && _MSC_VER >= 1300 |
1864 #pragma warning ( pop ) | 1865 #pragma warning ( pop ) |
(...skipping 400 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2265 mask->fImage = SkMask::AllocImage(size); | 2266 mask->fImage = SkMask::AllocImage(size); |
2266 memset(mask->fImage, 0, mask->computeImageSize()); | 2267 memset(mask->fImage, 0, mask->computeImageSize()); |
2267 } | 2268 } |
2268 | 2269 |
2269 if (SkMask::kJustComputeBounds_CreateMode != mode) { | 2270 if (SkMask::kJustComputeBounds_CreateMode != mode) { |
2270 draw_into_mask(*mask, devPath, style); | 2271 draw_into_mask(*mask, devPath, style); |
2271 } | 2272 } |
2272 | 2273 |
2273 return true; | 2274 return true; |
2274 } | 2275 } |
OLD | NEW |