简体   繁体   English

我如何限制选择的大小图像

[英]how i can limit size image selected

My problem's the consumption memory, I need limit size the image selected. 我的问题是消耗内存,我需要限制所选图像的大小。

Edit 编辑

I don't need to resize image after load, I can resize image using 加载后我不需要调整图像大小,我可以使用调整图像大小

Bitmap.createScaledBitmap(image, (int) 80, (int) 80, true);

I need to prevent user select images > 5 MB 我需要阻止用户选择图像> 5 MB

my code 我的代码

public void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (resultCode == RESULT_OK) {
      if (requestCode == SELECT_PICTURE) {
        Uri selectedImageUri = data.getData();

        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

      }
    }
}

Limit size folder not it's the better option. 限制大小文件夹不是它是更好的选择。

SOLUTION

I solved my problem with this method: 我用这个方法解决了我的问题:

public boolean MaxSizeImage(String imagePath) {
    boolean temp = false;
    File file = new File(imagePath);
    long length = file.length();

    if (length < 1500000) // 1.5 mb
        temp = true;

    return temp;
}

if you need imagePath, you can use this method 如果需要imagePath,可以使用此方法

 public String getImagePath(Uri uri){
     Cursor cursor = getContentResolver().query(uri, null, null, null, null);
     cursor.moveToFirst();
     String document_id = cursor.getString(0);
     document_id = document_id.substring(document_id.lastIndexOf(":")+1);
     cursor.close();

     cursor = getContentResolver().query(
             android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
             null, MediaStore.Images.Media._ID + " = ? ", new String[]{document_id}, null);
     cursor.moveToFirst();
     String path = cursor.getString(cursor.getColumnIndex(MediaStore.Images.Media.DATA));
     cursor.close();

     return path;
 }

If you care about memory consumption, I think you can use Fresco image library developed by Facebook. 如果您关心内存消耗,我认为您可以使用Facebook开发的Fresco图像库。 In its docs you would find: 在其文档中,您会发现:

Fresco is a powerful system for displaying images in Android applications. Fresco是一个功能强大的系统,用于在Android应用程序中显示图像。 It takes care of image loading and display so you don't have to. 它负责图像加载和显示,因此您不必这样做。

Fresco's image pipeline will load images from the network, local storage, or local resources. Fresco的图像管道将从网络,本地存储或本地资源加载图像。 To save data and CPU, it has three levels of cache; 为了保存数据和CPU,它有三级缓存; two in memory and another in internal storage . 两个在内存中,另一个在内部存储中

Fresco's Drawees show a placeholder for you until the image has loaded and automatically show to the image when it arrives. Fresco的Drawees为您显示占位符,直到图像加载并在图像到达时自动显示。 When the image goes off-screen, it automatically releases its memory. 当图像离开屏幕时,它会自动释放内存。

Then in Features section you would found: 然后在功能部分,您会发现:

Memory 记忆

A decompressed image - an Android Bitmap - takes up a lot of memory. 解压缩的图像 - 一个Android Bitmap - 占用了大量内存。 This leads to more frequent runs of the Java garbage collector. 这导致更频繁地运行Java垃圾收集器。 This slows apps down. 这会减慢应用程序的速度。 The problem is especially bad without the improvements to the garbage collector made in Android 5.0. 如果不对Android 5.0中的垃圾收集器进行改进,问题尤其严重。

On Android 4.x and lower, Fresco puts images in a special region of Android memory. 在Android 4.x及更低版本中,Fresco将图像放在Android内存的特殊区域。 It also makes sure that images are automatically released from memory when they're no longer shown on screen. 它还可确保当图像不再显示在屏幕上时,图像会自动从内存中释放。 This lets your application run faster - and suffer fewer crashes. 这使您的应用程序运行得更快 - 并且遭受更少的崩溃。

Apps using Fresco can run even on low-end devices without having to constantly struggle to keep their image memory footprint under control. 使用Fresco的应用程序甚至可以在低端设备上运行,而无需经常努力控制图像内存占用。

Official site: http://frescolib.org/ 官方网站: http//frescolib.org/

GitHub: https://github.com/facebook/fresco GitHub: https//github.com/facebook/fresco

Article: Introducing Fresco: A new image library for Android 文章: Fresco简介:Android的新图像库

It seems to be fitted to your needs. 它似乎符合您的需求。 That's why I need to write an answer about it. 这就是我需要写一个答案的原因。

Hope it help 希望它有所帮助

use something like this to load the image at the memory youd like it to be, this is using a file path, there is methods for streams also check out BitmapFactory 使用类似这样的东西将图像加载到你想要的内存中,这是使用文件路径,有流的方法也检查出BitmapFactory

