I have wrote a function that do reduce image size then upload it
everything works very well except original image will lost it quality
it should only reduce uploaded image size not the original one
this is my function
public void ReduceAndUpload(File file)
{
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
o.inSampleSize = 6;
BitmapFactory.decodeFile(file.getPath(), o);
int Scale = 1;
while (o.outWidth / Scale / 2 >= 75 && o.outHeight / Scale / 2 >= 75)
{
Scale *= 2;
}
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = Scale;
Bitmap SelectedBitmap = BitmapFactory.decodeFile(file.getPath(), o2);
ByteArrayOutputStream OutputStream = new ByteArrayOutputStream();
SelectedBitmap.compress(Bitmap.CompressFormat.JPEG, 100, OutputStream);
String ImageEncode = Base64.encodeToString(OutputStream.toByteArray(), 0);
DoUpload(ImageEncode);
}
whats wrong ?
Full Code: http://paste.ubuntu.com/20529512/
Related
This code is used to compress and resize image in my app Image is showing blurry and size is reducing to much. Can yo Explain how this code works and how can i improve quality of my image with this existing code.
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new FileInputStream(f), null, o);
final int REQUIRED_SIZE = 200;
int scale = 1;
while (o.outWidth / scale / 2 >= REQUIRED_SIZE
&& o.outHeight / scale / 2 >= REQUIRED_SIZE)
scale *= 2;
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
Bitmap bit1 = BitmapFactory.decodeStream(new FileInputStream(f),
null, o2);
Your code is just initializing the bitmap options to work with a decodedStream ( the input image or file you will work with) after that is setting a rule thats say the required size should be >= 200 width and height and after that is just creating a final bitmap with the required output of the stream
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new FileInputStream(f), null, o);
final int REQUIRED_SIZE = 200;
int scale = 1;
while (o.outWidth / scale / 2 >= REQUIRED_SIZE
&& o.outHeight / scale / 2 >= REQUIRED_SIZE)
scale *= 2;
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
Bitmap bit1 = BitmapFactory.decodeStream(new FileInputStream(f),
null, o2);
bit1.compress(Bitmap.CompressFormat.PNG, 100, out); //you can use this line and play with the value 100 in order to set quality of the image when its compresed
Since your image is scaled to a certain size ( which is >= 200 width and height) your image output dimension will depend on the input bitmap at first
if you want to check out the Dimensions of the bitmap you can do this
Log.e("Dimensions", bit1.getWidth()+" "+bit1.getHeight());
Bitmap.compress
compress(Bitmap.CompressFormat format, int quality, OutputStream
stream) Write a compressed version of the bitmap to the specified
outputstream.
EDIT: As Vladyslav Matviienko suggests you could increase your REQUIRED_SIZE to a bigger value, since like i wrote above, you are setting a fixed size at first
I`m editing a bitmap to optimize it for an OCR scan. One of the things I need to do is to rotate the image 270 degrees. I'm using the following code:
Matrix matrix = new Matrix();
matrix.PostRotate (270);
canvas.DrawBitmap(alteredBitmap, matrix, paint);
Apparently, this does not work for me. Can someone point out where I am wrong?
The bitmap comes from a byte[].
This is the snippet of code I use to rotate a byte[] in my projects. It receives and returns a byte[], but by removing the last 5 lines of code it'll return a Bitmap instead. It works wonders:
public async Task<byte[]> RotateImage(byte[] source, int rotation)
{
//This is optional, use it to reduce your images a little
var options = new BitmapFactory.Options();
options.InJustDecodeBounds = false;
options.InSampleSize = 2;
var bitmap = await BitmapFactory.DecodeByteArrayAsync(source, 0, source.Length, options);
Matrix matrix = new Matrix();
matrix.PostRotate(rotation);
var rotated = Bitmap.CreateBitmap(bitmap, 0, 0, bitmap.Width, bitmap.Height, matrix, true);
var stream = new MemoryStream();
await rotated.CompressAsync(Bitmap.CompressFormat.Jpeg, 100, stream);
var result = stream.ToArray();
await stream.FlushAsync();
return result;
}
All awaitable calls have non-async counterparts, so this can be converted to run in a blocking way without major issues. Just beware that removing the options variable might cause OutOfMemoryException, so make sure you know what you're doing before removing.
This method has always worked for me
Matrix matrix = new Matrix();
//myBitmap is the bitmap which is to be rotated
matrix.postRotate(rotateDegree);
Bitmap bitmap = Bitmap.createBitmap(myBitmap, 0, 0, myBitmap.getWidth(), myBitmap.getHeight(), matrix, true);//Rotated Bitmap
Well if you have this bitmap generated from a url , go ahead and use this function
public Bitmap decodeBitmap(File f) {
try {
//Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new FileInputStream(f), null, o);
//The new size we want to scale to
final int REQUIRED_SIZE = 490;
//Find the correct scale value. It should be the power of 2.
int scale = 1;
while (o.outWidth / scale / 2 >= REQUIRED_SIZE && o.outHeight / scale / 2 >= REQUIRED_SIZE)
scale *= 2;
//Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
return BitmapFactory.decodeStream(new FileInputStream(f), null, o2);
} catch (FileNotFoundException e) {
}
return null;
}
I am trying to set the background for an ImageView using a saved path. However the following code crashes.
selectSavedImagefromGallery(imagePath);
Here imagePath = "/storage/sdcard0/Downloads/image.jpg" which is a valid path. It works when I set the image choosing it from the gallery. But I would like to save the path so it can be used at anytime.
private void selectSavedImagefromGallery(String savedImagePath) {
Bitmap bm;
BitmapFactory.Options options = new BitmapFactory.Options();
options.inJustDecodeBounds = true;
BitmapFactory.decodeFile(savedImagePath, options);
final int REQUIRED_SIZE = 200;
int scale = 1;
while (options.outWidth / scale / 2 >= REQUIRED_SIZE
&& options.outHeight / scale / 2 >= REQUIRED_SIZE)
scale *= 2;
options.inSampleSize = scale;
options.inJustDecodeBounds = false;
bm = BitmapFactory.decodeFile(savedImagePath, options);
profile_pic.setImageBitmap(bm);
}
The error is being caused by this the last line:
profile_pic.setImageBitmap(bm);
What can I do to make it work?
Thanks.
What does BitmapFactory.Options in android.graphics.BitmapFactory.Options do?
There is no theoretical explanation in the android sdk reference manual about this class, it only contains the explanation about the methods of the class.
Bitmapfactory is mainly used for Scaling
Bitmap lBmp = BitmapFactory.decodeResource(getResources(), R.Drawable.ic_dolphin);
It gets the "dolpin" image and it will reduce the image size, if we dnt use bitmapfactory then it leads to insufficient memory allocations
It's used to pass options to the BitmapFactory - as you might expect :)
For example, you can use it to explicitly scale the Bitmap up or down from the source.
See this example
This method is used to create bitmap of given specific size which is stored in sdcard.
public Bitmap decodeFile(String path,int size) {
try {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeFile(path, o);
// The new size we want to scale to
final int REQUIRED_SIZE = size;
// Find the correct scale value. It should be the power of 2.
int scale = 1;
while (o.outWidth / scale / 2 >= REQUIRED_SIZE && o.outHeight / scale / 2 >= REQUIRED_SIZE)
scale *= 2;
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
return BitmapFactory.decodeFile(path, o2);
} catch (Throwable e) {
e.printStackTrace();
}
return null;
}
So here is my problem. I've got an image view containing a large bitmap (meaning that the imageview only shows a part of it since the bitmap is larger than the image view). I want to be able to center the bitmap in the imageview at the coordinates x, y (x and y are coordinate of the bitmap).
Any idea how I could achieve it ?
Regards,
Rob
try with
ImageView.ScaleType FIT_CENTER
see here the documentation http://developer.android.com/reference/android/widget/ImageView.ScaleType.html
now depending on how large is exactly your bitmap you might want to reduce it's size by using something like this
private Bitmap decodeFile(File f) {
Bitmap b = null;
try {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
FileInputStream fis = new FileInputStream(f);
BitmapFactory.decodeStream(fis, null, o);
fis.close();
int scale = 1;
if (o.outHeight > 1024 || o.outWidth > 900) {
scale = (int) Math.pow(2, (int) Math.round(Math.log(1024 / (double) Math.max(o.outHeight, o.outWidth)) / Math.log(0.5)));
}
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
fis = new FileInputStream(f);
b = BitmapFactory.decodeStream(fis, null, o2);
fis.close();
} catch (IOException e) {
}
return b;
}
credits to How to scale bitmap to screen size?