AAkira / ExpandableLayout

[Deprecated] An android library that brings the expandable layout with various animation. You can include optional contents and use everywhere.
Apache License 2.0
1.65k stars 325 forks source link

Strange behavior #28

Closed AlexandruDev closed 8 years ago

AlexandruDev commented 8 years ago

I want to use this library in my app but I'm facing some issues with it. I have a ViewPager with 3 Tabs, first 2 are displaying some images and the last one has a RecyclerView displaying 5 Card Views. Once expanded, each Card will display 3 paragraphs, except the last Card which has only 1 paragraph and it's the one that's bodering me because it expands too much . I recorded a bit so you can make an idea of what's going on. Also the second Card is showing only 1 paragraph instead of 3, but not always... Sorry for my english and thanks a lot for this library!

The video: https://vid.me/HGTv

Last tab from the ViewPager:

public class Tab3 extends Fragment {

public Tab3 () {
    // Required empty public constructor
}
public Tab3 newInstance() {
    return new Tab3 ();
}

@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
    return inflater.inflate(R.layout.tab_3, container, false);
}

@Override
public void onViewCreated(View view, @Nullable Bundle savedInstanceState) {
    super.onViewCreated(view, savedInstanceState);

    final RecyclerView recyclerView = (RecyclerView) view.findViewById(R.id.recyclerView);
    recyclerView.setHasFixedSize(true);
    recyclerView.addItemDecoration(new DividerItemDecoration(getActivity()));
    recyclerView.setLayoutManager(new LinearLayoutManager(getActivity()));

    final List<DataTab3> data = new ArrayList<>();
    data.add(new DataTab3(
            "CardView no.1",
            Utils.createInterpolator(Utils.FAST_OUT_LINEAR_IN_INTERPOLATOR)));
    data.add(new DataTab3(
            "CardView no.2",
            Utils.createInterpolator(Utils.FAST_OUT_LINEAR_IN_INTERPOLATOR)));
    data.add(new DataTab3(
            "CardView no.3",
            Utils.createInterpolator(Utils.FAST_OUT_LINEAR_IN_INTERPOLATOR)));
    data.add(new DataTab3(
            "CardView no.4",
            Utils.createInterpolator(Utils.FAST_OUT_LINEAR_IN_INTERPOLATOR)));
    data.add(new DataTab3(
            "CardView no.5",
            Utils.createInterpolator(Utils.FAST_OUT_LINEAR_IN_INTERPOLATOR)));

    recyclerView.setAdapter(new NewAdapter(data));
}
}

The Adapter:

public class NewAdapter extends RecyclerView.Adapter<NewAdapter.ViewHolder> {

private final List<DataTab3> data;
private Context context;
private SparseBooleanArray expandState = new SparseBooleanArray();

public NewAdapter(final List<DataTab3> data) {
    this.data = data;
    for (int i = 0; i < data.size(); i++) {
        expandState.append(i, false);
    }
}

@Override
public ViewHolder onCreateViewHolder(final ViewGroup parent, final int viewType) {
    this.context = parent.getContext();
    return new ViewHolder(LayoutInflater.from(context)
            .inflate(R.layout.tab_3_adapter, parent, false));
}

@Override
public void onBindViewHolder(final ViewHolder holder, final int position) {
    final DataTab31 item = data.get(position);
    holder.SecondTextView.setText(DataTab3.Tab3Content[position]);
    holder.textView.setText(item.description);
    holder.expandableLayout.setInterpolator(item.interpolator);
    holder.expandableLayout.setExpanded(expandState.get(position));
    holder.expandableLayout.setListener(new ExpandableLayoutListenerAdapter() {
        @Override
        public void onPreOpen() {
            createRotateAnimator(holder.buttonLayout, 0f, 180f).start();
            expandState.put(position, true);
        }

        @Override
        public void onPreClose() {
            createRotateAnimator(holder.buttonLayout, 180f, 0f).start();
            expandState.put(position, false);
        }
    });

    holder.buttonLayout.setRotation(expandState.get(position) ? 180f : 0f);
    holder.buttonLayout.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(final View v) {
            onClickButton(holder.expandableLayout);
        }
    });
}

private void onClickButton(final ExpandableLayout expandableLayout) {
    expandableLayout.toggle();
}

@Override
public int getItemCount() {
    return data.size();
}

public static class ViewHolder extends RecyclerView.ViewHolder {
    public TextView textView;
    public TextView SecondTextView;
    public RelativeLayout buttonLayout;
    public ExpandableRelativeLayout expandableLayout;

