# 自适应高度的ImageView

App中经常会用到ImageView, 比如头像, 详情等. 很多时候ImageView的宽高是固定的, 很多时候只有一个边固定另一个边不确定. 一般来说我们都会使用图片加载框架将图片加载到ImageView上, 如果因为有一个边不确定而使用wrap\_content的话, 图片就会显示不出来. AdaptiveImageView就是针对宽固定而高不固定的情况.

宽固定而高不固定的情况一般用于阅读, 展示类App, 如新闻图片, 商品展示图片等. AdaptiveImageView的使用方式与ImageView没有任何区别, 把其当作ImageView就行:

```
<com.corelibs.views.AdaptiveImageView
    android:id="@+id/iv_picture"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_marginBottom="@dimen/activity_horizontal_margin"
    android:layout_marginTop="@dimen/activity_horizontal_margin"/>
```

```
@Bind(R.id.iv_picture) AdaptiveImageView ivPicture;

Picasso.with(this).load(test.imageUrl).into(ivPicture);
```

效果:

![效果](/files/-LsLm8J6KZASyPNlROot)

AdaptiveImageView的关键代码:

```
   @Override
    public void setImageDrawable(final Drawable drawable) {
        super.setImageDrawable(drawable);
        if (drawable != null) {
            post(new Runnable() {
                @Override public void run() {
                    float mWidth = getWidth();
                    float pWidth = drawable.getBounds().width();
                    float pHeight = drawable.getBounds().height();
                    int mHeight = (int) ((mWidth / pWidth) * pHeight);

                    LayoutParams params = getLayoutParams();
                    params.height = mHeight;
                    params.width = (int) mWidth;
                    setLayoutParams(params);
                }
            });
        }
    }
```

研究发现, Picasso为ImageView设置图片最终会调用setImageDrawable. 因此我们可以在此方法内做一些操作去设置ImageView的高度. 首先, 如果drawable不为空, 则通过drawable.getBounds()去获取drawable边界的宽和高. 在根据ImageView的宽与drawable的宽的比例去计算高度, 最后通过LayoutParams设置ImageView的高度. 为什么要使用post(new Runnable())方法? 因为有时候直接去获取drawable宽高会为0, post一下可以保证宽和高都有值.


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://ryan-8.gitbook.io/android-architecture-journey/widgets/adaptive_imageview.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
