Mostrar y ocultar una vista con una animación de desplazamiento hacia arriba / abajo

318

Tengo un LinearLayoutque quiero mostrar u ocultar con unAnimation que empuja el diseño hacia arriba o hacia abajo cada vez que cambio su visibilidad.

He visto algunas muestras por ahí, pero ninguna de ellas satisface mis necesidades.

He creado dos archivos xml para las animaciones, pero no sé cómo iniciarlos cuando cambio la visibilidad de a LinearLayout.

MichelReap
fuente

Respuestas:

640

Con la nueva API de animación que se introdujo en Android 3.0 (Honeycomb) es muy sencillo crear tales animaciones.

Deslizando un Viewdown por una distancia:

view.animate().translationY(distance);

Más tarde, puede deslizar la parte Viewposterior a su posición original de esta manera:

view.animate().translationY(0);

También puede combinar fácilmente múltiples animaciones. La siguiente animación se deslizará Viewhacia abajo por su altura y se desvanecerá al mismo tiempo:

// Prepare the View for the animation
view.setVisibility(View.VISIBLE);
view.setAlpha(0.0f);

// Start the animation
view.animate()
    .translationY(view.getHeight())
    .alpha(1.0f)
    .setListener(null);

Luego puede desvanecer el Viewrespaldo y deslizarlo nuevamente a su posición original. También configuramos un AnimatorListenermodo para que podamos configurar la visibilidad de la parte Viewposterior GONEuna vez que finaliza la animación:

view.animate()
    .translationY(0)
    .alpha(0.0f)
    .setListener(new AnimatorListenerAdapter() {
        @Override
        public void onAnimationEnd(Animator animation) {
            super.onAnimationEnd(animation);
            view.setVisibility(View.GONE);
        }
    });
Xaver Kapeller
fuente
1
¿Por qué la vista no es visible una vez que se fue?
Ram
1
Quiero animar la vista cuando sea visible y cuando desaparezca. pero si primero fui a ver. no se puede ver y el lugar de vista está en blanco
Ram
3
@Ram ¿Qué estás tratando de lograr animando un Viewcuando su visibilidad está configurada View.GONE? Si establece su visibilidad en cualquier cosa además de View.VISIBLEeso View, no será visible. No entiendo lo que preguntas. Si desea que su animación sea visible, no configure la visibilidad de Viewa View.GONE.
Xaver Kapeller
2
enfrentando el mismo problema al que se enfrentaba Ram, la primera vez funciona bien, pero desde la próxima vez que haga esa vista en estado inactivo e intente hacer que esa vista sea visible nuevamente, no aparece.
Pankaj kumar
12
@XaverKapeller Creo que el problema es que muchos tienen de que el oyente onAnimationEndse llama cada vez que para una animación múltiples que ocurren, lo que significa que onAnimationEndse llama también cuando la vista consigue muestra, que establece su visibilidad a Ido, etc.
oldergod
129

Estaba teniendo problemas para entender y aplicar la respuesta aceptada. Necesitaba un poco más de contexto. Ahora que lo he descubierto, aquí hay un ejemplo completo:

ingrese la descripción de la imagen aquí

MainActivity.java

public class MainActivity extends AppCompatActivity {

    Button myButton;
    View myView;
    boolean isUp;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        myView = findViewById(R.id.my_view);
        myButton = findViewById(R.id.my_button);

        // initialize as invisible (could also do in xml)
        myView.setVisibility(View.INVISIBLE);
        myButton.setText("Slide up");
        isUp = false;
    }

    // slide the view from below itself to the current position
    public void slideUp(View view){
        view.setVisibility(View.VISIBLE);
        TranslateAnimation animate = new TranslateAnimation(
                0,                 // fromXDelta
                0,                 // toXDelta
                view.getHeight(),  // fromYDelta
                0);                // toYDelta
        animate.setDuration(500);
        animate.setFillAfter(true);
        view.startAnimation(animate);
    }

    // slide the view from its current position to below itself
    public void slideDown(View view){
        TranslateAnimation animate = new TranslateAnimation(
                0,                 // fromXDelta
                0,                 // toXDelta
                0,                 // fromYDelta
                view.getHeight()); // toYDelta
        animate.setDuration(500);
        animate.setFillAfter(true);
        view.startAnimation(animate);
    }

    public void onSlideViewButtonClick(View view) {
        if (isUp) {
            slideDown(myView);
            myButton.setText("Slide up");
        } else {
            slideUp(myView);
            myButton.setText("Slide down");
        }
        isUp = !isUp;
    }
}

