在实际应用开发中,我们可以将一个图像文件,指定显示按照屏幕的大小进行显示,或者对指定的图像文件进行裁剪的功能。下面我们就来学习一下使用ImageView实现图片裁剪和显示的功能

1. 在讲这部分内容之前,我们需要补充一些知识点:

1) 首先是Android的BitmapFactory类:从不同的资源,包括文件,流,和字节数组中创建一个Bitmap对象。查看Android api文档:BitmapFactory,它带有一个匿名内部类[重要]:如下所示,其中这个类表示裁剪图片


这个匿名内部类很重要,主要是完成一些裁剪的功能
2) 我们在ImageView中显示图片的信息,它不但可以显示一张图片的信息,它还可以显示一个有字节数组等解码后的一张图片,它们一般是在 BitmapFactory中获得的.

从BitmapFactory中的方法我们可以看出这好比一个工厂模式中工厂角色类,它提供了很多方法来生成Bitmap对象,比如
public static Bitmap decodeByteArray (byte[] data, int offset, int length, BitmapFactory.Options opts)

它可以从一个字节数组编码成一个bitmap图像,参数说明

data ---> byte array of compressed image data [需要压缩为图像的字节数组数据] offset---> offset into imageData for where the decoder should begin parsing.[字节数组的位置偏移] length---> the number of bytes, beginning at offset, to parse [数组长度] opts---> null-ok; Options that control downsampling and whether the image should be completely decoded,
or just is size returned. [接受Options内部类的实例,用来裁剪用的]
3) 查看这个匿名内部类:BitmapFactory.Options其中用的比较多的方法是:
public boolean inJustDecodeBounds() ---> 如果设置为真,译码器不会返回图像,但是outXXXX等方法或者属性仍将被设置,允许调用者来查询图而无需为其像素分配内存。 public int outHeight ()---> 输出图片的高度 public int outWidth ()---> 输出图片的宽度

2. 程序主要代码

1) 布局文件

<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:layout_width="fill_parent"    android:layout_height="fill_parent"    android:orientation="vertical" >        <Button android:id="@+id/selectImageBtn"         android:layout_width="fill_parent"        android:layout_height="wrap_content"        android:text="选择图片"/>    <Button android:id="@+id/cutImageBtn"         android:layout_width="fill_parent"        android:layout_height="wrap_content"        android:text="选择图片进行裁剪"/>    <!-- 用户显示图片信息  -->    <ImageView android:id="@+id/imageview"        android:layout_width="wrap_content"        android:layout_height="wrap_content"/></LinearLayout>

2) 主要代码

