Apply display color matrix in Skia-RenderEngine.

Also adjust docs to ensure that applying the color matrix matches
HWC expectations. Specifically, the color matrix needs to be
applied in the output color space, rather than in linear space
as the docs suggest.

Bug: 164223050
Test: adjust HWC to always allow for display color transforms, and do
color inversion

Change-Id: I866a79b87b7a0f9432c7292f9237ecc4dd2139d7
diff --git a/libs/renderengine/include/renderengine/DisplaySettings.h b/libs/renderengine/include/renderengine/DisplaySettings.h
index ca16d2c..a637796 100644
--- a/libs/renderengine/include/renderengine/DisplaySettings.h
+++ b/libs/renderengine/include/renderengine/DisplaySettings.h
@@ -47,8 +47,8 @@
     // DataSpace::UNKNOWN otherwise.
     ui::Dataspace outputDataspace = ui::Dataspace::UNKNOWN;
 
-    // Additional color transform to apply in linear space after transforming
-    // to the output dataspace.
+    // Additional color transform to apply after transforming to the output
+    // dataspace, in non-linear space.
     mat4 colorTransform = mat4();
 
     // Region that will be cleared to (0, 0, 0, 1) prior to rendering.
diff --git a/libs/renderengine/skia/SkiaGLRenderEngine.cpp b/libs/renderengine/skia/SkiaGLRenderEngine.cpp
index 1719cd8..69ad189 100644
--- a/libs/renderengine/skia/SkiaGLRenderEngine.cpp
+++ b/libs/renderengine/skia/SkiaGLRenderEngine.cpp
@@ -20,13 +20,13 @@
 #define LOG_TAG "RenderEngine"
 #define ATRACE_TAG ATRACE_TAG_GRAPHICS
 
-#include "SkiaGLRenderEngine.h"
-
 #include <EGL/egl.h>
 #include <EGL/eglext.h>
 #include <GLES2/gl2.h>
 #include <GrContextOptions.h>
 #include <SkCanvas.h>
+#include <SkColorFilter.h>
+#include <SkColorMatrix.h>
 #include <SkColorSpace.h>
 #include <SkImage.h>
 #include <SkImageFilters.h>
@@ -40,6 +40,7 @@
 #include <cmath>
 
 #include "../gl/GLExtensions.h"
+#include "SkiaGLRenderEngine.h"
 #include "filters/BlurFilter.h"
 
 extern "C" EGLAPI const char* eglQueryStringImplementationANDROID(EGLDisplay dpy, EGLint name);
@@ -395,6 +396,13 @@
     }
 }
 
+static SkColorMatrix toSkColorMatrix(const mat4& matrix) {
+    return SkColorMatrix(matrix[0][0], matrix[1][0], matrix[2][0], matrix[3][0], 0, matrix[0][1],
+                         matrix[1][1], matrix[2][1], matrix[3][1], 0, matrix[0][2], matrix[1][2],
+                         matrix[2][2], matrix[3][2], 0, matrix[0][3], matrix[1][3], matrix[2][3],
+                         matrix[3][3], 0);
+}
+
 void SkiaGLRenderEngine::unbindExternalTextureBuffer(uint64_t bufferId) {
     std::lock_guard<std::mutex> lock(mRenderingMutex);
     mImageCache.erase(bufferId);
@@ -566,6 +574,8 @@
             paint.setColor(SkColor4f{.fR = color.r, .fG = color.g, .fB = color.b, layer->alpha});
         }
 
+        paint.setColorFilter(SkColorFilters::Matrix(toSkColorMatrix(display.colorTransform)));
+
         // Layers have a local transform matrix that should be applied to them.
         canvas->save();
         canvas->concat(getSkM44(layer->geometry.positionTransform));