create and modify matrices in lua

BUG=skia:

Review URL: https://codereview.chromium.org/651823004
diff --git a/resources/slides.lua b/resources/slides.lua
index bae5206..a4de5b7 100644
--- a/resources/slides.lua
+++ b/resources/slides.lua
@@ -76,25 +76,35 @@
 
 gSlides = parse_file(io.open("/skia/trunk/resources/slides_content.lua", "r"))
 
-function make_paint(size, color)
+function make_rect(l, t, r, b)
+    return { left = l, top = t, right = r, bottom = b }
+end
+
+function make_paint(typefacename, stylebits, size, color)
     local paint = Sk.newPaint();
     paint:setAntiAlias(true)
     paint:setSubpixelText(true)
+    paint:setTypeface(Sk.newTypeface(typefacename, stylebits))
     paint:setTextSize(size)
     paint:setColor(color)
     return paint
 end
 
-function drawSlide(canvas, slide, template, paints)
+function drawSlide(canvas, slide, template)
+    template = template.slide   -- need to sniff the slide to know if we're title or slide
+
+    local x = template.margin_x
+    local y = template.margin_y
+
     local scale = 1.15
-    local y = 0
     for i = 1, #slide do
         local node = slide[i]
-        local temp = template[node.indent + 1]
-        local paint = paints[node.indent + 1]
+        local paint = template[node.indent + 1]
         local fm = paint:getFontMetrics()
+        local x_offset = -fm.ascent * node.indent
+
         y = y - fm.ascent * scale
-        canvas:drawText(node.text, temp.x, y, paint)
+        canvas:drawText(node.text, x + x_offset, y, paint)
         y = y + fm.descent * scale
     end
 end
@@ -171,17 +181,31 @@
 
 --------------------------------------------------------------------------------------
 
-gTemplate = {
-    { x = 10, textSize = 40, bullet = "" },
-    { x = 40, textSize = 30, bullet = "\xE2\x80\xA2" },
-    { x = 70, textSize = 20, bullet = "\xE2\x97\xA6" },
-}
+function SkiaPoint_make_template()
+    local title = {
+        margin_x = 30,
+        margin_y = 100,
+    }
+    title[1] = make_paint("Arial", 1, 50, { a=1, r=0, g=0, b=0 })
+    title[1]:setTextAlign("center")
+    title[2] = make_paint("Arial", 1, 25, { a=1, r=.3, g=.3, b=.3 })
+    title[2]:setTextAlign("center")
 
-gPaints = {
-    make_paint(gTemplate[1].textSize, { a=1, r=0, g=0, b=0 } ),
-    make_paint(gTemplate[2].textSize, { a=1, r=1, g=0, b=0 } ),
-    make_paint(gTemplate[3].textSize, { a=1, r=0, g=1, b=0 } ),
-}
+    local slide = {
+        margin_x = 20,
+        margin_y = 30,
+    }
+    slide[1] = make_paint("Arial", 1, 36, { a=1, r=0, g=0, b=0 })
+    slide[2] = make_paint("Arial", 0, 30, { a=1, r=0, g=0, b=0 })
+    slide[3] = make_paint("Arial", 0, 24, { a=1, r=.2, g=.2, b=.2 })
+
+    return {
+        title = title,
+        slide = slide,
+    }
+end
+
+gTemplate = SkiaPoint_make_template()
 
 gRedPaint = Sk.newPaint()
 gRedPaint:setAntiAlias(true)
@@ -253,10 +277,10 @@
 
     local rec = Sk.newPictureRecorder()
 
-    drawSlide(rec:beginRecording(640, 480), prevSlide, gTemplate, gPaints)
+    drawSlide(rec:beginRecording(640, 480), prevSlide, gTemplate)
     local prevDrawable = new_drawable_picture(rec:endRecording())
 
-    drawSlide(rec:beginRecording(640, 480), nextSlide, gTemplate, gPaints)
+    drawSlide(rec:beginRecording(640, 480), nextSlide, gTemplate)
     local nextDrawable = new_drawable_picture(rec:endRecording())
 
     gCurrAnimation = transition(prevDrawable, nextDrawable, is_forward)
@@ -313,9 +337,13 @@
     }
 end
 
-function onDrawContent(canvas)
+function onDrawContent(canvas, width, height)
+    local matrix = Sk.newMatrix()
+    matrix:setRectToRect(make_rect(0, 0, 640, 480), make_rect(0, 0, width, height), "center")
+    canvas:concat(matrix)
+
     local drawSlideProc = function(canvas)
-        drawSlide(canvas, gSlides[gSlideIndex], gTemplate, gPaints)
+        drawSlide(canvas, gSlides[gSlideIndex], gTemplate)
     end
 
     if gCurrAnimation then