public class ImageViewCut extends Activity implements OnClickListener {    private Button selectImageBtn;    private Button cutImageBtn;    private ImageView imageView;    // 主要用户 Intent的返回标志    private static final int IMAGE_SELECT = 1; // 选择图片    private static final int IMAGE_CUT = 2; // 裁剪图片    /** Called when the activity is first created. */    @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.main);        initComponent();        selectImageBtn.setOnClickListener(this);        cutImageBtn.setOnClickListener(this);    }    @Override    protected void onActivityResult(int requestCode, int resultCode, Intent data) {        // TODO Auto-generated method stub        super.onActivityResult(requestCode, resultCode, data);        if (resultCode == RESULT_OK) {            // 处理图片按照手机的屏幕大小显示            if (requestCode == IMAGE_SELECT) {                Uri uri = data.getData(); // 获得图片路径                int dw = getWindowManager().getDefaultDisplay().getWidth(); // 获得屏幕的宽度                int dh = getWindowManager().getDefaultDisplay().getHeight() / 2;                try {                    // 实现对图片的裁剪的类,是一个匿名内部类                    BitmapFactory.Options factory = new BitmapFactory.Options();                    factory.inJustDecodeBounds = true; // 如果设置为真,译码器不会返回图像,但是outXXXX等方法或者属性仍将被设置,允许调用者来查询图而无需为其像素分配内存。                    Bitmap bmp = BitmapFactory.decodeStream(                            getContentResolver().openInputStream(uri), null, factory);                    /*                     * 对图片的宽度和高度对应手机的屏幕进行匹配                           * 设计这段代码的目的是可以减少对系统资源的要求。                     * 首先要判断当图片宽度或者高度大于屏幕宽度高度的时候,如果高度大于宽度,则以高度为准,进行等比例的缩放,缩放比例为原有图像 1/hRatio 房子宽度进行缩放                     */                              //如果大于1表示图片的高度大于手机屏幕的高度                    int hRatio = (int)Math.ceil(factory.outHeight/(float)dh);                  //如果大于1表示图片的宽度大于手机屏幕的宽度                    int wRatio = (int)Math.ceil(factory.outWidth/(float)dh);                                        //缩放到1/ratio的尺寸 和 1/ratio 像素                    if(hRatio > 1 || wRatio > 1){                        if(hRatio > wRatio){                            factory.inSampleSize = hRatio;                        }else {                            factory.inSampleSize = wRatio;                        }                    }                                        factory.inJustDecodeBounds = false;                    bmp = BitmapFactory.decodeStream(getContentResolver().openInputStream(uri), null, factory);                    imageView.setImageBitmap(bmp);                                    } catch (Exception e) {                    // TODO: handle exception                }            } else if(requestCode == IMAGE_CUT){                //表示裁剪图片                //注意:getParcelableExtra("data")中"data"标签必须是要和getImageClipIntent()方法中的                //intent.putExtra("return-data", true);的 "return-data"的后面"data"的标签是一样的                Bitmap bitmap = data.getParcelableExtra("data");                 imageView.setImageBitmap(bitmap);            }        }    }    @Override    public void onClick(View v) {        // TODO Auto-generated method stub        // v.getId(): 获得当前视图的ID        switch (v.getId()) {            case R.id.selectImageBtn:                // 如何提取手机的图片库,并且进行选择图片的功能                Intent intent = new Intent(Intent.ACTION_PICK,                        android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI); // 打开手机的图库功能                startActivityForResult(intent, IMAGE_SELECT);                break;            case R.id.cutImageBtn:                Intent intent2 = getImageClipIntent();                startActivityForResult(intent2, IMAGE_CUT);                break;        }    }    private Intent getImageClipIntent() {        // action_get_content是通过intent中设置的type属性来判断具体调用哪个程序的        Intent intent = new Intent(Intent.ACTION_GET_CONTENT, null);        // 实现对图片的裁剪,必须要设置图片的属性和大小        intent.setType("image/*");        intent.putExtra("crop", "true");// 设置滑动覆盖区域选中图片        intent.putExtra("aspectX", 1); // 表示剪切框的比例1:1的效果        intent.putExtra("aspectY", 1);        intent.putExtra("outputX", 80); // 指定输出图片的大小        intent.putExtra("outputY", 80);        intent.putExtra("return-data", true);        // TODO Auto-generated method stub        return intent;    }    private void initComponent() {        selectImageBtn = (Button) findViewById(R.id.selectImageBtn);        cutImageBtn = (Button) findViewById(R.id.cutImageBtn);        imageView = (ImageView) findViewById(R.id.imageview);    }}

3. 程序运行结果

【Android 开发】:UI控件之 ImageView 实现适屏和裁剪图片的功能_第1张图片 --> 【Android 开发】:UI控件之 ImageView 实现适屏和裁剪图片的功能_第2张图片

【Android 开发】:UI控件之 ImageView 实现适屏和裁剪图片的功能_第3张图片 --> 【Android 开发】:UI控件之 ImageView 实现适屏和裁剪图片的功能_第4张图片


更多相关文章

  1. Android底下多线程下载远程图片
  2. Android APP内存优化之图片优化
  3. Android 使用Glide4.9 压缩并保存图片(jpg/png/gif)到本地
  4. Android中ListView使用- 网络图片的异步加载
  5. Android带进度条的下载图片示例(AsyncTask异步任务)
  6. [置顶] android从图库(gallery)选择一张图片
  7. 【Android 内存优化】Android 工程中使用 libjpeg-turbo 压缩图
  8. Android中关于Volley的使用(四)利用NetworkImageView来加载图片
  9. Android中网络图片的异步加载

随机推荐

  1. Android(安卓)WebView挂马漏洞--各大厂商
  2. Android 9.0 关机流程分析
  3. android异步向服务器请求数据
  4. android jdk环境的配置
  5. Android属性动画(ObjectAnimator、Proper
  6. android 常见错误
  7. Android——HttpURLConnection和HttpClie
  8. Android中常用的List滚动列表操作
  9. Android Broadcast广播机制深入解析
  10. Android(安卓)- RGB颜色查询对照表