| OLD | NEW |
| 1 | 1 |
| 2 /* | 2 /* |
| 3 * Copyright 2008 The Android Open Source Project | 3 * Copyright 2008 The Android Open Source Project |
| 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 | 9 |
| 10 #include "SkCanvas.h" | 10 #include "SkCanvas.h" |
| (...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 84 const int count = fPixelRef ? fPixelRef->getLockCount() : 0; | 84 const int count = fPixelRef ? fPixelRef->getLockCount() : 0; |
| 85 SkASSERT(count == fLockCount); | 85 SkASSERT(count == fLockCount); |
| 86 } | 86 } |
| 87 | 87 |
| 88 private: | 88 private: |
| 89 const SkPixelRef* fPixelRef; | 89 const SkPixelRef* fPixelRef; |
| 90 int fLockCount; | 90 int fLockCount; |
| 91 }; | 91 }; |
| 92 #endif | 92 #endif |
| 93 | 93 |
| 94 class AutoCheckNoSetContext { | |
| 95 public: | |
| 96 AutoCheckNoSetContext(const SkPaint& paint) : fPaint(paint) { | |
| 97 this->assertNoSetContext(fPaint); | |
| 98 } | |
| 99 ~AutoCheckNoSetContext() { | |
| 100 this->assertNoSetContext(fPaint); | |
| 101 } | |
| 102 | |
| 103 private: | |
| 104 const SkPaint& fPaint; | |
| 105 | |
| 106 void assertNoSetContext(const SkPaint& paint) { | |
| 107 SkShader* s = paint.getShader(); | |
| 108 if (s) { | |
| 109 SkASSERT(!s->setContextHasBeenCalled()); | |
| 110 } | |
| 111 } | |
| 112 }; | |
| 113 | |
| 114 #define CHECK_LOCKCOUNT_BALANCE(bitmap) AutoCheckLockCountBalance clcb(bitmap) | 94 #define CHECK_LOCKCOUNT_BALANCE(bitmap) AutoCheckLockCountBalance clcb(bitmap) |
| 115 #define CHECK_SHADER_NOSETCONTEXT(paint) AutoCheckNoSetContext cshsc(paint) | |
| 116 | 95 |
| 117 #else | 96 #else |
| 118 #define CHECK_LOCKCOUNT_BALANCE(bitmap) | 97 #define CHECK_LOCKCOUNT_BALANCE(bitmap) |
| 119 #define CHECK_SHADER_NOSETCONTEXT(paint) | |
| 120 #endif | 98 #endif |
| 121 | 99 |
| 122 typedef SkTLazy<SkPaint> SkLazyPaint; | 100 typedef SkTLazy<SkPaint> SkLazyPaint; |
| 123 | 101 |
| 124 void SkCanvas::predrawNotify() { | 102 void SkCanvas::predrawNotify() { |
| 125 if (fSurfaceBase) { | 103 if (fSurfaceBase) { |
| 126 fSurfaceBase->aboutToDraw(SkSurface::kRetain_ContentChangeMode); | 104 fSurfaceBase->aboutToDraw(SkSurface::kRetain_ContentChangeMode); |
| 127 } | 105 } |
| 128 } | 106 } |
| 129 | 107 |
| (...skipping 1633 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1763 while (iter.next()) { | 1741 while (iter.next()) { |
| 1764 iter.fDevice->clear(color); | 1742 iter.fDevice->clear(color); |
| 1765 } | 1743 } |
| 1766 } | 1744 } |
| 1767 | 1745 |
| 1768 void SkCanvas::drawPaint(const SkPaint& paint) { | 1746 void SkCanvas::drawPaint(const SkPaint& paint) { |
| 1769 this->internalDrawPaint(paint); | 1747 this->internalDrawPaint(paint); |
| 1770 } | 1748 } |
| 1771 | 1749 |
| 1772 void SkCanvas::internalDrawPaint(const SkPaint& paint) { | 1750 void SkCanvas::internalDrawPaint(const SkPaint& paint) { |
| 1773 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 1774 | |
| 1775 LOOPER_BEGIN(paint, SkDrawFilter::kPaint_Type, NULL) | 1751 LOOPER_BEGIN(paint, SkDrawFilter::kPaint_Type, NULL) |
| 1776 | 1752 |
| 1777 while (iter.next()) { | 1753 while (iter.next()) { |
| 1778 iter.fDevice->drawPaint(iter, looper.paint()); | 1754 iter.fDevice->drawPaint(iter, looper.paint()); |
| 1779 } | 1755 } |
| 1780 | 1756 |
| 1781 LOOPER_END | 1757 LOOPER_END |
| 1782 } | 1758 } |
| 1783 | 1759 |
| 1784 void SkCanvas::drawPoints(PointMode mode, size_t count, const SkPoint pts[], | 1760 void SkCanvas::drawPoints(PointMode mode, size_t count, const SkPoint pts[], |
| 1785 const SkPaint& paint) { | 1761 const SkPaint& paint) { |
| 1786 if ((long)count <= 0) { | 1762 if ((long)count <= 0) { |
| 1787 return; | 1763 return; |
| 1788 } | 1764 } |
| 1789 | 1765 |
| 1790 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 1791 | |
| 1792 SkRect r, storage; | 1766 SkRect r, storage; |
| 1793 const SkRect* bounds = NULL; | 1767 const SkRect* bounds = NULL; |
| 1794 if (paint.canComputeFastBounds()) { | 1768 if (paint.canComputeFastBounds()) { |
| 1795 // special-case 2 points (common for drawing a single line) | 1769 // special-case 2 points (common for drawing a single line) |
| 1796 if (2 == count) { | 1770 if (2 == count) { |
| 1797 r.set(pts[0], pts[1]); | 1771 r.set(pts[0], pts[1]); |
| 1798 } else { | 1772 } else { |
| 1799 r.set(pts, SkToInt(count)); | 1773 r.set(pts, SkToInt(count)); |
| 1800 } | 1774 } |
| 1801 bounds = &paint.computeFastStrokeBounds(r, &storage); | 1775 bounds = &paint.computeFastStrokeBounds(r, &storage); |
| 1802 if (this->quickReject(*bounds)) { | 1776 if (this->quickReject(*bounds)) { |
| 1803 return; | 1777 return; |
| 1804 } | 1778 } |
| 1805 } | 1779 } |
| 1806 | 1780 |
| 1807 SkASSERT(pts != NULL); | 1781 SkASSERT(pts != NULL); |
| 1808 | 1782 |
| 1809 LOOPER_BEGIN(paint, SkDrawFilter::kPoint_Type, bounds) | 1783 LOOPER_BEGIN(paint, SkDrawFilter::kPoint_Type, bounds) |
| 1810 | 1784 |
| 1811 while (iter.next()) { | 1785 while (iter.next()) { |
| 1812 iter.fDevice->drawPoints(iter, mode, count, pts, looper.paint()); | 1786 iter.fDevice->drawPoints(iter, mode, count, pts, looper.paint()); |
| 1813 } | 1787 } |
| 1814 | 1788 |
| 1815 LOOPER_END | 1789 LOOPER_END |
| 1816 } | 1790 } |
| 1817 | 1791 |
| 1818 void SkCanvas::drawRect(const SkRect& r, const SkPaint& paint) { | 1792 void SkCanvas::drawRect(const SkRect& r, const SkPaint& paint) { |
| 1819 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 1820 | |
| 1821 SkRect storage; | 1793 SkRect storage; |
| 1822 const SkRect* bounds = NULL; | 1794 const SkRect* bounds = NULL; |
| 1823 if (paint.canComputeFastBounds()) { | 1795 if (paint.canComputeFastBounds()) { |
| 1824 bounds = &paint.computeFastBounds(r, &storage); | 1796 bounds = &paint.computeFastBounds(r, &storage); |
| 1825 if (this->quickReject(*bounds)) { | 1797 if (this->quickReject(*bounds)) { |
| 1826 return; | 1798 return; |
| 1827 } | 1799 } |
| 1828 } | 1800 } |
| 1829 | 1801 |
| 1830 LOOPER_BEGIN(paint, SkDrawFilter::kRect_Type, bounds) | 1802 LOOPER_BEGIN(paint, SkDrawFilter::kRect_Type, bounds) |
| 1831 | 1803 |
| 1832 while (iter.next()) { | 1804 while (iter.next()) { |
| 1833 iter.fDevice->drawRect(iter, r, looper.paint()); | 1805 iter.fDevice->drawRect(iter, r, looper.paint()); |
| 1834 } | 1806 } |
| 1835 | 1807 |
| 1836 LOOPER_END | 1808 LOOPER_END |
| 1837 } | 1809 } |
| 1838 | 1810 |
| 1839 void SkCanvas::drawOval(const SkRect& oval, const SkPaint& paint) { | 1811 void SkCanvas::drawOval(const SkRect& oval, const SkPaint& paint) { |
| 1840 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 1841 | |
| 1842 SkRect storage; | 1812 SkRect storage; |
| 1843 const SkRect* bounds = NULL; | 1813 const SkRect* bounds = NULL; |
| 1844 if (paint.canComputeFastBounds()) { | 1814 if (paint.canComputeFastBounds()) { |
| 1845 bounds = &paint.computeFastBounds(oval, &storage); | 1815 bounds = &paint.computeFastBounds(oval, &storage); |
| 1846 if (this->quickReject(*bounds)) { | 1816 if (this->quickReject(*bounds)) { |
| 1847 return; | 1817 return; |
| 1848 } | 1818 } |
| 1849 } | 1819 } |
| 1850 | 1820 |
| 1851 LOOPER_BEGIN(paint, SkDrawFilter::kOval_Type, bounds) | 1821 LOOPER_BEGIN(paint, SkDrawFilter::kOval_Type, bounds) |
| 1852 | 1822 |
| 1853 while (iter.next()) { | 1823 while (iter.next()) { |
| 1854 iter.fDevice->drawOval(iter, oval, looper.paint()); | 1824 iter.fDevice->drawOval(iter, oval, looper.paint()); |
| 1855 } | 1825 } |
| 1856 | 1826 |
| 1857 LOOPER_END | 1827 LOOPER_END |
| 1858 } | 1828 } |
| 1859 | 1829 |
| 1860 void SkCanvas::drawRRect(const SkRRect& rrect, const SkPaint& paint) { | 1830 void SkCanvas::drawRRect(const SkRRect& rrect, const SkPaint& paint) { |
| 1861 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 1862 | |
| 1863 SkRect storage; | 1831 SkRect storage; |
| 1864 const SkRect* bounds = NULL; | 1832 const SkRect* bounds = NULL; |
| 1865 if (paint.canComputeFastBounds()) { | 1833 if (paint.canComputeFastBounds()) { |
| 1866 bounds = &paint.computeFastBounds(rrect.getBounds(), &storage); | 1834 bounds = &paint.computeFastBounds(rrect.getBounds(), &storage); |
| 1867 if (this->quickReject(*bounds)) { | 1835 if (this->quickReject(*bounds)) { |
| 1868 return; | 1836 return; |
| 1869 } | 1837 } |
| 1870 } | 1838 } |
| 1871 | 1839 |
| 1872 if (rrect.isRect()) { | 1840 if (rrect.isRect()) { |
| (...skipping 10 matching lines...) Expand all Loading... |
| 1883 | 1851 |
| 1884 while (iter.next()) { | 1852 while (iter.next()) { |
| 1885 iter.fDevice->drawRRect(iter, rrect, looper.paint()); | 1853 iter.fDevice->drawRRect(iter, rrect, looper.paint()); |
| 1886 } | 1854 } |
| 1887 | 1855 |
| 1888 LOOPER_END | 1856 LOOPER_END |
| 1889 } | 1857 } |
| 1890 | 1858 |
| 1891 void SkCanvas::onDrawDRRect(const SkRRect& outer, const SkRRect& inner, | 1859 void SkCanvas::onDrawDRRect(const SkRRect& outer, const SkRRect& inner, |
| 1892 const SkPaint& paint) { | 1860 const SkPaint& paint) { |
| 1893 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 1894 | |
| 1895 SkRect storage; | 1861 SkRect storage; |
| 1896 const SkRect* bounds = NULL; | 1862 const SkRect* bounds = NULL; |
| 1897 if (paint.canComputeFastBounds()) { | 1863 if (paint.canComputeFastBounds()) { |
| 1898 bounds = &paint.computeFastBounds(outer.getBounds(), &storage); | 1864 bounds = &paint.computeFastBounds(outer.getBounds(), &storage); |
| 1899 if (this->quickReject(*bounds)) { | 1865 if (this->quickReject(*bounds)) { |
| 1900 return; | 1866 return; |
| 1901 } | 1867 } |
| 1902 } | 1868 } |
| 1903 | 1869 |
| 1904 LOOPER_BEGIN(paint, SkDrawFilter::kRRect_Type, bounds) | 1870 LOOPER_BEGIN(paint, SkDrawFilter::kRRect_Type, bounds) |
| 1905 | 1871 |
| 1906 while (iter.next()) { | 1872 while (iter.next()) { |
| 1907 iter.fDevice->drawDRRect(iter, outer, inner, looper.paint()); | 1873 iter.fDevice->drawDRRect(iter, outer, inner, looper.paint()); |
| 1908 } | 1874 } |
| 1909 | 1875 |
| 1910 LOOPER_END | 1876 LOOPER_END |
| 1911 } | 1877 } |
| 1912 | 1878 |
| 1913 void SkCanvas::drawPath(const SkPath& path, const SkPaint& paint) { | 1879 void SkCanvas::drawPath(const SkPath& path, const SkPaint& paint) { |
| 1914 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 1915 | |
| 1916 if (!path.isFinite()) { | 1880 if (!path.isFinite()) { |
| 1917 return; | 1881 return; |
| 1918 } | 1882 } |
| 1919 | 1883 |
| 1920 SkRect storage; | 1884 SkRect storage; |
| 1921 const SkRect* bounds = NULL; | 1885 const SkRect* bounds = NULL; |
| 1922 if (!path.isInverseFillType() && paint.canComputeFastBounds()) { | 1886 if (!path.isInverseFillType() && paint.canComputeFastBounds()) { |
| 1923 const SkRect& pathBounds = path.getBounds(); | 1887 const SkRect& pathBounds = path.getBounds(); |
| 1924 bounds = &paint.computeFastBounds(pathBounds, &storage); | 1888 bounds = &paint.computeFastBounds(pathBounds, &storage); |
| 1925 if (this->quickReject(*bounds)) { | 1889 if (this->quickReject(*bounds)) { |
| (...skipping 255 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2181 start.fY); | 2145 start.fY); |
| 2182 r.fTop = offset; | 2146 r.fTop = offset; |
| 2183 r.fBottom = offset + height; | 2147 r.fBottom = offset + height; |
| 2184 DrawRect(draw, paint, r, textSize); | 2148 DrawRect(draw, paint, r, textSize); |
| 2185 } | 2149 } |
| 2186 } | 2150 } |
| 2187 } | 2151 } |
| 2188 | 2152 |
| 2189 void SkCanvas::drawText(const void* text, size_t byteLength, | 2153 void SkCanvas::drawText(const void* text, size_t byteLength, |
| 2190 SkScalar x, SkScalar y, const SkPaint& paint) { | 2154 SkScalar x, SkScalar y, const SkPaint& paint) { |
| 2191 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 2192 | |
| 2193 LOOPER_BEGIN(paint, SkDrawFilter::kText_Type, NULL) | 2155 LOOPER_BEGIN(paint, SkDrawFilter::kText_Type, NULL) |
| 2194 | 2156 |
| 2195 while (iter.next()) { | 2157 while (iter.next()) { |
| 2196 SkDeviceFilteredPaint dfp(iter.fDevice, looper.paint()); | 2158 SkDeviceFilteredPaint dfp(iter.fDevice, looper.paint()); |
| 2197 iter.fDevice->drawText(iter, text, byteLength, x, y, dfp.paint()); | 2159 iter.fDevice->drawText(iter, text, byteLength, x, y, dfp.paint()); |
| 2198 DrawTextDecorations(iter, dfp.paint(), | 2160 DrawTextDecorations(iter, dfp.paint(), |
| 2199 static_cast<const char*>(text), byteLength, x, y); | 2161 static_cast<const char*>(text), byteLength, x, y); |
| 2200 } | 2162 } |
| 2201 | 2163 |
| 2202 LOOPER_END | 2164 LOOPER_END |
| 2203 } | 2165 } |
| 2204 | 2166 |
| 2205 void SkCanvas::drawPosText(const void* text, size_t byteLength, | 2167 void SkCanvas::drawPosText(const void* text, size_t byteLength, |
| 2206 const SkPoint pos[], const SkPaint& paint) { | 2168 const SkPoint pos[], const SkPaint& paint) { |
| 2207 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 2208 | |
| 2209 LOOPER_BEGIN(paint, SkDrawFilter::kText_Type, NULL) | 2169 LOOPER_BEGIN(paint, SkDrawFilter::kText_Type, NULL) |
| 2210 | 2170 |
| 2211 while (iter.next()) { | 2171 while (iter.next()) { |
| 2212 SkDeviceFilteredPaint dfp(iter.fDevice, looper.paint()); | 2172 SkDeviceFilteredPaint dfp(iter.fDevice, looper.paint()); |
| 2213 iter.fDevice->drawPosText(iter, text, byteLength, &pos->fX, 0, 2, | 2173 iter.fDevice->drawPosText(iter, text, byteLength, &pos->fX, 0, 2, |
| 2214 dfp.paint()); | 2174 dfp.paint()); |
| 2215 } | 2175 } |
| 2216 | 2176 |
| 2217 LOOPER_END | 2177 LOOPER_END |
| 2218 } | 2178 } |
| 2219 | 2179 |
| 2220 void SkCanvas::drawPosTextH(const void* text, size_t byteLength, | 2180 void SkCanvas::drawPosTextH(const void* text, size_t byteLength, |
| 2221 const SkScalar xpos[], SkScalar constY, | 2181 const SkScalar xpos[], SkScalar constY, |
| 2222 const SkPaint& paint) { | 2182 const SkPaint& paint) { |
| 2223 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 2224 | |
| 2225 LOOPER_BEGIN(paint, SkDrawFilter::kText_Type, NULL) | 2183 LOOPER_BEGIN(paint, SkDrawFilter::kText_Type, NULL) |
| 2226 | 2184 |
| 2227 while (iter.next()) { | 2185 while (iter.next()) { |
| 2228 SkDeviceFilteredPaint dfp(iter.fDevice, looper.paint()); | 2186 SkDeviceFilteredPaint dfp(iter.fDevice, looper.paint()); |
| 2229 iter.fDevice->drawPosText(iter, text, byteLength, xpos, constY, 1, | 2187 iter.fDevice->drawPosText(iter, text, byteLength, xpos, constY, 1, |
| 2230 dfp.paint()); | 2188 dfp.paint()); |
| 2231 } | 2189 } |
| 2232 | 2190 |
| 2233 LOOPER_END | 2191 LOOPER_END |
| 2234 } | 2192 } |
| 2235 | 2193 |
| 2236 void SkCanvas::drawTextOnPath(const void* text, size_t byteLength, | 2194 void SkCanvas::drawTextOnPath(const void* text, size_t byteLength, |
| 2237 const SkPath& path, const SkMatrix* matrix, | 2195 const SkPath& path, const SkMatrix* matrix, |
| 2238 const SkPaint& paint) { | 2196 const SkPaint& paint) { |
| 2239 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 2240 | |
| 2241 LOOPER_BEGIN(paint, SkDrawFilter::kText_Type, NULL) | 2197 LOOPER_BEGIN(paint, SkDrawFilter::kText_Type, NULL) |
| 2242 | 2198 |
| 2243 while (iter.next()) { | 2199 while (iter.next()) { |
| 2244 iter.fDevice->drawTextOnPath(iter, text, byteLength, path, | 2200 iter.fDevice->drawTextOnPath(iter, text, byteLength, path, |
| 2245 matrix, looper.paint()); | 2201 matrix, looper.paint()); |
| 2246 } | 2202 } |
| 2247 | 2203 |
| 2248 LOOPER_END | 2204 LOOPER_END |
| 2249 } | 2205 } |
| 2250 | 2206 |
| 2251 void SkCanvas::drawVertices(VertexMode vmode, int vertexCount, | 2207 void SkCanvas::drawVertices(VertexMode vmode, int vertexCount, |
| 2252 const SkPoint verts[], const SkPoint texs[], | 2208 const SkPoint verts[], const SkPoint texs[], |
| 2253 const SkColor colors[], SkXfermode* xmode, | 2209 const SkColor colors[], SkXfermode* xmode, |
| 2254 const uint16_t indices[], int indexCount, | 2210 const uint16_t indices[], int indexCount, |
| 2255 const SkPaint& paint) { | 2211 const SkPaint& paint) { |
| 2256 CHECK_SHADER_NOSETCONTEXT(paint); | |
| 2257 | |
| 2258 LOOPER_BEGIN(paint, SkDrawFilter::kPath_Type, NULL) | 2212 LOOPER_BEGIN(paint, SkDrawFilter::kPath_Type, NULL) |
| 2259 | 2213 |
| 2260 while (iter.next()) { | 2214 while (iter.next()) { |
| 2261 iter.fDevice->drawVertices(iter, vmode, vertexCount, verts, texs, | 2215 iter.fDevice->drawVertices(iter, vmode, vertexCount, verts, texs, |
| 2262 colors, xmode, indices, indexCount, | 2216 colors, xmode, indices, indexCount, |
| 2263 looper.paint()); | 2217 looper.paint()); |
| 2264 } | 2218 } |
| 2265 | 2219 |
| 2266 LOOPER_END | 2220 LOOPER_END |
| 2267 } | 2221 } |
| (...skipping 195 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2463 if (!bitmap.allocPixels(info)) { | 2417 if (!bitmap.allocPixels(info)) { |
| 2464 return NULL; | 2418 return NULL; |
| 2465 } | 2419 } |
| 2466 | 2420 |
| 2467 // should this functionality be moved into allocPixels()? | 2421 // should this functionality be moved into allocPixels()? |
| 2468 if (!bitmap.info().isOpaque()) { | 2422 if (!bitmap.info().isOpaque()) { |
| 2469 bitmap.eraseColor(0); | 2423 bitmap.eraseColor(0); |
| 2470 } | 2424 } |
| 2471 return SkNEW_ARGS(SkCanvas, (bitmap)); | 2425 return SkNEW_ARGS(SkCanvas, (bitmap)); |
| 2472 } | 2426 } |
| OLD | NEW |