web-dev-qa-db-ja.com

Android Pull-to-Refreshを実装する方法

Twitter(公式アプリ)などのAndroidアプリケーションでは、ListViewに遭遇したときにそれをプルダウンして(リリースされると元に戻ります)、コンテンツを更新することができます。

それを実行するための最善の方法は何でしょうか。

私が考えることができるいくつかの可能性:

  1. ListViewの上にある項目 - ただし、ListView上のアニメーションで項目位置1(0から始まる)までスクロールバックするのは簡単な作業ではないと思います。
  2. ListViewの外側の別のビュー - しかし、ListViewの位置を引っ張ったときに下に移動するように注意する必要があります。ListViewへのドラッグが実際にListViewの項目をスクロールするかどうかを確認できるかどうかわかりません。

何かアドバイスはありますか?

P.S公式のTwitterアプリのソースコードがいつリリースされるのだろうか。リリースされる予定だと言われていますが、6ヶ月が経ちました。それ以来、それについては聞いていません。

397

ついに、Googleは公式版のpull-to-refreshライブラリをリリースしました!

これはサポートライブラリの中ではSwipeRefreshLayoutと呼ばれ、ドキュメントは ここ です

1)ビューの親としてSwipeRefreshLayoutを追加します。これはレイアウトを更新するためのプルとして扱われます。 (私は例としてListViewを取りました、それはViewのようなどんなLinearLayoutでも構いません、ScrollViewなど)

<Android.support.v4.widget.SwipeRefreshLayout
    Android:id="@+id/pullToRefresh"
    Android:layout_width="match_parent"
    Android:layout_height="wrap_content">
    <ListView
        Android:id="@+id/listView"
        Android:layout_width="match_parent"
        Android:layout_height="match_parent"/>
</Android.support.v4.widget.SwipeRefreshLayout>

2)あなたのクラスにリスナーを追加する

protected void onCreate(Bundle savedInstanceState) {
    SwipeRefreshLayout pullToRefresh = findViewById(R.id.pullToRefresh);
    pullToRefresh.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
        @Override
        public void onRefresh() {
            refreshData(); // your code
            pullToRefresh.setRefreshing(false);
        }
    });
}

必要に応じてpullToRefresh.setRefreshing(true/false);を呼び出すこともできます。

255

私はpull-to-refreshコンポーネントを実装しようとしました、完全には程遠いしかし可能な実装を示しています、 https:// github .com/johannilsson/Android-pulltorefresh

メインロジックはPullToRefreshListViewを拡張するListViewに実装されています。 内部的にはsmoothScrollByを使ってヘッダビューのスクロールを制御します(API Level 8)。 このウィジェットは1.5以降のサポートでアップデートされました。1.5サポートのためのREADMEを読んでください。

あなたのレイアウトでは、単にこのようにそれを追加します。

<com.markupartist.Android.widget.PullToRefreshListView
    Android:id="@+id/Android:list"
    Android:layout_height="fill_parent"
    Android:layout_width="fill_parent"
    />
79

私はまた、堅牢でオープンソースの、使いやすく高度にカスタマイズ可能なAndroid用PullToRefreshライブラリも実装しました。プロジェクトページのドキュメントの説明に従って、ListViewをPullToRefreshListViewに置き換えることができます。

https://github.com/erikwt/PullToRefresh-ListView

54
Erik

私が思う最も簡単な方法は、Androidサポートライブラリによって提供されるものです:

Android.support.v4.widget.SwipeRefreshLayout;

それがインポートされると、あなたは次のようにあなたのレイアウトを定義することができます:

  <Android.support.v4.widget.SwipeRefreshLayout
        Android:id="@+id/refresh"
        Android:layout_height="match_parent"
        Android:layout_width="match_parent">
    <Android.support.v7.widget.RecyclerView
        xmlns:recycler_view="http://schemas.Android.com/apk/res-auto"
        Android:id="@Android:id/list"
        Android:theme="@style/Theme.AppCompat.Light"
        Android:layout_width="match_parent"
        Android:layout_height="wrap_content"
        Android:background="@color/button_material_light"
        >

    </Android.support.v7.widget.RecyclerView>
</Android.support.v4.widget.SwipeRefreshLayout>

