运动布局不适用 window 插图

Motion layout does not apply window insets

ViewCompat.setOnApplyWindowInsetsListener(fab) { view, insets ->
        val lp = fab.layoutParams as ConstraintLayout.LayoutParams
        lp.bottomMargin += insets.systemWindowInsetBottom
        fab.layoutParams = lp
        insets
    }

Motion 布局不会将任何 window 插入传递给子级,尽管在 OnApplyWindowInsetsListener 侦听器中显式使用了插入。

当运动布局的 applyMotionScene 属性设置为 false 时,可以正确应用插图。

with(ml) { //ml -> your motionLayout id
                    updateState(R.id.start, ConstraintSet().apply {
                        clone(ml)
                        constrainHeight(viewWhichHeightNeedsToChange.id, height.dp + insets.systemWindowInsetTop)
                        applyTo(ml)
                    })
                    setState(R.id.end, ml.width, ml.height)
                    updateState(R.id.end, ConstraintSet().apply {
                        clone(ml)
                        constrainHeight(viewWhichHeightNeedsToChange.id, height.dp + insets.systemWindowInsetTop)
                        applyTo(ml)
                    })
                    setState(R.id.start, ml.width, ml.height)
                }

基本上,您需要更新两个运动布局集中的 padding/size 个视图。如果有一种方法可以在不切换状态的情况下这样做,那就太好了。此代码在 setOnApplyWindowInsetsListener { } 中执行 与

合作

androidx.constraintlayout:constraintlayout:2.0.0-beta3

您可以直接更新每个状态,按照 documentation getConstraintSet return link 到状态。

Get the ConstraintSet associated with an id This returns a link to the constraintset But in most cases can be used. createConstraintSet makes a copy which is more expensive.

ViewCompat.setOnApplyWindowInsetsListener(fab) { view, insets ->
    val bottom = lp.marginBottom + insets.systemWindowInsetBottom

    with(motionLaytout) {
        getConstraintSet(R.id.state_id).apply {
            setMargin(fab.id, ConstraintSet.BOTTOM, bottom)
        }

        getConstraintSet(R.id.another_state_id).apply {
            setMargin(fab.id, ConstraintSet.BOTTOM, bottom)
        }
    }

    insets
}