android图片选择

    xiaoxiao2021-03-25  182

    图片选择功能基本都有吧 坑也很多记录一下。

    android 打开照相机

    String outFileFolder = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DCIM).getAbsolutePath(); String outFilePath = getNowDateTime("yyyyMMdd_HHmmssSSS") + ".jpg"; File file = new File(outFileFolder, outFilePath); mCameraFilePath = file.getAbsolutePath(); Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE); uri = Uri.fromFile(file); //有的手机得不到照相的路径,只能把相片保存到自定义的文件夹下面。 intent.putExtra(MediaStore.EXTRA_OUTPUT, uri); startActivityForResult(intent, TOKE_PIC); protected void onActivityResult(int requestCode, int resultCode, Intent data) { super.onActivityResult(requestCode, resultCode, data); if (resultCode == RESULT_OK) { Log.e("ljl", "获取相片的路径==" + mCameraFilePath + "-----" + mCameraFilePath.getBytes().toString()); Bitmap bmp = BitmapFactory.decodeFile(mCameraFilePath); Log.e("ljl", "bmp" + bmp.getWidth() + "----bmp----" + bmp.getHeight()); // 获取屏幕分辨率 DisplayMetrics dm = new DisplayMetrics(); getWindowManager().getDefaultDisplay().getMetrics(dm); // 图片分辨率与屏幕分辨率 float scale_2 = bmp.getWidth() / (float) dm.widthPixels; //显示图片的时候必须要对图片进行出来要不然图片不显示 Bitmap newBitMap_2 = null; if (scale_2 > 1) { newBitMap_2 = zoomBitmap(bmp, bmp.getWidth() / scale_2, bmp.getHeight() / scale_2); bmp.recycle(); isBig = true; imageView.setImageBitmap(newBitMap_2); } else { imageView.setImageBitmap(bmp); } } } // 对分辨率较大的图片进行缩放 public Bitmap zoomBitmap(Bitmap bitmap, float width, float height) { int w = bitmap.getWidth(); int h = bitmap.getHeight(); Matrix matrix = new Matrix(); float scaleWidth = ((float) width / w); float scaleHeight = ((float) height / h); matrix.postScale(scaleWidth, scaleHeight);// 利用矩阵进行缩放不会造成内存溢出 Bitmap newbmp = Bitmap.createBitmap(bitmap, 0, 0, w, h, matrix, true); return newbmp; }

    三、计算机解析图片的方式和Android中大图片Bitmap的压缩显示处理

    这个问题有点老生长谈了,平时我们经常遇到一些图片资源,我们把它加载到内存发现抛出内存不够用的异常,即OOM,当然加载图片时出现的OOM情况有很多种,比如单张图片没有做压缩,导致图片占用内存过大而发生内存溢出,也有多张图片一次性加载进来,导致的内存溢出。 通常单张大图,我们加载进来往往会经过一个图片的压缩处理的过程,而如果多张图片加载,我们可能就需要一些缓存机制,再加上一些算法来保证程序不出现OOM。 我们这里想要讲的知识点跟单张大图比较有关系 首先,我们知道一个图片,它是由很多像素点来表示的,而像素点的个数只跟图片的分辨率有关,而跟图片所占的内存空间大小无关。比如我们的桌面壁纸:1280 * 768 的分辨率,那么它就有 1280 * 768 = 983040个像素点,这意味着什么呢?我们知道我们要表示一个像素点的颜色,最经常我们需要RGB三种颜色来表示,而R:0~255,相当于两个FF的位置,就是8位,这样的话RGB合起来,一个像素点的表示就需要24位(这就是我们平衡听到的24位图),而加上透明度的8位,就是平时说的32位图。那么一张图片,它加载到内存中的话,它会占用多大的空间呢?

    计算方法:(像素点 * 一个像素所占用的byte数) / 1024 / 1024 (MB)

    以1280 * 768 的分辨率,32位图为例:所占内存大小: ((1280 * 768 * (32 / 8)) / 1024)/1024=3.75(MB)

    图片压缩

    public static Bitmap getScaleBitmap(Context ctx, String filePath) { BitmapFactory.Options opt = new BitmapFactory.Options(); opt.inJustDecodeBounds = true; Bitmap bmp = BitmapFactory.decodeFile(filePath, opt); int bmpWidth = opt.outWidth; int bmpHeght = opt.outHeight; WindowManager windowManager = (WindowManager) ctx.getSystemService(Context.WINDOW_SERVICE); Display display = windowManager.getDefaultDisplay(); int screenWidth = display.getWidth(); int screenHeight = display.getHeight(); opt.inSampleSize = 1; if (bmpWidth > bmpHeght) { if (bmpWidth > screenWidth) opt.inSampleSize = bmpWidth / screenWidth; } else { if (bmpHeght > screenHeight) opt.inSampleSize = bmpHeght / screenHeight; } opt.inJustDecodeBounds = false; bmp = BitmapFactory.decodeFile(filePath, opt); Log.e("ljl", "新的bitmap的宽=" + bmp.getWidth() + "--新的bitmap的高=" + bmp.getHeight()); return bmp; }

    在介绍之前先说下一个概念性问题: 一、URI    通用资源标志符(Universal Resource Identifier, 简称”URI”)。   Uri代表要操作的数据,Android上可用的每种资源 - 图像、视频片段等都可以用Uri来表示。   URI一般由三部分组成:     访问资源的命名机制。     存放资源的主机名。     资源自身的名称,由路径表示。   Android的Uri由以下三部分组成: “content://”、数据的路径、标示ID(可选)   举些例子,如:     所有联系人的Uri: content://contacts/people     某个联系人的Uri: content://contacts/people/5     所有图片Uri: content://media/external     某个图片的Uri:content://media/external/images/media/4

    打开相册

    Intent galleryIntent = new Intent(Intent.ACTION_GET_CONTENT); galleryIntent.addCategory(Intent.CATEGORY_OPENABLE); galleryIntent.setType("image/*");//图片 startActivityForResult(galleryIntent, IMAGE_CODE); //跳转,传递打开相册请求码 if (requestCode == IMAGE_CODE) {//相册数据 Log.e("ljl", "获取图片的uri=" + data.getData()); Uri p_uro = data.getData(); Log.e("ljl", "获取图片路径==" + getRealPathFromURI(p_uro)); if (p_uro != null) { //去裁剪 resizeImage(data.getData()); //imageView.setImageBitmap(getScaleBitmap(this, getRealPathFromURI(p_uro))); } //重塑图片大小 public void resizeImage(Uri uri) { Intent intent = new Intent("com.android.camera.action.CROP"); intent.setDataAndType(uri, "image/*"); // crop为true是设置在开启的intent中设置显示的view可以剪裁 intent.putExtra("crop", "true"); // aspectX aspectY 是宽高的比例 intent.putExtra("aspectX", 1); intent.putExtra("aspectY", 1); // outputX,outputY 是剪裁图片的宽高 intent.putExtra("outputX", 200); intent.putExtra("outputY", 200); intent.putExtra("scale", true); intent.putExtra("return-data", true); intent.putExtra("noFaceDetection", true); startActivityForResult(intent, RESIZE_CODE);//跳转,传递调整大小请求码 }

    处理裁剪的结果

    if (requestCode == RESIZE_CODE) { // 裁剪得到的数据 Log.e("ljl", "裁剪以后获取图片的uri=" + data.getData()); // Uri p_uro = data.getData(); // if (p_uro != null) { // imageView.setImageBitmap(getScaleBitmap(this, getRealPathFromURI(p_uro))); // } Log.e("ljl", "裁剪=====" + data); if (data != null) { // 剪裁图片并保存 Bundle bundle = data.getExtras(); if (bundle != null) { photo = bundle.getParcelable("data"); } else { try { photo = MediaStore.Images.Media.getBitmap(this.getContentResolver(), data.getData()); } catch (IOException e) { e.printStackTrace(); } } Log.e("ljl", "裁剪的bitmap" + photo.getWidth() + "-------------" + photo.getHeight()); imageView.setImageBitmap(photo); } }

    基本的功能就差不多了,以后有发现问题在记录。

    转载请注明原文地址: https://ju.6miu.com/read-2318.html

    最新回复(0)