изменить ширину макета с анимацией в Android - PullRequest
0 голосов
/ 05 февраля 2019

Я пытаюсь изменить мою относительную ширинуLayout с помощью анимации. Моя цель - изменить ширину WRAP_CONTENT на MATCH_PARENT с анимацией. Вот мой исходный код

private void setWidthAnimation(View view, int currentHeight, int newHeight) {
    ValueAnimator slideAnimator = ValueAnimator
            .ofInt(currentHeight, newHeight)
            .setDuration(1000);
    slideAnimator.addUpdateListener(animation -> {
        Integer value = (Integer) animation.getAnimatedValue();
        view.getLayoutParams().width = value.intValue();

        view.requestLayout();
    });
    AnimatorSet set = new AnimatorSet();

    set.play(slideAnimator);
    set.setInterpolator(new BounceInterpolator());
    set.start();
    view.setBackgroundColor(Color.RED);
}

Я называю этот метод следующим образом

  if (isKeyBoardOpen)
            setWidthAnimation(gifEditableLayout, ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.MATCH_PARENT);
        else
            setWidthAnimation(gifEditableLayout, ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT);

Но когда я запускаю свое приложение, ширина представления изменилась, но без анимации.Может кто-нибудь объяснить мне, что я делаю не так?Спасибо

Ответы [ 3 ]

0 голосов
/ 05 февраля 2019

Я действительно не знаю, что с вашим кодом, но я могу предложить вам свой вариант: поместить вашего родственника в Constraint и работать с анимацией набора ограничений.Запустите xml

<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"
    android:id="@+id/rootContainer"
    tools:context=".MainActivity">

    <RelativeLayout
        android:id="@+id/rLayout"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@color/colorAccent"
        app:layout_constraintTop_toTopOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintEnd_toEndOf="parent">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="Hello World!"
            app:layout_constraintBottom_toBottomOf="parent"
            app:layout_constraintLeft_toLeftOf="parent"
            app:layout_constraintRight_toRightOf="parent"
            app:layout_constraintTop_toTopOf="parent" />

    </RelativeLayout>

и код:

RelativeLayout layout;
ConstraintLayout root;

... 

layout = findViewById(R.id.rLayout);
root = findViewById(R.id.rootContainer);

public void animate() {
    ConstraintLayout.LayoutParams params = new ConstraintLayout.LayoutParams(0, 0);
    layout.setLayoutParams(params);
    ConstraintSet set = new ConstraintSet();
    set.clone(root);
    set.connect(layout.getId(), ConstraintSet.BOTTOM, root.getId(), ConstraintSet.BOTTOM);
    set.connect(layout.getId(), ConstraintSet.TOP, root.getId(), ConstraintSet.TOP);
    set.connect(layout.getId(), ConstraintSet.LEFT, root.getId(), ConstraintSet.LEFT);
    set.connect(layout.getId(), ConstraintSet.RIGHT, root.getId(), ConstraintSet.RIGHT);
    AutoTransition transition = new AutoTransition();
    transition.setDuration(1000);
    TransitionManager.beginDelayedTransition(root, transition);
    set.applyTo(root);
}
0 голосов
/ 05 февраля 2019

Основная проблема вашего кода в том, что у вас нет реальных значений ширины.

Если вы посмотрите на ваш setWidthAnimation() метод, посмотрите, где он говорит:

ValueAnimator slideAnimator = ValueAnimator
        .ofInt(currentHeight, newHeight)
        .setDuration(1000);

В частности, посмотрите на currentHeight и newHeight ,Вы знаете, каковы значения этих двух переменных типа int?

setWidthAnimation(gifEditableLayout, ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.MATCH_PARENT);

В качестве значений ширины вы используете ViewGroup.LayoutParams.WRAP_CONTENT и ViewGroup.LayoutParams.MATCH_PARENT.Однако ни один из них не является фактической шириной вашего просмотра.

Вместо этого они являются просто статическими константами LayoutParams:

  • MATCH_PARENT - статическая целая константа со значением -1

  • WRAP_CONTENT - статическая int-константа со значением -2

Таким образом, вы по сути указываете ValueAnimator анимировать значение -1до -2 или от -2 до -1 в течение 1 секунды.

Кроме того, вы просто устанавливаете -1 или -2 для ширины LayoutParam.К счастью для вас, это действительно обеспечивает готовый внешний вид вашего представления, поскольку ширина представления может иметь 3 типа возможностей:

  • layoutParams.width =-1; Это то же самое, что вызов FILL_PARENT или MATCH_PARENT

  • layoutParams.width = -2; Это то же самое, что вызовWRAP_CONTENT

  • layoutParams.width = ANY_OTHER_INT; Это то же самое, что и прямая установка ширины для этого значения.

Однако никакой анимации не произойдет.

Причина этого в том, что ValueAnimator на самом деле не выполняет анимацию.Вы можете думать об этом больше как счетчик чисел.Вы кодировали его для подсчета значений int от -1 до -2 за промежуток времени в 1 секунду.Поэтому, когда это начинается, это в WRAP_CONTENT.Следующее возможное значение типа int равно -2, что является окончательным значением, поэтому оно будет обновлено ровно через 1 секунду.Через секунду он обновляет и запускает код, который устанавливает ширину представления на -2.Это немедленно вынуждает Вид быть MATCH_PARENT.

Итак, чтобы это исправить, вам нужно передать действительные целочисленные значения в ваш метод setWidthAnimation().

0 голосов
/ 05 февраля 2019

Попробуйте поместить android:animateLayoutChanges="true" в родительское представление (XML).Дополнительная информация: https://proandroiddev.com/the-little-secret-of-android-animatelayoutchanges-e4caab2fddec

...