| OLD | NEW |
| 1 | 1 |
| 2 /* | 2 /* |
| 3 * Copyright 2011 Google Inc. | 3 * Copyright 2011 Google Inc. |
| 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 "SkPDFShader.h" | 10 #include "SkPDFShader.h" |
| 11 | 11 |
| 12 #include "SkData.h" | 12 #include "SkData.h" |
| 13 #include "SkPDFCanon.h" | 13 #include "SkPDFCanon.h" |
| 14 #include "SkPDFCatalog.h" | 14 #include "SkPDFCatalog.h" |
| 15 #include "SkPDFDevice.h" | 15 #include "SkPDFDevice.h" |
| 16 #include "SkPDFFormXObject.h" | 16 #include "SkPDFFormXObject.h" |
| 17 #include "SkPDFGraphicState.h" | 17 #include "SkPDFGraphicState.h" |
| 18 #include "SkPDFResourceDict.h" | 18 #include "SkPDFResourceDict.h" |
| 19 #include "SkPDFUtils.h" | 19 #include "SkPDFUtils.h" |
| 20 #include "SkScalar.h" | 20 #include "SkScalar.h" |
| 21 #include "SkStream.h" | 21 #include "SkStream.h" |
| 22 #include "SkTemplates.h" | 22 #include "SkTemplates.h" |
| 23 #include "SkThread.h" | 23 #include "SkThread.h" |
| 24 #include "SkTSet.h" | 24 #include "SkTSet.h" |
| 25 #include "SkTypes.h" | 25 #include "SkTypes.h" |
| 26 | 26 |
| 27 static bool inverseTransformBBox(const SkMatrix& matrix, SkRect* bbox) { | 27 static bool inverse_transform_bbox(const SkMatrix& matrix, SkRect* bbox) { |
| 28 SkMatrix inverse; | 28 SkMatrix inverse; |
| 29 if (!matrix.invert(&inverse)) { | 29 if (!matrix.invert(&inverse)) { |
| 30 return false; | 30 return false; |
| 31 } | 31 } |
| 32 inverse.mapRect(bbox); | 32 inverse.mapRect(bbox); |
| 33 return true; | 33 return true; |
| 34 } | 34 } |
| 35 | 35 |
| 36 static void unitToPointsMatrix(const SkPoint pts[2], SkMatrix* matrix) { | 36 static void unitToPointsMatrix(const SkPoint pts[2], SkMatrix* matrix) { |
| 37 SkVector vec = pts[1] - pts[0]; | 37 SkVector vec = pts[1] - pts[0]; |
| (...skipping 804 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 842 SkMatrix perspectiveInverseOnly = SkMatrix::I(); | 842 SkMatrix perspectiveInverseOnly = SkMatrix::I(); |
| 843 if (finalMatrix.hasPerspective()) { | 843 if (finalMatrix.hasPerspective()) { |
| 844 if (!split_perspective(finalMatrix, | 844 if (!split_perspective(finalMatrix, |
| 845 &finalMatrix, &perspectiveInverseOnly)) { | 845 &finalMatrix, &perspectiveInverseOnly)) { |
| 846 return NULL; | 846 return NULL; |
| 847 } | 847 } |
| 848 } | 848 } |
| 849 | 849 |
| 850 SkRect bbox; | 850 SkRect bbox; |
| 851 bbox.set(state.fBBox); | 851 bbox.set(state.fBBox); |
| 852 if (!inverseTransformBBox(finalMatrix, &bbox)) { | 852 if (!inverse_transform_bbox(finalMatrix, &bbox)) { |
| 853 return NULL; | 853 return NULL; |
| 854 } | 854 } |
| 855 | 855 |
| 856 SkAutoTUnref<SkPDFArray> domain(new SkPDFArray); | 856 SkAutoTUnref<SkPDFArray> domain(new SkPDFArray); |
| 857 domain->reserve(4); | 857 domain->reserve(4); |
| 858 domain->appendScalar(bbox.fLeft); | 858 domain->appendScalar(bbox.fLeft); |
| 859 domain->appendScalar(bbox.fRight); | 859 domain->appendScalar(bbox.fRight); |
| 860 domain->appendScalar(bbox.fTop); | 860 domain->appendScalar(bbox.fTop); |
| 861 domain->appendScalar(bbox.fBottom); | 861 domain->appendScalar(bbox.fBottom); |
| 862 | 862 |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 915 // The image shader pattern cell will be drawn into a separate device | 915 // The image shader pattern cell will be drawn into a separate device |
| 916 // in pattern cell space (no scaling on the bitmap, though there may be | 916 // in pattern cell space (no scaling on the bitmap, though there may be |
| 917 // translations so that all content is in the device, coordinates > 0). | 917 // translations so that all content is in the device, coordinates > 0). |
| 918 | 918 |
| 919 // Map clip bounds to shader space to ensure the device is large enough | 919 // Map clip bounds to shader space to ensure the device is large enough |
| 920 // to handle fake clamping. | 920 // to handle fake clamping. |
| 921 SkMatrix finalMatrix = state.fCanvasTransform; | 921 SkMatrix finalMatrix = state.fCanvasTransform; |
| 922 finalMatrix.preConcat(state.fShaderTransform); | 922 finalMatrix.preConcat(state.fShaderTransform); |
| 923 SkRect deviceBounds; | 923 SkRect deviceBounds; |
| 924 deviceBounds.set(state.fBBox); | 924 deviceBounds.set(state.fBBox); |
| 925 if (!inverseTransformBBox(finalMatrix, &deviceBounds)) { | 925 if (!inverse_transform_bbox(finalMatrix, &deviceBounds)) { |
| 926 return NULL; | 926 return NULL; |
| 927 } | 927 } |
| 928 | 928 |
| 929 const SkBitmap* image = &state.fImage; | 929 const SkBitmap* image = &state.fImage; |
| 930 SkRect bitmapBounds; | 930 SkRect bitmapBounds; |
| 931 image->getBounds(&bitmapBounds); | 931 image->getBounds(&bitmapBounds); |
| 932 | 932 |
| 933 // For tiling modes, the bounds should be extended to include the bitmap, | 933 // For tiling modes, the bounds should be extended to include the bitmap, |
| 934 // otherwise the bitmap gets clipped out and the shader is empty and awful. | 934 // otherwise the bitmap gets clipped out and the shader is empty and awful. |
| 935 // For clamp modes, we're only interested in the clip region, whether | 935 // For clamp modes, we're only interested in the clip region, whether |
| (...skipping 257 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1193 if (fType == SkShader::kNone_GradientType) { | 1193 if (fType == SkShader::kNone_GradientType) { |
| 1194 SkShader::BitmapType bitmapType; | 1194 SkShader::BitmapType bitmapType; |
| 1195 SkMatrix matrix; | 1195 SkMatrix matrix; |
| 1196 bitmapType = shader.asABitmap(&fImage, &matrix, fImageTileModes); | 1196 bitmapType = shader.asABitmap(&fImage, &matrix, fImageTileModes); |
| 1197 if (bitmapType != SkShader::kDefault_BitmapType) { | 1197 if (bitmapType != SkShader::kDefault_BitmapType) { |
| 1198 // Generic fallback for unsupported shaders: | 1198 // Generic fallback for unsupported shaders: |
| 1199 // * allocate a bbox-sized bitmap | 1199 // * allocate a bbox-sized bitmap |
| 1200 // * shade the whole area | 1200 // * shade the whole area |
| 1201 // * use the result as a bitmap shader | 1201 // * use the result as a bitmap shader |
| 1202 | 1202 |
| 1203 // bbox is in device space. While that's exactly what we want for si
zing our bitmap, |
| 1204 // we need to map it into shader space for adjustments (to match |
| 1205 // SkPDFImageShader::Create's behavior). |
| 1206 SkRect shaderRect = SkRect::Make(bbox); |
| 1207 if (!inverse_transform_bbox(canvasTransform, &shaderRect)) { |
| 1208 fImage.reset(); |
| 1209 return; |
| 1210 } |
| 1211 |
| 1203 // Clamp the bitmap size to about 1M pixels | 1212 // Clamp the bitmap size to about 1M pixels |
| 1204 static const SkScalar kMaxBitmapArea = 1024 * 1024; | 1213 static const SkScalar kMaxBitmapArea = 1024 * 1024; |
| 1205 SkScalar bitmapArea = rasterScale * bbox.width() * rasterScale * bbo
x.height(); | 1214 SkScalar bitmapArea = rasterScale * bbox.width() * rasterScale * bbo
x.height(); |
| 1206 if (bitmapArea > kMaxBitmapArea) { | 1215 if (bitmapArea > kMaxBitmapArea) { |
| 1207 rasterScale *= SkScalarSqrt(SkScalarDiv(kMaxBitmapArea, bitmapAr
ea)); | 1216 rasterScale *= SkScalarSqrt(SkScalarDiv(kMaxBitmapArea, bitmapAr
ea)); |
| 1208 } | 1217 } |
| 1209 | 1218 |
| 1210 SkISize size = SkISize::Make(SkScalarRoundToInt(rasterScale * bbox.w
idth()), | 1219 SkISize size = SkISize::Make(SkScalarRoundToInt(rasterScale * bbox.w
idth()), |
| 1211 SkScalarRoundToInt(rasterScale * bbox.h
eight())); | 1220 SkScalarRoundToInt(rasterScale * bbox.h
eight())); |
| 1212 SkSize scale = SkSize::Make(SkIntToScalar(size.width()) / SkIntToSca
lar(bbox.width()), | 1221 SkSize scale = SkSize::Make(SkIntToScalar(size.width()) / shaderRect
.width(), |
| 1213 SkIntToScalar(size.height()) / SkIntToSc
alar(bbox.height())); | 1222 SkIntToScalar(size.height()) / shaderRec
t.height()); |
| 1214 | 1223 |
| 1215 fImage.allocN32Pixels(size.width(), size.height()); | 1224 fImage.allocN32Pixels(size.width(), size.height()); |
| 1216 fImage.eraseColor(SK_ColorTRANSPARENT); | 1225 fImage.eraseColor(SK_ColorTRANSPARENT); |
| 1217 | 1226 |
| 1218 SkPaint p; | 1227 SkPaint p; |
| 1219 p.setShader(const_cast<SkShader*>(&shader)); | 1228 p.setShader(const_cast<SkShader*>(&shader)); |
| 1220 | 1229 |
| 1221 SkCanvas canvas(fImage); | 1230 SkCanvas canvas(fImage); |
| 1222 canvas.scale(scale.width(), scale.height()); | 1231 canvas.scale(scale.width(), scale.height()); |
| 1223 canvas.translate(-SkIntToScalar(bbox.x()), -SkIntToScalar(bbox.y()))
; | 1232 canvas.translate(-shaderRect.x(), -shaderRect.y()); |
| 1224 canvas.drawPaint(p); | 1233 canvas.drawPaint(p); |
| 1225 | 1234 |
| 1226 fShaderTransform.setTranslate(SkIntToScalar(bbox.x()), SkIntToScalar
(bbox.y())); | 1235 fShaderTransform.setTranslate(shaderRect.x(), shaderRect.y()); |
| 1227 fShaderTransform.preScale(1 / scale.width(), 1 / scale.height()); | 1236 fShaderTransform.preScale(1 / scale.width(), 1 / scale.height()); |
| 1228 } else { | 1237 } else { |
| 1229 SkASSERT(matrix.isIdentity()); | 1238 SkASSERT(matrix.isIdentity()); |
| 1230 } | 1239 } |
| 1231 fPixelGeneration = fImage.getGenerationID(); | 1240 fPixelGeneration = fImage.getGenerationID(); |
| 1232 } else { | 1241 } else { |
| 1233 AllocateGradientInfoStorage(); | 1242 AllocateGradientInfoStorage(); |
| 1234 shader.asAGradient(&fInfo); | 1243 shader.asAGradient(&fInfo); |
| 1235 } | 1244 } |
| 1236 } | 1245 } |
| (...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1306 return false; | 1315 return false; |
| 1307 } | 1316 } |
| 1308 | 1317 |
| 1309 void SkPDFShader::State::AllocateGradientInfoStorage() { | 1318 void SkPDFShader::State::AllocateGradientInfoStorage() { |
| 1310 fColorData.set(sk_malloc_throw( | 1319 fColorData.set(sk_malloc_throw( |
| 1311 fInfo.fColorCount * (sizeof(SkColor) + sizeof(SkScalar)))); | 1320 fInfo.fColorCount * (sizeof(SkColor) + sizeof(SkScalar)))); |
| 1312 fInfo.fColors = reinterpret_cast<SkColor*>(fColorData.get()); | 1321 fInfo.fColors = reinterpret_cast<SkColor*>(fColorData.get()); |
| 1313 fInfo.fColorOffsets = | 1322 fInfo.fColorOffsets = |
| 1314 reinterpret_cast<SkScalar*>(fInfo.fColors + fInfo.fColorCount); | 1323 reinterpret_cast<SkScalar*>(fInfo.fColors + fInfo.fColorCount); |
| 1315 } | 1324 } |
| OLD | NEW |