LayerDrawLooperTest.cpp revision 1f2f338e23789f3eef168dcbd8171a28820ba6c1
1/* 2 * Copyright 2013 Google Inc. 3 * 4 * Use of this source code is governed by a BSD-style license that can be 5 * found in the LICENSE file. 6 */ 7#include "Test.h" 8#include "SkBitmap.h" 9#include "SkBitmapDevice.h" 10#include "SkCanvas.h" 11#include "SkDraw.h" 12#include "SkLayerDrawLooper.h" 13#include "SkMatrix.h" 14#include "SkPaint.h" 15#include "SkRect.h" 16#include "SkRefCnt.h" 17#include "SkScalar.h" 18#include "SkXfermode.h" 19 20namespace { 21 22class FakeDevice : public SkBitmapDevice { 23public: 24 FakeDevice() : SkBitmapDevice(SkBitmap::kARGB_8888_Config, 100, 100, false) { } 25 26 virtual void drawRect(const SkDraw& draw, const SkRect& r, 27 const SkPaint& paint) SK_OVERRIDE { 28 fLastMatrix = *draw.fMatrix; 29 INHERITED::drawRect(draw, r, paint); 30 } 31 32 SkMatrix fLastMatrix; 33 34private: 35 typedef SkBitmapDevice INHERITED; 36}; 37 38} // namespace 39 40static void test_frontToBack(skiatest::Reporter* reporter) { 41 SkAutoTUnref<SkLayerDrawLooper> looper(SkNEW(SkLayerDrawLooper)); 42 SkLayerDrawLooper::LayerInfo layerInfo; 43 44 // Add the front layer, with the defaults. 45 (void)looper->addLayer(layerInfo); 46 47 // Add the back layer, with some layer info set. 48 layerInfo.fOffset.set(SkFloatToScalar(10.0f), SkFloatToScalar(20.0f)); 49 layerInfo.fPaintBits |= SkLayerDrawLooper::kXfermode_Bit; 50 SkPaint* layerPaint = looper->addLayer(layerInfo); 51 layerPaint->setXfermodeMode(SkXfermode::kSrc_Mode); 52 53 FakeDevice device; 54 SkCanvas canvas(&device); 55 SkPaint paint; 56 looper->init(&canvas); 57 58 // The back layer should come first. 59 REPORTER_ASSERT(reporter, looper->next(&canvas, &paint)); 60 REPORTER_ASSERT(reporter, SkXfermode::IsMode(paint.getXfermode(), SkXfermode::kSrc_Mode)); 61 canvas.drawRect(SkRect::MakeWH(SkFloatToScalar(50.0f), SkFloatToScalar(50.0f)), paint); 62 REPORTER_ASSERT(reporter, SkFloatToScalar(10.0f) == device.fLastMatrix.getTranslateX()); 63 REPORTER_ASSERT(reporter, SkFloatToScalar(20.0f) == device.fLastMatrix.getTranslateY()); 64 paint.reset(); 65 66 // Then the front layer. 67 REPORTER_ASSERT(reporter, looper->next(&canvas, &paint)); 68 REPORTER_ASSERT(reporter, SkXfermode::IsMode(paint.getXfermode(), SkXfermode::kSrcOver_Mode)); 69 canvas.drawRect(SkRect::MakeWH(SkFloatToScalar(50.0f), SkFloatToScalar(50.0f)), paint); 70 REPORTER_ASSERT(reporter, SkFloatToScalar(0.0f) == device.fLastMatrix.getTranslateX()); 71 REPORTER_ASSERT(reporter, SkFloatToScalar(0.0f) == device.fLastMatrix.getTranslateY()); 72 73 // Only two layers were added, so that should be the end. 74 REPORTER_ASSERT(reporter, !looper->next(&canvas, &paint)); 75} 76 77static void test_backToFront(skiatest::Reporter* reporter) { 78 SkAutoTUnref<SkLayerDrawLooper> looper(SkNEW(SkLayerDrawLooper)); 79 SkLayerDrawLooper::LayerInfo layerInfo; 80 81 // Add the back layer, with the defaults. 82 (void)looper->addLayerOnTop(layerInfo); 83 84 // Add the front layer, with some layer info set. 85 layerInfo.fOffset.set(SkFloatToScalar(10.0f), SkFloatToScalar(20.0f)); 86 layerInfo.fPaintBits |= SkLayerDrawLooper::kXfermode_Bit; 87 SkPaint* layerPaint = looper->addLayerOnTop(layerInfo); 88 layerPaint->setXfermodeMode(SkXfermode::kSrc_Mode); 89 90 FakeDevice device; 91 SkCanvas canvas(&device); 92 SkPaint paint; 93 looper->init(&canvas); 94 95 // The back layer should come first. 96 REPORTER_ASSERT(reporter, looper->next(&canvas, &paint)); 97 REPORTER_ASSERT(reporter, SkXfermode::IsMode(paint.getXfermode(), SkXfermode::kSrcOver_Mode)); 98 canvas.drawRect(SkRect::MakeWH(SkFloatToScalar(50.0f), SkFloatToScalar(50.0f)), paint); 99 REPORTER_ASSERT(reporter, SkFloatToScalar(0.0f) == device.fLastMatrix.getTranslateX()); 100 REPORTER_ASSERT(reporter, SkFloatToScalar(0.0f) == device.fLastMatrix.getTranslateY()); 101 paint.reset(); 102 103 // Then the front layer. 104 REPORTER_ASSERT(reporter, looper->next(&canvas, &paint)); 105 REPORTER_ASSERT(reporter, SkXfermode::IsMode(paint.getXfermode(), SkXfermode::kSrc_Mode)); 106 canvas.drawRect(SkRect::MakeWH(SkFloatToScalar(50.0f), SkFloatToScalar(50.0f)), paint); 107 REPORTER_ASSERT(reporter, SkFloatToScalar(10.0f) == device.fLastMatrix.getTranslateX()); 108 REPORTER_ASSERT(reporter, SkFloatToScalar(20.0f) == device.fLastMatrix.getTranslateY()); 109 110 // Only two layers were added, so that should be the end. 111 REPORTER_ASSERT(reporter, !looper->next(&canvas, &paint)); 112} 113 114static void test_mixed(skiatest::Reporter* reporter) { 115 SkAutoTUnref<SkLayerDrawLooper> looper(SkNEW(SkLayerDrawLooper)); 116 SkLayerDrawLooper::LayerInfo layerInfo; 117 118 // Add the back layer, with the defaults. 119 (void)looper->addLayer(layerInfo); 120 121 // Add the front layer, with some layer info set. 122 layerInfo.fOffset.set(SkFloatToScalar(10.0f), SkFloatToScalar(20.0f)); 123 layerInfo.fPaintBits |= SkLayerDrawLooper::kXfermode_Bit; 124 SkPaint* layerPaint = looper->addLayerOnTop(layerInfo); 125 layerPaint->setXfermodeMode(SkXfermode::kSrc_Mode); 126 127 FakeDevice device; 128 SkCanvas canvas(&device); 129 SkPaint paint; 130 looper->init(&canvas); 131 132 // The back layer should come first. 133 REPORTER_ASSERT(reporter, looper->next(&canvas, &paint)); 134 REPORTER_ASSERT(reporter, SkXfermode::IsMode(paint.getXfermode(), SkXfermode::kSrcOver_Mode)); 135 canvas.drawRect(SkRect::MakeWH(SkFloatToScalar(50.0f), SkFloatToScalar(50.0f)), paint); 136 REPORTER_ASSERT(reporter, SkFloatToScalar(0.0f) == device.fLastMatrix.getTranslateX()); 137 REPORTER_ASSERT(reporter, SkFloatToScalar(0.0f) == device.fLastMatrix.getTranslateY()); 138 paint.reset(); 139 140 // Then the front layer. 141 REPORTER_ASSERT(reporter, looper->next(&canvas, &paint)); 142 REPORTER_ASSERT(reporter, SkXfermode::IsMode(paint.getXfermode(), SkXfermode::kSrc_Mode)); 143 canvas.drawRect(SkRect::MakeWH(SkFloatToScalar(50.0f), SkFloatToScalar(50.0f)), paint); 144 REPORTER_ASSERT(reporter, SkFloatToScalar(10.0f) == device.fLastMatrix.getTranslateX()); 145 REPORTER_ASSERT(reporter, SkFloatToScalar(20.0f) == device.fLastMatrix.getTranslateY()); 146 147 // Only two layers were added, so that should be the end. 148 REPORTER_ASSERT(reporter, !looper->next(&canvas, &paint)); 149} 150 151static void TestLayerDrawLooper(skiatest::Reporter* reporter) { 152 test_frontToBack(reporter); 153 test_backToFront(reporter); 154 test_mixed(reporter); 155} 156 157#include "TestClassDef.h" 158DEFINE_TESTCLASS("LayerDrawLooper", TestLayerDrawLooperClass, TestLayerDrawLooper) 159