activity_mail.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context="com.example.slideview.MainActivity">

    <Button
        android:id="@+id/my_button"
        android:layout_centerHorizontal="true"
        android:layout_marginTop="100dp"
        android:onClick="onSlideViewButtonClick"
        android:layout_width="150dp"
        android:layout_height="wrap_content"/>

    <LinearLayout
        android:id="@+id/my_view"
        android:background="#a6e1aa"
        android:orientation="vertical"
        android:layout_alignParentBottom="true"
        android:layout_width="match_parent"
        android:layout_height="200dp">

    </LinearLayout>

</RelativeLayout>

Notas

  • Gracias a este articulo por señalarme en la dirección correcta. Fue más útil que las otras respuestas en esta página.
  • Si desea comenzar con la vista en pantalla, no la inicialice como INVISIBLE .
  • Como lo estamos animando completamente fuera de la pantalla, no es necesario volver a configurarlo INVISIBLE. Sin embargo, si no está animando completamente fuera de la pantalla, puede agregar una animación alfa y establecer la visibilidad con un AnimatorListenerAdapter.
  • Documentos de animación de propiedades
Suragch
fuente
android: visibilidad = "invisible" para inicializar la animación de vista como una ocultación
Goodlife
2
No recomiendo el uso de animate.setFillAfter (verdadero); si tiene vistas en las que se puede hacer clic debajo de la vista deslizada, no recibirá eventos
HOCiNE BEKKOUCHE
2
Tenga en cuenta que sin .setVisibility(View.INVISIBLE);la función deslizar hacia arriba no funcionará como se esperaba visualmente.
Avance S
Translate Animationmueve la vista. Si desea animar la vista al igual que su escala por sí mismo a continuación, utilizarScaleAnimation anim = new ScaleAnimation(1, 1, 0, 1)
Zohab Ali
33

Ahora las animaciones de cambio de visibilidad deben hacerse a través del Transition APIpaquete de soporte disponible (androidx). Simplemente llame al método TransitionManager.beginDelayedTransition con la transición Slide y luego cambie la visibilidad de la vista.

ingrese la descripción de la imagen aquí

import androidx.transition.Slide;
import androidx.transition.Transition;
import androidx.transition.TransitionManager;

private void toggle(boolean show) {
    View redLayout = findViewById(R.id.redLayout);
    ViewGroup parent = findViewById(R.id.parent);

    Transition transition = new Slide(Gravity.BOTTOM);
    transition.setDuration(600);
    transition.addTarget(R.id.redLayout);

    TransitionManager.beginDelayedTransition(parent, transition);
    redLayout.setVisibility(show ? View.VISIBLE : View.GONE);
}

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/parent"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <Button
        android:id="@+id/btn"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="play" />

    <LinearLayout
        android:id="@+id/redLayout"
        android:layout_width="match_parent"
        android:layout_height="400dp"
        android:background="#5f00"
        android:layout_alignParentBottom="true" />
</RelativeLayout>

Verifique esta respuesta con otros ejemplos de transición predeterminados y personalizados.

ashakirov
fuente
@akubi sí, debería ser
Aba
1
¡Una de las mejores y más fáciles respuestas! ¡Gracias!
krisDrOid
solo para tener en cuenta, esto requiereminSdkVersion 21
lasec0203
@ lasec0203 no, las clases son del androidxpaquete. Funciona bien en pre 21 api.
ashakirov
: thumbs_up: esto eliminó un error de ambigüedad del método que estaba recibiendo
lasec0203
30

La solución más fácil: configurar android:animateLayoutChanges="true"en el contenedor que contiene sus vistas.

Para ponerlo en algún contexto: si tiene un diseño como el siguiente, todos los cambios de visibilidad de las vistas en este contenedor se animarán automáticamente.

<LinearLayout android:id="@+id/container"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:animateLayoutChanges="true"
    >

    <Views_which_change_visibility>

</LinearLayout>

Puede encontrar más detalles sobre esto en Animating Layout Changes - Desarrollador de Android