diff --git a/samplecode/SampleLua.cpp b/samplecode/SampleLua.cpp
index 1536ed4..7825eca 100644
--- a/samplecode/SampleLua.cpp
+++ b/samplecode/SampleLua.cpp
@@ -100,12 +100,6 @@
     }
 
     virtual void onDrawContent(SkCanvas* canvas) SK_OVERRIDE {
-        SkMatrix matrix;
-        matrix.setRectToRect(SkRect::MakeWH(640, 480),
-                             SkRect::MakeWH(this->width(), this->height()),
-                             SkMatrix::kCenter_ScaleToFit);
-        canvas->concat(matrix);
-
         lua_State* L = this->ensureLua();
 
         lua_getglobal(L, gDrawName);
@@ -117,7 +111,9 @@
             // does it make sense to try to "cache" the lua version of this
             // canvas between draws?
             fLua->pushCanvas(canvas);
-            if (lua_pcall(L, 1, 1, 0) != LUA_OK) {
+            fLua->pushScalar(this->width());
+            fLua->pushScalar(this->height());
+            if (lua_pcall(L, 3, 1, 0) != LUA_OK) {
                 SkDebugf("lua err: %s\n", lua_tostring(L, -1));
             } else {
                 if (lua_isboolean(L, -1) && lua_toboolean(L, -1)) {
diff --git a/src/utils/SkLua.cpp b/src/utils/SkLua.cpp
index 827abc6..dd79a34 100644
--- a/src/utils/SkLua.cpp
+++ b/src/utils/SkLua.cpp
@@ -627,6 +627,11 @@
     return 0;
 }
 
+static int lcanvas_concat(lua_State* L) {
+    get_ref<SkCanvas>(L, 1)->concat(*get_obj<SkMatrix>(L, 2));
+    return 0;
+}
+
 static int lcanvas_newSurface(lua_State* L) {
     int width = lua2int_def(L, 2, 0);
     int height = lua2int_def(L, 2, 0);
@@ -668,6 +673,7 @@
     { "scale", lcanvas_scale },
     { "translate", lcanvas_translate },
     { "rotate", lcanvas_rotate },
+    { "concat", lcanvas_concat },
 
     { "newSurface", lcanvas_newSurface },
 
@@ -1182,12 +1188,44 @@
     return 1;
 }
 
+static int lmatrix_setRectToRect(lua_State* L) {
+    SkMatrix* matrix = get_obj<SkMatrix>(L, 1);
+    SkRect srcR, dstR;
+    lua2rect(L, 2, &srcR);
+    lua2rect(L, 3, &dstR);
+    const char* scaleToFitStr = lua_tostring(L, 4);
+    SkMatrix::ScaleToFit scaleToFit = SkMatrix::kFill_ScaleToFit;
+
+    if (scaleToFitStr) {
+        const struct {
+            const char* fName;
+            SkMatrix::ScaleToFit fScaleToFit;
+        } rec[] = {
+            { "fill",   SkMatrix::kFill_ScaleToFit },
+            { "start",  SkMatrix::kStart_ScaleToFit },
+            { "center", SkMatrix::kCenter_ScaleToFit },
+            { "end",    SkMatrix::kEnd_ScaleToFit },
+        };
+
+        for (size_t i = 0; i < SK_ARRAY_COUNT(rec); ++i) {
+            if (strcmp(rec[i].fName, scaleToFitStr) == 0) {
+                scaleToFit = rec[i].fScaleToFit;
+                break;
+            }
+        }
+    }
+
+    matrix->setRectToRect(srcR, dstR, scaleToFit);
+    return 0;
+}
+
 static const struct luaL_Reg gSkMatrix_Methods[] = {
     { "getType", lmatrix_getType },
     { "getScaleX", lmatrix_getScaleX },
     { "getScaleY", lmatrix_getScaleY },
     { "getTranslateX", lmatrix_getTranslateX },
     { "getTranslateY", lmatrix_getTranslateY },
+    { "setRectToRect", lmatrix_setRectToRect },
     { NULL, NULL }
 };
 
@@ -1650,6 +1688,11 @@
     }
 }
 
+static int lsk_newMatrix(lua_State* L) {
+    push_new<SkMatrix>(L)->reset();
+    return 1;
+}
+
 static int lsk_newPaint(lua_State* L) {
     push_new<SkPaint>(L);
     return 1;
@@ -1666,8 +1709,7 @@
 }
 
 static int lsk_newRRect(lua_State* L) {
-    SkRRect* rr = push_new<SkRRect>(L);
-    rr->setEmpty();
+    push_new<SkRRect>(L)->setEmpty();
     return 1;
 }
 
@@ -1734,6 +1776,7 @@
 
     setfield_function(L, "newDocumentPDF", lsk_newDocumentPDF);
     setfield_function(L, "loadImage", lsk_loadImage);
+    setfield_function(L, "newMatrix", lsk_newMatrix);
     setfield_function(L, "newPaint", lsk_newPaint);
     setfield_function(L, "newPath", lsk_newPath);
     setfield_function(L, "newPictureRecorder", lsk_newPictureRecorder);