解决ConstraintLayout布局中constraintDimensionRatio属性在ListView中的无法显示的问题。

ConstraintLayout是Android Studio2.2新增的主要功能之一,它使用约束的方式来指定控件的位置和大小。虽然使用起来还不能和IOS开发中StoryBoard中直接拖放控件那样方便,但也极大的方便了android的布局。它有效的解决了布局嵌套过多的问题,我们知道布局嵌套越多,性能越差,因此,使用ConstraintLayout布局复杂的界面能够极大的提高性能。

这里不介绍ConstraintLayout的使用,不清楚如何使用的建议百度学习一下,毕竟它实在是好用,一个复杂的布局使用它能够轻松搞定。

需要布局一个UI界面,实现的效果就是每一个列表项中平均分配有三个图片,图片的宽高相等。我们知道,ConstraintLayout布局中使用constraintDimensionRatio能够限制控件的宽高比。于是飞快的撸除了以下的代码:

列表Item布局代码:item_content.xml

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:app="http://schemas.android.com/apk/res-auto">

<TextView
    android:id="@+id/item_title"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="Hello"/>

<ImageView
    android:id="@+id/image1"
    android:layout_width="0dp"
    android:layout_height="0dp"
    android:layout_margin="5dp"
    android:src="@mipmap/ic_launcher"
    app:layout_constraintDimensionRatio="1:1"
    app:layout_constraintLeft_toLeftOf="parent"
    app:layout_constraintRight_toLeftOf="@id/image2"
    app:layout_constraintTop_toBottomOf="@id/item_title" />
<ImageView
    android:id="@+id/image2"
    android:layout_width="0dp"
    android:layout_height="0dp"
    app:layout_constraintDimensionRatio="h,1:1"
    app:layout_constraintLeft_toRightOf="@id/image1"
    app:layout_constraintRight_toRightOf="parent"
    app:layout_constraintTop_toTopOf="@id/image1"
    android:src="@mipmap/ic_launcher"
    android:layout_marginLeft="5dp"
    android:layout_marginRight="5dp"/>


</android.support.constraint.ConstraintLayout>
代码中有三个控件,我们主要关注两个ImageView,两个ImageView宽度平分屏幕宽度,高度和宽度相等,即
app:layout_constraintDimensionRatio="1:1"

预期结果应该是这样的:


然而然而,运行结果竟然是这样的,什么都没有,对的,不是显示代码有问题,就是两个ImageView都没有宽度和高度。


此时心理一万只草泥马正在飞奔,没办法,调试调试,将

android:layout_width="0dp"

改成

android:layout_width="100dp"

运行结果显示正常。然而这并不能解决我的问题,我需要的是平分屏幕宽度啊,于是百度到了GuideLine这个控件。这个是一个参考线,我可以设置多个参考线位于屏幕的不同位置,这样我的ImageView也可以得到占据屏幕一半的宽度了。修改代码如下:

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:app="http://schemas.android.com/apk/res-auto">
<android.support.constraint.Guideline
        android:id="@+id/guideline1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:orientation="vertical"
        app:layout_constraintGuide_percent="0.5"/>
<TextView
    android:id="@+id/item_title"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="Hello"/>

<ImageView
    android:id="@+id/image1"
    android:layout_width="0dp"
    android:layout_height="0dp"
    android:layout_margin="5dp"
    android:src="@mipmap/ic_launcher"
    app:layout_constraintDimensionRatio="1:1"
    app:layout_constraintLeft_toLeftOf="parent"
    app:layout_constraintRight_toLeftOf="@id/guideline1"
    app:layout_constraintTop_toBottomOf="@id/item_title" />
<ImageView
    android:id="@+id/image2"
    android:layout_width="0dp"
    android:layout_height="0dp"
    app:layout_constraintDimensionRatio="h,1:1"
    app:layout_constraintLeft_toRightOf="@id/guideline1"
    app:layout_constraintRight_toRightOf="parent"
    app:layout_constraintTop_toTopOf="@id/image1"
    android:src="@mipmap/ic_launcher"
    android:layout_marginLeft="5dp"
    android:layout_marginRight="5dp"/>


</android.support.constraint.ConstraintLayout>

代码其实就是在原来的代码上增加了一条位于屏幕50%的参考线。然后两个ImageView分别约束到它,于是就可以实现了需要的UI了。

总结

出现在ListView,ScrollView中无法显示控件的问题主要还是无法准确计算出控件的宽度和高度,导致他们的宽高为0.因此只要保证控件的宽度能够准确获取,就可以正常显示了。上述中直接设置宽度为100dp也好,或者设置参考线的方式也好,都是从这个思路进行解决的。

然而知道了如何解决这个问题,但还是不知道为什么在ListView,ScrollView中会出现这个问题,在Activity的布局中就不会出现这个问题。

最后附上MainActivity的布局文件和类文件。

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.qcymall.demotest.MainActivity">

<ListView
    android:id="@+id/listview"
    android:layout_width="match_parent"
    android:layout_height="0dp"
    app:layout_constraintTop_toTopOf="parent"
    app:layout_constraintBottom_toBottomOf="parent"
    android:background="#ff778899"/>
</android.support.constraint.ConstraintLayout>

MainActivity.kt

class MainActivity : AppCompatActivity() {

  override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.activity_main)
    val listView = findViewById<ListView>(R.id.listview)
    val datas = ArrayList<HashMap<String, Any>>()
    val data = HashMap<String, Any>()
    data.put("title", "Hello")
    datas.add(data)
    val adapter = SimpleAdapter(this, datas, R.layout.item_content, arrayOf("title"), intArrayOf(R.id.item_title))
    listView.setAdapter(adapter)
  }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值