Stefan Medack
fuente
Es el más fácil, pero su comportamiento difiere debido al fabricante del teléfono y a los cambios de código
B2mob
Esto anima el alfa, no la posición.
Suragch
Sí, pero de eso se trataba la pregunta original si la entendía correctamente. Si desea animar posiciones, puede usar un RecyclerView que use ViewHolders con identificadores estables.
Stefan Medack
12

Puede iniciar el correcto Animationcuando la visibilidad de los LinearLayoutcambios crea una nueva subclase de LinearLayouty anular setVisibility()para iniciar el Animations. Considera algo como esto:

public class SimpleViewAnimator extends LinearLayout
{
    private Animation inAnimation;
    private Animation outAnimation;

    public SimpleViewAnimator(Context context)
    {
        super(context);
    }

    public void setInAnimation(Animation inAnimation)
    {
        this.inAnimation = inAnimation;
    }

    public void setOutAnimation(Animation outAnimation)
    {
        this.outAnimation = outAnimation;
    }

    @Override
    public void setVisibility(int visibility)
    {
        if (getVisibility() != visibility)
        {
            if (visibility == VISIBLE)
            {
                if (inAnimation != null) startAnimation(inAnimation);
            }
            else if ((visibility == INVISIBLE) || (visibility == GONE))
            {
                if (outAnimation != null) startAnimation(outAnimation);
            }
        }

        super.setVisibility(visibility);
    }
}
Xaver Kapeller
fuente
1
De hecho, me gusta más el enfoque de subclase. Muchas gracias.
MichelReap
1
Esta es una solución increíble que voy a implementar en mi BaseView. Gracias por esto!
Bram Vandenbussche
1
Como esto funciona al mostrar, al ocultar, la vista desaparece antes de que se pueda ver la animación. ¿Alguna solución?
Bernardo
12
@BramVandenbussche Esta es una solución terrible. Hace al Viewresponsable de sus propias animaciones, que NUNCA es lo que quieres. Imagine que desea animar de manera Viewdiferente en otra parte de su aplicación. ¿Que haces entonces? ¿Agregar una bandera para no animar automáticamente la visibilidad? Subclase Viewy anular setVisibility()para eliminar la animación? ¿O peor aún implementar setVisibility()con otra animación? Simplemente se pone más y más feo a partir de ahí. No use esta "solución".
Xaver Kapeller
3
Mejor llámalo AnimatedLinearLayout
Roel
12

Kotlin

Basado en la respuesta de Suragch , aquí hay una manera elegante usando la extensión Ver:

fun View.slideUp(duration: Int = 500) {
    visibility = View.VISIBLE
    val animate = TranslateAnimation(0f, 0f, this.height.toFloat(), 0f)
    animate.duration = duration.toLong()
    animate.fillAfter = true
    this.startAnimation(animate)
}

fun View.slideDown(duration: Int = 500) {
    visibility = View.VISIBLE
    val animate = TranslateAnimation(0f, 0f, 0f, this.height.toFloat())
    animate.duration = duration.toLong()
    animate.fillAfter = true
    this.startAnimation(animate)
}

Y luego, donde quieras usarlo, solo necesitas myView.slideUp()omyView.slideDown()

Đorđe Nilović
fuente
El único error es que no necesita "fillAfter = true" ya que bloquea las vistas secundarias de accesibilidad de clics
Ranjan
También es probable que necesite agregar un oyente a la animación slideDown y hacer que la vista se vaya en AnimationEnd.
Manohar Reddy
9
if (filter_section.getVisibility() == View.GONE) {
    filter_section.animate()
            .translationY(filter_section.getHeight()).alpha(1.0f)
            .setListener(new AnimatorListenerAdapter() {
                @Override
                public void onAnimationStart(Animator animation) {
                    super.onAnimationStart(animation);
                    filter_section.setVisibility(View.VISIBLE);
                    filter_section.setAlpha(0.0f);
                }
            });
} else {
    filter_section.animate()
            .translationY(0).alpha(0.0f)
            .setListener(new AnimatorListenerAdapter() {
                @Override
                public void onAnimationEnd(Animator animation) {
                    super.onAnimationEnd(animation);
                    filter_section.setVisibility(View.GONE);
                }
            });
}
Ameen Maheen
fuente
10
Problemas con esta respuesta: 1) Formato de código terrible. 2) Utiliza un fragmento de código para publicar código que en realidad no se puede ejecutar en el navegador. Esto no solo agrega dos botones inútiles, sino que también destruye el resaltado de sintaxis. 3) Es solo un volcado de código aleatorio sin ninguna explicación o propósito. 4) Estás cambiando la visibilidad mientras realizas una animación. Aparte del hecho de que este código es obvio, esto tampoco funcionará correctamente. El cambio de visibilidad inicia un nuevo proceso de diseño, solo después de que finaliza, la animación realmente tiene valores con los que trabajar. La lista sigue y sigue ...
Xaver Kapeller
Ya edité su respuesta para corregir el formato y convertí el fragmento de código en un bloque de código real. Pero tienes que completar el resto ...
Xaver Kapeller
Lo siento, amigo, inventé el código tuyo porque no funciona bien para mí, este código mío funciona. Pero los cambios necesarios en la forma de publicación estoy de acuerdo.
Ameen Maheen
@AmeenMaheen ¿Para qué sirve setAlpha?
IgorGanapolsky
@ Igor Ganapolsky se utiliza para la transparencia es decir, para dar un efecto de desvanecimiento
Ameen Maheen
4

