1533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org/* 2533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org * Copyright 2013 The Android Open Source Project 3533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org * 4533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org * Use of this source code is governed by a BSD-style license that can be 5533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org * found in the LICENSE file. 6533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org */ 7533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 8533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org#include "SkPictureImageFilter.h" 9533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org#include "SkDevice.h" 10533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org#include "SkCanvas.h" 118b0e8ac5f582de80356019406e2975079bf0829dcommit-bot@chromium.org#include "SkReadBuffer.h" 128b0e8ac5f582de80356019406e2975079bf0829dcommit-bot@chromium.org#include "SkWriteBuffer.h" 13533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org#include "SkValidationUtils.h" 14533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 15533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.orgSkPictureImageFilter::SkPictureImageFilter(SkPicture* picture) 16533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org : INHERITED(0, 0), 17533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org fPicture(picture), 18cac5fd597f6e2495f50aaa6bcbe3dadc56f0b977commit-bot@chromium.org fCropRect(SkRect::MakeWH(picture ? SkIntToScalar(picture->width()) : 0, 19cac5fd597f6e2495f50aaa6bcbe3dadc56f0b977commit-bot@chromium.org picture ? SkIntToScalar(picture->height()) : 0)) { 20533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org SkSafeRef(fPicture); 21533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org} 22533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 23cac5fd597f6e2495f50aaa6bcbe3dadc56f0b977commit-bot@chromium.orgSkPictureImageFilter::SkPictureImageFilter(SkPicture* picture, const SkRect& cropRect) 24533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org : INHERITED(0, 0), 25533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org fPicture(picture), 26cac5fd597f6e2495f50aaa6bcbe3dadc56f0b977commit-bot@chromium.org fCropRect(cropRect) { 27533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org SkSafeRef(fPicture); 28533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org} 29533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 30533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.orgSkPictureImageFilter::~SkPictureImageFilter() { 31533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org SkSafeUnref(fPicture); 32533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org} 33533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 348b0e8ac5f582de80356019406e2975079bf0829dcommit-bot@chromium.orgSkPictureImageFilter::SkPictureImageFilter(SkReadBuffer& buffer) 35533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org : INHERITED(0, buffer), 36533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org fPicture(NULL) { 3797f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org if (!buffer.isCrossProcess()) { 3897f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org if (buffer.readBool()) { 3997f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org fPicture = SkPicture::CreateFromBuffer(buffer); 4097f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org } 4197f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org } else { 4297f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org buffer.validate(!buffer.readBool()); 435e0995e4b36178e1e4465a9f50114ed39f038c27commit-bot@chromium.org } 44cac5fd597f6e2495f50aaa6bcbe3dadc56f0b977commit-bot@chromium.org buffer.readRect(&fCropRect); 45533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org} 46533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 478b0e8ac5f582de80356019406e2975079bf0829dcommit-bot@chromium.orgvoid SkPictureImageFilter::flatten(SkWriteBuffer& buffer) const { 48533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org this->INHERITED::flatten(buffer); 4997f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org if (!buffer.isCrossProcess()) { 5097f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org bool hasPicture = (fPicture != NULL); 5197f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org buffer.writeBool(hasPicture); 5297f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org if (hasPicture) { 5397f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org fPicture->flatten(buffer); 5497f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org } 5597f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org } else { 5697f5fc651956287e78e35934cf62b9e1b45b4f6csenorblanco@chromium.org buffer.writeBool(false); 575e0995e4b36178e1e4465a9f50114ed39f038c27commit-bot@chromium.org } 58cac5fd597f6e2495f50aaa6bcbe3dadc56f0b977commit-bot@chromium.org buffer.writeRect(fCropRect); 59533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org} 60533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 614cb543d6057b692e1099e9f115155f0bf323a0c8senorblanco@chromium.orgbool SkPictureImageFilter::onFilterImage(Proxy* proxy, const SkBitmap&, const Context& ctx, 624cb543d6057b692e1099e9f115155f0bf323a0c8senorblanco@chromium.org SkBitmap* result, SkIPoint* offset) const { 63533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org if (!fPicture) { 646776b82d466fa93ccffd251fdf556fe058395444senorblanco@chromium.org offset->fX = offset->fY = 0; 65533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org return true; 66533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org } 67533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 68533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org SkRect floatBounds; 69533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org SkIRect bounds; 704cb543d6057b692e1099e9f115155f0bf323a0c8senorblanco@chromium.org ctx.ctm().mapRect(&floatBounds, fCropRect); 71533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org floatBounds.roundOut(&bounds); 72533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 73533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org if (bounds.isEmpty()) { 746776b82d466fa93ccffd251fdf556fe058395444senorblanco@chromium.org offset->fX = offset->fY = 0; 75533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org return true; 76533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org } 77533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 78533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org SkAutoTUnref<SkBaseDevice> device(proxy->createDevice(bounds.width(), bounds.height())); 79533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org if (NULL == device.get()) { 80533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org return false; 81533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org } 82533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 83533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org SkCanvas canvas(device.get()); 84533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org SkPaint paint; 85533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 86533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org canvas.translate(-SkIntToScalar(bounds.fLeft), -SkIntToScalar(bounds.fTop)); 874cb543d6057b692e1099e9f115155f0bf323a0c8senorblanco@chromium.org canvas.concat(ctx.ctm()); 889b14f26d0f3a974f3dd626c8354e1db1cfcd322frobertphillips canvas.drawPicture(fPicture); 89533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org 90533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org *result = device.get()->accessBitmap(false); 916776b82d466fa93ccffd251fdf556fe058395444senorblanco@chromium.org offset->fX = bounds.fLeft; 926776b82d466fa93ccffd251fdf556fe058395444senorblanco@chromium.org offset->fY = bounds.fTop; 93533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org return true; 94533330065a28b51808e5bf564ae45e56f8d9956asenorblanco@chromium.org} 95910702b564048d77e36a68b0f8dda7cc48a8fcffsenorblanco@chromium.org 96910702b564048d77e36a68b0f8dda7cc48a8fcffsenorblanco@chromium.orgbool SkPictureImageFilter::onFilterBounds(const SkIRect& src, const SkMatrix& ctm, 97910702b564048d77e36a68b0f8dda7cc48a8fcffsenorblanco@chromium.org SkIRect* dst) const { 98910702b564048d77e36a68b0f8dda7cc48a8fcffsenorblanco@chromium.org *dst = src; 99910702b564048d77e36a68b0f8dda7cc48a8fcffsenorblanco@chromium.org return true; 100910702b564048d77e36a68b0f8dda7cc48a8fcffsenorblanco@chromium.org} 101910702b564048d77e36a68b0f8dda7cc48a8fcffsenorblanco@chromium.org 102