示例#1
0
ImageTexture::ImageTexture(SkBitmapRef* img)
    : m_imageRef(img)
    , m_image(0)
    , m_textureId(0)
    , m_refCount(0)
{
#ifdef DEBUG_COUNT
    ClassTracker::instance()->increment("ImageTexture");
#endif
    if (!m_imageRef)
        return;

    SkBitmap* bitmap = &m_imageRef->bitmap();
    m_image = new SkBitmap();
    int w = bitmap->width();
    int h = bitmap->height();
    m_image->setConfig(SkBitmap::kARGB_8888_Config, w, h);
    m_image->allocPixels();
    SkDevice* device = new SkDevice(NULL, *m_image, false);
    SkCanvas canvas;
    canvas.setDevice(device);
    device->unref();
    SkRect dest;
    dest.set(0, 0, w, h);
    m_image->setIsOpaque(false);
    m_image->eraseARGB(0, 0, 0, 0);
    canvas.drawBitmapRect(*bitmap, 0, dest);
}
示例#2
0
static void make_bitmap(SkBitmap* bitmap, GrContext* ctx)
    {
    SkCanvas canvas;

    if (ctx)
        {
        SkDevice* dev = new SkGpuDevice(ctx, SkBitmap::kARGB_8888_Config, 64, 64);
        canvas.setDevice(dev)->unref();
        *bitmap = dev->accessBitmap(false);
        }
    else
        {
        bitmap->setConfig(SkBitmap::kARGB_8888_Config, 64, 64);
        bitmap->allocPixels();
        canvas.setBitmapDevice(*bitmap);
        }

    canvas.drawColor(SK_ColorRED);
    SkPaint paint;
    paint.setAntiAlias(true);
    const SkPoint pts[] = { { 0, 0 }, { 64, 64 } };
    const SkColor colors[] = { SK_ColorWHITE, SK_ColorBLUE };
    paint.setShader(SkGradientShader::CreateLinear(pts, colors, NULL, 2,
                    SkShader::kClamp_TileMode))->unref();
    canvas.drawCircle(32, 32, 32, paint);
    }
示例#3
0
TiledPipeController::TiledPipeController(const SkBitmap& bitmap,
                                         const SkMatrix* initial)
: INHERITED(NULL) {
    int32_t top = 0;
    int32_t bottom;
    int32_t height = bitmap.height() / NumberOfTiles;
    SkIRect rect;
    for (int i = 0; i < NumberOfTiles; i++) {
        bottom = i + 1 == NumberOfTiles ? bitmap.height() : top + height;
        rect.setLTRB(0, top, bitmap.width(), bottom);
        top = bottom;

        bool extracted = bitmap.extractSubset(&fBitmaps[i], rect);
        SkASSERT(extracted);
        SkDevice* device = new SkDevice(fBitmaps[i]);
        SkCanvas* canvas = new SkCanvas(device);
        device->unref();
        if (initial != NULL) {
            canvas->setMatrix(*initial);
        }
        canvas->translate(SkIntToScalar(-rect.left()),
                          SkIntToScalar(-rect.top()));
        if (0 == i) {
            fReader.setCanvas(canvas);
        } else {
            fReaders[i - 1].setCanvas(canvas);
        }
        canvas->unref();
    }
}
示例#4
0
	~DeviceCM() {
        if (NULL != fDevice) {
            fDevice->unlockPixels();
            fDevice->unref();
        }
		SkDELETE(fPaint);
	}
