Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(2393)

Side by Side Diff: src/core/SkScan_AAAPath.cpp

Issue 2430343003: Use Analytic AA in SkAAClip (Closed)
Patch Set: Nit fixes Created 4 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/core/SkScan.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright 2016 The Android Open Source Project 2 * Copyright 2016 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 "SkAntiRun.h" 8 #include "SkAntiRun.h"
9 #include "SkBlitter.h" 9 #include "SkBlitter.h"
10 #include "SkEdge.h" 10 #include "SkEdge.h"
(...skipping 255 matching lines...) Expand 10 before | Expand all | Expand 10 after
266 ~RunBasedAdditiveBlitter(); 266 ~RunBasedAdditiveBlitter();
267 267
268 SkBlitter* getRealBlitter(bool forceRealBlitter) override; 268 SkBlitter* getRealBlitter(bool forceRealBlitter) override;
269 269
270 void blitAntiH(int x, int y, const SkAlpha antialias[], int len) override; 270 void blitAntiH(int x, int y, const SkAlpha antialias[], int len) override;
271 void blitAntiH(int x, int y, const SkAlpha alpha) override; 271 void blitAntiH(int x, int y, const SkAlpha alpha) override;
272 void blitAntiH(int x, int y, int width, const SkAlpha alpha) override; 272 void blitAntiH(int x, int y, int width, const SkAlpha alpha) override;
273 273
274 int getWidth() override; 274 int getWidth() override;
275 275
276 // This should only be called when forceRLE = true which implies that SkAACl ip
277 // is calling us.
278 // SkAAClip requires that we blit in scan-line order so we have to flush
279 // for each row in order. Without this, we may have the first row unflushed,
280 // then blit the 2nd and the 3rd row with full alpha (so we won't flush the first row);
281 // finally when we blit the fourth row, we trigger the first row to flush, a nd this
282 // would cause SkAAClip to crash.
283 inline void flush_if_y_changed(SkFixed y, SkFixed nextY) {
284 if (SkFixedFloorToInt(y) != SkFixedFloorToInt(nextY)) {
285 this->flush();
286 }
287 }
288
276 private: 289 private:
277 SkBlitter* fRealBlitter; 290 SkBlitter* fRealBlitter;
278 291
279 /// Current y coordinate 292 /// Current y coordinate
280 int fCurrY; 293 int fCurrY;
281 /// Widest row of region to be blitted 294 /// Widest row of region to be blitted
282 int fWidth; 295 int fWidth;
283 /// Leftmost x coordinate in any row 296 /// Leftmost x coordinate in any row
284 int fLeft; 297 int fLeft;
285 /// Initial y coordinate (top of bounds). 298 /// Initial y coordinate (top of bounds).
(...skipping 428 matching lines...) Expand 10 before | Expand all | Expand 10 after
714 // We're going to use the left line ul-ll and the rite line ur-lr 727 // We're going to use the left line ul-ll and the rite line ur-lr
715 // to exclude the area that's not covered by the path. 728 // to exclude the area that's not covered by the path.
716 // Swapping (ul, ll) or (ur, lr) won't affect that exclusion 729 // Swapping (ul, ll) or (ur, lr) won't affect that exclusion
717 // so we'll do that for simplicity. 730 // so we'll do that for simplicity.
718 if (ul > ll) { SkTSwap(ul, ll); } 731 if (ul > ll) { SkTSwap(ul, ll); }
719 if (ur > lr) { SkTSwap(ur, lr); } 732 if (ur > lr) { SkTSwap(ur, lr); }
720 733
721 SkFixed joinLeft = SkFixedCeilToFixed(ll); 734 SkFixed joinLeft = SkFixedCeilToFixed(ll);
722 SkFixed joinRite = SkFixedFloorToFixed(ur); 735 SkFixed joinRite = SkFixedFloorToFixed(ur);
723 if (joinLeft <= joinRite) { // There's a rect from joinLeft to joinRite that we can blit 736 if (joinLeft <= joinRite) { // There's a rect from joinLeft to joinRite that we can blit
724 if (joinLeft < joinRite) {
725 blit_full_alpha(blitter, y, joinLeft >> 16, (joinRite - joinLeft) >> 16, fullAlpha,
726 maskRow, isUsingMask);
727 }
728 if (ul < joinLeft) { 737 if (ul < joinLeft) {
729 int len = SkFixedCeilToInt(joinLeft - ul); 738 int len = SkFixedCeilToInt(joinLeft - ul);
730 if (len == 1) { 739 if (len == 1) {
731 SkAlpha alpha = trapezoidToAlpha(joinLeft - ul, joinLeft - ll); 740 SkAlpha alpha = trapezoidToAlpha(joinLeft - ul, joinLeft - ll);
732 blit_single_alpha(blitter, y, ul >> 16, alpha, fullAlpha, maskRo w, isUsingMask); 741 blit_single_alpha(blitter, y, ul >> 16, alpha, fullAlpha, maskRo w, isUsingMask);
733 } else if (len == 2) { 742 } else if (len == 2) {
734 SkFixed first = joinLeft - SK_Fixed1 - ul; 743 SkFixed first = joinLeft - SK_Fixed1 - ul;
735 SkFixed second = ll - ul - first; 744 SkFixed second = ll - ul - first;
736 SkAlpha a1 = partialTriangleToAlpha(first, lDY); 745 SkAlpha a1 = partialTriangleToAlpha(first, lDY);
737 SkAlpha a2 = fullAlpha - partialTriangleToAlpha(second, lDY); 746 SkAlpha a2 = fullAlpha - partialTriangleToAlpha(second, lDY);
738 blit_two_alphas(blitter, y, ul >> 16, a1, a2, fullAlpha, maskRow , isUsingMask); 747 blit_two_alphas(blitter, y, ul >> 16, a1, a2, fullAlpha, maskRow , isUsingMask);
739 } else { 748 } else {
740 blit_aaa_trapezoid_row(blitter, y, ul, joinLeft, ll, joinLeft, l DY, SK_MaxS32, 749 blit_aaa_trapezoid_row(blitter, y, ul, joinLeft, ll, joinLeft, l DY, SK_MaxS32,
741 fullAlpha, maskRow, isUsingMask); 750 fullAlpha, maskRow, isUsingMask);
742 } 751 }
743 } 752 }
753 // SkAAClip requires that we blit from left to right.
754 // Hence we must blit [ul, joinLeft] before blitting [joinLeft, joinRite ]
755 if (joinLeft < joinRite) {
756 blit_full_alpha(blitter, y, SkFixedFloorToInt(joinLeft),
757 SkFixedFloorToInt(joinRite - joinLeft),
758 fullAlpha, maskRow, isUsingMask);
759 }
744 if (lr > joinRite) { 760 if (lr > joinRite) {
745 int len = SkFixedCeilToInt(lr - joinRite); 761 int len = SkFixedCeilToInt(lr - joinRite);
746 if (len == 1) { 762 if (len == 1) {
747 SkAlpha alpha = trapezoidToAlpha(ur - joinRite, lr - joinRite); 763 SkAlpha alpha = trapezoidToAlpha(ur - joinRite, lr - joinRite);
748 blit_single_alpha(blitter, y, joinRite >> 16, alpha, fullAlpha, maskRow, 764 blit_single_alpha(blitter, y, joinRite >> 16, alpha, fullAlpha, maskRow,
749 isUsingMask); 765 isUsingMask);
750 } else if (len == 2) { 766 } else if (len == 2) {
751 SkFixed first = joinRite + SK_Fixed1 - ur; 767 SkFixed first = joinRite + SK_Fixed1 - ur;
752 SkFixed second = lr - ur - first; 768 SkFixed second = lr - ur - first;
753 SkAlpha a1 = fullAlpha - partialTriangleToAlpha(first, rDY); 769 SkAlpha a1 = fullAlpha - partialTriangleToAlpha(first, rDY);
(...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after
873 return false; 889 return false;
874 } 890 }
875 if (*nextCurrE < *currE) { 891 if (*nextCurrE < *currE) {
876 SkTSwap(currE, nextCurrE); 892 SkTSwap(currE, nextCurrE);
877 } 893 }
878 return isSmoothEnough(leftE, currE, stop_y) && isSmoothEnough(riteE, nextCur rE, stop_y); 894 return isSmoothEnough(leftE, currE, stop_y) && isSmoothEnough(riteE, nextCur rE, stop_y);
879 } 895 }
880 896
881 static inline void aaa_walk_convex_edges(SkAnalyticEdge* prevHead, AdditiveBlitt er* blitter, 897 static inline void aaa_walk_convex_edges(SkAnalyticEdge* prevHead, AdditiveBlitt er* blitter,
882 int start_y, int stop_y, SkFixed leftBound, SkFixed r iteBound, 898 int start_y, int stop_y, SkFixed leftBound, SkFixed r iteBound,
883 bool isUsingMask) { 899 bool isUsingMask, bool forceRLE) {
884 validate_sort((SkAnalyticEdge*)prevHead->fNext); 900 validate_sort((SkAnalyticEdge*)prevHead->fNext);
885 901
886 SkAnalyticEdge* leftE = (SkAnalyticEdge*) prevHead->fNext; 902 SkAnalyticEdge* leftE = (SkAnalyticEdge*) prevHead->fNext;
887 SkAnalyticEdge* riteE = (SkAnalyticEdge*) leftE->fNext; 903 SkAnalyticEdge* riteE = (SkAnalyticEdge*) leftE->fNext;
888 SkAnalyticEdge* currE = (SkAnalyticEdge*) riteE->fNext; 904 SkAnalyticEdge* currE = (SkAnalyticEdge*) riteE->fNext;
889 905
890 SkFixed y = SkTMax(leftE->fUpperY, riteE->fUpperY); 906 SkFixed y = SkTMax(leftE->fUpperY, riteE->fUpperY);
891 907
892 #ifdef SK_DEBUG 908 #ifdef SK_DEBUG
893 int frac_y_cnt = 0; 909 int frac_y_cnt = 0;
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after
954 int fullTop = SkFixedCeilToInt(y); 970 int fullTop = SkFixedCeilToInt(y);
955 int fullBot = SkFixedFloorToInt(local_bot_fixed); 971 int fullBot = SkFixedFloorToInt(local_bot_fixed);
956 SkFixed partialTop = SkIntToFixed(fullTop) - y; 972 SkFixed partialTop = SkIntToFixed(fullTop) - y;
957 SkFixed partialBot = local_bot_fixed - SkIntToFixed(fullBot); 973 SkFixed partialBot = local_bot_fixed - SkIntToFixed(fullBot);
958 if (fullTop > fullBot) { // The rectangle is within one pixel height ... 974 if (fullTop > fullBot) { // The rectangle is within one pixel height ...
959 partialTop -= (SK_Fixed1 - partialBot); 975 partialTop -= (SK_Fixed1 - partialBot);
960 partialBot = 0; 976 partialBot = 0;
961 } 977 }
962 978
963 if (fullRite >= fullLeft) { 979 if (fullRite >= fullLeft) {
980 if (partialTop > 0) { // blit first partial row
981 if (partialLeft > 0) {
982 blitter->blitAntiH(fullLeft - 1, fullTop - 1,
983 f2a(SkFixedMul_lowprec(partialTop, partialLeft)) );
984 }
985 blitter->blitAntiH(fullLeft, fullTop - 1, fullRite - fullLef t,
986 f2a(partialTop));
987 if (partialRite > 0) {
988 blitter->blitAntiH(fullRite, fullTop - 1,
989 f2a(SkFixedMul_lowprec(partialTop, partialRite)) );
990 }
991 if (forceRLE) {
992 ((RunBasedAdditiveBlitter*)blitter)->flush_if_y_changed( y, y + partialTop);
993 }
994 }
995
964 // Blit all full-height rows from fullTop to fullBot 996 // Blit all full-height rows from fullTop to fullBot
965 if (fullBot > fullTop) { 997 if (fullBot > fullTop) {
966 blitter->getRealBlitter()->blitAntiRect(fullLeft - 1, fullTo p, 998 blitter->getRealBlitter()->blitAntiRect(fullLeft - 1, fullTo p,
967 fullRite - fullLeft, fullBot - fullTop, 999 fullRite - fullLeft, fullBot - fullTop,
968 f2a(partialLeft), f2 a(partialRite)); 1000 f2a(partialLeft), f2 a(partialRite));
969 } 1001 }
970 1002
971 if (partialTop > 0) { // blit first partial row
972 if (partialLeft > 0) {
973 blitter->blitAntiH(fullLeft - 1, fullTop - 1,
974 f2a(SkFixedMul_lowprec(partialTop, partialLeft)) );
975 }
976 if (partialRite > 0) {
977 blitter->blitAntiH(fullRite, fullTop - 1,
978 f2a(SkFixedMul_lowprec(partialTop, partialRite)) );
979 }
980 blitter->blitAntiH(fullLeft, fullTop - 1, fullRite - fullLef t,
981 f2a(partialTop));
982 }
983
984 if (partialBot > 0) { // blit last partial row 1003 if (partialBot > 0) { // blit last partial row
985 if (partialLeft > 0) { 1004 if (partialLeft > 0) {
986 blitter->blitAntiH(fullLeft - 1, fullBot, 1005 blitter->blitAntiH(fullLeft - 1, fullBot,
987 f2a(SkFixedMul_lowprec(partialBot, pa rtialLeft))); 1006 f2a(SkFixedMul_lowprec(partialBot, pa rtialLeft)));
988 } 1007 }
1008 blitter->blitAntiH(fullLeft, fullBot, fullRite - fullLeft, f 2a(partialBot));
989 if (partialRite > 0) { 1009 if (partialRite > 0) {
990 blitter->blitAntiH(fullRite, fullBot, 1010 blitter->blitAntiH(fullRite, fullBot,
991 f2a(SkFixedMul_lowprec(partialBot, pa rtialRite))); 1011 f2a(SkFixedMul_lowprec(partialBot, pa rtialRite)));
992 } 1012 }
993 blitter->blitAntiH(fullLeft, fullBot, fullRite - fullLeft, f 2a(partialBot));
994 } 1013 }
995 } else { // left and rite are within the same pixel 1014 } else { // left and rite are within the same pixel
996 if (partialTop > 0) { 1015 if (partialTop > 0) {
997 blitter->getRealBlitter()->blitV(fullLeft - 1, fullTop - 1, 1, 1016 blitter->getRealBlitter()->blitV(fullLeft - 1, fullTop - 1, 1,
998 f2a(SkFixedMul_lowprec(partialTop, rite - left))); 1017 f2a(SkFixedMul_lowprec(partialTop, rite - left)));
1018 if (forceRLE) {
1019 ((RunBasedAdditiveBlitter*)blitter)->flush_if_y_changed( y, y + partialTop);
1020 }
1021 }
1022 if (fullBot >= fullTop) {
1023 blitter->getRealBlitter()->blitV(fullLeft - 1, fullTop, full Bot - fullTop,
1024 f2a(rite - left));
999 } 1025 }
1000 if (partialBot > 0) { 1026 if (partialBot > 0) {
1001 blitter->getRealBlitter()->blitV(fullLeft - 1, fullBot, 1, 1027 blitter->getRealBlitter()->blitV(fullLeft - 1, fullBot, 1,
1002 f2a(SkFixedMul_lowprec(partialBot, rite - left))); 1028 f2a(SkFixedMul_lowprec(partialBot, rite - left)));
1003 } 1029 }
1004 if (fullBot >= fullTop) {
1005 blitter->getRealBlitter()->blitV(fullLeft - 1, fullTop, full Bot - fullTop,
1006 f2a(rite - left));
1007 }
1008 } 1030 }
1009 1031
1010 y = local_bot_fixed; 1032 y = local_bot_fixed;
1011 } else { 1033 } else {
1012 // The following constant are used to snap X 1034 // The following constant are used to snap X
1013 // We snap X mainly for speedup (no tiny triangle) and 1035 // We snap X mainly for speedup (no tiny triangle) and
1014 // avoiding edge cases caused by precision errors 1036 // avoiding edge cases caused by precision errors
1015 const SkFixed kSnapDigit = SK_Fixed1 >> 4; 1037 const SkFixed kSnapDigit = SK_Fixed1 >> 4;
1016 const SkFixed kSnapHalf = kSnapDigit >> 1; 1038 const SkFixed kSnapHalf = kSnapDigit >> 1;
1017 const SkFixed kSnapMask = (-1 ^ (kSnapDigit - 1)); 1039 const SkFixed kSnapMask = (-1 ^ (kSnapDigit - 1));
(...skipping 23 matching lines...) Expand all
1041 if (count > 1) { 1063 if (count > 1) {
1042 if ((int)(y & 0xFFFF0000) != y) { // There's a partial-row on th e top 1064 if ((int)(y & 0xFFFF0000) != y) { // There's a partial-row on th e top
1043 count--; 1065 count--;
1044 SkFixed nextY = SkFixedCeilToFixed(y + 1); 1066 SkFixed nextY = SkFixedCeilToFixed(y + 1);
1045 SkFixed dY = nextY - y; 1067 SkFixed dY = nextY - y;
1046 SkFixed nextLeft = left + SkFixedMul_lowprec(dLeft, dY); 1068 SkFixed nextLeft = left + SkFixedMul_lowprec(dLeft, dY);
1047 SkFixed nextRite = rite + SkFixedMul_lowprec(dRite, dY); 1069 SkFixed nextRite = rite + SkFixedMul_lowprec(dRite, dY);
1048 blit_trapezoid_row(blitter, y >> 16, left & kSnapMask, rite & kSnapMask, 1070 blit_trapezoid_row(blitter, y >> 16, left & kSnapMask, rite & kSnapMask,
1049 nextLeft & kSnapMask, nextRite & kSnapMask, leftE->f DY, riteE->fDY, 1071 nextLeft & kSnapMask, nextRite & kSnapMask, leftE->f DY, riteE->fDY,
1050 getPartialAlpha(0xFF, dY), maskRow, isUsingMask); 1072 getPartialAlpha(0xFF, dY), maskRow, isUsingMask);
1073 if (forceRLE) {
1074 ((RunBasedAdditiveBlitter*)blitter)->flush_if_y_changed( y, nextY);
1075 }
1051 left = nextLeft; rite = nextRite; y = nextY; 1076 left = nextLeft; rite = nextRite; y = nextY;
1052 } 1077 }
1053 1078
1054 while (count > 1) { // Full rows in the middle 1079 while (count > 1) { // Full rows in the middle
1055 count--; 1080 count--;
1056 if (isUsingMask) { 1081 if (isUsingMask) {
1057 maskRow = static_cast<MaskAdditiveBlitter*>(blitter)->ge tRow(y >> 16); 1082 maskRow = static_cast<MaskAdditiveBlitter*>(blitter)->ge tRow(y >> 16);
1058 } 1083 }
1059 SkFixed nextY = y + SK_Fixed1, nextLeft = left + dLeft, next Rite = rite + dRite; 1084 SkFixed nextY = y + SK_Fixed1, nextLeft = left + dLeft, next Rite = rite + dRite;
1060 blit_trapezoid_row(blitter, y >> 16, left & kSnapMask, rite & kSnapMask, 1085 blit_trapezoid_row(blitter, y >> 16, left & kSnapMask, rite & kSnapMask,
1061 nextLeft & kSnapMask, nextRite & kSnapMask, 1086 nextLeft & kSnapMask, nextRite & kSnapMask,
1062 leftE->fDY, riteE->fDY, 0xFF, maskRow, isUsingMask); 1087 leftE->fDY, riteE->fDY, 0xFF, maskRow, isUsingMask);
1088 if (forceRLE) {
1089 ((RunBasedAdditiveBlitter*)blitter)->flush_if_y_changed( y, nextY);
1090 }
1063 left = nextLeft; rite = nextRite; y = nextY; 1091 left = nextLeft; rite = nextRite; y = nextY;
1064 } 1092 }
1065 } 1093 }
1066 1094
1067 if (isUsingMask) { 1095 if (isUsingMask) {
1068 maskRow = static_cast<MaskAdditiveBlitter*>(blitter)->getRow(y > > 16); 1096 maskRow = static_cast<MaskAdditiveBlitter*>(blitter)->getRow(y > > 16);
1069 } 1097 }
1070 1098
1071 SkFixed dY = local_bot_fixed - y; // partial-row on the bottom 1099 SkFixed dY = local_bot_fixed - y; // partial-row on the bottom
1072 SkASSERT(dY <= SK_Fixed1); 1100 SkASSERT(dY <= SK_Fixed1);
1073 // Smooth jumping to integer y may make the last nextLeft/nextRite o ut of bound. 1101 // Smooth jumping to integer y may make the last nextLeft/nextRite o ut of bound.
1074 // Take them back into the bound here. 1102 // Take them back into the bound here.
1075 SkFixed nextLeft = SkTMax(left + SkFixedMul_lowprec(dLeft, dY), left Bound); 1103 // Note that we substract kSnapHalf later so we have to add them to leftBound/riteBound
1076 SkFixed nextRite = SkTMin(rite + SkFixedMul_lowprec(dRite, dY), rite Bound); 1104 SkFixed nextLeft = SkTMax(left + SkFixedMul_lowprec(dLeft, dY), left Bound + kSnapHalf);
1105 SkFixed nextRite = SkTMin(rite + SkFixedMul_lowprec(dRite, dY), rite Bound + kSnapHalf);
1077 blit_trapezoid_row(blitter, y >> 16, left & kSnapMask, rite & kSnapM ask, 1106 blit_trapezoid_row(blitter, y >> 16, left & kSnapMask, rite & kSnapM ask,
1078 nextLeft & kSnapMask, nextRite & kSnapMask, leftE->fDY, rite E->fDY, 1107 nextLeft & kSnapMask, nextRite & kSnapMask, leftE->fDY, rite E->fDY,
1079 getPartialAlpha(0xFF, dY), maskRow, isUsingMask); 1108 getPartialAlpha(0xFF, dY), maskRow, isUsingMask);
1109 if (forceRLE) {
1110 ((RunBasedAdditiveBlitter*)blitter)->flush_if_y_changed(y, local _bot_fixed);
1111 }
1080 left = nextLeft; rite = nextRite; y = local_bot_fixed; 1112 left = nextLeft; rite = nextRite; y = local_bot_fixed;
1081 left -= kSnapHalf; rite -= kSnapHalf; 1113 left -= kSnapHalf; rite -= kSnapHalf;
1082 } 1114 }
1083 1115
1084 leftE->fX = left; 1116 leftE->fX = left;
1085 riteE->fX = rite; 1117 riteE->fX = rite;
1086 leftE->fY = riteE->fY = y; 1118 leftE->fY = riteE->fY = y;
1087 } 1119 }
1088 1120
1089 END_WALK: 1121 END_WALK:
1090 ; 1122 ;
1091 #ifdef SK_DEBUG 1123 #ifdef SK_DEBUG
1092 SkDebugf("frac_y_cnt = %d, total_y_cnt = %d\n", frac_y_cnt, total_y_cnt); 1124 SkDebugf("frac_y_cnt = %d, total_y_cnt = %d\n", frac_y_cnt, total_y_cnt);
1093 #endif 1125 #endif
1094 } 1126 }
1095 1127
1096 void SkScan::aaa_fill_path(const SkPath& path, const SkIRect* clipRect, Additive Blitter* blitter, 1128 void SkScan::aaa_fill_path(const SkPath& path, const SkIRect* clipRect, Additive Blitter* blitter,
1097 int start_y, int stop_y, const SkRegion& clipRgn, bool isUsin gMask) { 1129 int start_y, int stop_y, const SkRegion& clipRgn, bool isUsin gMask,
1130 bool forceRLE) { // forceRLE implies that SkAAClip is calling us
1098 SkASSERT(blitter); 1131 SkASSERT(blitter);
1099 1132
1100 if (path.isInverseFillType() || !path.isConvex()) { 1133 if (path.isInverseFillType() || !path.isConvex()) {
1101 // fall back to supersampling AA 1134 // fall back to supersampling AA
1102 SkScan::AntiFillPath(path, clipRgn, blitter->getRealBlitter(true), false ); 1135 SkScan::AntiFillPath(path, clipRgn, blitter->getRealBlitter(true), false );
1103 return; 1136 return;
1104 } 1137 }
1105 1138
1106 SkEdgeBuilder builder; 1139 SkEdgeBuilder builder;
1107 1140
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after
1163 if (clipRect && start_y < clipRect->fTop) { 1196 if (clipRect && start_y < clipRect->fTop) {
1164 start_y = clipRect->fTop; 1197 start_y = clipRect->fTop;
1165 } 1198 }
1166 if (clipRect && stop_y > clipRect->fBottom) { 1199 if (clipRect && stop_y > clipRect->fBottom) {
1167 stop_y = clipRect->fBottom; 1200 stop_y = clipRect->fBottom;
1168 } 1201 }
1169 1202
1170 if (!path.isInverseFillType() && path.isConvex()) { 1203 if (!path.isInverseFillType() && path.isConvex()) {
1171 SkASSERT(count >= 2); // convex walker does not handle missing right e dges 1204 SkASSERT(count >= 2); // convex walker does not handle missing right e dges
1172 aaa_walk_convex_edges(&headEdge, blitter, start_y, stop_y, 1205 aaa_walk_convex_edges(&headEdge, blitter, start_y, stop_y,
1173 rect.fLeft << 16, rect.fRight << 16, isUsingMask); 1206 rect.fLeft << 16, rect.fRight << 16, isUsingMask,
1207 forceRLE);
1174 } else { 1208 } else {
1175 SkFAIL("Concave AAA is not yet implemented!"); 1209 SkFAIL("Concave AAA is not yet implemented!");
1176 } 1210 }
1177 } 1211 }
1178 1212
1179 /////////////////////////////////////////////////////////////////////////////// 1213 ///////////////////////////////////////////////////////////////////////////////
1180 1214
1181 void SkScan::AAAFillPath(const SkPath& path, const SkRegion& origClip, SkBlitter * blitter) { 1215 void SkScan::AAAFillPath(const SkPath& path, const SkRegion& origClip, SkBlitter * blitter,
1216 bool forceRLE) {
1182 if (origClip.isEmpty()) { 1217 if (origClip.isEmpty()) {
1183 return; 1218 return;
1184 } 1219 }
1185 1220
1186 const bool isInverse = path.isInverseFillType(); 1221 const bool isInverse = path.isInverseFillType();
1187 SkIRect ir; 1222 SkIRect ir;
1188 path.getBounds().roundOut(&ir); 1223 path.getBounds().roundOut(&ir);
1189 if (ir.isEmpty()) { 1224 if (ir.isEmpty()) {
1190 if (isInverse) { 1225 if (isInverse) {
1191 blitter->blitRegion(origClip); 1226 blitter->blitRegion(origClip);
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
1237 blitter = clipper.getBlitter(); 1272 blitter = clipper.getBlitter();
1238 1273
1239 if (isInverse) { 1274 if (isInverse) {
1240 // Currently, we use the old path to render the inverse path, 1275 // Currently, we use the old path to render the inverse path,
1241 // so we don't need this. 1276 // so we don't need this.
1242 // sk_blit_above(blitter, ir, *clipRgn); 1277 // sk_blit_above(blitter, ir, *clipRgn);
1243 } 1278 }
1244 1279
1245 SkASSERT(SkIntToScalar(ir.fTop) <= path.getBounds().fTop); 1280 SkASSERT(SkIntToScalar(ir.fTop) <= path.getBounds().fTop);
1246 1281
1247 if (MaskAdditiveBlitter::canHandleRect(ir) && !isInverse) { 1282 if (MaskAdditiveBlitter::canHandleRect(ir) && !isInverse && !forceRLE) {
1248 MaskAdditiveBlitter additiveBlitter(blitter, ir, *clipRgn, isInverse); 1283 MaskAdditiveBlitter additiveBlitter(blitter, ir, *clipRgn, isInverse);
1249 aaa_fill_path(path, clipRect, &additiveBlitter, ir.fTop, ir.fBottom, *cl ipRgn, true); 1284 aaa_fill_path(path, clipRect, &additiveBlitter, ir.fTop, ir.fBottom, *cl ipRgn, true,
1285 forceRLE);
1250 } else { 1286 } else {
1251 RunBasedAdditiveBlitter additiveBlitter(blitter, ir, *clipRgn, isInverse ); 1287 RunBasedAdditiveBlitter additiveBlitter(blitter, ir, *clipRgn, isInverse );
1252 aaa_fill_path(path, clipRect, &additiveBlitter, ir.fTop, ir.fBottom, *cl ipRgn, false); 1288 aaa_fill_path(path, clipRect, &additiveBlitter, ir.fTop, ir.fBottom, *cl ipRgn, false,
1289 forceRLE);
1253 } 1290 }
1254 1291
1255 if (isInverse) { 1292 if (isInverse) {
1256 // Currently, we use the old path to render the inverse path, 1293 // Currently, we use the old path to render the inverse path,
1257 // so we don't need this. 1294 // so we don't need this.
1258 // sk_blit_below(blitter, ir, *clipRgn); 1295 // sk_blit_below(blitter, ir, *clipRgn);
1259 } 1296 }
1260 } 1297 }
1261 1298
1262 // This almost copies SkScan::AntiFillPath 1299 // This almost copies SkScan::AntiFillPath
1263 void SkScan::AAAFillPath(const SkPath& path, const SkRasterClip& clip, SkBlitter * blitter) { 1300 void SkScan::AAAFillPath(const SkPath& path, const SkRasterClip& clip, SkBlitter * blitter) {
1264 if (clip.isEmpty()) { 1301 if (clip.isEmpty()) {
1265 return; 1302 return;
1266 } 1303 }
1267 1304
1268 if (clip.isBW()) { 1305 if (clip.isBW()) {
1269 AAAFillPath(path, clip.bwRgn(), blitter); 1306 AAAFillPath(path, clip.bwRgn(), blitter);
1270 } else { 1307 } else {
1271 SkRegion tmp; 1308 SkRegion tmp;
1272 SkAAClipBlitter aaBlitter; 1309 SkAAClipBlitter aaBlitter;
1273 1310
1274 tmp.setRect(clip.getBounds()); 1311 tmp.setRect(clip.getBounds());
1275 aaBlitter.init(blitter, &clip.aaRgn()); 1312 aaBlitter.init(blitter, &clip.aaRgn());
1276 AAAFillPath(path, tmp, &aaBlitter); 1313 AAAFillPath(path, tmp, &aaBlitter);
1277 } 1314 }
1278 } 1315 }
OLDNEW
« no previous file with comments | « src/core/SkScan.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698