Update VectorDrawables cache at frame start

Draw VectorDrawables in GPU backed surface. Render VD cache
at the beginning of the frame to avoid context switching.

Test: CTS graphics tests pass.
Change-Id: Ia14e0ec4049c3fa87f03547fbda44043bf8dd793
diff --git a/libs/hwui/VectorDrawable.cpp b/libs/hwui/VectorDrawable.cpp
index 8823a92..f6b2912 100644
--- a/libs/hwui/VectorDrawable.cpp
+++ b/libs/hwui/VectorDrawable.cpp
@@ -491,6 +491,36 @@
     return *mCache.bitmap;
 }
 
+void Tree::updateCache(sk_sp<SkSurface> surface) {
+    if (surface.get()) {
+        mCache.surface = surface;
+    }
+    if (surface.get() || mCache.dirty) {
+        SkSurface* vdSurface = mCache.surface.get();
+        SkCanvas* canvas = vdSurface->getCanvas();
+        float scaleX = vdSurface->width() / mProperties.getViewportWidth();
+        float scaleY = vdSurface->height() / mProperties.getViewportHeight();
+        SkAutoCanvasRestore acr(canvas, true);
+        canvas->clear(SK_ColorTRANSPARENT);
+        canvas->scale(scaleX, scaleY);
+        mRootNode->draw(canvas, false);
+        mCache.dirty = false;
+        canvas->flush();
+    }
+}
+
+void Tree::draw(SkCanvas* canvas) {
+   /*
+    * TODO address the following...
+    *
+    * 1) figure out how to set path's as volatile during animation
+    * 2) if mRoot->getPaint() != null either promote to layer (during
+    *    animation) or cache in SkSurface (for static content)
+    */
+    canvas->drawImageRect(mCache.surface->makeImageSnapshot().get(),
+        mutateProperties()->getBounds(), getPaint());
+}
+
 void Tree::updateBitmapCache(Bitmap& bitmap, bool useStagingData) {
     SkBitmap outCache;
     bitmap.getSkBitmap(&outCache);