I have a PNG file that I want to use for an overlay - however, this file has to be mirrored (and rotated by 180°), but in order to save space, I don't want to place the mirrored file in the apk, but do this action programmatically.
How can I do this with Froyo and above?
Scaling by -1.0 causes the image to be flipped. Assuming bmp is the bitmap you want to mirror (here on the x axis) you can do :
Matrix matrix = new Matrix();
matrix.preScale(-1.0f, 1.0f);
Bitmap mirroredBitmap = Bitmap.createBitmap(bmp, 0, 0, bmp.width(), bmp.height(), matrix, false);
If you don't want to create a second bitmap, you can do the same with canvas.scale :
canvas.save();
canvas.scale(-1.0f, 1.0f);
canvas.drawBitmap(bitmap, ...); // The bitmap is flipped
canvas.restore();
You can simply use View.setScaleX()
For example
public void mirrorView(View v){
v.setScaleX(-1.0f);
}
Related
I am trying to further process a Camera2 image. Because the cameras in devices have different rotations and flipped based on back and front camera, I use transforms to properly rotate it.
transformationMatrix is that matrix for the front camera that has 270 rotation.
Then from that transformed camera image, I want to copy a scrolling window to another bitmap. I want to retain that bitmap/state and draw a line before drawing finalBitmapWithScanner on the phone screen.
Is there a way to do this more efficiently and fast? The second line takes 200ms to complete which is the main issue here.
Canvas canvas = new Canvas(tempBitmap);
canvas.drawBitmap(cameraBitmap, transformationMatrix, paint); // <= 200ms
Rect src = new Rect((int) lastXPos, 0, (int) mXPos, mViewHeight);
Canvas canvas2 = new Canvas(finalBitmap);
canvas2.drawBitmap(tempBitmap, src, src, paint);
Canvas canvas3 = new Canvas(finalBitmapWithScanner);
canvas3.drawBitmap(finalBitmap, 0, 0, paint);
canvas3.drawLine(mXPos, 0, mXPos, mViewHeight/2, scrollerPaint);
transformationMatrix.reset();
transformationMatrix.setRotate(270, imageHeight, 0);
transformationMatrix.postTranslate(-imageHeight, 0);
transformationMatrix.postScale(scaleFactor, scaleFactor);
transformationMatrix.postScale(-1f, 1f, mViewWidth / 2f, mViewHeight / 2f);
There are bunch of ways you can try to achieve fast rendering:
You can pass parameters "paint" an null.
also you can use function CreateScaledBitmap and notice you have to set scale and size before rendering as see in below:
As you can see in documentation enter link description here; you have to resize and rescale your bitmap before rendering so you can use code below for your BitmapFactory.Options :
mBitmapOptions.inScaled = true;
mBitmapOptions.inDensity = srcWidth;
mBitmapOptions.inTargetDensity = dstWidth;
// will load & resize the image to be 1/inSampleSize dimensions
mCurrentBitmap = BitmapFactory.decodeResources(getResources(),
mImageIDs, mBitmapOptions);
use canvas.restore() after draw func.
I have an image in drawable folder for clock hand. I want to rotate it in fixed point like a clock hand. I have tried below code which rotates the hand in circular path around a fixed point but not as like clock hand.
Matrix matrix = new Matrix();
matrix.reset();
matrix.preTranslate(0, 0);
matrix.postRotate(angleRotation, -0, -0);
matrix.postTranslate(240, 480);
canvas.drawColor(Color.WHITE);
canvas.drawBitmap(bitmap, matrix, null);
I am struggling for hours to get it sorted out. Any help will be greatly appreciated.
I have tried below links for help as well with no success.
SurfaceView, draw image and reduce size, rotate image
Android: How to rotate a bitmap on a center point
How to rotate a bitmap in Android about images center smoothly without oscillatory movement
I found the answer. Let px and py be any point on canvas. bitmap.getWidth()/2 is middle point along bitmap width. It can be any point for x cordinate. For y cordinate I have taken it as 10. angleRotation is the angle that is as per required.
So matrix.postTranslate(-bitmap.getWidth()/2, -10); is the point of rotation.
Below is the code.
Matrix matrix = new Matrix();
matrix.reset();
Paint paint = new Paint();
float px = 240;
float py = 480;
matrix.postTranslate(-bitmap.getWidth()/2, -10);
matrix.postRotate(angleRotation);
matrix.postTranslate(px, py);
canvas.drawBitmap(bitmap, matrix, paint);
Above code satisfy my requirements. Please modify it as per your need.
I use this to rotate my bitmaps.
private Bitmap rotateImage(Bitmap src,int degrees) {
Matrix matrix = new Matrix();
matrix.postRotate(degrees);
return Bitmap.createBitmap(src, 0, 0, src.getWidth(), src.getHeight(), matrix, true);
}
I have tried several hours to rotate a bitmap with no success. I have read numerous articles about this subject on this web site and it seems the prefered solution involves creating a temporary canvas. Well I did this and I still do not see a roated bitmap.
My bitmap is a 40x40 blue square and I am trying to rotate it 45 degrees. Thats not asking for much is it? When the code runs, the bitmap that appears on the screen is the non-rotated original. ( I have also tried a translate with no success as well)
Here is my code:
// Load the bitmap resource
fillBMP2 = BitmapFactory.decodeResource(context.getResources(), R.drawable.test1);
// Copy to a mutable bitmap
mb = fillBMP2.copy(Bitmap.Config.ARGB_8888, true);
// Create canvas to draw to
Canvas offscreenCanvas = new Canvas (mb);
// Create Matrix so I can rotate it
Matrix matrix = new Matrix();
matrix.setRotate (45);
offscreenCanvas.setMatrix (matrix);
// Send the contents of the canvas into a bitmap
offscreenCanvas.setBitmap(mb);
Later in an OnDraw I do the following:
canvas.drawBitmap(mb, 200, 200, null);
Any ideas what I am doing wrong? Seems like it should work.
Thanks
Try using this
Matrix matrix = new Matrix();
matrix.setRotate(15);
canvas.drawBitmap(bmp, matrix, paint);
setRotation method takes in a float representing
the degrees of rotation.
Try this...
Matrix matrix = new Matrix();
float px = 200;
float py = 200;
matrix.postTranslate(-bitmap.getWidth()/2, -bitmap.getWidth()/2);
matrix.postRotate(45);
matrix.postTranslate(px, py);
canvas.drawBitmap(bitmap, matrix, paint);
You definitely want to use transformations: check out this link.
Basically it's this:
// save the canvas
ctx.save();
// move origin to center
ctx.translate(x,y);
// rotate
ctx.rotate(angle * (Math.PI / 180));
// draw image
ctx.drawImage(image, x, y, w, h, .w/2, h/2, w, h);
// restore
ctx.restore();
I am facing problme in rotating image
Following code works fine
Matrix matrix = new Matrix();
matrix.postRotate(DEGREE,mBitmap.getWidth() / 2, mBitmap.getHeight() / 2);
Bitmap m = Bitmap.createBitmap(mBitmap, 0, 0, mBitmap.getWidth(),mBitmap.getHeight(), matrix, true);
canvas.drawBitmap(m, mX, mY, null);
But I dont want to create a new bitmap again and again so I am using the following code
Matrix matrix = new Matrix();
matrix.postTranslate(mX, mY);
matrix.postRotate(DEGREE,mBitmap.getWidth() / 2, mBitmap.getHeight() / 2);
canvas.drawBitmap(mBitmap, matrix, null);
In that case image goes out of the view. It is not visible.
Matrix matrix = new Matrix();
canvas.translate(mX, mY);
canvas.drawBitmap(...);
canvas.translate(-mX, -mY);
Try first rotating it then translating it, because when you translate it first the center is not in the middle any more so you are rotating it with wrong pivot coordinates.
The pivot point by default when rotating is the top left corner of the image, which is why the view goes out of view. You need to add logic to make the pivot point the center of the image. Unfortunately, geometry is not my strong suit so maybe someone who somewhat enjoys geometry can give you the calculations to make this happen.
I have a rectangle-shaped Bitmap, which I need to rotate it by 90 degrees clockwise or counter-clockwise.
I can do the rotation using this code:
Matrix matrix = new Matrix();
matrix.setRotate(90, originalBitmap.getWidth()/2, originalBitmap.getHeight()/2);
return Bitmap.createBitmap(originalBitmap, 0, 0, originalBitmap.getWidth(), originalBitmap.getHeight(), matrix, true);
However, this code rotates image "in-place" using old values for height/width. And the resulting image looks stretched and ugly.
Is there any good way to rotate the image by 90 degrees into new height/width? Probably, one possible solution is to modify dimensions of the original bitmap first?
Thanks
Don't you use old values while creating new bitmap? Just replace them in the last line:
return Bitmap.createBitmap(originalBitmap, 0, 0, originalBitmap.getWidth()/2, originalBitmap.getHeight()/2, matrix, true);