Index: src/effects/SkColorMatrixFilter.cpp |
diff --git a/src/effects/SkColorMatrixFilter.cpp b/src/effects/SkColorMatrixFilter.cpp |
index 319617016c20dec09b32edd773d75747d435458a..a63666e4c0dd4d114a06510da13d2dcb01d87731 100644 |
--- a/src/effects/SkColorMatrixFilter.cpp |
+++ b/src/effects/SkColorMatrixFilter.cpp |
@@ -137,6 +137,9 @@ |
result[3] = a; |
} |
+#define kNO_ALPHA_FLAGS (SkColorFilter::kAlphaUnchanged_Flag | \ |
+ SkColorFilter::kHasFilter16_Flag) |
+ |
// src is [20] but some compilers won't accept __restrict__ on anything |
// but an raw pointer or reference |
void SkColorMatrixFilter::initState(const SkScalar* SK_RESTRICT src) { |
@@ -178,7 +181,7 @@ |
fProc = shiftIs16 ? General16 : General; |
fFlags = changesAlpha ? 0 : SkColorFilter::kAlphaUnchanged_Flag; |
} else { |
- fFlags = SkColorFilter::kAlphaUnchanged_Flag; |
+ fFlags = kNO_ALPHA_FLAGS; |
int32_t needsScale = (array[SkColorMatrix::kR_Scale] - one) | |
(array[SkColorMatrix::kG_Scale] - one) | |
@@ -357,6 +360,40 @@ |
// re-prepremultiply if needed |
dst[i] = SkPremultiplyARGBInline(a, r, g, b); |
} |
+ } |
+} |
+ |
+void SkColorMatrixFilter::filterSpan16(const uint16_t src[], int count, |
+ uint16_t dst[]) const { |
+ SkASSERT(fFlags & SkColorFilter::kHasFilter16_Flag); |
+ |
+ Proc proc = fProc; |
+ const State& state = fState; |
+ int32_t result[4]; |
+ |
+ if (NULL == proc) { |
+ if (src != dst) { |
+ memcpy(dst, src, count * sizeof(uint16_t)); |
+ } |
+ return; |
+ } |
+ |
+ for (int i = 0; i < count; i++) { |
+ uint16_t c = src[i]; |
+ |
+ // expand to 8bit components (since our matrix translate is 8bit biased |
+ unsigned r = SkPacked16ToR32(c); |
+ unsigned g = SkPacked16ToG32(c); |
+ unsigned b = SkPacked16ToB32(c); |
+ |
+ proc(state, r, g, b, 0, result); |
+ |
+ r = pin(result[0], SK_R32_MASK); |
+ g = pin(result[1], SK_G32_MASK); |
+ b = pin(result[2], SK_B32_MASK); |
+ |
+ // now packed it back down to 16bits (hmmm, could dither...) |
+ dst[i] = SkPack888ToRGB16(r, g, b); |
} |
} |