示例#5
0
static SkBitmap createBitmap(const SkPath& path) {
    SkBitmap bitmap;
    bitmap.setConfig(SkBitmap::kARGB_8888_Config,
                     SkImageWidget::kImageWidgetWidth,
                     SkImageWidget::kImageWidgetHeight);
    bitmap.allocPixels();
    bitmap.eraseColor(SK_ColorWHITE);
    SkDevice* device = new SkDevice(bitmap);

    SkCanvas canvas(device);
    device->unref();

    const SkRect& bounds = path.getBounds();

    if (bounds.width() > bounds.height()) {
        canvas.scale(SkDoubleToScalar((0.9*SkImageWidget::kImageWidgetWidth)/bounds.width()),
                     SkDoubleToScalar((0.9*SkImageWidget::kImageWidgetHeight)/bounds.width()));
    } else {
        canvas.scale(SkDoubleToScalar((0.9*SkImageWidget::kImageWidgetWidth)/bounds.height()),
                     SkDoubleToScalar((0.9*SkImageWidget::kImageWidgetHeight)/bounds.height()));
    }
    canvas.translate(-bounds.fLeft+2, -bounds.fTop+2);

    SkPaint p;
    p.setColor(SK_ColorBLACK);
    p.setStyle(SkPaint::kStroke_Style);

    canvas.drawPath(path, p);

    return bitmap;
}
示例#6
0
static void
_canvas_device_region(SkCanvas *canvas, SkRegion *region) {
    SkDevice *device;
    int w, h;

    device = canvas->getDevice();
    w = device->width();
    h = device->height();
    region->setRect(0, 0, w, h);
}
bool SkGpuCanvas::getViewport(SkIPoint* size) const {
    if (size) {
        SkDevice* device = this->getDevice();
        if (device) {
            size->set(device->width(), device->height());
        } else {
            size->set(0, 0);
        }
    }
    return true;
}
示例#8
0
String ImageBuffer::toDataURL(const String& mimeType, const double* quality) const
{
    ASSERT(MIMETypeRegistry::isSupportedImageMIMETypeForEncoding(mimeType));

    Vector<char> encodedImage, base64Data;
    SkDevice* device = context()->platformContext()->canvas()->getDevice();
    if (!encodeImage(device->accessBitmap(false), mimeType, quality, &encodedImage))
        return "data:,";

    base64Encode(encodedImage, base64Data);
    return "data:" + mimeType + ";base64," + base64Data;
}
/// M: added for HTML5-benchmark performance @{
PassRefPtr<Image> ImageBuffer::getContextImageRef() const
{
    SkCanvas* canvas = imageBufferCanvas(this);
    if (!canvas)
        return 0;
    SkDevice* device = canvas->getDevice();
    const SkBitmap& orig = device->accessBitmap(false);

    SkBitmapRef* ref = new SkBitmapRef(orig);
    RefPtr<Image> image = BitmapImage::create(ref, 0);
    ref->unref();

    return image;
}
bool SkMergeImageFilter::onFilterImage(Proxy* proxy, const SkBitmap& src,
                                       const SkMatrix& ctm,
                                       SkBitmap* result, SkIPoint* loc) {
    if (fCount < 1) {
        return false;
    }

    const SkIRect srcBounds = SkIRect::MakeXYWH(loc->x(), loc->y(),
                                                src.width(), src.height());
    SkIRect bounds;
    if (!this->filterBounds(srcBounds, ctm, &bounds)) {
        return false;
    }

    const int x0 = bounds.left();
    const int y0 = bounds.top();

    SkDevice* dst = proxy->createDevice(bounds.width(), bounds.height());
    if (NULL == dst) {
        return false;
    }
    OwnDeviceCanvas canvas(dst);
    SkPaint paint;

    for (int i = 0; i < fCount; ++i) {
        SkBitmap tmp;
        const SkBitmap* srcPtr;
        SkIPoint pos = *loc;
        SkImageFilter* filter = fFilters[i];
        if (filter) {
            if (!filter->filterImage(proxy, src, ctm, &tmp, &pos)) {
                return false;
            }
            srcPtr = &tmp;
        } else {
            srcPtr = &src;
        }

        if (fModes) {
            paint.setXfermodeMode((SkXfermode::Mode)fModes[i]);
        } else {
            paint.setXfermode(NULL);
        }
        canvas.drawSprite(*srcPtr, pos.x() - x0, pos.y() - y0, &paint);
    }

    loc->set(bounds.left(), bounds.top());
    *result = dst->accessBitmap(false);
    return true;
}
bool SkDownSampleImageFilter::onFilterImage(Proxy* proxy, const SkBitmap& src,
                                            const SkMatrix& matrix,
                                            SkBitmap* result, SkIPoint*) {
    SkScalar scale = fScale;
    if (scale > SK_Scalar1 || scale <= 0) {
        return false;
    }

    int dstW = SkScalarRoundToInt(src.width() * scale);
    int dstH = SkScalarRoundToInt(src.height() * scale);
    if (dstW < 1) {
        dstW = 1;
    }
    if (dstH < 1) {
        dstH = 1;
    }

    SkBitmap tmp;

    // downsample
    {
        SkDevice* dev = proxy->createDevice(dstW, dstH);
        if (NULL == dev) {
            return false;
        }
        OwnDeviceCanvas canvas(dev);
        SkPaint paint;

        paint.setFilterBitmap(true);
        canvas.scale(scale, scale);
        canvas.drawBitmap(src, 0, 0, &paint);
        tmp = dev->accessBitmap(false);
    }

    // upscale
    {
        SkDevice* dev = proxy->createDevice(src.width(), src.height());
        if (NULL == dev) {
            return false;
        }
        OwnDeviceCanvas canvas(dev);

        SkRect r = SkRect::MakeWH(SkIntToScalar(src.width()),
                                  SkIntToScalar(src.height()));
        canvas.drawBitmapRect(tmp, NULL, r, NULL);
        *result = dev->accessBitmap(false);
    }
    return true;
}
String ImageBuffer::toDataURL(const String& mimeType, const double* quality) const
{
    SkDevice* device = context()->platformContext()->canvas()->getDevice();
    SkBitmap bitmap = device->accessBitmap(false);

    // if we can't see the pixels directly, call readPixels() to get a copy.
    // this could happen if the device is backed by a GPU.
    bitmap.lockPixels(); // balanced by our destructor, or explicitly if getPixels() fails
    if (!bitmap.getPixels()) {
        bitmap.unlockPixels();
        SkIRect bounds = SkIRect::MakeWH(device->width(), device->height());
        if (!device->readPixels(bounds, &bitmap))
            return "data:,";
    }

    return ImageToDataURL(bitmap, mimeType, quality);
}
PassRefPtr<Image> ImageBuffer::copyImage() const
{
    ASSERT(context());

    SkCanvas* canvas = imageBufferCanvas(this);
    if (!canvas)
      return 0;

    SkDevice* device = canvas->getDevice();
    const SkBitmap& orig = device->accessBitmap(false);

    SkBitmap copy;
    if (PlatformBridge::canSatisfyMemoryAllocation(orig.getSize()))
        orig.copyTo(&copy, orig.config());

    SkBitmapRef* ref = new SkBitmapRef(copy);
    RefPtr<Image> image = BitmapImage::create(ref, 0);
    ref->unref();
    return image;
}
示例#14
0
    void updateMC(const SkMatrix& totalMatrix, const SkRegion& totalClip,
                  const SkClipStack& clipStack, SkRegion* updateClip) {
        int x = fDevice->getOrigin().x();
        int y = fDevice->getOrigin().y();
        int width = fDevice->width();
        int height = fDevice->height();

        if ((x | y) == 0) {
            fMatrix = &totalMatrix;
            fClip = totalClip;
        } else {
            fMatrixStorage = totalMatrix;
            fMatrixStorage.postTranslate(SkIntToScalar(-x),
                                         SkIntToScalar(-y));
            fMatrix = &fMatrixStorage;

            totalClip.translate(-x, -y, &fClip);
        }

        fClip.op(0, 0, width, height, SkRegion::kIntersect_Op);

        // intersect clip, but don't translate it (yet)

        if (updateClip) {
            updateClip->op(x, y, x + width, y + height,
                           SkRegion::kDifference_Op);
        }

        fDevice->setMatrixClip(*fMatrix, fClip, clipStack);

#ifdef SK_DEBUG
        if (!fClip.isEmpty()) {
            SkIRect deviceR;
            deviceR.set(0, 0, width, height);
            SkASSERT(deviceR.contains(fClip.getBounds()));
        }
#endif
        // default is to assume no external matrix
        fMVMatrix = NULL;
        fExtMatrix = NULL;
    }