puede deslizar hacia arriba y hacia abajo cualquier vista o diseño utilizando el siguiente código en la aplicación de Android

boolean isClicked=false;
LinearLayout mLayoutTab = (LinearLayout)findViewById(R.id.linearlayout);

        if(isClicked){
                    isClicked = false;
                    mLayoutTab.animate()
                    .translationYBy(120)
                    .translationY(0)     
                    .setDuration(getResources().getInteger(android.R.integer.config_mediumAnimTime));

        }else{
                isClicked = true;
                mLayoutTab.animate()
                .translationYBy(0)
                .translationY(120)
                .setDuration(getResources().getInteger(android.R.integer.config_mediumAnimTime));
                }
varotariya vajsi
fuente
que es 120 y que es 0? ¿Cuál es la unidad para setDuration si quiero codificar esto?
Stanley Santos el
1
aquí 120 y 0 es la distancia relacionada con el eje Y si coloca un código rígido en lugar de tener un problema en una pantalla grande o tableta, por lo tanto, debe poner el valor de su valor string.xml para todos los dispositivos diferentes. y la duración es el tiempo que desea mostrar la animación del diseño ... !!! disculpa mi pobre ingles...!
varotariya vajsi
@varotariyavajsi Esto en realidad no muestra / oculta la visibilidad de una vista.
IgorGanapolsky
hola igor ganapolsky, lo sé ... es solo traducir la vista en y dirección, si el usuario necesita aparecer arriba y abajo como un control deslizante inferior, funcionará bien.
varotariya vajsi
4

Usa esta clase:

public class ExpandCollapseExtention {

 public static void expand(View view) {
    view.setVisibility(View.VISIBLE);

    final int widthSpec = View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED);
    final int heightSpec = View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED);
    view.measure(widthSpec, heightSpec);

    ValueAnimator mAnimator = slideAnimator(view, 0, view.getMeasuredHeight());
    mAnimator.start();
}


public static void collapse(final View view) {
    int finalHeight = view.getHeight();

    ValueAnimator mAnimator = slideAnimator(view, finalHeight, 0);

    mAnimator.addListener(new Animator.AnimatorListener() {

        @Override
        public void onAnimationEnd(Animator animator) {               
            view.setVisibility(View.GONE);
        }


        @Override
        public void onAnimationStart(Animator animation) {

        }


        @Override
        public void onAnimationCancel(Animator animation) {

        }


        @Override
        public void onAnimationRepeat(Animator animation) {

        }
    });
    mAnimator.start();
}


private static ValueAnimator slideAnimator(final View v, int start, int end) {

    ValueAnimator animator = ValueAnimator.ofInt(start, end);

    animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {

        @Override
        public void onAnimationUpdate(ValueAnimator valueAnimator) {

            int value = (Integer) valueAnimator.getAnimatedValue();
            ViewGroup.LayoutParams layoutParams = v.getLayoutParams();
            layoutParams.height = value;
            v.setLayoutParams(layoutParams);
        }
    });
    return animator;
}
}
amin
fuente
3

Usando ObjectAnimator

private fun slideDown(view: View) {
    val height = view.height
    ObjectAnimator.ofFloat(view, "translationY", 0.toFloat(), height.toFloat()).apply {
        duration = 1000
        start()
    }
}