私はあなたがリストビューの代わりにリサイクラービューを使うと思います。ただし、listviewは引き続き機能するため、recyclerviewをlistviewに置き換えて、Javaコード内の参照を更新する必要があります(フラグメント)。

アクティビティの断片では、最初にインターフェースSwipeRefreshLayout.OnRefreshListener:i、eを実装します。

public class MySwipeFragment extends Fragment implements SwipeRefreshLayout.OnRefreshListener{
private SwipeRefreshLayout swipeRefreshLayout;

@Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_item, container, false);
        swipeRefreshLayout = (SwipeRefreshLayout) view.findViewById(R.id.refresh);
        swipeRefreshLayout.setOnRefreshListener(this);
}


 @Override
  public void onRefresh(){
     swipeRefreshLayout.setRefreshing(true);
     refreshList();
  }
  refreshList(){
    //do processing to get new data and set your listview's adapter, maybe  reinitialise the loaders you may be using or so
   //when your data has finished loading, cset the refresh state of the view to false
   swipeRefreshLayout.setRefreshing(false);

   }
}

これが大衆に役立つことを願っています

37
larrytech

このリンクでは、有名なPullToRefreshビューのフォークで、PullTorRefreshWebViewPullToRefreshGridViewのような新しく興味深い実装、あるいはリストの下端にPullToRefreshを追加することができます。

https://github.com/chrisbanes/Android-PullToRefresh

そしてそれの最も良いのは、Android 4.1で完璧に動作することです(通常のPullToRefreshは動作しません)。

21
Aracem

AndroidのPull-to-Refreshを実装するには、このコードを試してください。

<Android.support.v4.widget.SwipeRefreshLayout
        Android:id="@+id/pullToRefresh"
        Android:layout_width="match_parent"
        Android:layout_height="wrap_content">

    <ListView
        Android:id="@+id/lv"
        Android:layout_width="match_parent"
        Android:layout_height="match_parent" >
    </ListView>

</Android.support.v4.widget.SwipeRefreshLayout>

活動クラス:

ListView lv = (ListView) findViewById(R.id.lv);
SwipeRefreshLayout pullToRefresh = (SwipeRefreshLayout) findViewById(R.id.pullToRefresh);


lv.setAdapter(mAdapter);

pullToRefresh.setOnRefreshListener(new OnRefreshListener() {

        @Override
        public void onRefresh() {
            // TODO Auto-generated method stub

            refreshContent();

        }
    });



private void refreshContent(){ 

     new Handler().postDelayed(new Runnable() {
            @Override public void run() {
                pullToRefresh.setRefreshing(false);
            }
        }, 5000);

 }
18
mani

私はこれをする非常に簡単な方法を持っていますが、今ではその絶対確実な方法を確認してください私のコードPullDownListView.Javaがあります

package com.myproject.widgets;

import Android.content.Context;
import Android.util.AttributeSet;
import Android.view.MotionEvent;
import Android.widget.AbsListView;
import Android.widget.AbsListView.OnScrollListener;
import Android.widget.ListView;

/**
 * @author Pushpan
 * @date Nov 27, 2012
 **/
public class PullDownListView extends ListView implements OnScrollListener {

    private ListViewTouchEventListener mTouchListener;
    private boolean pulledDown;

    public PullDownListView(Context context) {
        super(context);
        init();
    }

    public PullDownListView(Context context, AttributeSet attrs) {
        super(context, attrs);
        init();
    }

    public PullDownListView(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
        init();
    }

    private void init() {
        setOnScrollListener(this);
    }

    private float lastY;

    @Override
    public boolean dispatchTouchEvent(MotionEvent ev) {
        if (ev.getAction() == MotionEvent.ACTION_DOWN) {
            lastY = ev.getRawY();
        } else if (ev.getAction() == MotionEvent.ACTION_MOVE) {
            float newY = ev.getRawY();
            setPulledDown((newY - lastY) > 0);
            postDelayed(new Runnable() {
                @Override
                public void run() {
                    if (isPulledDown()) {
                        if (mTouchListener != null) {
                            mTouchListener.onListViewPulledDown();
                            setPulledDown(false);
                        }
                    }
                }
            }, 400);
            lastY = newY;
        } else if (ev.getAction() == MotionEvent.ACTION_UP) {
            lastY = 0;
        }
        return super.dispatchTouchEvent(ev);
    }

