Merge "Fix Bitmap leaks in ImageWallpaper" into lmp-mr1-dev
This commit is contained in:
@@ -174,7 +174,7 @@ public class ImageWallpaper extends WallpaperService {
|
|||||||
|
|
||||||
public void trimMemory(int level) {
|
public void trimMemory(int level) {
|
||||||
if (level >= ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW &&
|
if (level >= ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW &&
|
||||||
mBackground != null && mIsHwAccelerated) {
|
mBackground != null) {
|
||||||
if (DEBUG) {
|
if (DEBUG) {
|
||||||
Log.d(TAG, "trimMemory");
|
Log.d(TAG, "trimMemory");
|
||||||
}
|
}
|
||||||
@@ -212,6 +212,7 @@ public class ImageWallpaper extends WallpaperService {
|
|||||||
unregisterReceiver(mReceiver);
|
unregisterReceiver(mReceiver);
|
||||||
}
|
}
|
||||||
mBackground = null;
|
mBackground = null;
|
||||||
|
mWallpaperManager.forgetLoadedWallpaper();
|
||||||
}
|
}
|
||||||
|
|
||||||
void updateSurfaceSize(SurfaceHolder surfaceHolder) {
|
void updateSurfaceSize(SurfaceHolder surfaceHolder) {
|
||||||
@@ -337,111 +338,116 @@ public class ImageWallpaper extends WallpaperService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void drawFrame() {
|
void drawFrame() {
|
||||||
int newRotation = ((WindowManager) getSystemService(WINDOW_SERVICE)).
|
try {
|
||||||
getDefaultDisplay().getRotation();
|
int newRotation = ((WindowManager) getSystemService(WINDOW_SERVICE)).
|
||||||
|
getDefaultDisplay().getRotation();
|
||||||
|
|
||||||
// Sometimes a wallpaper is not large enough to cover the screen in one dimension.
|
// Sometimes a wallpaper is not large enough to cover the screen in one dimension.
|
||||||
// Call updateSurfaceSize -- it will only actually do the update if the dimensions
|
// Call updateSurfaceSize -- it will only actually do the update if the dimensions
|
||||||
// should change
|
// should change
|
||||||
if (newRotation != mLastRotation) {
|
if (newRotation != mLastRotation) {
|
||||||
// Update surface size (if necessary)
|
// Update surface size (if necessary)
|
||||||
updateSurfaceSize(getSurfaceHolder());
|
updateSurfaceSize(getSurfaceHolder());
|
||||||
}
|
|
||||||
SurfaceHolder sh = getSurfaceHolder();
|
|
||||||
final Rect frame = sh.getSurfaceFrame();
|
|
||||||
final int dw = frame.width();
|
|
||||||
final int dh = frame.height();
|
|
||||||
boolean surfaceDimensionsChanged = dw != mLastSurfaceWidth || dh != mLastSurfaceHeight;
|
|
||||||
|
|
||||||
boolean redrawNeeded = surfaceDimensionsChanged || newRotation != mLastRotation;
|
|
||||||
if (!redrawNeeded && !mOffsetsChanged) {
|
|
||||||
if (DEBUG) {
|
|
||||||
Log.d(TAG, "Suppressed drawFrame since redraw is not needed "
|
|
||||||
+ "and offsets have not changed.");
|
|
||||||
}
|
}
|
||||||
return;
|
SurfaceHolder sh = getSurfaceHolder();
|
||||||
}
|
final Rect frame = sh.getSurfaceFrame();
|
||||||
mLastRotation = newRotation;
|
final int dw = frame.width();
|
||||||
|
final int dh = frame.height();
|
||||||
|
boolean surfaceDimensionsChanged = dw != mLastSurfaceWidth
|
||||||
|
|| dh != mLastSurfaceHeight;
|
||||||
|
|
||||||
// Load bitmap if it is not yet loaded or if it was loaded at a different size
|
boolean redrawNeeded = surfaceDimensionsChanged || newRotation != mLastRotation;
|
||||||
if (mBackground == null || surfaceDimensionsChanged) {
|
if (!redrawNeeded && !mOffsetsChanged) {
|
||||||
if (DEBUG) {
|
|
||||||
Log.d(TAG, "Reloading bitmap: mBackground, bgw, bgh, dw, dh = " +
|
|
||||||
mBackground + ", " +
|
|
||||||
((mBackground == null) ? 0 : mBackground.getWidth()) + ", " +
|
|
||||||
((mBackground == null) ? 0 : mBackground.getHeight()) + ", " +
|
|
||||||
dw + ", " + dh);
|
|
||||||
}
|
|
||||||
mWallpaperManager.forgetLoadedWallpaper();
|
|
||||||
updateWallpaperLocked();
|
|
||||||
if (mBackground == null) {
|
|
||||||
if (DEBUG) {
|
if (DEBUG) {
|
||||||
Log.d(TAG, "Unable to load bitmap");
|
Log.d(TAG, "Suppressed drawFrame since redraw is not needed "
|
||||||
|
+ "and offsets have not changed.");
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (DEBUG) {
|
mLastRotation = newRotation;
|
||||||
if (dw != mBackground.getWidth() || dh != mBackground.getHeight()) {
|
|
||||||
Log.d(TAG, "Surface != bitmap dimensions: surface w/h, bitmap w/h: " +
|
// Load bitmap if it is not yet loaded or if it was loaded at a different size
|
||||||
dw + ", " + dh + ", " + mBackground.getWidth() + ", " +
|
if (mBackground == null || surfaceDimensionsChanged) {
|
||||||
mBackground.getHeight());
|
if (DEBUG) {
|
||||||
|
Log.d(TAG, "Reloading bitmap: mBackground, bgw, bgh, dw, dh = " +
|
||||||
|
mBackground + ", " +
|
||||||
|
((mBackground == null) ? 0 : mBackground.getWidth()) + ", " +
|
||||||
|
((mBackground == null) ? 0 : mBackground.getHeight()) + ", " +
|
||||||
|
dw + ", " + dh);
|
||||||
|
}
|
||||||
|
mWallpaperManager.forgetLoadedWallpaper();
|
||||||
|
updateWallpaperLocked();
|
||||||
|
if (mBackground == null) {
|
||||||
|
if (DEBUG) {
|
||||||
|
Log.d(TAG, "Unable to load bitmap");
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (DEBUG) {
|
||||||
|
if (dw != mBackground.getWidth() || dh != mBackground.getHeight()) {
|
||||||
|
Log.d(TAG, "Surface != bitmap dimensions: surface w/h, bitmap w/h: " +
|
||||||
|
dw + ", " + dh + ", " + mBackground.getWidth() + ", " +
|
||||||
|
mBackground.getHeight());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
// Center the scaled image
|
// Center the scaled image
|
||||||
mScale = Math.max(1f, Math.max(dw / (float) mBackground.getWidth(),
|
mScale = Math.max(1f, Math.max(dw / (float) mBackground.getWidth(),
|
||||||
dh / (float) mBackground.getHeight()));
|
dh / (float) mBackground.getHeight()));
|
||||||
final int availw = dw - (int) (mBackground.getWidth() * mScale);
|
final int availw = dw - (int) (mBackground.getWidth() * mScale);
|
||||||
final int availh = dh - (int) (mBackground.getHeight() * mScale);
|
final int availh = dh - (int) (mBackground.getHeight() * mScale);
|
||||||
int xPixels = availw / 2;
|
int xPixels = availw / 2;
|
||||||
int yPixels = availh / 2;
|
int yPixels = availh / 2;
|
||||||
|
|
||||||
// Adjust the image for xOffset/yOffset values. If window manager is handling offsets,
|
// Adjust the image for xOffset/yOffset values. If window manager is handling offsets,
|
||||||
// mXOffset and mYOffset are set to 0.5f by default and therefore xPixels and yPixels
|
// mXOffset and mYOffset are set to 0.5f by default and therefore xPixels and yPixels
|
||||||
// will remain unchanged
|
// will remain unchanged
|
||||||
final int availwUnscaled = dw - mBackground.getWidth();
|
final int availwUnscaled = dw - mBackground.getWidth();
|
||||||
final int availhUnscaled = dh - mBackground.getHeight();
|
final int availhUnscaled = dh - mBackground.getHeight();
|
||||||
if (availwUnscaled < 0) xPixels += (int)(availwUnscaled * (mXOffset - .5f) + .5f);
|
if (availwUnscaled < 0)
|
||||||
if (availhUnscaled < 0) yPixels += (int)(availhUnscaled * (mYOffset - .5f) + .5f);
|
xPixels += (int) (availwUnscaled * (mXOffset - .5f) + .5f);
|
||||||
|
if (availhUnscaled < 0)
|
||||||
|
yPixels += (int) (availhUnscaled * (mYOffset - .5f) + .5f);
|
||||||
|
|
||||||
mOffsetsChanged = false;
|
mOffsetsChanged = false;
|
||||||
mRedrawNeeded = false;
|
mRedrawNeeded = false;
|
||||||
if (surfaceDimensionsChanged) {
|
if (surfaceDimensionsChanged) {
|
||||||
mLastSurfaceWidth = dw;
|
mLastSurfaceWidth = dw;
|
||||||
mLastSurfaceHeight = dh;
|
mLastSurfaceHeight = dh;
|
||||||
}
|
|
||||||
if (!redrawNeeded && xPixels == mLastXTranslation && yPixels == mLastYTranslation) {
|
|
||||||
if (DEBUG) {
|
|
||||||
Log.d(TAG, "Suppressed drawFrame since the image has not "
|
|
||||||
+ "actually moved an integral number of pixels.");
|
|
||||||
}
|
}
|
||||||
return;
|
if (!redrawNeeded && xPixels == mLastXTranslation && yPixels == mLastYTranslation) {
|
||||||
}
|
if (DEBUG) {
|
||||||
mLastXTranslation = xPixels;
|
Log.d(TAG, "Suppressed drawFrame since the image has not "
|
||||||
mLastYTranslation = yPixels;
|
+ "actually moved an integral number of pixels.");
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
mLastXTranslation = xPixels;
|
||||||
|
mLastYTranslation = yPixels;
|
||||||
|
|
||||||
if (DEBUG) {
|
if (DEBUG) {
|
||||||
Log.d(TAG, "Redrawing wallpaper");
|
Log.d(TAG, "Redrawing wallpaper");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mIsHwAccelerated) {
|
if (mIsHwAccelerated) {
|
||||||
if (!drawWallpaperWithOpenGL(sh, availw, availh, xPixels, yPixels)) {
|
if (!drawWallpaperWithOpenGL(sh, availw, availh, xPixels, yPixels)) {
|
||||||
|
drawWallpaperWithCanvas(sh, availw, availh, xPixels, yPixels);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
drawWallpaperWithCanvas(sh, availw, availh, xPixels, yPixels);
|
drawWallpaperWithCanvas(sh, availw, availh, xPixels, yPixels);
|
||||||
}
|
}
|
||||||
} else {
|
} finally {
|
||||||
drawWallpaperWithCanvas(sh, availw, availh, xPixels, yPixels);
|
if (FIXED_SIZED_SURFACE && !mIsHwAccelerated) {
|
||||||
if (FIXED_SIZED_SURFACE) {
|
|
||||||
// If the surface is fixed-size, we should only need to
|
// If the surface is fixed-size, we should only need to
|
||||||
// draw it once and then we'll let the window manager
|
// draw it once and then we'll let the window manager
|
||||||
// position it appropriately. As such, we no longer needed
|
// position it appropriately. As such, we no longer needed
|
||||||
// the loaded bitmap. Yay!
|
// the loaded bitmap. Yay!
|
||||||
// hw-accelerated path retains bitmap for faster rotation
|
// hw-accelerated renderer retains bitmap for faster rotation
|
||||||
mBackground = null;
|
mBackground = null;
|
||||||
mWallpaperManager.forgetLoadedWallpaper();
|
mWallpaperManager.forgetLoadedWallpaper();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void updateWallpaperLocked() {
|
private void updateWallpaperLocked() {
|
||||||
|
|||||||
Reference in New Issue
Block a user