Android 之 SwipeLayout 的基本使用

dartye 8年前
   <p>使用方法( 以listview作为例子):</p>    <h2><strong>Step 1 添加项目依赖</strong></h2>    <p>项目依赖如下:</p>    <p>在你的app中的build.gradle文件中添加以下依赖</p>    <pre>  <code class="language-java">dependencies {      compile fileTree(dir: 'libs', include: ['*.jar'])      testCompile 'junit:junit:4.12'  //swipeLayout      compile 'com.android.support:appcompat-v7:23.4.0'      compile "com.daimajia.swipelayout:library:1.2.0@aar"      compile 'com.daimajia.easing:library:1.0.0@aar'      compile 'com.daimajia.androidanimations:library:1.1.2@aar'      compile 'com.nineoldandroids:library:2.4.0'  }</code></pre>    <p>注意:</p>    <p>compile 'com.daimajia.androidanimations:library:1.1.2@aar'<br> compile'com.nineoldandroids:library:2.4.0'</p>    <p>这两个库的引用是滑动bottomView所需要依赖的。</p>    <h2>S<strong>tep 2 添加swipeLayout的xml文件</strong></h2>    <p>首先创建一个swipelayout作为列表项(listview_item)的布局</p>    <p>swipelayout由两部分view组成:surfaceView 和 bottomView</p>    <p style="text-align:center"><img src="https://simg.open-open.com/show/d88d9c7583d1684f305a3b2ec21cdc1f.png"></p>    <p>图中左边是surfaceView,右边被滑动出来的是bottomView</p>    <p>Tips:</p>    <ol>     <li> <p>surfaceView应当写在此view中的最后,其余的都是bottomView</p> </li>     <li> <p>在你的bottomView中最好使用layout_gravity这个属性</p> </li>    </ol>    <p>xml模版格式:</p>    <pre>  <code class="language-java"><?xml version="1.0" encoding="utf-8"?>  <com.daimajia.swipe.SwipeLayout android:id="@+id/swipe"                                  xmlns:android="http://schemas.android.com/apk/res/android"                                  android:layout_width="match_parent"                                  android:layout_height="wrap_content">          <!-- Bottom View Start-->      <LinearLayout          android:layout_width="wrap_content"          android:layout_height="match_parent"          android:background="@color/red"          android:orientation="horizontal"          android:padding="4dp"          android:weightSum="1">        <!--some view in it-->        </LinearLayout>      <!-- Bottom View End-->          <!--surfaceView Start-->      <LinearLayout          android:layout_width="match_parent"          android:layout_height="wrap_content"          android:orientation="vertical">            <!--some view in it-->        </LinearLayout>      <!--surfaceView End-->    </com.daimajia.swipe.SwipeLayout></code></pre>    <p>Example:</p>    <pre>  <code class="language-java"><?xml version="1.0" encoding="utf-8"?>  <com.daimajia.swipe.SwipeLayout android:id="@+id/swipe"                                  xmlns:android="http://schemas.android.com/apk/res/android"                                  android:layout_width="match_parent"                                  android:layout_height="wrap_content">          <!-- Bottom View Start-->      <LinearLayout          android:layout_width="wrap_content"          android:layout_height="match_parent"          android:background="@color/red"          android:orientation="horizontal"          android:padding="4dp"          android:weightSum="1">            <TextView              android:id="@+id/tv_cancel_favorite"              android:layout_width="wrap_content"              android:layout_height="match_parent"              android:gravity="center"              android:text="取消收藏"              android:textColor="@color/white"              android:textSize="14sp"/>      </LinearLayout>      <!-- Bottom View End-->          <!--surfaceView Start-->      <LinearLayout          android:layout_width="match_parent"          android:layout_height="wrap_content"          android:orientation="vertical">            <LinearLayout              android:layout_width="match_parent"              android:layout_height="wrap_content"              android:layout_marginTop="8dp"              android:orientation="horizontal"              android:paddingLeft="10dp">                <TextView                  android:id="@+id/tv_station_name"                  android:layout_width="wrap_content"                  android:layout_height="wrap_content"                  android:gravity="center_vertical"                  android:text="@string/text_station_title"                  android:textColor="@color/popup_title_gray"                  android:textSize="16sp"/>                <ImageView                  android:id="@+id/iv_pop_openImage"                  android:layout_width="wrap_content"                  android:layout_height="wrap_content"                  android:layout_gravity="center_vertical"                  android:layout_marginLeft="6dp"                  android:src="@mipmap/station_open_up"                  android:visibility="gone"/>                <ImageView                  android:id="@+id/iv_pop_freeImage"                  android:layout_width="wrap_content"                  android:layout_height="wrap_content"                  android:layout_gravity="center_vertical"                  android:layout_marginLeft="4dp"                  android:gravity="center_vertical"                  android:src="@mipmap/station_free_park"                  android:visibility="gone"/>          </LinearLayout>            <LinearLayout              android:layout_width="match_parent"              android:layout_height="wrap_content"              android:orientation="horizontal"              android:paddingLeft="10dp">                <ImageView                  android:id="@+id/iv_navi_icon"                  android:layout_width="wrap_content"                  android:layout_height="wrap_content"                  android:layout_marginTop="10dp"                  android:src="@drawable/address"/>                <TextView                  android:id="@+id/tv_pop_distance"                  android:layout_width="wrap_content"                  android:layout_height="wrap_content"                  android:layout_marginLeft="6dp"                  android:layout_marginTop="10dp"                  android:text="@string/text_station_distance"                  android:textColor="@color/popup_distance_gray"                  android:textSize="13sp"/>                <View                  android:layout_width="1dp"                  android:layout_height="15dp"                  android:layout_marginLeft="10dp"                  android:layout_marginTop="10dp"                  android:background="@color/div_line"/>                <TextView                  android:id="@+id/tv_pop_address"                  android:layout_width="wrap_content"                  android:layout_height="wrap_content"                  android:layout_marginLeft="10dp"                  android:layout_marginTop="10dp"                  android:singleLine="true"                  android:text="@string/text_station_address"                  android:textColor="@color/popup_address_gray"                  android:textSize="13sp"/>          </LinearLayout>            <LinearLayout              android:layout_width="match_parent"              android:layout_height="wrap_content"              android:layout_marginTop="10dp"              android:orientation="horizontal"              android:paddingBottom="6dp"              android:paddingLeft="10dp">                <TextView                  android:layout_width="wrap_content"                  android:layout_height="wrap_content"                  android:text="@string/text_station_opentime"                  android:textColor="@color/popup_address_gray"                  android:textSize="13sp"/>                <TextView                  android:id="@+id/tv_pop_opentime"                  android:layout_width="wrap_content"                  android:layout_height="wrap_content"                  android:layout_marginLeft="10dp"                  android:text="@string/text_station_time"                  android:textColor="@color/popup_address_gray"                  android:textSize="13sp"/>          </LinearLayout>        </LinearLayout>      <!--surfaceView End-->    </com.daimajia.swipe.SwipeLayout></code></pre>    <p>现在你已经创建好的列表项的布局了,要想在activity中让listview使用这个swipelayout你还需要一个listviewAdapter</p>    <h2><strong>Step 3 创建swipeLayout的adapter</strong></h2>    <p>首先swipelayout的adapter是继承于BaseAdapter,不同的是你不需要重写getView(),取而代之的是你需要重写以下三个方法来代替getView():</p>    <pre>  <code class="language-java">//return the `SwipeLayout` resource id in your listview | gridview item layout.  public abstract int getSwipeLayoutResourceId(int position);    //generate a new item layout.  public abstract View generateView(int position, ViewGroup parent);    /*fill values to your item layout returned from `generateView`.    The position param here is passed from the BaseAdapter's 'getView()*/  public abstract void fillValues(int position, View convertView);</code></pre>    <p>所以最终你在实现ListViewAdapter的时候需要重写6个方法:</p>    <ol>     <li>public int <strong>getSwipeLayoutResourceId</strong> (int position)</li>     <li>public View <strong>generateView</strong> (final int position, ViewGroup parent)</li>     <li>public void <strong>fillValues</strong> (int position, View convertView)</li>     <li>public int <strong>getCount</strong> ()</li>     <li>public Object <strong>getItem</strong> (int position)</li>     <li>public long <strong>getItemId</strong> (int position)</li>    </ol>    <p>Tips:</p>    <ol>     <li> <p>如果你想绑定监听事件应当在 fillValues() 方法中去实现而不是在 generateView() 方法中!!</p> <p>如果你按照该项目作者在github上的demo把bind listener以及fill values的具体实现写在 generateView() 中,则会出现删除item控件错乱的问题。</p> </li>     <li> <p>为了避免滑动事件在滑回来不与该swipelayout的点击事件冲突,swipelayout的点击事件请使用 swipeLayout.getSurfaceView().setOnClickListener 方法去实现。</p> <p>Example:</p> </li>    </ol>    <pre>  <code class="language-java">/**       * swipeLayout控件的listviewAdapter       */      public class FavoriteStationListViewAdapter extends BaseSwipeAdapter {            private Context mContext;          private ArrayList<FavoriteStationEntity> dataList;            private SwipeLayout mSwipeLayout;            public FavoriteStationListViewAdapter(Context mContext, ArrayList<FavoriteStationEntity> dataList) {              this.mContext = mContext;              this.dataList = dataList;          }            @Override          public int getSwipeLayoutResourceId(int position) {              return R.id.swipe;          }            /**           * 此方法中一定不能绑定监听器和填充数据           * never bind listeners or fill values, just genertate view here !!           *           * @param position           * @param parent           * @return           */          @Override          public View generateView(final int position, ViewGroup parent) {                View v = LayoutInflater.from(mContext).inflate(R.layout.listview_item_favorite_station, null);              return v;          }            @Override          public void fillValues(final int position, View convertView) {                favoriteStation = dataList.get(position);                //填充数据              TextView stationName = (TextView) convertView.findViewById(R.id.tv_station_name);              stationName.setText(favoriteStation.getStationName());                if (favoriteStation.getCompetence() == 0) {//对外开放                  convertView.findViewById(R.id.iv_pop_openImage).setVisibility(View.VISIBLE);              } else {                  convertView.findViewById(R.id.iv_pop_openImage).setVisibility(View.GONE);              }                if (favoriteStation.getParkPrice().equals("免费")) {//免停车费                  convertView.findViewById(R.id.iv_pop_freeImage).setVisibility(View.VISIBLE);              } else {                  convertView.findViewById(R.id.iv_pop_freeImage).setVisibility(View.GONE);              }                TextView stationAddress = (TextView) convertView.findViewById(R.id.tv_pop_address);              stationAddress.setText(favoriteStation.getAddress());                TextView openTime = (TextView) convertView.findViewById(R.id.tv_pop_opentime);              openTime.setText(favoriteStation.getServiceStartTime() + "--" + favoriteStation.getServiceEndTime());                TextView stationDistance = (TextView) convertView.findViewById(R.id.tv_pop_distance);              stationDistance.setText(favoriteStation.getDistance());                  mSwipeLayout = (SwipeLayout) convertView.findViewById(getSwipeLayoutResourceId(position));              //绑定监听事件              mSwipeLayout.addSwipeListener(new SimpleSwipeListener() {                  @Override                  public void onOpen(SwipeLayout layout) {                      YoYo.with(Techniques.Tada).duration(500).delay(100).playOn(layout.findViewById(R.id.tv_cancel_favorite));                  }              });                /**               * 用getSurfaceView()可以防止滑回与点击事件冲突               */              mSwipeLayout.getSurfaceView().setOnClickListener(new View.OnClickListener() {                  @Override                  public void onClick(View v) {//跳转到充电站详情                        favoriteStation = dataList.get(position);                      Log.d("favoriteActivity", "favoriteActivity--position--->" + position);                      Log.d("favoriteActivity", "favoriteActivity--stationName--->" + favoriteStation.getStationName());                      int stationId = favoriteStation.getStationId();                      Intent intentStationDetail = new Intent().putExtra("stationId", stationId);                      intentStationDetail.setClass(FavoriteActivity.this, StationDetailActivity.class);                      startActivity(intentStationDetail);                  }              });                convertView.findViewById(R.id.tv_cancel_favorite).setOnClickListener(new View.OnClickListener() {                  @Override                  public void onClick(View view) {//bottomView点击事件 取消收藏站点                        favoriteStation = dataList.get(position);                      Log.d("favoriteActivity", "favoriteActivity--cancelStationName--->" + favoriteStation.getStationName());                      mFavoritePresenter.cancelFavorite(favoriteStation.getId());                      mSwipeLayout.close();                    }              });          }            @Override          public int getCount() {              Log.d("dataListSize", "dataListSize--->" + dataList.size());              return dataList.size();          }            @Override          public Object getItem(int position) {              return null;          }            @Override          public long getItemId(int position) {              return position;          }      }</code></pre>    <p>至此,我们已经写好了listview_item布局,listview的adapter。最后看一下在activity中如何使用这个滑动控件。</p>    <h2><strong>Step 4 使用swipeLayout</strong></h2>    <p>在activity中使用swipelayout</p>    <p>Example:</p>    <p>根据需要在 onCreate() 或者 onResume() 中使用</p>    <pre>  <code class="language-java">favoriteListLv = (ListView) findViewById(R.id.lv_favorite_station);  favoriteStaionListAdapter = new FavoriteStationListViewAdapter(FavoriteActivity.this,                  favoriteStationList);  favoriteStaionListAdapter.setMode(Attributes.Mode.Single);  favoriteListLv.setAdapter(favoriteStaionListAdapter);</code></pre>    <p>以上就是swipelayout的基本用法,当然还有很多可以设置的地方,swipelayout这个view还可以用在gridview、recyclerView等等</p>    <p> </p>    <p>来自:http://jngoogle.farbox.com/post/android/view/swipelayoutde-ji-ben-shi-yong</p>    <p> </p>