Font variations.

Multiple Master and TrueType fonts support variation axes.
This implements back-end support for axes on platforms which
support it.

Committed: https://skia.googlesource.com/skia/+/05773ed30920c0214d1433c07cf6360a05476c97

Committed: https://skia.googlesource.com/skia/+/3489ee0f4fa34f124f9de090d12bdc2107d52aa9

Review URL: https://codereview.chromium.org/1027373002
diff --git a/src/core/SkFontDescriptor.cpp b/src/core/SkFontDescriptor.cpp
index 4a6b5db..cb149b9 100644
--- a/src/core/SkFontDescriptor.cpp
+++ b/src/core/SkFontDescriptor.cpp
@@ -17,12 +17,13 @@
 
     // These count backwards from 0xFF, so as not to collide with the SFNT
     // defines for names in its 'name' table.
+    kFontAxes       = 0xFC,
     kFontIndex      = 0xFD,
     kFontFileName   = 0xFE,  // Remove when MIN_PICTURE_VERSION > 41
     kSentinel       = 0xFF,
 };
 
-SkFontDescriptor::SkFontDescriptor(SkTypeface::Style style) : fFontIndex(0), fStyle(style) { }
+SkFontDescriptor::SkFontDescriptor(SkTypeface::Style style) : fStyle(style) { }
 
 static void read_string(SkStream* stream, SkString* string) {
     const uint32_t length = SkToU32(stream->readPackedUInt());
@@ -40,8 +41,7 @@
     }
 }
 
-static void write_string(SkWStream* stream, const SkString& string,
-                         uint32_t id) {
+static void write_string(SkWStream* stream, const SkString& string, uint32_t id) {
     if (!string.isEmpty()) {
         stream->writePackedUInt(id);
         stream->writePackedUInt(string.size());
@@ -58,9 +58,12 @@
     stream->writePackedUInt(n);
 }
 
-SkFontDescriptor::SkFontDescriptor(SkStream* stream) : fFontIndex(0) {
+SkFontDescriptor::SkFontDescriptor(SkStream* stream) {
     fStyle = (SkTypeface::Style)stream->readPackedUInt();
 
+    SkAutoSTMalloc<4, SkFixed> axis;
+    size_t axisCount = 0;
+    size_t index = 0;
     for (size_t id; (id = stream->readPackedUInt()) != kSentinel;) {
         switch (id) {
             case kFontFamilyName:
@@ -72,8 +75,15 @@
             case kPostscriptName:
                 read_string(stream, &fPostscriptName);
                 break;
+            case kFontAxes:
+                axisCount = read_uint(stream);
+                axis.reset(axisCount);
+                for (size_t i = 0; i < axisCount; ++i) {
+                    axis[i] = read_uint(stream);
+                }
+                break;
             case kFontIndex:
-                fFontIndex = read_uint(stream);
+                index = read_uint(stream);
                 break;
             case kFontFileName:  // Remove when MIN_PICTURE_VERSION > 41
                 skip_string(stream);
@@ -88,7 +98,8 @@
     if (length > 0) {
         SkAutoTUnref<SkData> data(SkData::NewUninitialized(length));
         if (stream->read(data->writable_data(), length) == length) {
-            fFontData.reset(SkNEW_ARGS(SkMemoryStream, (data)));
+            fFontData.reset(new SkFontData(SkNEW_ARGS(SkMemoryStream, (data)), index,
+                                           axis, axisCount));
         }
     }
 }
@@ -99,16 +110,25 @@
     write_string(stream, fFamilyName, kFontFamilyName);
     write_string(stream, fFullName, kFullName);
     write_string(stream, fPostscriptName, kPostscriptName);
-    if (fFontIndex) {
-        write_uint(stream, fFontIndex, kFontIndex);
+    if (fFontData.get()) {
+        if (fFontData->getIndex()) {
+            write_uint(stream, fFontData->getIndex(), kFontIndex);
+        }
+        if (fFontData->getAxisCount()) {
+            write_uint(stream, fFontData->getAxisCount(), kFontAxes);
+            for (int i = 0; i < fFontData->getAxisCount(); ++i) {
+                stream->writePackedUInt(fFontData->getAxis()[i]);
+            }
+        }
     }
 
     stream->writePackedUInt(kSentinel);
 
-    if (fFontData) {
-        size_t length = fFontData->getLength();
+    if (fFontData.get() && fFontData->hasStream()) {
+        SkAutoTDelete<SkStreamAsset> fontData(fFontData->detachStream());
+        size_t length = fontData->getLength();
         stream->writePackedUInt(length);
-        stream->writeStream(fFontData, length);
+        stream->writeStream(fontData, length);
     } else {
         stream->writePackedUInt(0);
     }