ImageView: adjustViewBounds does not work with lay

2019-03-18 01:52发布

问题:

I'm trying to place in single row the EditText with the ImageView on the left. But I can't get the image to be scaled properly to match the height of text entry.

The layout is simple:

    <LinearLayout
        android:orientation="horizontal"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content">
        <ImageView
            android:id="@+id/icon"
            android:layout_width="wrap_content"
            android:layout_height="fill_parent"
            android:adjustViewBounds="true"
            android:scaleType="fitStart"
            android:background="#f00"
            android:src="@drawable/icon" />
        <EditText
            android:id="@+id/text"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content" />
    </LinearLayout>

(I highlighted image background by red color to see the actual space allocated by ImageView)


If I specify the exact height for ImageView:

            android:layout_height="48dp"

then I get the closest view what I needed:

But I do not know the exact height of EditText, so I can't specify it for ImageView here.


When the height for ImageView is specified to fill its parent (to match ``EditText` height):

            android:layout_height="fill_parent"

then I get unexpected extra margin between the image and text entry:

Actually, in this case the ImageView width equals to unscaled image width, whereas the image was scaled.


It's the similar to picture shown below if I specify layout_height to 48dp and set adjustViewBounds to false:

            android:layout_height="48dp"
            android:adjustViewBounds="false"


So, the question here is: how to define the layout correctly to scale the image to match edit entry height and in the same time to have width of ImageView to be shrunk to scaled image width ? In other words how to get rid this extra space off?

回答1:

This is a LinearLayout bug. If you look at forceUniformHeight in the source here. You can see that to handle sizing child views which supply match_parent as the height when the LinearLayout is set to wrap_content, the LinearLayout pretends to have an absolute height, recalculates the child height and then reuses the child width from the previous measure pass. Basically your image is calculating height and width unconstrained and getting default width and height, and then having height recalculated but being forced to use the old width. You will need to supply a height or override some View onMeasures



回答2:

you can also put gravity to be centered on the linear layout

NOTE: that you should also have different images in drawables-hdpi/ldpi and mdpi