private fun slideUp(view: View) {
    val height = view.height
    ObjectAnimator.ofFloat(view, "translationY", height.toFloat(),0.toFloat()).apply {
        duration = 1000
        start()
    }
}
Vihaan Verma
fuente
2
Mejoras menores: podemos usar View.TRANSLATION_Y constante en lugar de "translationY" y también en el ObjectAnimation deslizable hacia arriba podemos hacer .apply {doOnEnd {view.visibility = View.GONE} .......}. Start ()
tashi
0.toFloat()también puede ser0f
styler1972
2

Tenía una vitrina en la que la altura de mi vista todavía era zerotan ...

import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.view.View;

public final class AnimationUtils {

  public static void slideDown(final View view) {
        view.animate()
                .translationY(view.getHeight())
                .alpha(0.f)
                .setListener(new AnimatorListenerAdapter() {
                    @Override
                    public void onAnimationEnd(Animator animation) {
                        // superfluous restoration
                        view.setVisibility(View.GONE);
                        view.setAlpha(1.f);
                        view.setTranslationY(0.f);
                    }
                });
    }

    public static void slideUp(final View view) {
        view.setVisibility(View.VISIBLE);
        view.setAlpha(0.f);

        if (view.getHeight() > 0) {
            slideUpNow(view);
        } else {
            // wait till height is measured
            view.post(new Runnable() {
                @Override
                public void run() {
                    slideUpNow(view);
                }
            });
        }
    }

    private static void slideUpNow(final View view) {
        view.setTranslationY(view.getHeight());
        view.animate()
                .translationY(0)
                .alpha(1.f)
                .setListener(new AnimatorListenerAdapter() {
                    @Override
                    public void onAnimationEnd(Animator animation) {
                        view.setVisibility(View.VISIBLE);
                        view.setAlpha(1.f);
                    }
                });
    }

}
Samuel
fuente
1

Aquí está mi solución. Simplemente obtenga una referencia a su punto de vista y llame a este método:

public static void animateViewFromBottomToTop(final View view){

    view.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {

        @Override
        public void onGlobalLayout() {

            view.getViewTreeObserver().removeOnGlobalLayoutListener(this);

            final int TRANSLATION_Y = view.getHeight();
            view.setTranslationY(TRANSLATION_Y);
            view.setVisibility(View.GONE);
            view.animate()
                .translationYBy(-TRANSLATION_Y)
                .setDuration(500)
                .setStartDelay(200)
                .setListener(new AnimatorListenerAdapter() {

                    @Override
                    public void onAnimationStart(final Animator animation) {

                        view.setVisibility(View.VISIBLE);
                    }
                })
                .start();
        }
    });
}

No es necesario hacer nada más =)

Tiago
fuente
1
¿Por qué necesitarías un GlobalLayoutListener para hacer esto? ¿Por qué estás configurando la visibilidad de una manera tan extraña? ¿Por qué incluye cosas como un retraso de inicio que es irrelevante para la pregunta en su respuesta?
Xaver Kapeller
1

La respuesta de Suragch en Kotlin. Esto funcionó para mí.

class MainActivity : AppCompatActivity() {

var isUp: Boolean = false

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.activity_main)

    var myView: View = findViewById(R.id.my_view)
    var myButton: Button = findViewById(R.id.my_button)

    //Initialize as invisible
    myView.visibility = View.INVISIBLE
    myButton.setText("Slide up")

    isUp = false

}


fun View.slideUp(duration: Int = 500){
    visibility = View.VISIBLE
    val animate = TranslateAnimation(0f, 0f, this.height.toFloat(), 0f)
    animate.duration = duration.toLong()
    animate.fillAfter = true
    this.startAnimation(animate)
}

fun View.slideDown(duration: Int = 500) {
    visibility = View.VISIBLE
    val animate = TranslateAnimation(0f, 0f, 0f, this.height.toFloat())
    animate.duration = duration.toLong()
    animate.fillAfter = true
    this.startAnimation(animate)
}

fun onSlideViewButtonClick(view: View){
    if(isUp){
        my_view.slideDown()
        my_button.setText("Slide Up")

    }
    else{
        my_view.slideUp()
        my_button.setText("Slide Down")
    }
    isUp = !isUp
}

}

olle
fuente
0

Puede usar las tres líneas de código simples para mostrar la animación ...

