Merge "Use median instead of mean for sampling border luma" into rvc-dev am: 3e7dd91752
Change-Id: Ib7346cbd10c73abf022466c6726df639d218d156
This commit is contained in:
@@ -205,7 +205,7 @@ class ScreenRotationAnimation {
|
|||||||
SurfaceControl.ScreenshotGraphicBuffer gb =
|
SurfaceControl.ScreenshotGraphicBuffer gb =
|
||||||
mService.mDisplayManagerInternal.screenshot(displayId);
|
mService.mDisplayManagerInternal.screenshot(displayId);
|
||||||
if (gb != null) {
|
if (gb != null) {
|
||||||
mStartLuma = RotationAnimationUtils.getAvgBorderLuma(gb.getGraphicBuffer(),
|
mStartLuma = RotationAnimationUtils.getMedianBorderLuma(gb.getGraphicBuffer(),
|
||||||
gb.getColorSpace());
|
gb.getColorSpace());
|
||||||
try {
|
try {
|
||||||
surface.attachAndQueueBufferWithColorSpace(gb.getGraphicBuffer(),
|
surface.attachAndQueueBufferWithColorSpace(gb.getGraphicBuffer(),
|
||||||
|
|||||||
@@ -26,6 +26,8 @@ import android.view.Display;
|
|||||||
import android.view.Surface;
|
import android.view.Surface;
|
||||||
import android.view.SurfaceControl;
|
import android.view.SurfaceControl;
|
||||||
|
|
||||||
|
import java.util.Arrays;
|
||||||
|
|
||||||
|
|
||||||
/** Helper functions for the {@link com.android.server.wm.ScreenRotationAnimation} class*/
|
/** Helper functions for the {@link com.android.server.wm.ScreenRotationAnimation} class*/
|
||||||
public class RotationAnimationUtils {
|
public class RotationAnimationUtils {
|
||||||
@@ -35,31 +37,35 @@ public class RotationAnimationUtils {
|
|||||||
* luminance at the borders of the bitmap
|
* luminance at the borders of the bitmap
|
||||||
* @return the average luminance of all the pixels at the borders of the bitmap
|
* @return the average luminance of all the pixels at the borders of the bitmap
|
||||||
*/
|
*/
|
||||||
public static float getAvgBorderLuma(GraphicBuffer graphicBuffer, ColorSpace colorSpace) {
|
public static float getMedianBorderLuma(GraphicBuffer graphicBuffer, ColorSpace colorSpace) {
|
||||||
Bitmap hwBitmap = Bitmap.wrapHardwareBuffer(graphicBuffer, colorSpace);
|
Bitmap hwBitmap = Bitmap.wrapHardwareBuffer(graphicBuffer, colorSpace);
|
||||||
if (hwBitmap == null) {
|
if (hwBitmap == null) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
Bitmap swaBitmap = hwBitmap.copy(Bitmap.Config.ARGB_8888, false);
|
Bitmap swaBitmap = hwBitmap.copy(Bitmap.Config.ARGB_8888, false);
|
||||||
float totalLuma = 0;
|
|
||||||
int height = swaBitmap.getHeight();
|
int height = swaBitmap.getHeight();
|
||||||
int width = swaBitmap.getWidth();
|
int width = swaBitmap.getWidth();
|
||||||
|
float[] borderLumas = new float[2 * width + 2 * height];
|
||||||
int i;
|
int i;
|
||||||
for (i = 0; i < width; i++) {
|
int index = 0;
|
||||||
totalLuma += swaBitmap.getColor(i, 0).luminance();
|
for (i = 0; i < width; i++, index += 2) {
|
||||||
totalLuma += swaBitmap.getColor(i, height - 1).luminance();
|
borderLumas[index] = swaBitmap.getColor(i, 0).luminance();
|
||||||
|
borderLumas[index + 1] = swaBitmap.getColor(i, height - 1).luminance();
|
||||||
}
|
}
|
||||||
for (i = 0; i < height; i++) {
|
for (i = 0; i < height; i++, index += 2) {
|
||||||
totalLuma += swaBitmap.getColor(0, i).luminance();
|
borderLumas[index] = swaBitmap.getColor(0, i).luminance();
|
||||||
totalLuma += swaBitmap.getColor(width - 1, i).luminance();
|
borderLumas[index + 1] = swaBitmap.getColor(width - 1, i).luminance();
|
||||||
}
|
}
|
||||||
return totalLuma / (2 * width + 2 * height);
|
// Oh, is this too simple and inefficient for you?
|
||||||
|
// How about implementing a O(n) solution? https://en.wikipedia.org/wiki/Median_of_medians
|
||||||
|
Arrays.sort(borderLumas);
|
||||||
|
return borderLumas[borderLumas.length / 2];
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the average border luma by taking a screenshot of the {@param surfaceControl}.
|
* Gets the average border luma by taking a screenshot of the {@param surfaceControl}.
|
||||||
* @see #getAvgBorderLuma(GraphicBuffer, ColorSpace)
|
* @see #getMedianBorderLuma(GraphicBuffer, ColorSpace)
|
||||||
*/
|
*/
|
||||||
public static float getLumaOfSurfaceControl(Display display, SurfaceControl surfaceControl) {
|
public static float getLumaOfSurfaceControl(Display display, SurfaceControl surfaceControl) {
|
||||||
if (surfaceControl == null) {
|
if (surfaceControl == null) {
|
||||||
@@ -75,7 +81,7 @@ public class RotationAnimationUtils {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
return RotationAnimationUtils.getAvgBorderLuma(buffer.getGraphicBuffer(),
|
return RotationAnimationUtils.getMedianBorderLuma(buffer.getGraphicBuffer(),
|
||||||
buffer.getColorSpace());
|
buffer.getColorSpace());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -50,7 +50,7 @@ public class RotationAnimationUtilsTest {
|
|||||||
public void blackLuma() {
|
public void blackLuma() {
|
||||||
Bitmap swBitmap = createBitmap(0);
|
Bitmap swBitmap = createBitmap(0);
|
||||||
GraphicBuffer gb = swBitmapToGraphicsBuffer(swBitmap);
|
GraphicBuffer gb = swBitmapToGraphicsBuffer(swBitmap);
|
||||||
float borderLuma = RotationAnimationUtils.getAvgBorderLuma(gb, mColorSpace);
|
float borderLuma = RotationAnimationUtils.getMedianBorderLuma(gb, mColorSpace);
|
||||||
assertEquals(0, borderLuma, 0);
|
assertEquals(0, borderLuma, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -58,7 +58,15 @@ public class RotationAnimationUtilsTest {
|
|||||||
public void whiteLuma() {
|
public void whiteLuma() {
|
||||||
Bitmap swBitmap = createBitmap(1);
|
Bitmap swBitmap = createBitmap(1);
|
||||||
GraphicBuffer gb = swBitmapToGraphicsBuffer(swBitmap);
|
GraphicBuffer gb = swBitmapToGraphicsBuffer(swBitmap);
|
||||||
float borderLuma = RotationAnimationUtils.getAvgBorderLuma(gb, mColorSpace);
|
float borderLuma = RotationAnimationUtils.getMedianBorderLuma(gb, mColorSpace);
|
||||||
|
assertEquals(1, borderLuma, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void unevenBitmapDimens() {
|
||||||
|
Bitmap swBitmap = createBitmap(1, BITMAP_WIDTH + 1, BITMAP_HEIGHT + 1);
|
||||||
|
GraphicBuffer gb = swBitmapToGraphicsBuffer(swBitmap);
|
||||||
|
float borderLuma = RotationAnimationUtils.getMedianBorderLuma(gb, mColorSpace);
|
||||||
assertEquals(1, borderLuma, 0);
|
assertEquals(1, borderLuma, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -67,7 +75,7 @@ public class RotationAnimationUtilsTest {
|
|||||||
Bitmap swBitmap = createBitmap(1);
|
Bitmap swBitmap = createBitmap(1);
|
||||||
setBorderLuma(swBitmap, 0);
|
setBorderLuma(swBitmap, 0);
|
||||||
GraphicBuffer gb = swBitmapToGraphicsBuffer(swBitmap);
|
GraphicBuffer gb = swBitmapToGraphicsBuffer(swBitmap);
|
||||||
float borderLuma = RotationAnimationUtils.getAvgBorderLuma(gb, mColorSpace);
|
float borderLuma = RotationAnimationUtils.getMedianBorderLuma(gb, mColorSpace);
|
||||||
assertEquals(0, borderLuma, 0);
|
assertEquals(0, borderLuma, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -76,7 +84,7 @@ public class RotationAnimationUtilsTest {
|
|||||||
Bitmap swBitmap = createBitmap(0);
|
Bitmap swBitmap = createBitmap(0);
|
||||||
setBorderLuma(swBitmap, 1);
|
setBorderLuma(swBitmap, 1);
|
||||||
GraphicBuffer gb = swBitmapToGraphicsBuffer(swBitmap);
|
GraphicBuffer gb = swBitmapToGraphicsBuffer(swBitmap);
|
||||||
float borderLuma = RotationAnimationUtils.getAvgBorderLuma(gb, mColorSpace);
|
float borderLuma = RotationAnimationUtils.getMedianBorderLuma(gb, mColorSpace);
|
||||||
assertEquals(1, borderLuma, 0);
|
assertEquals(1, borderLuma, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -123,9 +131,13 @@ public class RotationAnimationUtilsTest {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private Bitmap createBitmap(float luma) {
|
private Bitmap createBitmap(float luma) {
|
||||||
Bitmap bitmap = Bitmap.createBitmap(BITMAP_WIDTH, BITMAP_HEIGHT, ARGB_8888);
|
return createBitmap(luma, BITMAP_WIDTH, BITMAP_HEIGHT);
|
||||||
for (int i = 0; i < BITMAP_WIDTH; i++) {
|
}
|
||||||
for (int j = 0; j < BITMAP_HEIGHT; j++) {
|
|
||||||
|
private Bitmap createBitmap(float luma, int width, int height) {
|
||||||
|
Bitmap bitmap = Bitmap.createBitmap(width, height, ARGB_8888);
|
||||||
|
for (int i = 0; i < width; i++) {
|
||||||
|
for (int j = 0; j < height; j++) {
|
||||||
bitmap.setPixel(i, j, Color.argb(1, luma, luma, luma));
|
bitmap.setPixel(i, j, Color.argb(1, luma, luma, luma));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user