BitmapFactory.Options options = new BitmapFactory.Options();
options.inJustDecodeBounds = true;
BitmapFactory.decodeFile(picturePath, options);
int imageHeight = options.outHeight;
int imageWidth = options.outWidth;
String imageType = options.outMimeType;
options.inSampleSize = calculateInSampleSize(options,512,256);//512 and 256 whatever you want as scale
options.inJustDecodeBounds = false;
Bitmap yourSelectedImage = BitmapFactory.decodeFile(selectedImagePath,options);

helper method 辅助方法

public static int calculateInSampleSize(
        BitmapFactory.Options options, int reqWidth, int reqHeight) {
// Raw height and width of image
final int height = options.outHeight;
final int width = options.outWidth;
int inSampleSize = 1;

if (height > reqHeight || width > reqWidth) {

    // Calculate ratios of height and width to requested height and width
    final int heightRatio = Math.round((float) height / (float) reqHeight);
    final int widthRatio = Math.round((float) width / (float) reqWidth);

    // Choose the smallest ratio as inSampleSize value, this will guarantee
    // a final image with both dimensions larger than or equal to the
    // requested height and width.
    inSampleSize = heightRatio < widthRatio ? heightRatio : widthRatio;
}

return inSampleSize;
}

You could try using Picasso to fetch images. 您可以尝试使用Picasso来获取图像。 There's a resize option when you call and get images, that could help with size. 调用和获取图像时有一个调整大小选项,这可能有助于大小。 You'd probably be limited to "one size fits all" for images though. 尽管如此,你可能只限于“一刀切”。 It also makes a lot of additional features simple when loading images, such as placeholders, error images when your image doesn't load, and a few other utilities. 它还可以在加载图像时简化许多其他功能,例如占位符,图像无法加载时的错误图像以及一些其他实用程序。

Here's an example request from the link: 以下是链接的示例请求:

Picasso.with(context)
  .load(url)
  .resize(50, 50)
  .centerCrop()
  .into(imageView)

Try This Hackro :D 试试这个Hackro:D

First: 第一:

public static final int PICK_IMAGE = 1;
private void takePictureFromGalleryOrAnyOtherFolder() 
{
 Intent intent = new Intent();
 intent.setType("image/*");
 intent.setAction(Intent.ACTION_GET_CONTENT);
 startActivityForResult(Intent.createChooser(intent, "Select Picture"),PICK_IMAGE);
}

Then: 然后:

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        if (resultCode == Activity.RESULT_OK) {
           if (requestCode == PICK_IMAGE) {
                Uri selectedImageUri = data.getData();
                String imagePath = getRealPathFromURI(selectedImageUri);
               //Now you have imagePath do whatever you want to do now
             }//end of inner if
         }//end of outer if
  }

public String getRealPathFromURI(String contentURI) {
    Uri contentUri = Uri.parse(contentURI);

    String[] projection = { MediaStore.Images.Media.DATA };
    Cursor cursor = null;
    try {
        if (Build.VERSION.SDK_INT > 19) {
            // Will return "image:x*"
            String wholeID = DocumentsContract.getDocumentId(contentUri);
            // Split at colon, use second item in the array
            String id = wholeID.split(":")[1];
            // where id is equal to
            String sel = MediaStore.Images.Media._ID + "=?";

            cursor = context.getContentResolver().query(
                    MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
                    projection, sel, new String[] { id }, null);
        } else {
            cursor = context.getContentResolver().query(contentUri,
                    projection, null, null, null);
        }
    } catch (Exception e) {
        e.printStackTrace();
    }

    String path = null;
    try {
        int column_index = cursor
                .getColumnIndex(MediaStore.Images.Media.DATA);
        cursor.moveToFirst();
        path = cursor.getString(column_index).toString();
        cursor.close();
    } catch (NullPointerException e) {
        e.printStackTrace();
    }
    return path;
}

I don't know how to do that while selecting an image, but you can check size of file after select image. 我不知道在选择图像时如何做到这一点,但您可以在选择图像后检查文件大小。

public void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (resultCode == RESULT_OK) {
        if (requestCode == SELECT_PICTURE) {
        Uri selectedImageUri = data.getData();
        String imagepath = getPath(selectedImageUri);
        Bitmap bitmap=BitmapFactory.decodeFile(imagepath);

        int sizeInBytes = 0;
        int MAX_BYTES = your_number_of_bytes;

        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.HONEYCOMB_MR1) {
                sizeInBytes = bitmap.getRowBytes() * bitmap.getHeight();
        } else {
                sizeInBytes = bitmap.getByteCount();
        }

        if(sizeInBytes > MAX_BYTES) {
                // If the image is higher than max number of bytes, start all over again.
        }

        }
    }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM