Make DisplayListRenderer inherit from Canvas, merge JNI

Incrementally unify the upper layers for Skia and HWUI.
Remove redundant code from GLES20Canvas.java; instead
use inherited mNativeCanvasWrapper and superclass method
definitions.

Moves some unrelated SkPaint utility functions from Renderer
to new utils/PaintUtils.

bug: 15672762
Change-Id: I4ddd4214b8e9eeb95289d054ef423f2542bb5fa5
diff --git a/libs/hwui/DisplayListRenderer.cpp b/libs/hwui/DisplayListRenderer.cpp
index 1eefa89..5a13293 100644
--- a/libs/hwui/DisplayListRenderer.cpp
+++ b/libs/hwui/DisplayListRenderer.cpp
@@ -28,6 +28,7 @@
 #include "DisplayListOp.h"
 #include "DisplayListRenderer.h"
 #include "RenderNode.h"
+#include "utils/PaintUtils.h"
 
 namespace android {
 namespace uirenderer {
@@ -63,7 +64,7 @@
 }
 
 void DisplayListRenderer::prepareDirty(float left, float top,
-        float right, float bottom, bool opaque) {
+        float right, float bottom) {
 
     LOG_ALWAYS_FATAL_IF(mDisplayListData,
             "prepareDirty called a second time during a recording!");
@@ -72,7 +73,7 @@
     mState.initializeSaveStack(0, 0, mState.getWidth(), mState.getHeight(), Vector3());
 
     mDeferredBarrierType = kBarrier_InOrder;
-    mState.setDirtyClip(opaque);
+    mState.setDirtyClip(false);
     mRestoreSaveCount = -1;
 }
 
@@ -94,9 +95,9 @@
     mDisplayListData->functors.add(functor);
 }
 
