I'm trying to move a BitmapDrawable
in a custom view. It works fine with a ShapeDrawable
as follows:
public class MyView extends View {
private Drawable image;
public MyView() {
image = new ShapeDrawable(new RectShape());
image.setBounds(0, 0, 100, 100);
((ShapeDrawable) image).getPaint().setColor(Color.BLACK);
}
@Override
protected void onDraw(Canvas canvas) {
image.draw(canvas);
}
public void move(int x, int y) {
Rect bounds = image.getBounds();
bounds.left += x;
bounds.right += x;
bounds.top += y;
bounds.bottom += y;
invalidate();
}
}
However, if I use a BitmapDrawable
, the drawable's bounds change, the onDraw
method is called, but the image stays where it is on the screen.
The following constructor will reproduce the problem by creating a BitmapDrawable instead:
public MyView() {
image = getResources().getDrawable(R.drawable.image);
image.setBounds(0, 0, 100, 100);
}
How can I move a BitmapDrawable
?
android.graphics.drawable.BitmapDrawable. A Drawable that wraps a bitmap and can be tiled, stretched, or aligned. You can create a BitmapDrawable from a file path, an input stream, through XML inflation, or from a Bitmap object. It can be defined in an XML file with the <bitmap> element.
A drawable resource is a general concept for a graphic that can be drawn to the screen and which you can retrieve with APIs such as getDrawable(int) or apply to another XML resource with attributes such as android:drawable and android:icon . There are several different types of drawables: Bitmap File.
To create a bitmap from a resource, you use the BitmapFactory method decodeResource(): Bitmap bitmap = BitmapFactory. decodeResource(getResources(), R. drawable.
The documentation for Drawable.getBounds() says the following:
Note: for efficiency, the returned object may be the same object stored in the drawable (though this is not guaranteed), so if a persistent copy of the bounds is needed, call copyBounds(rect) instead. You should also not change the object returned by this method as it may be the same object stored in the drawable.
This is not cristal clear but it looks like we must not change value returned by getBounds(), it fires some nasty side effects.
By using copyBounds() and setBounds() it works like a charm.
public void move(int x, int y) {
Rect bounds = image.copyBounds();
bounds.left += x;
bounds.right += x;
bounds.top += y;
bounds.bottom += y;
image.setBounds(bounds);
invalidate();
}
Another way of moving a Drawable could be to move the Canvas on wich you are drawing:
@Override
protected void onDraw(Canvas canvas) {
canvas.translate(x, y);
image.draw(canvas);
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With