I want to create a bitmap from an imageView, but I first need to rotate my imageView before converting the bitmap. I use the following code to convert the imageView to Bitmap.
BitmapDrawable drawable = (BitmapDrawable) imgPhoto.getDrawable();
Bitmap photo = drawable.getBitmap();
The imageView implements a rotation gesture. I want to be able to rotate the imageView and then create a Bitmap using the rotated imageView. However, it seems my Bitmap is still getting the original imageView instead of the rotated position. The following is the complete code. Thank you.
public class MainActivity extends AppCompatActivity implements RotationGestureDetector.OnRotationGestureListener{
private ImageView imgPhoto, imgBackground, imgCombine;
private RotationGestureDetector mRotationDetector;
private Button btnCombine;
private float angle;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mRotationDetector = new RotationGestureDetector(this);
imgPhoto = (ImageView) findViewById(R.id.imgPhoto);
imgBackground = (ImageView) findViewById(R.id.imgBackground);
collageImage = (ImageView) findViewById(R.id.imgCombine);
btnCombine = (Button)findViewById(R.id.btnCombineImage);
btnCombine.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
BitmapDrawable drawable = (BitmapDrawable) imgPhoto.getDrawable();
Bitmap photo = drawable.getBitmap();
}
});
}
#Override
public boolean onTouchEvent(MotionEvent event){
mRotationDetector.onTouchEvent(event);
return super.onTouchEvent(event);
}
#Override
public void OnRotation(RotationGestureDetector rotationDetector) {
angle = rotationDetector.getAngle();
Log.d("RotationGestureDetector", "Rotation: " + Float.toString(angle));
imgPhoto.setRotation(imgPhoto.getRotation() + (-angle));
}
}
To rotate ImageView:
Matrix matrix = new Matrix();
imageView.setScaleType(ImageView.ScaleType.MATRIX); //required
matrix.postRotate((float) angle, pivotX, pivotY);
imageView.setImageMatrix(matrix);
Source: https://stackoverflow.com/a/10104318/7639113
Then you can create the bitmap by using DrawingCache,
imageView.setDrawingCacheEnabled(true);
Bitmap bitmap = imageView.getDrawingCache();
Try using this code after the onClick. It should provide a rotated bitmap with the angle specified.
Matrix matrix = new Matrix();
matrix.postRotate(angle);
Bitmap rotatedPhoto = Bitmap.createBitmap(photo, 0, 0, photo.getWidth(), photo.getHeight(), matrix, true);
The rotate effect is actually applied at the Canvas level. So, what you can do is get the current Canvas augmentations and then draw your Bitmap into a new one with the changes.
Matrix transformMatrix = imgPhoto.getImageMatrix()
Bitmap original = photo;
Bitmap adjusted = Bitmap.createBitmap(original.getWidth(),
original.getHeight(),
original.getConfig());
Canvas canvas = new Canvas(adjusted);
canvas.setMatrix(transformMatrix);
canvas.drawBitmap(original, 0, 0, null);
//at this point adjusted bitmap contains the rotated image
Related
I wanted to know if it was possible to crop a picture to any other shape not just square, rectangle or circle.
Basically what I am looking for is that, the user can select a template of a png file (already present) and it cuts the picture in that shape.
Check out this code:
public class MainActivity extends AppCompatActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
final ImageView imageViewPreview = (ImageView) findViewById(R.id.imageview_preview);
new Thread(new Runnable() {
#Override
public void run() {
final Bitmap source = BitmapFactory.decodeResource(MainActivity.this.getResources(),
R.drawable.source);
final Bitmap mask = BitmapFactory.decodeResource(MainActivity.this.getResources(),
R.drawable.mask);
final Bitmap croppedBitmap = cropBitmap(source, mask);
runOnUiThread(new Runnable() {
#Override
public void run() {
imageViewPreview.setImageBitmap(croppedBitmap);
}
});
}
}).start();
}
private Bitmap cropBitmap(final Bitmap source, final Bitmap mask){
final Bitmap croppedBitmap = Bitmap.createBitmap(
source.getWidth(), source.getHeight(),
Bitmap.Config.ARGB_8888);
final Canvas canvas = new Canvas(croppedBitmap);
canvas.drawBitmap(source, 0, 0, null);
final Paint maskPaint = new Paint();
maskPaint.setXfermode(
new PorterDuffXfermode(PorterDuff.Mode.DST_OUT));
canvas.drawBitmap(mask, 0, 0, maskPaint);
return croppedBitmap;
}
}
The main function is the "cropBitmap" function. Basically it receives two bitmaps, a source and a mask, and then it "crops" the source bitmap using the mask's shape.
This is my source bitmap:
This is the mask bitmap:
And this is the result:
Also, check out this great presentation, this might help you too: Fun with Android shaders and filters
I have an ImageView and a bitmap. I want the ImageView to draw the bitmap mirrored horizontally. I'm trying to do it using a matrix, like so:
ImageView iv = ...;
Matrix matrix = new Matrix();
iv.setScaleType(ScaleType.MATRIX);
matrix.preScale(-1, 1);
iv.setImageMatrix(matrix);
But the ImageView does not appear after using the above. If I comment out the above, it appears ok. How can I do this?
Thanks
You might consider trying to flip the bitmap passed into the image view, rather than flipping the image view itself. Here is an example:
public class Main extends Activity {
ImageView imViewAndroid;
public static final int FLIP_VERTICAL = 1;
public static final int FLIP_HORIZONTAL = 2;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
imViewAndroid = (ImageView) findViewById(R.id.imViewAndroid);
imViewAndroid.setImageBitmap(flipImage(BitmapFactory.decodeResource(getResources(), R.drawable.car),2));
}
public Bitmap flipImage(Bitmap src, int type) {
// create new matrix for transformation
Matrix matrix = new Matrix();
// if vertical
if(type == FLIP_VERTICAL) {
// y = y * -1
matrix.preScale(1.0f, -1.0f);
}
// if horizonal
else if(type == FLIP_HORIZONTAL) {
// x = x * -1
matrix.preScale(-1.0f, 1.0f);
// unknown type
} else {
return null;
}
// return transformed image
return Bitmap.createBitmap(src, 0, 0, src.getWidth(), src.getHeight(), matrix, true);
}
}
This works, you need to offset by the width of the image after the flip:
ImageView iv = ...;
Matrix matrix = new Matrix();
matrix.preScale(-1, 1);
matrix.postTranslate(iv.getLayoutParams().width, 0);
iv.setScaleType(ScaleType.MATRIX);
iv.setImageMatrix(matrix);
First get Bitmap from your Drawable like
BitmapFactory.decodeResource(getResources(), R.drawable.car),2);
and then
public enum Direction { VERTICAL, HORIZONTAL };
/**
Creates a new bitmap by flipping the specified bitmap
vertically or horizontally.
#param src Bitmap to flip
#param type Flip direction (horizontal or vertical)
#return New bitmap created by flipping the given one
vertically or horizontally as specified by
the <code>type</code> parameter or
the original bitmap if an unknown type
is specified.
**/
public static Bitmap flip(Bitmap src, Direction type) {
Matrix matrix = new Matrix();
if(type == Direction.VERTICAL) {
matrix.preScale(1.0f, -1.0f);
}
else if(type == Direction.HORIZONTAL) {
matrix.preScale(-1.0f, 1.0f);
} else {
return src;
}
return Bitmap.createBitmap(src, 0, 0, src.getWidth(), src.getHeight(), matrix, true);
}
In my App I should rotate a picture like hand of clock clockwise and anticlockwise around bottom center.
I use this code :
private ImageView myImageView;
private float curScale = 1F;
private float curRotate = 70;
private Bitmap bitmap;
private int bmpHeight;
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
myImageView = (ImageView) findViewById(R.id.imageview);
bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.teste);//here you insert your image
bmpHeight = bitmap.getHeight();
drawMatrix();
}
private void drawMatrix() {
Matrix matrix = new Matrix();
Matrix matrixb = new Matrix();
Matrix matrixc = new Matrix();
matrix.postScale(curScale, curScale);
matrixb.setRotate(curRotate, 100, bmpHeight);
matrixc.setTranslate(100, 0);
matrix.setConcat(matrixb, matrixc);
Bitmap targetBitmap = Bitmap.createBitmap(200, bmpHeight,
bitmap.getConfig());
Canvas canvas = new Canvas(targetBitmap);
canvas.drawBitmap(bitmap, matrix, new Paint());
myImageView.setImageBitmap(targetBitmap);
}
But I couldn't rotate it anticlockwise because the width of picture change.
is there any solution?
Thanks in Advance.
I need to be able to create a custom image through code, and then set that image to an imageview
I want this image to have a solid background colour, a title and an icon.
I want it to be customisable so that I can call to create an image with values
for example
createImage(String bckgColourHex, String title, int iconResource){
// create image using value here
return image.
}
Then I can use the drawable to set it to my imageView
This is what I am trying so far
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ImageView image = (ImageView) findViewById(R.id.imageView1);
BitmapDrawable customImage = writeOnDrawable(R.drawable.background_gradient, "TEXT GOES HERE");
image.setBackgroundDrawable(customImage);
}
public BitmapDrawable writeOnDrawable(int drawableId, String text){
Bitmap bm = BitmapFactory.decodeResource(getResources(), drawableId).copy(Bitmap.Config.ARGB_8888, true);
Paint paint = new Paint();
paint.setStyle(Style.FILL);
paint.setColor(Color.BLACK);
paint.setTextSize(20);
Canvas canvas = new Canvas(bm);
canvas.drawText(text, 0, bm.getHeight()/2, paint);
return new BitmapDrawable(bm);
}
Thank you
public static Drawable makeBorderedDrawable(Context mContext, int width, String xCode, Boolean unAvail) {
Paint p = new Paint();
Bitmap bkg = null;
final int FULL_ALPHA = 0xFF123456; // of whatever color you want
int pixel = FULL_ALPHA;
// first create a mutable bitmap
bkg = Bitmap.createBitmap(width, width, Bitmap.Config.ARGB_8888);
Canvas c = new Canvas(bkg);
p.setColor(pixel);
c.drawCircle(width / 2, width / 2, width / 2, p);
// or draw rect, or lines, or drawtext....or whatever
return new BitmapDrawable(mContext.getResources(), bkg);
// or you could return a Bitmap if you prefer.
}
I don't don't get any warning on eclipse when I compile this code, but when I run it on device or emulator, that program was forced to close.
public class MainActivity extends Activity {
ImageView img;
Button btn;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//convert imageview to bitmap
img =(ImageView) findViewById(R.id.imageView1);
BitmapDrawable drawable = (BitmapDrawable) img.getDrawable();
final Bitmap imgbitmap = drawable.getBitmap();
btn.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
//convert bitmap to grayscale
Bitmap imgnew;
imgnew = toGrayscale(imgbitmap);
//convert bitmap to imageview
ImageView imgbit;
imgbit = (ImageView) findViewById(R.id.imageView2);
imgbit.setImageBitmap(imgnew);
}
});
}
public Bitmap toGrayscale(Bitmap bmpOriginal){
int width, height;
height = bmpOriginal.getHeight();
width = bmpOriginal.getWidth();
Bitmap bmpGrayscale = Bitmap.createBitmap(width, height, Bitmap.Config.RGB_565);
Canvas c = new Canvas(bmpGrayscale);
Paint paint = new Paint();
ColorMatrix cm = new ColorMatrix();
cm.setSaturation(0);
ColorMatrixColorFilter f = new ColorMatrixColorFilter(cm);
paint.setColorFilter(f);
c.drawBitmap(bmpOriginal, 0, 0, paint);
return bmpGrayscale;
}
}
If above is your full code then, basic problem is there, you haven't define btn. You need to define it before using it, else when you ar egoing to click on the button it will not work. and this might closing your application.
btn=(Button) findViewById(R.id.button1);