    @Override
    public void onScroll(AbsListView view, int firstVisibleItem,
            int visibleItemCount, int totalItemCount) {
        setPulledDown(false);
    }

    @Override
    public void onScrollStateChanged(AbsListView view, int scrollState) {
    }

    public interface ListViewTouchEventListener {
        public void onListViewPulledDown();
    }

    public void setListViewTouchListener(
            ListViewTouchEventListener touchListener) {
        this.mTouchListener = touchListener;
    }

    public ListViewTouchEventListener getListViewTouchListener() {
        return mTouchListener;
    }

    public boolean isPulledDown() {
        return pulledDown;
    }

    public void setPulledDown(boolean pulledDown) {
        this.pulledDown = pulledDown;
    }
}

このListViewを使用しリスナーを設定したいアクティビティにListViewTouchEventListenerを実装するだけです。

PullDownListViewActivityに実装しています

package com.myproject.activities;

import Android.app.Activity;
import Android.os.Bundle;

/**
 * @author Pushpan
 *
 */
public class PullDownListViewActivity extends Activity implements ListViewTouchEventListener {

    private PullDownListView listView;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        listView = new PullDownListView(this);
        setContentView(listView);
        listView.setListViewTouchListener(this);

        //setItems in listview
    }

    public void onListViewPulledDown(){
        Log.("PullDownListViewActivity", "ListView pulled down");
    }
}

わたしにはできる :)

18
Pushpan

Google NowやGmailアプリケーションのように、アクションバーの上に表示される新しいタイプの "更新するためのプル"については、誰も言及していません。

まったく同じように動作するライブラリ ActionBar-PullToRefresh があります。

9
tomrozb

AndroidおよびWPで実装する際には、UXの問題に対処する必要があります。

「デザイナー/開発者がiOSアプリのスタイルでプルトゥリフレッシュを実装してはいけない理由の優れた指標は、GoogleとそのチームがiOSでプルトゥリフレッシュを使用している間、決して使用しないことです。」

https://plus.google.com/109453683460749241197/posts/eqYxXR8L4eb

7
uobroin

あなたのプログラムをAndroidに強制フィットされたiPhoneプログラムのように見せたくない場合は、よりネイティブなルックアンドフィールを目指して、Gingerbreadに似たことをしてください。

alt text

4
Lie Ryan

ここでコンポーネントを更新するためのプルを書いています。 https://github.com/guillep/PullToRefresh リストに項目がない場合はイベントが発生し、テストしました1.6 Androidフォン以上.

任意の提案や改善をいただければ幸いです:)

4
Guille Polito

私は最高のライブラリだと思います。 https://github.com/chrisbanes/Android-PullToRefresh

で動作します:

ListView
ExpandableListView
GridView
WebView
ScrollView
HorizontalScrollView
ViewPager
2
Jossy Paul

最新のLollipop Pull-To Refreshを入手するには、次の手順を実行します。

  1. 最新のLollipop SDKとExtras/Androidサポートライブラリをダウンロードしてください。
  2. プロジェクトのビルドターゲットをAndroid 5.0に設定します(そうでなければサポートパッケージはリソースでエラーを起こす可能性があります)。
  3. Libs/Android-support-v4.jarを21バージョンに更新します
  4. Android.support.v4.widget.SwipeRefreshLayoutAndroid.support.v4.widget.SwipeRefreshLayout.OnRefreshListenerを使う

詳細なガイドはここにあります: http://antonioleiva.com/swiperefreshlayout/

ListViewのために私はコメントでcanChildScrollUp()について読むことを勧めます;)

1
goRGon

非常に興味深い プルアップリフレッシュ による Yalantis 。 iOS用のGifですが、確認できます:)

<com.yalantis.pulltorefresh.library.PullToRefreshView
Android:id="@+id/pull_to_refresh"
Android:layout_width="match_parent"
Android:layout_height="match_parent">
<ListView
    Android:id="@+id/list_view"
    Android:divider="@null"
    Android:dividerHeight="0dp"
    Android:layout_width="match_parent"
    Android:layout_height="match_parent" />
1
edbaev