Java – Android visibility from GONE to VISIBLE didn’t work for the first time

Android visibility from GONE to VISIBLE didn’t work for the first time… here is a solution to the problem.

Android visibility from GONE to VISIBLE didn’t work for the first time

Hello, I have a problem with the animation I tried to make.

I use this library AndroidViewAnimations

Here is my layout xml code:

    <Button
         android:id="@+id/buttonDetails"
         style="@style/Button_Details"/>

<LinearLayout
        android:id="@+id/linearLayoutDetails"
        android:visibility="gone"
        style="@style/LinearLayout_Details">

<CheckBox
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="@string/checkbox_clmn_text"
            android:checked="true"/>
        <CheckBox
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="@string/checkbox_clme_text"
            android:checked="true"/>
        <CheckBox
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="@string/checkbox_clmn_text"
            android:checked="true"/>
        <CheckBox
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="@string/checkbox_clmn_text"
            android:checked="true"/>
        <CheckBox
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="@string/checkbox_clmn_text"
            android:checked="true"/>
        <CheckBox
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="@string/checkbox_clmn_text"
            android:checked="true"/>

</LinearLayout>

Here is my java code:

// Declare Variables
@ViewById
LinearLayout linearLayoutDetails;

@Click
void buttonDetails() {
     Checks Linear Layout Visibility
    if (linearLayoutDetails.getVisibility() == View.GONE) {
         Sets linearLayoutDetails Visibility to VISIBLE
        linearLayoutDetails.setVisibility(View.VISIBLE);
         Makes Appear Animation
        YoYo.with(Techniques.SlideInDown)
                .duration(700)
                .playOn(linearLayoutDetails);
    } else {
        linearLayoutDetails.setVisibility(View.GONE);
    }
}

The problem now is that the animation doesn’t work the first time I press the button, but every other time after that.

I

did some research and found that the problem was that I set the visibility to disappear and if I set it to invisible, it worked fine from the first time. The thing is I don’t want visibility to be invisible but disappear because I don’t want the linear layout to take up space when hidden.

Any ideas?

Solution

I solved this problem just a few minutes ago using ViewTreeObserver. In the example below, the variable currentMode is the View I want to animate in and out. Its default value is “disappear” and the problem I’m having is exactly the same as the one you’re having.

Here’s how I solved it :

ViewTreeObserver vto = currentMode.getViewTreeObserver();
vto.addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
    @Override
    public void onGlobalLayout() {
        if(currentMode.isShown()) {
            YoYo.with(Techniques.SlideInDown).duration(250).playOn(currentMode);
        }
    }
});
currentMode.setVisibility(mShouldShowMode ? View.VISIBLE : View.GONE);

Using ViewTreeObserver, we can observe global changes in the UI and then use react. The View.isShown() method checks if it is visible. If so, then I start playing the animation. This works well for me.

Then for the exit animation

, you must attach the listener to the exit animation like this:

YoYo.with(Techniques.SlideOutUp).duration(250).withListener(new Animator.AnimatorListener() {
    @Override
    public void onAnimationStart(Animator animation) {

}

@Override
    public void onAnimationEnd(Animator animation) {
        currentMode.setVisibility(View.GONE);
    }

@Override
    public void onAnimationCancel(Animator animation) {

}

@Override
    public void onAnimationRepeat(Animator animation) {

}
}).playOn(currentMode);

Related Problems and Solutions