    public ViewHolder(View v) {
        super(v);
        SecondTextView = (TextView) v.findViewById(R.id.secondTextView);
        textView = (TextView) v.findViewById(R.id.textView);
        buttonLayout = (RelativeLayout) v.findViewById(R.id.button);
        expandableLayout = (ExpandableRelativeLayout) v.findViewById(R.id.expandableLayout);
    }
}

public ObjectAnimator createRotateAnimator(final View target, final float from, final float to) {
    ObjectAnimator animator = ObjectAnimator.ofFloat(target, "rotation", from, to);
    animator.setDuration(300);
    animator.setInterpolator(Utils.createInterpolator(Utils.LINEAR_INTERPOLATOR));
    return animator;
}
}

ItemModel:

public class ItemModel {
public final String description;
public final TimeInterpolator interpolator;

public ItemModel(String description, TimeInterpolator interpolator) {
    this.description = description;
    this.interpolator = interpolator;
}

public static final String[] Tab3Content = {
        "• This is a simple example, no1\n" +
                "       Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.\n" +
                "\n" +
                "• Sample.sample.Sample.sample.\n" +
                "           Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample." +
                "\n" +
                "• Sample.sample.Sample.sample.\n" +
                "           Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.",

        "• This is a simple example, no2\n" +
                "       Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.\n" +
                "\n" +
                "• Sample.sample.Sample.sample.\n" +
                "           Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample." +
                "\n" +
                "• Sample.sample.Sample.sample.\n" +
                "           Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.",

        "• This is a simple example, no3\n" +
                "       Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.\n" +
                "\n" +
                "• Sample.sample.Sample.sample.\n" +
                "           Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample." +
                "\n" +
                "• Sample.sample.Sample.sample.\n" +
                "           Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.",

        "• This is a simple example, no4\n" +
                "       Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.\n" +
                "\n" +
                "• Sample.sample.Sample.sample.\n" +
                "           Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample." +
                "\n" +
                "• Sample.sample.Sample.sample.\n" +
                "           Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.",

        "• This is a simple example, no5\n" +
                "           Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.Sample.sample.",
};
}

The adapter's layout:

<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.CardView
xmlns:card_view="http://schemas.android.com/apk/res-auto"
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/tools"
android:id="@+id/card_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
card_view:cardCornerRadius="2dp"
android:layout_marginLeft="5dp"
android:layout_marginRight="5dp"
android:layout_marginTop="5dp"
android:layout_marginBottom="5dp"
android:background="@color/md_white_1000"
app:cardElevation="5dp">

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="wrap_content">

    <RelativeLayout
        android:id="@+id/button"
        android:layout_width="48dp"
        android:layout_height="48dp"
        android:layout_alignParentRight="true"
        android:layout_alignParentEnd="true"
        android:layout_alignParentTop="true"
        android:gravity="center">

        <View
            android:layout_width="12dp"
            android:layout_height="12dp"
            android:background="@drawable/triangle" />
    </RelativeLayout>

    <TextView
        android:id="@+id/textView"
        android:layout_width="match_parent"
        android:layout_height="50dp"
        android:layout_alignParentTop="true"
        android:layout_toLeftOf="@id/button"
        android:layout_toStartOf="@+id/button"
        android:padding="8dp"
        android:textColor="@color/green_teal"
        android:textSize="18sp" />

    <com.github.aakira.expandablelayout.ExpandableRelativeLayout
        android:id="@+id/expandableLayout"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_below="@id/textView"
        android:background="@color/md_white_1000"
        app:ael_expanded="false"
        app:ael_duration="400"
        app:ael_orientation="vertical">

        <TextView
            android:id="@+id/secondTextView"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:padding="5dp"
            android:textColor="@color/md_grey_900"
            android:textSize="18sp" />
    </com.github.aakira.expandablelayout.ExpandableRelativeLayout>
</RelativeLayout>

</android.support.v7.widget.CardView>
AAkira commented 8 years ago

@MasterzYuri

Thank you for reporting the issue and easy to understand explanation. I'll search this issue.

Maybe you can fix to set holder.setIsRecyclable(false) if you need to fix soon. But it doesn't become a solution to the root of the problem.

AlexandruDev commented 8 years ago

I added the line you mentioned above, holder.setIsRecyclable(false), and now it works perfectly.

Thank you and good luck on finding the problem!

AAkira commented 8 years ago

:+1: