1 2 #include "SkTestImageFilters.h" 3 #include "SkCanvas.h" 4 #include "SkDevice.h" 5 #include "SkReadBuffer.h" 6 #include "SkWriteBuffer.h" 7 8 // Simple helper canvas that "takes ownership" of the provided device, so that 9 // when this canvas goes out of scope, so will its device. Could be replaced 10 // with the following: 11 // 12 // SkCanvas canvas(device); 13 // SkAutoTUnref<SkBaseDevice> aur(device); 14 // 15 class OwnDeviceCanvas : public SkCanvas { 16 public: 17 OwnDeviceCanvas(SkBaseDevice* device) : SkCanvas(device) { 18 SkSafeUnref(device); 19 } 20 }; 21 22 /////////////////////////////////////////////////////////////////////////////// 23 24 bool SkDownSampleImageFilter::onFilterImage(Proxy* proxy, const SkBitmap& src, 25 const Context&, 26 SkBitmap* result, SkIPoint*) const { 27 SkScalar scale = fScale; 28 if (scale > SK_Scalar1 || scale <= 0) { 29 return false; 30 } 31 32 int dstW = SkScalarRoundToInt(src.width() * scale); 33 int dstH = SkScalarRoundToInt(src.height() * scale); 34 if (dstW < 1) { 35 dstW = 1; 36 } 37 if (dstH < 1) { 38 dstH = 1; 39 } 40 41 SkBitmap tmp; 42 43 // downsample 44 { 45 SkBaseDevice* dev = proxy->createDevice(dstW, dstH); 46 if (NULL == dev) { 47 return false; 48 } 49 OwnDeviceCanvas canvas(dev); 50 SkPaint paint; 51 52 paint.setFilterLevel(SkPaint::kLow_FilterLevel); 53 canvas.scale(scale, scale); 54 canvas.drawBitmap(src, 0, 0, &paint); 55 tmp = dev->accessBitmap(false); 56 } 57 58 // upscale 59 { 60 SkBaseDevice* dev = proxy->createDevice(src.width(), src.height()); 61 if (NULL == dev) { 62 return false; 63 } 64 OwnDeviceCanvas canvas(dev); 65 66 SkRect r = SkRect::MakeWH(SkIntToScalar(src.width()), 67 SkIntToScalar(src.height())); 68 canvas.drawBitmapRect(tmp, NULL, r, NULL); 69 *result = dev->accessBitmap(false); 70 } 71 return true; 72 } 73 74 void SkDownSampleImageFilter::flatten(SkWriteBuffer& buffer) const { 75 this->INHERITED::flatten(buffer); 76 77 buffer.writeScalar(fScale); 78 } 79 80 SkDownSampleImageFilter::SkDownSampleImageFilter(SkReadBuffer& buffer) 81 : INHERITED(1, buffer) { 82 fScale = buffer.readScalar(); 83 buffer.validate(SkScalarIsFinite(fScale)); 84 } 85