示例#15
0
static SkBitmap createBitmap(const SkBitmap& input, const SkRect* srcRect) {
    SkBitmap bitmap;
    bitmap.setConfig(SkBitmap::kARGB_8888_Config,
                     SkImageWidget::kImageWidgetWidth,
                     SkImageWidget::kImageWidgetHeight);
    bitmap.allocPixels();
    bitmap.eraseColor(SK_ColorLTGRAY);
    SkDevice* device = new SkDevice(bitmap);

    SkCanvas canvas(device);
    device->unref();

    SkScalar xScale = (SkImageWidget::kImageWidgetWidth-2.0) / input.width();
    SkScalar yScale = (SkImageWidget::kImageWidgetHeight-2.0) / input.height();

    if (input.width() > input.height()) {
        yScale *= input.height() / (float) input.width();
    } else {
        xScale *= input.width() / (float) input.height();
    }

    SkRect dst = SkRect::MakeXYWH(SK_Scalar1, SK_Scalar1,
                                  xScale * input.width(),
                                  yScale * input.height());

    canvas.drawBitmapRect(input, NULL, dst);

    if (NULL != srcRect) {
        SkRect r = SkRect::MakeLTRB(srcRect->fLeft * xScale + SK_Scalar1,
                                    srcRect->fTop * yScale + SK_Scalar1,
                                    srcRect->fRight * xScale + SK_Scalar1,
                                    srcRect->fBottom * yScale + SK_Scalar1);
        SkPaint p;
        p.setColor(SK_ColorRED);
        p.setStyle(SkPaint::kStroke_Style);

        canvas.drawRect(r, p);
    }

    return bitmap;
}
示例#16
0
static void make_bitmap(SkBitmap* bitmap, GrContext* ctx, SkIRect* center) {
    SkDevice* dev;
    SkCanvas canvas;

    const int kFixed = 28;
    const int kStretchy = 8;
    const int kSize = 2*kFixed + kStretchy;

#if SK_SUPPORT_GPU
    if (ctx) {
        dev = new SkGpuDevice(ctx, SkBitmap::kARGB_8888_Config, kSize, kSize);
        *bitmap = dev->accessBitmap(false);
    } else
#endif
    {
        bitmap->setConfig(SkBitmap::kARGB_8888_Config, kSize, kSize);
        bitmap->allocPixels();
        dev = new SkDevice(*bitmap);
    }

    canvas.setDevice(dev)->unref();
    canvas.clear(0);

    SkRect r = SkRect::MakeWH(SkIntToScalar(kSize), SkIntToScalar(kSize));
    const SkScalar strokeWidth = SkIntToScalar(6);
    const SkScalar radius = SkIntToScalar(kFixed) - strokeWidth/2;

    center->setXYWH(kFixed, kFixed, kStretchy, kStretchy);

    SkPaint paint;
    paint.setAntiAlias(true);

    paint.setColor(0xFFFF0000);
    canvas.drawRoundRect(r, radius, radius, paint);
    r.setXYWH(SkIntToScalar(kFixed), 0, SkIntToScalar(kStretchy), SkIntToScalar(kSize));
    paint.setColor(0x8800FF00);
    canvas.drawRect(r, paint);
    r.setXYWH(0, SkIntToScalar(kFixed), SkIntToScalar(kSize), SkIntToScalar(kStretchy));
    paint.setColor(0x880000FF);
    canvas.drawRect(r, paint);
}
示例#17
0
文件: SampleApp.cpp 项目: avary/skia
SkCanvas* SampleWindow::beforeChildren(SkCanvas* canvas) {
#ifdef SK_SUPPORT_GL
#ifndef USE_OFFSCREEN
    aglSetWindowRef(gAGLContext, NULL);
#endif
#endif
    switch (fCanvasType) {
    case kRaster_CanvasType:
        canvas = this->INHERITED::beforeChildren(canvas);
        break;
    case kPicture_CanvasType:
        fPicture = new SkPicture;
        canvas = fPicture->beginRecording(9999, 9999);
        break;
#ifdef SK_SUPPORT_GL
    case kOpenGL_CanvasType: {
        //SkGLCanvas::DeleteAllTextures();  // just for testing
        SkDevice* device = canvas->getDevice();
        const SkBitmap& bitmap = device->accessBitmap(true);
        // first clear the raster bitmap, so we don't see any leftover bits
        bitmap.eraseColor(0);
        // now setup our glcanvas
        setup_offscreen_gl(bitmap, (WindowRef)this->getHWND());
        fGLCanvas = new SkGLCanvas;
        fGLCanvas->setViewport(bitmap.width(), bitmap.height());
        canvas = fGLCanvas;
        break;
    }
#endif
    }

    if (fUseClip) {
        canvas->drawColor(0xFFFF88FF);
        canvas->clipPath(fClipPath);
    }

    return canvas;
}
示例#18
0
PassRefPtr<Image> ImageBuffer::copyImage() const
{
    ASSERT(context() && context()->platformContext());
#if ENABLE(ACCELERATED_2D_CANVAS)
    context()->syncSoftwareCanvas();
#endif
    // Request for canvas bitmap; conversion required.
    if (context()->platformContext()->isRecording())
        context()->platformContext()->convertToNonRecording();

    SkCanvas* canvas = context()->platformContext()->mCanvas;
    SkDevice* device = canvas->getDevice();
    const SkBitmap& orig = device->accessBitmap(false);

    SkBitmap copy;
    if (PlatformBridge::canSatisfyMemoryAllocation(orig.getSize()))
        orig.copyTo(&copy, orig.config());

    SkBitmapRef* ref = new SkBitmapRef(copy);
    RefPtr<Image> image = BitmapImage::create(ref, 0);
    ref->unref();
    return image;
}
示例#19
0
CGContextRef BitLockerSkia::cgContext()
{
    SkDevice* device = m_canvas->getDevice();
    ASSERT(device);
    if (!device)
        return 0;
    releaseIfNeeded();
    const SkBitmap& bitmap = device->accessBitmap(true);
    bitmap.lockPixels();
    void* pixels = bitmap.getPixels();
    m_cgContext = CGBitmapContextCreate(pixels, device->width(),
        device->height(), 8, bitmap.rowBytes(), CGColorSpaceCreateDeviceRGB(), 
        kCGBitmapByteOrder32Host | kCGImageAlphaPremultipliedFirst);

    // Apply device matrix.
    CGAffineTransform contentsTransform = CGAffineTransformMakeScale(1, -1);
    contentsTransform = CGAffineTransformTranslate(contentsTransform, 0, -device->height());
    CGContextConcatCTM(m_cgContext, contentsTransform);

    // Apply clip in device coordinates.
    CGMutablePathRef clipPath = CGPathCreateMutable();
    SkRegion::Iterator iter(m_canvas->getTotalClip());
    for (; !iter.done(); iter.next()) {
        IntRect rect = iter.rect();
        CGPathAddRect(clipPath, 0, rect);
    }
    CGContextAddPath(m_cgContext, clipPath);
    CGContextClip(m_cgContext);
    CGPathRelease(clipPath);

    // Apply content matrix.
    const SkMatrix& skMatrix = m_canvas->getTotalMatrix();
    CGAffineTransform affine = SkMatrixToCGAffineTransform(skMatrix);
    CGContextConcatCTM(m_cgContext, affine);

    return m_cgContext;
}
bool SkColorFilterImageFilter::onFilterImage(Proxy* proxy, const SkBitmap& src,
                                             const SkMatrix& matrix,
                                             SkBitmap* result,
                                             SkIPoint* loc) {
    SkColorFilter* cf = fColorFilter;
    if (NULL == cf) {
        *result = src;
        return true;
    }

    SkDevice* dev = proxy->createDevice(src.width(), src.height());
    if (NULL == dev) {
        return false;
    }
    OwnDeviceCanvas canvas(dev);
    SkPaint paint;

    paint.setXfermodeMode(SkXfermode::kSrc_Mode);
    paint.setColorFilter(fColorFilter);
    canvas.drawSprite(src, 0, 0, &paint);

    *result = dev->accessBitmap(false);
    return true;
}
示例#21
0
void RasterRenderer::setupCanvas(const TileRenderInfo& renderInfo, SkCanvas* canvas)
{
    if (renderInfo.baseTile->isLayerTile()) {
        g_bitmap->setIsOpaque(false);
        g_bitmap->eraseARGB(0, 0, 0, 0);
    } else {
        Color defaultBackground = Color::white;
        Color* background = renderInfo.tilePainter->background();
        if (!background) {
            ALOGV("No background color for base layer!");
            background = &defaultBackground;
        }
        ALOGV("setupCanvas use background on Base Layer %x", background->rgb());
        g_bitmap->setIsOpaque(!background->hasAlpha());
        g_bitmap->eraseARGB(background->alpha(), background->red(),
                            background->green(), background->blue());
    }

    SkDevice* device = new SkDevice(*g_bitmap);

    canvas->setDevice(device);

    device->unref();
}
示例#22
0
String ImageBuffer::toDataURL(const String& mimeType, const double* quality) const
{
    ASSERT(context() && context()->platformContext());

    // Request for canvas bitmap; conversion required.
    if (context()->platformContext()->isRecording())
        context()->platformContext()->convertToNonRecording();
// CAPPFIX_WEB_WEBGL
     SkCanvas* canvas = imageBufferCanvas(this);
// CAPPFIX_WEB_WEBGL_END
     SkDevice* device = canvas->getDevice();
     SkBitmap bitmap = device->accessBitmap(false);
     // if we can't see the pixels directly, call readPixels() to get a copy.
     // this could happen if the device is backed by a GPU.
     bitmap.lockPixels(); // balanced by our destructor, or explicitly if getPixels() fails
     if (!bitmap.getPixels()) {
         bitmap.unlockPixels();
         SkIRect bounds = SkIRect::MakeWH(device->width(), device->height());
         if (!canvas->readPixels(bounds, &bitmap))
             return "data:,";
     }

     return ImageToDataURL(bitmap, mimeType, quality);
}
示例#23
0
String ImageBuffer::toDataURL(const String& mimeType, const double* quality) const
{
    m_context->platformContext()->makeGrContextCurrent();
    SkDevice* device = context()->platformContext()->canvas()->getDevice();
    return ImageToDataURL(device->accessBitmap(false), mimeType, quality);
}
示例#24
0
PassRefPtr<ByteArray> getImageData(const IntRect& rect, SkCanvas& srcCanvas,
                                   const IntSize& size)
{
    RefPtr<ByteArray> result = ByteArray::create(rect.width() * rect.height() * 4);

	SkDevice* srcDevice = srcCanvas.getDevice();
    SkBitmap::Config srcConfig = srcDevice->accessBitmap(false).config();

    if (srcConfig == SkBitmap::kNo_Config) {
        // This is an empty SkBitmap that could not be configured.
        ASSERT(!size.width() || !size.height());
        return result.release();
    }

    unsigned char* data = result->data();

    if (rect.x() < 0
        || rect.y() < 0
        || rect.maxX() > size.width()
        || rect.maxY() > size.height())
        memset(data, 0, result->length());

    int originX = rect.x();
    int destX = 0;
    if (originX < 0) {
        destX = -originX;
        originX = 0;
    }
    int endX = rect.maxX();
    if (endX > size.width())
        endX = size.width();
    int numColumns = endX - originX;

    if (numColumns <= 0)
        return result.release();

    int originY = rect.y();
    int destY = 0;
    if (originY < 0) {
        destY = -originY;
        originY = 0;
    }
    int endY = rect.maxY();
    if (endY > size.height())
        endY = size.height();
    int numRows = endY - originY;

    if (numRows <= 0)
        return result.release();

    ASSERT(srcConfig == SkBitmap::kARGB_8888_Config);

    unsigned destBytesPerRow = 4 * rect.width();

    SkBitmap srcBitmap;
	srcBitmap.setConfig(SkBitmap::kARGB_8888_Config, numColumns, numRows, destBytesPerRow);
	srcBitmap.setPixels(data);
	//srcDevice.readPixels(SkIRect::MakeXYWH(originX, originY, numColumns, numRows), &srcBitmap, SkCanvas::kNative_Premul_Config8888);
	SkCanvas::Config8888 config8888;
	if (multiplied == Premultiplied)
		config8888 = SkCanvas::kRGBA_Premul_Config8888;
	else
		config8888 = SkCanvas::kRGBA_Unpremul_Config8888;
	srcCanvas.readPixels(&srcBitmap, originX, originY, SkCanvas::kNative_Premul_Config8888);

    unsigned char* destRow = data + destY * destBytesPerRow + destX * 4;

    // Do conversion of byte order and alpha divide (if necessary)
    for (int y = 0; y < numRows; ++y) {
        SkPMColor* srcBitmapRow = srcBitmap.getAddr32(0, y);
        for (int x = 0; x < numColumns; ++x) {
            SkPMColor srcPMColor = srcBitmapRow[x];
            unsigned char* destPixel = &destRow[x * 4];
            if (multiplied == Unmultiplied) {
                unsigned char a = SkGetPackedA32(srcPMColor);
                destPixel[0] = a ? SkGetPackedR32(srcPMColor) * 255 / a : 0;
                destPixel[1] = a ? SkGetPackedG32(srcPMColor) * 255 / a : 0;
                destPixel[2] = a ? SkGetPackedB32(srcPMColor) * 255 / a : 0;
                destPixel[3] = a;
            } else {
                // Input and output are both pre-multiplied, we just need to re-arrange the
                // bytes from the bitmap format to RGBA.
                destPixel[0] = SkGetPackedR32(srcPMColor);
                destPixel[1] = SkGetPackedG32(srcPMColor);
                destPixel[2] = SkGetPackedB32(srcPMColor);
                destPixel[3] = SkGetPackedA32(srcPMColor);
            }
        }
        destRow += destBytesPerRow;
    }

    return result.release();
}
 static void blowup(SkCanvas* canvas, const SkIRect& src, const SkRect& dst) {
     SkDevice* device = canvas->getDevice();
     const SkBitmap& bm = device->accessBitmap(false);
     canvas->drawBitmapRect(bm, &src, dst, NULL);
 }