//getting the hiding view by animation

 mbinding.butn.setOnClickListener {

                val SlideOutLeft = AnimationUtils.loadAnimation(this, R.anim.slide_out_left)
                simplelayout.visibility = View.INVISIBLE
                simplelayout.startAnimation(SlideOutLeft)


                val SlideInRight = AnimationUtils.loadAnimation(applicationContext, R.anim.slide_in_right)
                animation1.visibility = View.VISIBLE
                animation1.startAnimation(SlideInRight)

            }
            //again unhide the view animation
            mbinding.buttn.setOnClickListener {


               val SlideInLeft=AnimationUtils.loadAnimation(this,R.anim.slide_in_left)
                //set the layout
               simplelayout.visibility=View.VISIBLE
               simplelayout.startAnimation(SlideInLeft)

               val SlideOutRight=AnimationUtils.loadAnimation(this,R.anim.slide_out_right)
               animation1.visibility=View.INVISIBLE
               animation1.startAnimation(SlideOutRight)

            }
Yogesh Singh Pathania
fuente
0

Con las extensiones de Kotlin puedes usar esto:

enum class SlideDirection{
    UP,
    DOWN,
    LEFT,
    RIGHT
}

enum class SlideType{
    SHOW,
    HIDE
}

fun View.slideAnimation(direction: SlideDirection, type: SlideType, duration: Long = 250){
    val fromX: Float
    val toX: Float
    val fromY: Float
    val toY: Float
    val array = IntArray(2)
    getLocationInWindow(array)
    if((type == SlideType.HIDE && (direction == SlideDirection.RIGHT || direction == SlideDirection.DOWN)) ||
        (type == SlideType.SHOW && (direction == SlideDirection.LEFT || direction == SlideDirection.UP))   ){
        val displayMetrics = DisplayMetrics()
        val windowManager = context.getSystemService(Context.WINDOW_SERVICE) as WindowManager
        windowManager.defaultDisplay.getMetrics(displayMetrics)
        val deviceWidth = displayMetrics.widthPixels
        val deviceHeight = displayMetrics.heightPixels
        array[0] = deviceWidth
        array[1] = deviceHeight
    }
    when (direction) {
        SlideDirection.UP -> {
            fromX = 0f
            toX = 0f
            fromY = if(type == SlideType.HIDE) 0f else (array[1] + height).toFloat()
            toY = if(type == SlideType.HIDE) -1f * (array[1] + height)  else 0f
        }
        SlideDirection.DOWN -> {
            fromX = 0f
            toX = 0f
            fromY = if(type == SlideType.HIDE) 0f else -1f * (array[1] + height)
            toY = if(type == SlideType.HIDE) 1f * (array[1] + height)  else 0f
        }
        SlideDirection.LEFT -> {
            fromX = if(type == SlideType.HIDE) 0f else 1f * (array[0] + width)
            toX = if(type == SlideType.HIDE) -1f * (array[0] + width) else 0f
            fromY = 0f
            toY = 0f
        }
        SlideDirection.RIGHT -> {
            fromX = if(type == SlideType.HIDE) 0f else -1f * (array[0] + width)
            toX = if(type == SlideType.HIDE) 1f * (array[0] + width) else 0f
            fromY = 0f
            toY = 0f
        }
    }
    val animate = TranslateAnimation(
        fromX,
        toX,
        fromY,
        toY
    )
    animate.duration = duration
    animate.setAnimationListener(object: Animation.AnimationListener{
        override fun onAnimationRepeat(animation: Animation?) {

        }

        override fun onAnimationEnd(animation: Animation?) {
            if(type == SlideType.HIDE){
                visibility = View.INVISIBLE
            }
        }

        override fun onAnimationStart(animation: Animation?) {
            visibility = View.VISIBLE
        }

    })
    startAnimation(animate)
}

Ejemplo para la extensión:

view.slideAnimation(SlideDirection.UP, SlideType.HIDE)//to make it disappear through top of the screen
view.slideAnimation(SlideDirection.DOWN, SlideType.SHOW)//to make it reappear from top of the screen

view.slideAnimation(SlideDirection.DOWN, SlideType.HIDE)//to make it disappear through bottom of the screen
view.slideAnimation(SlideDirection.UP, SlideType.SHOW)//to make it reappear from bottom of the screen
Mertcan Çüçen
fuente
0

Una de las formas simples:

containerView.setLayoutTransition(LayoutTransition())
containerView.layoutTransition.enableTransitionType(LayoutTransition.CHANGING)
hallz12
fuente