如何在ConstraintLayout中刷新约束视图的高度 [英] How to refresh height of a Constrained View in ConstraintLayout

查看:156
本文介绍了如何在ConstraintLayout中刷新约束视图的高度的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个ConstraintLayout,其中有一个View(称为Bar)和一个RecyclerView,约束到Bar的底部,RecyclerView的高度设置为与Constraint(0dp)匹配,

I have a ConstraintLayout in which i have a View(called Bar) and a RecyclerView Constrained to The Bottom of The Bar, The RecyclerView has it's height set to match Constraint(0dp),

例如,如果我在Android布局编辑器中将Bar向上移动,则RecyclerView高度增加并且始终锚定"到Bar,这是可行的,

So if in The Android Layout Editor i move up The Bar for example, The RecyclerView height increase and is always "anchored" To The Bar, it's work,

但是在运行时,这是不一样的行为,当我移动Bar(使用onTouchListener)时,RecyclerView的高度根本不会改变,就像Bar在同一位置一样.

But This is Not the same behavior at runtime, when i move the Bar(with an onTouchListener), The RecyclerView height does not change at all and stay like if the Bar was at the same position..

要实现此行为(将Bar增加/减少RecyclerView的高度),我已经考虑并尝试了ConstraintLayout解决方案,

To achieve this Behavior(move the Bar increase/decrease the RecyclerView height), i have thinked and tried to The ConstraintLayout Solution,

所以我在Bar的底部设置了一个Constraint(Top),并且我将高度设置为与Constraint相匹配,

So i have set a constraint(Top) to the Bottom of the Bar and i have set the height to match the Constraint,

我也尝试使用LayoutParam实现此行为,根据移动的像素更改高度,但是公式不是100%好的,并且使用这种方式从视图的底部和顶部更改高度(显然不是通过约束解)

I have also tried to achieve this behavior with the LayoutParam, changing the height based on pixels moved, But the formula is not 100% good and using this way change height from both bottom and top of the view(apparently not with the Constraint solution)

<ConstraintLayout>
...

 <!-- Removed all Constraint to the Bar to let it freely move on Touch on it's Y Axis, also tried to constraint start, end, top to the parent, but same behavior -->
 <include layout="@layout/theBar"
             android:layout_width="match_parent" 
             android:layout_height="wrap_content"
             android:id="@+id/theBarWhoMove"/>

    <android.support.v7.widget.RecyclerView
            android:id="@+id/recyclerViewConstrainedToTheBar"
            android:layout_width="0dp"
            android:layout_height="0dp"
            android:layout_marginBottom="2dp"
            app:layout_constraintBottom_toBottomOf="parent"
            app:layout_constraintStart_toStartOf="parent"
            android:layout_marginStart="2dp"
            app:layout_constraintEnd_toEndOf="parent"
            android:layout_marginEnd="2dp"
            android:layout_marginTop="8dp"              

        app:layout_constraintTop_toBottomOf="@+id/theBarWhoMove"/>

...
</ConstraintLayout>


barWhoMove.setOnTouchListener { v, event ->

        when(event.actionMasked) {

            MotionEvent.ACTION_DOWN -> {
                barWhoMoveDY = v.y - event.rawY
                return@setOnTouchListener true
            }
            MotionEvent.ACTION_MOVE -> {
                ////We move the Bar
                v.animate().translationY(barWhoMoveDY + 
                event.rawY).setDuration(0).start()

               /* To try to relayout and resize based on match Constrain taking in consideration the new barWhoMove position*/
                recyclerViewConstrainedToTheBar.invalidate()
                recyclerViewConstrainedToTheBar.requestLayout()
                recyclerViewConstrainedToTheBar.forceLayout()

                ////Tried Also
   constraintSet.constrainHeight(recyclerViewConstrainedToTheBar.id, 
ConstraintSet.MATCH_CONSTRAINT)
   constraintSet.applyTo(rootConstraintLayout)

   ////Tried Also
   rootConstraintLayout.invalidate()
   rootConstraintLayout.requestLayout()
   rootConstraintLayout.forceLayout()

                if(v.y < oldDY) {

               /*#Solution 2 increase with LayoutParam but The formula is not 100% correct and it change height from both bottom and top, When View is moving Up or Down(it's work for detecting this)*/

              ....
              oldDy = v.y
                }
                else {
                ....
                oldDy = v.y
                }

                return@setOnTouchListener true
            }
            MotionEvent.ACTION_UP -> {
            }
        }

        return@setOnTouchListener false
    }

这是布局1中<include>标记的内容:

This is the content of The <include> tag in the layout 1 :

<?xml version="1.0" encoding="utf-8"?>

<layout 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"
    tools:showIn="@layout/fragment_layout_main">

<data>
    <variable name="variable" type="com.demo.ourClass" />
</data>

<android.support.v7.widget.CardView
  android:id="@+id/card"
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  app:layout_constraintStart_toStartOf="parent"
  app:layout_constraintTop_toBottomOf="@id/textViewTitle"
  android:layout_marginTop="8dp"
  app:cardElevation="6dp">

  <android.support.constraint.ConstraintLayout 
  android:layout_width="match_parent"                                        
  android:layout_height="match_parent">
  <ImageView
          android:layout_width="wrap_content"
          android:layout_height="wrap_content"
          app:srcCompat="@mipmap/ic_launcher_round"
          android:id="@+id/imageViewA"
          android:layout_marginTop="8dp"
          app:layout_constraintTop_toTopOf="parent"
          app:layout_constraintStart_toStartOf="parent"
          android:layout_marginStart="8dp"/>
  <TextView
          android:text="@{variable.name}"
          tools:text="TextView"
          android:textAppearance="@style/TextAppearance.AppCompat.Light.SearchResult.Title"
          android:layout_width="wrap_content"
          android:layout_height="wrap_content"
          android:id="@+id/textViewA"
          app:layout_constraintStart_toEndOf="@+id/imageViewA"
          app:layout_constraintBottom_toBottomOf="@id/imageViewA"
          android:layout_marginStart="8dp" 
          android:layout_marginTop="8dp"
          app:layout_constraintTop_toTopOf="parent"/>

  </android.support.constraint.ConstraintLayout>

</android.support.v7.widget.CardView>

推荐答案

您正在为视图的translationY属性设置动画.更改此值将移动视图帖子布局.换句话说,先完成布局,然后进行移动.结果,RecyclerView被限制在平移之前的布局后位置.参见 setTranslationY(float):

You are animating the translationY property of the view. Changing this value moved the view post layout. In other words, the layout is completed then the move is made. As a result, the RecyclerView is constrained to the post-layout position before the translation. See setTranslationY(float):

设置此视图相对于其顶部位置的垂直位置.除了将对象的布局放置在任何位置之外,这还可以有效地放置对象在布局后的位置.

Sets the vertical location of this view relative to its top position. This effectively positions the object post-layout, in addition to wherever the object's layout placed it.

这篇关于如何在ConstraintLayout中刷新约束视图的高度的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