Android ListView 행의 추가 또는 제거에 애니메이션을 적용하는 방법 기본 애니메이션을 보여주는 YouTube 비디오의

iOS에는 UITableView 행의 추가 및 제거에 애니메이션을 적용하는 매우 쉽고 강력한 기능이 있습니다. 여기 에는 기본 애니메이션을 보여주는 YouTube 비디오의 클립이 있습니다 . 주변 행이 삭제 된 행으로 축소되는 방법에 유의하십시오. 이 애니메이션을 통해 사용자는 목록에서 변경된 사항과 데이터가 변경된 시점을보고 있던 목록을 추적 할 수 있습니다.

Android에서 개발 한 이후 TableView 에서 개별 행에 애니메이션을 적용하는 동등한 기능을 찾지 못했습니다 . notifyDataSetChanged()내 어댑터를 호출 하면 ListView가 해당 내용을 새로운 정보로 즉시 업데이트합니다. 데이터가 변경 될 때 새 행을 밀어 넣거나 빼는 간단한 애니메이션을 보여주고 싶지만 문서화 된 방법을 찾을 수 없습니다. LayoutAnimationController 가 이것을 작동시키는 열쇠를 가지고있는 것처럼 보이지만 ListView에서 LayoutAnimationController를 설정하고 ( ApiDemo의 LayoutAnimation2 와 유사 ) 목록이 표시된 후 어댑터에서 요소를 제거하면 요소가 애니메이션되지 않고 즉시 사라집니다. .

또한 개별 항목이 제거 될 때 애니메이션을 적용하기 위해 다음과 같은 것을 시도했습니다.

@Override
protected void onListItemClick(ListView l, View v, final int position, long id) {
    Animation animation = new ScaleAnimation(1, 1, 1, 0);
    animation.setDuration(100);
    getListView().getChildAt(position).startAnimation(animation);
    l.postDelayed(new Runnable() {
        public void run() {
            mStringList.remove(position);
            mAdapter.notifyDataSetChanged();
        }
    }, 100);
}

그러나 애니메이션 행을 둘러싼 행 notifyDataSetChanged()은 호출 될 때 새 위치로 이동할 때까지 위치를 이동하지 않습니다 . 요소가 배치되면 ListView가 레이아웃을 업데이트하지 않는 것 같습니다.

ListView의 자체 구현 / 포크를 작성하는 것이 내 마음을 넘어 섰지 만, 그렇게 어렵지 않아야하는 것 같습니다.

감사!



답변

Animation anim = AnimationUtils.loadAnimation(
                     GoTransitApp.this, android.R.anim.slide_out_right
                 );
anim.setDuration(500);
listView.getChildAt(index).startAnimation(anim );

new Handler().postDelayed(new Runnable() {

    public void run() {

        FavouritesManager.getInstance().remove(
            FavouritesManager.getInstance().getTripManagerAtIndex(index)
        );
        populateList();
        adapter.notifyDataSetChanged();

    }

}, anim.getDuration());

하향식 애니메이션 사용 :

<set xmlns:android="http://schemas.android.com/apk/res/android">
        <translate android:fromYDelta="20%p" android:toYDelta="-20"
            android:duration="@android:integer/config_mediumAnimTime"/>
        <alpha android:fromAlpha="0.0" android:toAlpha="1.0"
            android:duration="@android:integer/config_mediumAnimTime" />
</set>


답변


답변

Google 솔루션을 살펴보십시오. 삭제 방법 만 있습니다.

ListViewRemovalAnimation 프로젝트 코드 및 비디오 데모

Android 4.1 이상 (API 16)이 필요합니다. 그러나 우리는 2014 년 밖에 있습니다.


답변

ListViews고도로 최적화되어 있기 때문에 이것이 불가능하다고 생각합니다. 코드로 “ListView”를 만들려고 했습니까 (예 : xml에서 행을 팽창시키고 행에 추가하여 LinearLayout) 애니메이션을 적용하셨습니까?


답변

오른쪽으로 쓸어 넘기는 애니메이션을 고려 했습니까? 목록 항목 상단에 점진적으로 더 큰 흰색 막대를 그린 다음 목록에서 제거하는 것과 같은 작업을 수행 할 수 있습니다. 다른 세포는 여전히 제자리에 고정되지만 아무것도 아닌 것보다 낫습니다.


답변

call listView.scheduleLayoutAnimation (); 목록을 변경하기 전에


답변

목록보기를 조작하지 않고도 다른 방법으로 해킹했습니다. 불행히도 일반적인 Android 애니메이션은 행의 내용을 조작하는 것처럼 보이지만 실제로 뷰를 축소하는 데는 효과가 없습니다. 따라서 먼저이 핸들러를 고려하십시오.

private Handler handler = new Handler() {
@Override
public void handleMessage(Message message) {
    Bundle bundle = message.getData();

    View view = listView.getChildAt(bundle.getInt("viewPosition") -
        listView.getFirstVisiblePosition());

    int heightToSet;
    if(!bundle.containsKey("viewHeight")) {
        Rect rect = new Rect();
        view.getDrawingRect(rect);
        heightToSet = rect.height() - 1;
    } else {
        heightToSet = bundle.getInt("viewHeight");
    }

    setViewHeight(view, heightToSet);

    if(heightToSet == 1)
        return;

    Message nextMessage = obtainMessage();
    bundle.putInt("viewHeight", (heightToSet - 5 > 0) ? heightToSet - 5 : 1);
    nextMessage.setData(bundle);
    sendMessage(nextMessage);
}

이 콜렉션을 목록 어댑터에 추가하십시오.

private Collection<Integer> disabledViews = new ArrayList<Integer>();

그리고 추가

public boolean isEnabled(int position) {
   return !disabledViews.contains(position);
}

다음으로 행을 숨기고 싶은 곳에 다음을 추가하십시오.

Message message = handler.obtainMessage();
Bundle bundle = new Bundle();
bundle.putInt("viewPosition", listView.getPositionForView(view));
message.setData(bundle);
handler.sendMessage(message);
disabledViews.add(listView.getPositionForView(view));

그게 다야! 높이를 한 번에 축소하는 픽셀 수를 변경하여 애니메이션 속도를 변경할 수 있습니다. 정교하지는 않지만 작동합니다!