示例#26
0
    virtual void onDraw(SkCanvas* canvas) {
        SkDevice* device = canvas->getDevice();
        GrRenderTarget* target = (GrRenderTarget*) device->accessRenderTarget();
        GrContext* ctx = GetGr();
        if (ctx && target) {
            SkPMColor gTextureData[(2 * S) * (2 * S)];
            static const int stride = 2 * S;
            static const SkPMColor gray  = SkPackARGB32(0x40, 0x40, 0x40, 0x40);
            static const SkPMColor white = SkPackARGB32(0xff, 0xff, 0xff, 0xff);
            static const SkPMColor red   = SkPackARGB32(0x80, 0x80, 0x00, 0x00);
            static const SkPMColor blue  = SkPackARGB32(0x80, 0x00, 0x00, 0x80);
            static const SkPMColor green = SkPackARGB32(0x80, 0x00, 0x80, 0x00);
            static const SkPMColor black = SkPackARGB32(0x00, 0x00, 0x00, 0x00);
            for (int i = 0; i < 2; ++i) {
                int offset = 0;
                // fill upper-left
                for (int y = 0; y < S; ++y) {
                    for (int x = 0; x < S; ++x) {
                        gTextureData[offset + y * stride + x] = gray;
                    }
                }
                // fill upper-right
                offset = S;
                for (int y = 0; y < S; ++y) {
                    for (int x = 0; x < S; ++x) {
                        gTextureData[offset + y * stride + x] = white;
                    }
                }
                // fill lower left
                offset = S * stride;
                for (int y = 0; y < S; ++y) {
                    for (int x = 0; x < S; ++x) {
                        gTextureData[offset + y * stride + x] = black;
                    }
                }
                // fill lower right
                offset = S * stride + S;
                for (int y = 0; y < S; ++y) {
                    for (int x = 0; x < S; ++x) {
                        gTextureData[offset + y * stride + x] = gray;
                    }
                }

                GrTextureDesc desc;
                desc.fAALevel   = kNone_GrAALevel;
                // use RT flag bit because in GL it makes the texture be bottom-up
                desc.fFlags     = i ? kRenderTarget_GrTextureFlagBit :
                                      kNone_GrTextureFlags;
                desc.fConfig    = kSkia8888_PM_GrPixelConfig;
                desc.fWidth     = 2 * S;
                desc.fHeight    = 2 * S;
                GrTexture* texture = 
                    ctx->createUncachedTexture(desc, gTextureData, 0);

                if (!texture) {
                    return;
                }
                GrAutoUnref au(texture);

                ctx->setClip(GrRect::MakeWH(2*S, 2*S));
                ctx->setRenderTarget(target);

                GrPaint paint;
                paint.reset();
                paint.fColor = 0xffffffff;
                paint.fSrcBlendCoeff = kOne_BlendCoeff;
                paint.fDstBlendCoeff = kISA_BlendCoeff;
                GrMatrix vm;
                if (i) {
                    vm.setRotate(90 * SK_Scalar1,
                                 S * SK_Scalar1,
                                 S * SK_Scalar1);
                } else {
                    vm.reset();
                }
                ctx->setMatrix(vm);
                GrMatrix tm;
                tm = vm;
                tm.postIDiv(2*S, 2*S);
                paint.textureSampler(0)->setMatrix(tm);
                paint.setTexture(0, texture);

                ctx->drawRect(paint, GrRect::MakeWH(2*S, 2*S));

                // now update the lower right of the texture in first pass
                // or upper right in second pass
                offset = 0;
                for (int y = 0; y < S; ++y) {
                    for (int x = 0; x < S; ++x) {
                        gTextureData[offset + y * stride + x] = 
                            ((x + y) % 2) ? (i ? green : red) : blue;
                    }
                }
                texture->writePixels(S, (i ? 0 : S), S, S,
                                     texture->config(), gTextureData,
                                     4 * stride);
                ctx->drawRect(paint, GrRect::MakeWH(2*S, 2*S));
            }
        }
    }