-int DisplayListRenderer::save(int flags) {
-    addStateOp(new (alloc()) SaveOp(flags));
-    return mState.save(flags);
+int DisplayListRenderer::save(SkCanvas::SaveFlags flags) {
+    addStateOp(new (alloc()) SaveOp((int) flags));
+    return mState.save((int) flags);
 }
 
 void DisplayListRenderer::restore() {
@@ -117,22 +118,21 @@
 }
 
 int DisplayListRenderer::saveLayer(float left, float top, float right, float bottom,
-        const SkPaint* paint, int flags) {
+        const SkPaint* paint, SkCanvas::SaveFlags flags) {
     // force matrix/clip isolation for layer
     flags |= SkCanvas::kClip_SaveFlag | SkCanvas::kMatrix_SaveFlag;
 
     paint = refPaint(paint);
-    addStateOp(new (alloc()) SaveLayerOp(left, top, right, bottom, paint, flags));
-    return mState.save(flags);
+    addStateOp(new (alloc()) SaveLayerOp(left, top, right, bottom, paint, (int) flags));
+    return mState.save((int) flags);
 }
 
-void DisplayListRenderer::translate(float dx, float dy, float dz) {
-    // ignore dz, not used at defer time
+void DisplayListRenderer::translate(float dx, float dy) {
     mHasDeferredTranslate = true;
     mTranslateX += dx;
     mTranslateY += dy;
     flushRestoreToCount();
-    mState.translate(dx, dy, dz);
+    mState.translate(dx, dy, 0.0f);
 }
 
 void DisplayListRenderer::rotate(float degrees) {
@@ -155,11 +155,27 @@
     mState.setMatrix(matrix);
 }
 
-void DisplayListRenderer::concatMatrix(const SkMatrix& matrix) {
+void DisplayListRenderer::concat(const SkMatrix& matrix) {
     addStateOp(new (alloc()) ConcatMatrixOp(matrix));
     mState.concatMatrix(matrix);
 }
 
+bool DisplayListRenderer::getClipBounds(SkRect* outRect) const {
+    Rect bounds = mState.getLocalClipBounds();
+    *outRect = SkRect::MakeLTRB(bounds.left, bounds.top, bounds.right, bounds.bottom);
+    return !(outRect->isEmpty());
+}
+
+bool DisplayListRenderer::quickRejectRect(float left, float top, float right, float bottom) const {
+    return mState.quickRejectConservative(left, top, right, bottom);
+}
+
+bool DisplayListRenderer::quickRejectPath(const SkPath& path) const {
+    SkRect bounds = path.getBounds();
+    return mState.quickRejectConservative(bounds.fLeft, bounds.fTop, bounds.fRight, bounds.fBottom);
+}
+
+
 bool DisplayListRenderer::clipRect(float left, float top, float right, float bottom,
         SkRegion::Op op) {
     addStateOp(new (alloc()) ClipRectOp(left, top, right, bottom, op));
@@ -201,23 +217,50 @@
     addDrawOp(new (alloc()) DrawBitmapOp(bitmap, paint));
 }
 
-void DisplayListRenderer::drawBitmap(const SkBitmap* bitmap, float srcLeft, float srcTop,
+void DisplayListRenderer::drawBitmap(const SkBitmap& bitmap, float left, float top,
+        const SkPaint* paint) {
+    save(SkCanvas::kMatrix_SaveFlag);
+    translate(left, top);
+    drawBitmap(&bitmap, paint);
+    restore();
+}
+
+void DisplayListRenderer::drawBitmap(const SkBitmap& bitmap, const SkMatrix& matrix,
+        const SkPaint* paint) {
+    if (matrix.isIdentity()) {
+        drawBitmap(&bitmap, paint);
+    } else if (!(matrix.getType() & ~(SkMatrix::kScale_Mask | SkMatrix::kTranslate_Mask))) {
+        // SkMatrix::isScaleTranslate() not available in L
+        SkRect src;
+        SkRect dst;
+        bitmap.getBounds(&src);
+        matrix.mapRect(&dst, src);
+        drawBitmap(bitmap, src.fLeft, src.fTop, src.fRight, src.fBottom,
+                   dst.fLeft, dst.fTop, dst.fRight, dst.fBottom, paint);
+    } else {
+        save(SkCanvas::kMatrix_SaveFlag);
+        concat(matrix);
+        drawBitmap(&bitmap, paint);
+        restore();
+    }
+}
+
+void DisplayListRenderer::drawBitmap(const SkBitmap& bitmap, float srcLeft, float srcTop,
         float srcRight, float srcBottom, float dstLeft, float dstTop,
         float dstRight, float dstBottom, const SkPaint* paint) {
     if (srcLeft == 0 && srcTop == 0
-            && srcRight == bitmap->width() && srcBottom == bitmap->height()
+            && srcRight == bitmap.width() && srcBottom == bitmap.height()
             && (srcBottom - srcTop == dstBottom - dstTop)
             && (srcRight - srcLeft == dstRight - dstLeft)) {
         // transform simple rect to rect drawing case into position bitmap ops, since they merge
         save(SkCanvas::kMatrix_SaveFlag);
         translate(dstLeft, dstTop);
-        drawBitmap(bitmap, paint);
+        drawBitmap(&bitmap, paint);
         restore();
     } else {
-        bitmap = refBitmap(bitmap);
         paint = refPaint(paint);
 
-        addDrawOp(new (alloc()) DrawBitmapRectOp(bitmap,
+        addDrawOp(new (alloc()) DrawBitmapRectOp(refBitmap(&bitmap),
                 srcLeft, srcTop, srcRight, srcBottom,
                 dstLeft, dstTop, dstRight, dstBottom, paint));
     }
@@ -230,16 +273,15 @@
     addDrawOp(new (alloc()) DrawBitmapDataOp(bitmap, paint));
 }
 
-void DisplayListRenderer::drawBitmapMesh(const SkBitmap* bitmap, int meshWidth, int meshHeight,
+void DisplayListRenderer::drawBitmapMesh(const SkBitmap& bitmap, int meshWidth, int meshHeight,
         const float* vertices, const int* colors, const SkPaint* paint) {
     int vertexCount = (meshWidth + 1) * (meshHeight + 1);
-    bitmap = refBitmap(bitmap);
     vertices = refBuffer<float>(vertices, vertexCount * 2); // 2 floats per vertex
     paint = refPaint(paint);
     colors = refBuffer<int>(colors, vertexCount); // 1 color per vertex
 
-    addDrawOp(new (alloc()) DrawBitmapMeshOp(bitmap, meshWidth, meshHeight,
-                    vertices, colors, paint));
+    addDrawOp(new (alloc()) DrawBitmapMeshOp(refBitmap(&bitmap), meshWidth, meshHeight,
+           vertices, colors, paint));
 }
 
 void DisplayListRenderer::drawPatch(const SkBitmap* bitmap, const Res_png_9patch* patch,
@@ -255,16 +297,22 @@
     addDrawOp(new (alloc()) DrawColorOp(color, mode));
 }
 
+void DisplayListRenderer::drawPaint(const SkPaint& paint) {
+    SkRect bounds;
+    if (getClipBounds(&bounds)) {
+        drawRect(bounds.fLeft, bounds.fTop, bounds.fRight, bounds.fBottom, paint);
+    }
+}
+
+
 void DisplayListRenderer::drawRect(float left, float top, float right, float bottom,
-        const SkPaint* paint) {
-    paint = refPaint(paint);
-    addDrawOp(new (alloc()) DrawRectOp(left, top, right, bottom, paint));
+        const SkPaint& paint) {
+    addDrawOp(new (alloc()) DrawRectOp(left, top, right, bottom, refPaint(&paint)));
 }
 
 void DisplayListRenderer::drawRoundRect(float left, float top, float right, float bottom,
-        float rx, float ry, const SkPaint* paint) {
-    paint = refPaint(paint);
-    addDrawOp(new (alloc()) DrawRoundRectOp(left, top, right, bottom, rx, ry, paint));
+        float rx, float ry, const SkPaint& paint) {
+    addDrawOp(new (alloc()) DrawRoundRectOp(left, top, right, bottom, rx, ry, refPaint(&paint)));
 }
 
 void DisplayListRenderer::drawRoundRect(
@@ -283,9 +331,8 @@
             &right->value, &bottom->value, &rx->value, &ry->value, &paint->value));
 }
 
-void DisplayListRenderer::drawCircle(float x, float y, float radius, const SkPaint* paint) {
-    paint = refPaint(paint);
-    addDrawOp(new (alloc()) DrawCircleOp(x, y, radius, paint));
+void DisplayListRenderer::drawCircle(float x, float y, float radius, const SkPaint& paint) {
+    addDrawOp(new (alloc()) DrawCircleOp(x, y, radius, refPaint(&paint)));
 }
 
 void DisplayListRenderer::drawCircle(CanvasPropertyPrimitive* x, CanvasPropertyPrimitive* y,
@@ -299,65 +346,56 @@
 }
 
 void DisplayListRenderer::drawOval(float left, float top, float right, float bottom,
-        const SkPaint* paint) {
-    paint = refPaint(paint);
-    addDrawOp(new (alloc()) DrawOvalOp(left, top, right, bottom, paint));
+        const SkPaint& paint) {
+    addDrawOp(new (alloc()) DrawOvalOp(left, top, right, bottom, refPaint(&paint)));
 }
 
 void DisplayListRenderer::drawArc(float left, float top, float right, float bottom,
-        float startAngle, float sweepAngle, bool useCenter, const SkPaint* paint) {
+        float startAngle, float sweepAngle, bool useCenter, const SkPaint& paint) {
     if (fabs(sweepAngle) >= 360.0f) {
         drawOval(left, top, right, bottom, paint);
     } else {
-        paint = refPaint(paint);
         addDrawOp(new (alloc()) DrawArcOp(left, top, right, bottom,
-                        startAngle, sweepAngle, useCenter, paint));
+                        startAngle, sweepAngle, useCenter, refPaint(&paint)));
     }
 }
 
-void DisplayListRenderer::drawPath(const SkPath* path, const SkPaint* paint) {
-    path = refPath(path);
-    paint = refPaint(paint);
-
-    addDrawOp(new (alloc()) DrawPathOp(path, paint));
+void DisplayListRenderer::drawPath(const SkPath& path, const SkPaint& paint) {
+    addDrawOp(new (alloc()) DrawPathOp(refPath(&path), refPaint(&paint)));
 }
 
-void DisplayListRenderer::drawLines(const float* points, int count, const SkPaint* paint) {
+void DisplayListRenderer::drawLines(const float* points, int count, const SkPaint& paint) {
     points = refBuffer<float>(points, count);
-    paint = refPaint(paint);
 
-    addDrawOp(new (alloc()) DrawLinesOp(points, count, paint));
+    addDrawOp(new (alloc()) DrawLinesOp(points, count, refPaint(&paint)));
 }
 
-void DisplayListRenderer::drawPoints(const float* points, int count, const SkPaint* paint) {
+void DisplayListRenderer::drawPoints(const float* points, int count, const SkPaint& paint) {
     points = refBuffer<float>(points, count);
-    paint = refPaint(paint);
 
-    addDrawOp(new (alloc()) DrawPointsOp(points, count, paint));
+    addDrawOp(new (alloc()) DrawPointsOp(points, count, refPaint(&paint)));
 }
 
-void DisplayListRenderer::drawTextOnPath(const char* text, int bytesCount, int count,
-        const SkPath* path, float hOffset, float vOffset, const SkPaint* paint) {
-    if (!text || count <= 0) return;
+void DisplayListRenderer::drawTextOnPath(const uint16_t* glyphs, int count,
+        const SkPath& path, float hOffset, float vOffset, const SkPaint& paint) {
+    if (!glyphs || count <= 0) return;
 
-    text = refText(text, bytesCount);
-    path = refPath(path);
-    paint = refPaint(paint);
-
-    DrawOp* op = new (alloc()) DrawTextOnPathOp(text, bytesCount, count, path,
-            hOffset, vOffset, paint);
+    int bytesCount = 2 * count;
+    DrawOp* op = new (alloc()) DrawTextOnPathOp(refText((const char*) glyphs, bytesCount),
+            bytesCount, count, refPath(&path),
+            hOffset, vOffset, refPaint(&paint));
     addDrawOp(op);
 }
 
-void DisplayListRenderer::drawPosText(const char* text, int bytesCount, int count,
-        const float* positions, const SkPaint* paint) {
+void DisplayListRenderer::drawPosText(const uint16_t* text, const float* positions,
+        int count, int posCount, const SkPaint& paint) {
     if (!text || count <= 0) return;
 
-    text = refText(text, bytesCount);
+    int bytesCount = 2 * count;
     positions = refBuffer<float>(positions, count * 2);
-    paint = refPaint(paint);
 
-    DrawOp* op = new (alloc()) DrawPosTextOp(text, bytesCount, count, positions, paint);
+    DrawOp* op = new (alloc()) DrawPosTextOp(refText((const char*) text, bytesCount),
+                                             bytesCount, count, positions, refPaint(&paint));
     addDrawOp(op);
 }
 
@@ -371,40 +409,41 @@
     paint->setLooper(NULL);
 }
 
-void DisplayListRenderer::drawText(const char* text, int bytesCount, int count,
-        float x, float y, const float* positions, const SkPaint* paint,
-        float totalAdvance, const Rect& bounds, DrawOpMode drawOpMode) {
+void DisplayListRenderer::drawText(const uint16_t* glyphs, const float* positions,
+        int count, const SkPaint& paint, float x, float y,
+        float boundsLeft, float boundsTop, float boundsRight, float boundsBottom,
+        float totalAdvance) {
 
-    if (!text || count <= 0 || paintWillNotDrawText(*paint)) return;
+    if (!glyphs || count <= 0 || PaintUtils::paintWillNotDrawText(paint)) return;
 
-    text = refText(text, bytesCount);
+    int bytesCount = count * 2;
+    const char* text = refText((const char*) glyphs, bytesCount);
     positions = refBuffer<float>(positions, count * 2);
+    Rect bounds(boundsLeft, boundsTop, boundsRight, boundsBottom);
 
     if (CC_UNLIKELY(mHighContrastText)) {
         // high contrast draw path
-        int color = paint->getColor();
+        int color = paint.getColor();
         int channelSum = SkColorGetR(color) + SkColorGetG(color) + SkColorGetB(color);
         bool darken = channelSum < (128 * 3);
 
         // outline
-        SkPaint* outlinePaint = copyPaint(paint);
+        SkPaint* outlinePaint = copyPaint(&paint);
         simplifyPaint(darken ? SK_ColorWHITE : SK_ColorBLACK, outlinePaint);
         outlinePaint->setStyle(SkPaint::kStrokeAndFill_Style);
         addDrawOp(new (alloc()) DrawTextOp(text, bytesCount, count,
                 x, y, positions, outlinePaint, totalAdvance, bounds)); // bounds?
 
         // inner
-        SkPaint* innerPaint = copyPaint(paint);
+        SkPaint* innerPaint = copyPaint(&paint);
         simplifyPaint(darken ? SK_ColorBLACK : SK_ColorWHITE, innerPaint);
         innerPaint->setStyle(SkPaint::kFill_Style);
         addDrawOp(new (alloc()) DrawTextOp(text, bytesCount, count,
                 x, y, positions, innerPaint, totalAdvance, bounds));
     } else {
         // standard draw path
-        paint = refPaint(paint);
-
         DrawOp* op = new (alloc()) DrawTextOp(text, bytesCount, count,
-                x, y, positions, paint, totalAdvance, bounds);
+                x, y, positions, refPaint(&paint), totalAdvance, bounds);
         addDrawOp(op);
     }
 }
@@ -477,7 +516,7 @@
 size_t DisplayListRenderer::addDrawOp(DrawOp* op) {
     Rect localBounds;
     if (op->getLocalBounds(localBounds)) {
-        bool rejected = quickRejectConservative(localBounds.left, localBounds.top,
+        bool rejected = quickRejectRect(localBounds.left, localBounds.top,
                 localBounds.right, localBounds.bottom);
         op->setQuickRejected(rejected);
     }