I have a list of bitmap images in asset folder to display(using ViewPager). I tried to set the width and height of the image based on screen-size(using layout params). But the image quality gets disturbed. How to make the image quality better?
Drawable drw = Drawable.createFromStream(getAssets().
open("Parts/"+drawables[i]),null);
Here, drawables[i] is the String[] (say like ball.bmp and "Parts" is the subfolder of asset).
Now, I have set the image in imageview as,
imageView.setBackgroundDrawable(imageArray[position]);
The image looks good in mobile but looks stretched in tab.
Try this; decode your image and find the correct scale value:
private Bitmap getBitmap(String url) {
// from web
try {
Bitmap bitmap = null;
URL imageUrl = new URL(url);
HttpURLConnection conn = (HttpURLConnection) imageUrl
.openConnection();
conn.setConnectTimeout(1000);
conn.setReadTimeout(1000);
conn.setInstanceFollowRedirects(true);
InputStream is = conn.getInputStream();
OutputStream os = new FileOutputStream(f);
Utils.CopyStream(is, os);
os.close();
bitmap = decodeFile(f);
return bitmap;
} catch (Exception ex) {
ex.printStackTrace();
return null;
}
}
// decodes image and scales it to reduce memory consumption
private Bitmap decodeFile(File f) {
try {
// decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new FileInputStream(f), null, o);
// Find the correct scale value. It should be the power of 2.
final int REQUIRED_SIZE = 150;
int width_tmp = o.outWidth, height_tmp = o.outHeight;
int scale = 1;
while (true) {
if (width_tmp / 2 < REQUIRED_SIZE
|| height_tmp / 2 < REQUIRED_SIZE)
break;
width_tmp /= 2;
height_tmp /= 2;
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;
}
Related
I'm using this method:
public Bitmap decodeUri(Uri selectedImage) throws FileNotFoundException {
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(getContentResolver().openInputStream(selectedImage), null, o);
final int REQUIRED_SIZE = 800;
int width_tmp = o.outWidth, height_tmp = o.outHeight;
int scale = 1;
while (true) {
if (width_tmp / 2 < REQUIRED_SIZE || height_tmp / 2 < REQUIRED_SIZE) {
break;
}
width_tmp /= 2;
height_tmp /= 2;
scale *= 2;
}
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
return BitmapFactory.decodeStream(getContentResolver().openInputStream(selectedImage), null, o2);
}
To decode an URI from mi camera and then send to my webserver via an HttpURLConnection object in POST headers. But my instead get my original image:
I get an cropped imagen:
I don't know why. Perhaps my decodeURI method is wrong? Anybody know other best method to send my image compressed to my webserver?
I used right now the next way insteaf of my decodeUri method:
mybitMap = MediaStore.Images.Media.getBitmap(this.getContentResolver(), selectedImageUri);
and I have the same problem. And when I tried to open the image in my webserver with Photoshop, I see an advertisement wich says "This document may be damaged (the file may be truncated or incomplete). Do you want continue?" And , after continue, I see a black space in the bottom of the image...
Anybody knows why? My code:
Bitmap mybitMap = null;
try {
mybitMap = MediaStore.Images.Media.getBitmap(this.getContentResolver(), selectedImageUri);
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
ByteArrayOutputStream baos = new ByteArrayOutputStream();
imagen.compress(Bitmap.CompressFormat.JPEG, 100, baos);
And I send this in POST Headers:
Base64.encodeToString(baos.toByteArray(), Base64.DEFAULT);
I am trying to parse images ...large images from url!
// Decodes image and scales it to reduce memory consumption
private Bitmap decodeFile(File f) {
try {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
FileInputStream stream1 = new FileInputStream(f);
BitmapFactory.decodeStream(stream1, null, o);
stream1.close();
// Find the correct scale value. It should be the power of 2.
// Recommended Size 512
final int REQUIRED_SIZE = 70;
int width_tmp = o.outWidth, height_tmp = o.outHeight;
int scale = 1;
while (true) {
if (width_tmp / 2 < REQUIRED_SIZE
|| height_tmp / 2 < REQUIRED_SIZE)
break;
width_tmp /= 2;
height_tmp /= 2;
scale *= 2;
}
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
FileInputStream stream2 = new FileInputStream(f);
Bitmap bitmap = BitmapFactory.decodeStream(stream2, null, o2);
stream2.close();
return bitmap;
} catch (FileNotFoundException e) {
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
when I parse small size images it works but when I use it in large one it crashes and bitmap is null and gives me this error
ReadStreamToBuffer : Qmage Stream read error!! required length 12 bytes, but red 0 bytes
isQmage : input SkStreamRewindable length is less than Qmage minimum size : 0
Try with this library
Picasso
Volley
Android-Universal-Image-Loader
I am using this code:
Bitmap itemImage = reduceImageAtFilePathFromGallery(imageName);
ByteArrayOutputStream stream = new ByteArrayOutputStream();
itemImage.compress(Bitmap.CompressFormat.PNG, 100, stream);
imageAnswer = Image.getInstance(stream.toByteArray());
private Bitmap reduceImageAtFilePathFromGallery(String filePath) {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeFile(filePath, o);
// The new size we want to scale to
final int REQUIRED_SIZE = 256;
// Find the correct scale value. It should be the power of 2.
int width_tmp = o.outWidth, height_tmp = o.outHeight;
int scale = 1;
while (true) {
if (width_tmp < REQUIRED_SIZE && height_tmp < REQUIRED_SIZE)
break;
width_tmp /= 2;
height_tmp /= 2;
scale *= 2;
}
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
Bitmap bitmap = BitmapFactory.decodeFile(filePath, o2);
return bitmap;
}
But the image's quality becomes bad.
Then, I also tried below code:
Image imageAnswer = getAndResizeImage(imageName);
private Image getAndResizeImage(String imageFilename){
final File imageFile = new File(imageFilename);
if (imageFile.exists()) {
Bitmap b = null;
try {
File f = new File(imageFilename);
b = BitmapFactory.decodeFile(f.getAbsolutePath());
//calculate how many bytes our image consists of.
int bytes = getSizeInBytes(b);
ByteBuffer buffer = ByteBuffer.allocate(bytes); //Create a new buffer
b.copyPixelsToBuffer(buffer); //Move the byte data to the buffer
byte[] array = buffer.array(); //Get the underlying array containing the data.
Image image = Image.getInstance(array);
return image;
} catch (Exception e) {
e.printStackTrace();
return null;
}
return null;
}
and it gives this error:
09-09 15:08:58.368: W/S
ystem.err(1385): java.io.IOException: The byte array is not a
recognized imageformat. 09-09 15:08:58.378: W/System.err(1385): at
com.itextpdf.text.Image.getInstance(Image.java:442) 09-09
on this line of code:
Image image = Image.getInstance(array);
Is there any way I can have good quality of image on PDF using iText?
Use JPEG compress format rather PNG
itemImage.compress(Bitmap.CompressFormat.JPEG, 100, stream);
I currently have a decode bitmap method to optimize the size of the image file, however the input file won’t be a bitmap and will decode to bitmap afterward. So my problem is, how can I resize it if my input is a bitmap already? Thanks.
private Bitmap compressFile(File f) {
int REQUIRED_SIZE = 80;
try {
// decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new FileInputStream(f), null, o);
// Find the correct scale value. It should be the power of 2.
int width_tmp = o.outWidth;// , height_tmp = o.outHeight;
int scale = 1;
while (REQUIRED_SIZE > 0) {
if (width_tmp <= REQUIRED_SIZE)
break;
width_tmp /= 2;
// height_tmp /= 2;
scale++;
}
// 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;
}
What I would like to change to is compressFile (Bitmap f)
You may use this too
Bitmap b = BitmapFactory.decodeByteArray(imageAsBytes, 0, imageAsBytes.length)
profileImage.setImageBitmap(Bitmap.createScaledBitmap(b, 120, 120, false));
or are you asking for:
bitmap.compress(Bitmap.CompressFormat.PNG, quality, outStream);
check this link for more info
i am displaying my images from assests/image folder ,
but this code is not working . this code display images from assets folder in gallery . i am using gallery prefine library or jar file.
please expert check it . thank u
AssetManager assetManager = getAssets();
String[] files = null;
try {
files = assetManager.list("image");
} catch (IOException e) {
Log.e("tag", e.getMessage());
}
for(String filename : files) {
System.out.println("File name => "+filename);
InputStream in = null;
try {
ImageViewTouch imageView = new ImageViewTouch(Rahul.this);
imageView.setLayoutParams(new Gallery.LayoutParams(LayoutParams.FILL_PARENT, LayoutParams.FILL_PARENT));
final Options options = new Options();
options.outHeight = (int) scaleHeight;
options.outWidth = (int) scaleWidth;
options.inScaled = true;
options.inPurgeable = true;
options.inSampleSize = 2;
in = assetManager.open("image/"+filename);
Bitmap bit=BitmapFactory.decodeStream(in);
imageView.setImageBitmap(bit);
} catch(Exception e) {
Log.e("tag", e.getMessage());
}
}
gallery.setAdapter(arrayAdapter);
Hey please check my answer on the same issue: bitmap size exceeds Vm budget error android
And also always try to use maximum options while dealing with bitmaps like this:
final Options options = new Options();
options.outHeight = (int) scaleHeight; // new smaller height
options.outWidth = (int) scaleWidth; // new smaller width
options.inScaled = true;
options.inPurgeable = true;
// to scale the image to 1/8
options.inSampleSize = 8;
bitmap = BitmapFactory.decodeFile(imagePath, options);
This might solve your problem.
1) try to use bitmap.recycle(); to release memory before setting a new bitmap to your images
BitmapDrawable drawable = (BitmapDrawable) myImage.getDrawable();
Bitmap bitmap = drawable.getBitmap();
if (bitmap != null)
{
bitmap.recycle();
}
2) if your images are too large scale down them:
public static Bitmap decodeFile(File file, int requiredSize) {
try {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new FileInputStream(file), null, o);
// The new size we want to scale to
// Find the correct scale value. It should be the power of 2.
int width_tmp = o.outWidth, height_tmp = o.outHeight;
int scale = 1;
while (true) {
if (width_tmp / 2 < requiredSize
|| height_tmp / 2 < requiredSize)
break;
width_tmp /= 2;
height_tmp /= 2;
scale *= 2;
}
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
Bitmap bmp = BitmapFactory.decodeStream(new FileInputStream(file),
null, o2);
return bmp;
} catch (FileNotFoundException e) {
} finally {
}
return null;
}
Update
something like this:
for(int i=0; i<it.size();i++) {
ImageViewTouch imageView = new ImageViewTouch(GalleryTouchTestActivity.this);
imageView.setLayoutParams(new Gallery.LayoutParams(LayoutParams.FILL_PARENT, LayoutParams.FILL_PARENT));
Options options = new Options();
options.inSampleSize = 2;
String photoURL = it.get(i);
BitmapDrawable drawable = (BitmapDrawable) imageView.getDrawable();
Bitmap bitmap = drawable.getBitmap();
if (bitmap != null)
{
bitmap.recycle();
}
bitmap = BitmapFactory.decodeFile(photoURL);
imageView.setImageBitmap(bitmap);
arrayAdapter.add(imageView);
}