Android Pulltorefreshlayout Drop-down Refreshes the terminator of the control _android

Source: Internet
Author: User
Tags event listener gety rollback touch visibility

When it comes to drop-down refresh control, there are a lot of online versions, and many software also have a drop-down refresh function. There is a call Xlistview, I see others used, have not seen is how to achieve, see the name is estimated to inherit from ListView modified, but the effect looks very ugly, also no extensibility, too monotonous. Look at the list of QQ2014 Drop-down refresh, found quite good-looking, I like to paste the picture to look at QQ drop-down Refresh effect:


Nice, huh? Well, yes. A look at the implementation of a different way. We're going to implement a Drop-down refresh control today. Because sometimes it is not just ListView need to pull the refresh, Expandablelistview and GridView also have this requirement, because Listview,gridview are all Abslistview subclasses, Expandablelistview is a subclass of ListView, so it is also a abslistview subclass. So my idea is to customize a common Drop-down management layout for all Abslistview subclasses, called Pulltorefreshlayout, and if you need a GridView, just replace ListView in the layout file with a GridView. Expandablelistview also, do not need to inherit what the GridView Ah ListView ah mess.


Looking at the figure, the main task is to define a large black layout, the red part is not pull the visible part of the time, can be arbitrary abslistview subclasses (Gridview,listview,expandablelistview, etc.). In fact, I have written, first look at the effect of the picture:

Normal Rafah:

Obsessive-Compulsive disorder Rafah:


It's ListView, and the following is the GridView.


Let's take a look at the Drop-down refresh effect of Expandablelistview:


As you can see, click events and long press events can be triggered normally without a false trigger, when using expandablelistview need to be aware of the ban when expanding automatically scrolling, otherwise there will be bugs. The following will provide demo source download, you can according to their needs to modify.

The following explains the implementation of Pulltorefreshlayout, before pasting the complete source code to understand the general idea of the whole class:

 public class Pulltorefreshlayout extends Relativelayout implements Ontouchlistener { 
 Drop down distance public float Movedeltay = 0; 
  
  
 Whether you can drop the private Boolean canpull = true; 
 private void Hidehead () {///here begins the asynchronous hiding of the Drop-down header, hiding} public void refreshfinish (int refreshresult) at the time of letting go or when this refresh is complete 
  {//complete refresh operation, show refresh result} private void changestate (int to) {//change the current state, there are four states: Drop-down refresh, release refresh, refresh, Refresh complete}/* * (non-Javadoc) determines whether events are distributed by the parent control, preventing event conflicts * * @see android.view.viewgroup#dispatchtouchevent (android.view.MotionEvent) * /@Override public boolean dispatchtouchevent (motionevent ev) {switch (ev.getactionmasked ()) {case Motion 
  Event.action_down: * * When the fingers are pressed, it is not possible to determine whether to pull down, so the break let the parent class to distribute the down event to the child view record press the coordinates * * break; Case Motionevent.action_move:/* If sliding up and movedetay==0 is not drop-down, the break continues to distribute the move event to the child view if you pull down, calculate the pull distance movedeltay, according to move DeltaY layout the child controls again. However, because the down event is passed to the child view, if the child view event is not cleared, it causes the child view to trigger the long press eventand click events. 
   So here clears the child view's event callback. 
  When pulling over a certain distance, change the current state * * * break; 
  Case MOTIONEVENT.ACTION_UP://Refresh operation or Hidehead Default:break according to current state; 
 //Event distribution to Parent return super.dispatchtouchevent (EV); 
  * * * (non-Javadoc) to draw shadow effects, color values can be modified * * @see Android.view.viewgroup#dispatchdraw (Android.graphics.Canvas) * * @Override protected void Dispatchdraw (Canvas Canvas) {//Draw boundary shadow with a gradient here} @Override protected 
 
  
 void OnLayout (Boolean changed, int l, int t, int r, int b) {//This method is to layout the child view again, according to Movedeltay to locate the position of the child view} @Override public boolean Ontouch (View V, motionevent event) {//This is the Ontouchlistener method that only judges the Abslistview state to determine whether CANPU ll, otherwise than do other processing}} 

As you can see, this is a replication of the ViewGroup dispatchtouchevent, so you can control the distribution of events, if you do not understand this method can look at this Android event distribution, view event listener full resolution. The reason to control the distribution of events is because we cannot know whether the finger will be abslistview or down after the drop, so the down event will be distributed to Abslistview, but it needs to be seen at move time. Because we don't want the Abslistview to slide at the same time as the dropdown, we don't distribute the move event at the drop down, but that's the problem, and the previous Abslistview has already received the down event, and if you don't distribute the move event to it, It triggers a long press event or click event, so you also need to clear the callback in the Abslistview message list here.
OnLayout is used to rearrange the position of the Pull-down head and the Abslistview, which is not difficult to understand.

After understanding the general idea, look at the Pulltorefreshlayout complete source code it ~

Package Com.jingchen.pulltorefresh; 
Import Java.lang.reflect.Field; 
Import Java.util.Timer; 
 
Import Java.util.TimerTask; 
Import Android.content.Context; 
Import Android.graphics.Canvas; 
Import android.graphics.LinearGradient; 
Import Android.graphics.Paint; 
Import Android.graphics.Paint.Style; 
Import Android.graphics.RectF; 
Import Android.graphics.Shader.TileMode; 
Import Android.os.Handler; 
Import Android.os.Message; 
Import Android.util.AttributeSet; 
Import Android.util.Log; 
Import android.view.MotionEvent; 
Import Android.view.View; 
Import Android.view.View.OnTouchListener; 
Import Android.view.ViewGroup; 
Import Android.view.animation.AnimationUtils; 
Import Android.view.animation.LinearInterpolator; 
Import android.view.animation.RotateAnimation; 
Import Android.widget.AbsListView; 
Import Android.widget.RelativeLayout; 
 
Import Android.widget.TextView; /** * The entire drop-down refreshes on this one layout, which is used to manage two child controls, one of which is the drop down header and the other is the Contentview that contains the content (can be any subclass of Abslistview) * * @author Chen Jing/PublIC class Pulltorefreshlayout extends Relativelayout implements Ontouchlistener {public static final String TAG = "Pull 
 Torefreshlayout "; 
 Drop-down Refresh public static final int pull_to_refresh = 0; 
 Release flush public static final int release_to_refresh = 1; 
 Refreshing public static final int refreshing = 2; 
 Refresh completed public static final int done = 3; 
 Current status private int state = Pull_to_refresh; 
 Refresh callback interface private Onrefreshlistener Mlistener; 
 Refresh succeeded public static final int refresh_succeed = 0; 
 Refresh failed public static final int refresh_fail = 1; 
 The dropdown head private View Headview; 
 Content private View Contentview; 
 Press Y-coordinate, the previous event point y-coordinate private float downY, lasty; 
 Drop down distance public float Movedeltay = 0; 
 Release refresh distance private float refreshdist = 200; 
 private timer timer; 
 Private Mytimertask Mtask; 
 Rollback speed public float move_speed = 8; 
 First execution Layout Private Boolean islayout = false; 
 Whether you can drop the private Boolean canpull = true; Sliding operations in the refresh process private Boolean IStouchinrefreshing = false; 
 The sliding distance of the finger is more than that of the drop head, and the middle will change with the tangent function. Private float radio = 2; 
 The dropdown arrow of the rotary 180° animation private rotateanimation rotateanimation; 
 Uniform rotation Animation private rotateanimation refreshinganimation; 
 Down-Pull arrows private View pullview; 
 The icon being refreshed private View refreshingview; 
 Refresh the results icon private View Stateimageview; 
 Refresh Result: Success or failure private TextView statetextview; /** * Handler/Handler for automatic rollback updatehandler = new Handler () {@Override public void Handlemessage (Mess  Age msg) {//rebound speed increases with lower pull distance movedeltay increase move_speed = (float) (8 + 5 * Math.tan (MATH.PI/2/Getmeasuredheight () 
   * Movedeltay)); if (state = = Refreshing && movedeltay <= refreshdist &&!istouchinrefreshing) {//is refreshing and not pushing up 
    Then hover to show "refreshing ..." movedeltay = refreshdist; 
   Mtask.cancel (); 
   } if (canpull) movedeltay-= Move_speed; 
    if (movedeltay <= 0) {//completed rebound Movedeltay = 0; 
    Pullview.clearanimation ();It is possible to refresh the dropdown while hiding it, and only change the status if the current state is not refreshing (state!= refreshing) changestate (Pull_to_refresh); 
   Mtask.cancel (); 
  //Refresh layout, automatically invoke OnLayout requestlayout (); 
 
 } 
 
 }; 
 public void Setonrefreshlistener (Onrefreshlistener listener) {Mlistener = listener; 
  Public Pulltorefreshlayout {Super (context); 
 Initview (context); 
  Public Pulltorefreshlayout (context, AttributeSet attrs) {Super (context, attrs); 
 Initview (context); Pulltorefreshlayout (context, AttributeSet attrs, int defstyle) {Super (context, attrs, Defstyle) 
  ; 
 Initview (context); 
  private void Initview (context context) {timer = new timer (); 
  Mtask = new Mytimertask (Updatehandler); 
  Rotateanimation = (rotateanimation) animationutils.loadanimation (context, R.anim.reverse_anim); 
  Refreshinganimation = (rotateanimation) animationutils.loadanimation (context, r.anim.rotating); Add Shiting animation LinearinterpolaTor lir = new Linearinterpolator (); 
  Rotateanimation.setinterpolator (LIR); 
 Refreshinganimation.setinterpolator (LIR); 
   private void Hidehead () {if (mtask!= null) {mtask.cancel (); 
  Mtask = null; 
  } mtask = new Mytimertask (Updatehandler); 
 Timer.schedule (mtask, 0, 5); 
  /** * Completes the refresh operation, displaying the refresh result/public void refreshfinish (int refreshresult) {refreshingview.clearanimation (); 
  Refreshingview.setvisibility (View.gone); 
   Switch (refreshresult) {case refresh_succeed://Refresh successful stateimageview.setvisibility (view.visible); 
   Statetextview.settext (R.string.refresh_succeed); 
   Stateimageview.setbackgroundresource (R.drawable.refresh_succeed); 
  Break 
   Case Refresh_fail://Refresh failed stateimageview.setvisibility (view.visible); 
   Statetextview.settext (R.string.refresh_fail); 
   Stateimageview.setbackgroundresource (r.drawable.refresh_failed); 
  Break 
  Default:break; 
 //Refresh results stay 1 seconds New Handler () {  @Override public void Handlemessage (msg) {state = Pull_to_refresh; 
   Hidehead (); 
 }}.sendemptymessagedelayed (0, 1000); 
  private void Changestate (int to) {state = to; 
   Switch (state) {case Pull_to_refresh://Dropdown refresh stateimageview.setvisibility (View.gone); 
   Statetextview.settext (R.string.pull_to_refresh); 
   Pullview.clearanimation (); 
   Pullview.setvisibility (view.visible); 
  Break 
   Case Release_to_refresh://Release Refresh Statetextview.settext (R.string.release_to_refresh); 
   Pullview.startanimation (rotateanimation); 
  Break 
   Case refreshing://Is refreshing pullview.clearanimation (); 
   Refreshingview.setvisibility (view.visible); 
   Pullview.setvisibility (view.invisible); 
   Refreshingview.startanimation (refreshinganimation); 
   Statetextview.settext (r.string.refreshing); 
  Break 
  Default:break; }/* * (non-Javadoc) determines whether events are distributed by the parent control to prevent event conflicts * * @see Android.view.viewgroup#dispatchtOuchevent (android.view.MotionEvent)/@Override public boolean dispatchtouchevent (motionevent ev) {switch (E 
   V.getactionmasked ()) {Case MotionEvent.ACTION_DOWN:downY = ev.gety (); 
   Lasty = DownY; 
   if (mtask!= null) {mtask.cancel (); 
    * * * Touch is located in the drop down header layout, because we do not have an incident response to the drop head, this time it will return a false cause the next event is no longer distributed in. 
   * So we can't give it to the parent class, direct return True/if (Ev.gety () < Movedeltay) returns true; 
  Break Case Motionevent.action_move://Canpull This value will be changed in the ontouch below according to whether ListView is sliding to the top, meaning whether it can be dropdown if (canpull) {//to the actual 
    The sliding distance does shrink, causing the feeling of Movedeltay = Movedeltay + (ev.gety ()-lasty)/radio; 
    if (Movedeltay < 0) Movedeltay = 0; 
    if (Movedeltay > Getmeasuredheight ()) Movedeltay = Getmeasuredheight (); 
    if (state = = refreshing) {//is refreshing when the touch moves istouchinrefreshing = true; 
   } lasty = Ev.gety (); Change the proportional radio = (float) (2 + 2 * Math.tan) according to the drop distance (MATH.PI/2/GetmeasurEdheight () * movedeltay)); 
   Requestlayout (); 
    if (Movedeltay <= refreshdist && state = = Release_to_refresh) {//If the drop distance does not reach the refresh distance and the current state is a release refresh, the change status is a drop-down refresh 
   Changestate (Pull_to_refresh); 
   } if (Movedeltay >= refreshdist && state = = Pull_to_refresh) {changestate (Release_to_refresh); 
   } if (Movedeltay > 8) {//Prevent the drop down process to trigger the long press event and click event Clearcontentviewevents (); 
   if (Movedeltay > 0) {//is being pulled down, do not let the child control catch event return true; 
  } break; Case MotionEvent.ACTION_UP:if (Movedeltay > Refreshdist)//is refreshing to pull down after releasing the dropdown head does not hide istouchinrefreshing = Fals 
   E 
    if (state = = Release_to_refresh) {changestate (refreshing); 
   The refresh operation if (Mlistener!= null) Mlistener.onrefresh (); 
  } else {} hidehead (); 
  Default:break; 
 //Event distribution to Parent return super.dispatchtouchevent (EV); /** * Modify fields by reflection to remove long press events and click events/private void ClearcontentvieweveNTS () {try {field[] fields = AbsListView.class.getDeclaredFields (); 
     for (int i = 0; i < fields.length i++) if (Fields[i].getname (). Equals ("Mpendingcheckforlongpress")) { 
     Mpendingcheckforlongpress is a field in Abslistview that is retrieved by reflection and removed from the message list, removing the long press event fields[i].setaccessible (true); 
    Contentview.gethandler (). Removecallbacks (Runnable) fields[i].get (Contentview)); else if (Fields[i].getname (). Equals ("Mtouchmode")) {//Touch_mode_rest =-1, this can remove the Click event Fields[i].seta 
     Ccessible (TRUE); 
    Fields[i].set (Contentview,-1); 
  //Remove focus ((Abslistview) contentview). Getselector (). SetState (new int[] {0}); 
  catch (Exception e) {log.d (TAG, "error:" + e.tostring ()); 
  }/* * (non-Javadoc) to draw shadow effects, color values can be modified * * @see Android.view.viewgroup#dispatchdraw (Android.graphics.Canvas) 
  * * @Override protected void Dispatchdraw (Canvas Canvas) {Super.dispatchdraw (Canvas); if (Movedeltay = = 0) rEturn; 
  RECTF RECTF = new RECTF (0, 0, getmeasuredwidth (), Movedeltay); 
  Paint Paint = new Paint (); 
  Paint.setantialias (TRUE); The height of the shadow is lineargradient lineargradient = new LinearGradient (0, Movedeltay, 0, moveDeltaY-26, 0x66000000, 0x0000000 
  0, Tilemode.clamp); 
  Paint.setshader (lineargradient); 
  Paint.setstyle (Style.fill); 
 In the Movedeltay place to the upper light canvas.drawrect (RECTF, paint); 
  private void Initview () {Pullview = Headview.findviewbyid (R.id.pull_icon); 
  Statetextview = (TextView) Headview.findviewbyid (R.ID.STATE_TV); 
  Refreshingview = Headview.findviewbyid (R.id.refreshing_icon); 
 Stateimageview = Headview.findviewbyid (R.ID.STATE_IV); @Override protected void OnLayout (Boolean changed, int l, int t, int r, int b) {if (!islayout) {//This 
   It's the first time you come in. Initialize Headview = getchildat (0); 
   Contentview = Getchildat (1); 
   Set up Ontouchlistener Contentview.setontouchlistener for Abslistview (this); 
   Islayout = true; Initview (); 
   Refreshdist = ((ViewGroup) headview). Getchildat (0). Getmeasuredheight (); } if (Canpull) {//change the layout of the child control Headview.layout (0, (int) movedeltay-headview.getmeasuredheight (), headview.ge 
   Tmeasuredwidth (), (int) movedeltay); Contentview.layout (0, (int) Movedeltay, Contentview.getmeasuredwidth (), (int) Movedeltay + 
  Contentview.getmeasuredheight ()); 
 }else super.onlayout (changed, L, T, R, b); 
 
  Class Mytimertask extends TimerTask {Handler Handler; 
  Public Mytimertask (Handler Handler) {this.handler = Handler; 
  @Override public void Run () {handler.sendmessage (Handler.obtainmessage ()); @Override public boolean Ontouch (View V, motionevent event) {//The first item is visible and slides to the top abslistview ALV = n 
  ull; 
  try {ALV = (abslistview) v; 
   catch (Exception e) {log.d (TAG, E.getmessage ()); 
  return false; 
  if (alv.getcount () = = 0) {//No item can also be pulled down to refresh Canpull = true; else if (ALV. getfirstvisibleposition () = = 0 && alv.getchildat (0). GetTop () >= 0) {//slide to the top of the Abslistview Canpull = 
  True 
  else Canpull = false; 
 return false; 
 } 
}

The comments in the code are already well written.
Now that the pulltorefreshlayout has been written, the next step is to use this layout to implement the dropdown refresh ~

First you have to write a Onrefreshlistener interface refresh operation:

Public interface Onrefreshlistener { 
 void Onrefresh (); 
} 

In the way of a refresh operation, you can perform a refresh operation in the activity by allowing the activity to implement this interface later.

Look at the layout of the mainactivity:

<com.jingchen.pulltorefresh.pulltorefreshlayout xmlns:android= "Http://schemas.android.com/apk/res/android" 
 android:id= "@+id/refresh_view" 
 android:layout_width= "match_parent" 
 android:layout_height= "Match_" Parent "> 
 
 <include layout=" @layout/refresh_head "/> 
  
 <!--all subclasses that support Abslistview--> 
 < ListView 
  android:id= "@+id/content_view" 
  android:layout_width= "match_parent" 
  android:layout_height= "Match_parent" 
  android:background= "@color/white" 
  android:divider= "@color/gray" 
  android: dividerheight= "1DP" > 
 </ListView> 
 
</com.jingchen.pulltorefresh.PullToRefreshLayout> 

Pulltorefreshlayout can contain only two child controls: Refresh_head and Content_view.
Look at the layout of the Refresh_head:

 <?xml version= "1.0" encoding= "Utf-8"?> <relativelayout xmlns:android= "http ://schemas.android.com/apk/res/android "android:id=" @+id/head_view "android:layout_width=" Match_parent "Android: layout_height= "Match_parent" android:background= "@color/light_blue" > <relativelayout android:layout_width= "Match_parent" android:layout_height= "Wrap_content" android:layout_alignparentbottom= "true" Android:paddingBottom = "20DP" android:paddingtop= "20DP" > <relativelayout android:layout_width= "match_parent" Android:layo ut_height= "Wrap_content" android:layout_centerinparent= "true" > <imageview android:id= "@+id/pull_icon" "Android:layout_width=" wrap_content "android:layout_height=" wrap_content "android:layout_centervertical=" t 
    Rue "android:layout_marginleft=" 60DP "android:background=" @drawable/pull_icon_big "/> <imageview Android:id= "@+id/refreshing_iCon "android:layout_width=" wrap_content "android:layout_height=" Wrap_content "android:layout_centervertical = "true" android:layout_marginleft= "60DP" android:background= "@drawable/refreshing" android:visibility= "gone "/> <textview android:id=" @+id/state_tv "android:layout_width=" Wrap_content "Android:layout_he" ight= "Wrap_content" android:layout_centerinparent= "true" android:text= "@string/pull_to_refresh" Android:tex Tcolor= "@color/white" android:textsize= "16sp"/> <imageview android:id= "@+id/state_iv" Android: Layout_width= "Wrap_content" android:layout_height= "Wrap_content" android:layout_centervertical= "true" Andro id:layout_marginright= "8DP" android:layout_toleftof= "@id/state_tv" android:visibility= "Gone"/> </Relat ivelayout> </RelativeLayout> </RelativeLayout> 

You can modify the layout of the Refresh_head as needed and then handle it in Pulltorefreshlayout, but the ID of the related view should be kept in sync with the pulltorefreshlayout.

Next is the Mainactivity code:

Package Com.jingchen.pulltorefresh; 
Import java.util.ArrayList; 
 
Import java.util.List; 
Import android.app.Activity; 
Import Android.content.Context; 
Import Android.os.Bundle; 
Import Android.os.Handler; 
Import Android.os.Message; 
Import Android.support.v4.view.PagerAdapter; 
Import Android.support.v4.view.ViewPager; 
Import Android.support.v4.view.ViewPager.OnPageChangeListener; 
Import Android.view.LayoutInflater; 
Import Android.view.View; 
Import Android.view.View.OnClickListener; 
Import Android.view.ViewGroup; 
Import Android.view.animation.AnimationUtils; 
Import Android.view.animation.LinearInterpolator; 
Import android.view.animation.RotateAnimation; 
Import Android.widget.AbsListView; 
Import Android.widget.AdapterView; 
Import Android.widget.AdapterView.OnItemClickListener; 
Import Android.widget.AdapterView.OnItemLongClickListener; 
Import Android.widget.BaseExpandableListAdapter; 
Import Android.widget.ExpandableListView; Import Android.widget.ExpandableListView. 
Onchildclicklistener; 
Import Android.widget.ExpandableListView.OnGroupClickListener; 
Import Android.widget.ListView; 
Import Android.widget.TextView; 
 
Import Android.widget.Toast; /** * In addition to the Drop-down refresh, in the case of Contenview for ListView I gave ListView added Footerview, realize click load More * * @author Chen Jing */public class Mainacti 
 Vity extends activity implements Onrefreshlistener, Onclicklistener {private Abslistview ALV; 
 Private Pulltorefreshlayout refreshlayout; 
 private View loading; 
 Private Rotateanimation loadinganimation; 
 Private TextView Loadtextview; 
 Private Myadapter adapter; 
 
 Private Boolean isloading = false; 
  @Override protected void OnCreate (Bundle savedinstancestate) {super.oncreate (savedinstancestate); 
  Setcontentview (R.layout.activity_main); 
 Init (); 
  private void init () {ALV = (abslistview) Findviewbyid (R.id.content_view); 
  Refreshlayout = (pulltorefreshlayout) Findviewbyid (R.id.refresh_view); 
  Refreshlayout.setonrefreshlistener (this); InitlistView (); 
  Loadinganimation = (rotateanimation) animationutils.loadanimation (this, r.anim.rotating); 
  Add Shiting animation Linearinterpolator lir = new Linearinterpolator (); 
 Loadinganimation.setinterpolator (LIR); /** * ListView Initialization method */private void Initlistview () {list&lt;string&gt; items = new arraylist&lt;string 
  &gt; (); 
  for (int i = 0; i &lt; i++) {Items.Add ("Here is Item" + i); 
  //Add head View Headview = Getlayoutinflater (). Inflate (r.layout.listview_head, NULL); 
  ((ListView) ALV). Addheaderview (Headview, NULL, FALSE); 
  Add footer View Footerview = Getlayoutinflater (). Inflate (R.layout.load_more, NULL); 
  Loading = Footerview.findviewbyid (R.id.loading_icon); 
  Loadtextview = (TextView) Footerview.findviewbyid (R.ID.LOADMORE_TV); 
  ((ListView) ALV). Addfooterview (Footerview, NULL, FALSE); 
  Footerview.setonclicklistener (this); 
  adapter = new Myadapter (this, items); 
  Alv.setadapter (adapter); Alv.setonitemlongclicklistener (New onItemlongclicklistener () {@Override public boolean Onitemlongclick (adapterview&lt;?&gt; parent, view view, in T position, long ID) {Toast.maketext (Mainactivity.this, "Longclick on" + Parent.getadapter (). Getitemid (position 
    ), Toast.length_short). Show (); 
   return true; 
  } 
  });  Alv.setonitemclicklistener (New Onitemclicklistener () {@Override public void Onitemclick (adapterview&lt;?&gt; Parent, view view, int position, long id) {Toast.maketext (Mainactivity.this, "click on" + Parent.getadapter () 
   . Getitemid (position), Toast.length_short). Show (); 
 } 
  }); /** * GridView Initialization method */private void Initgridview () {list&lt;string&gt; items = new arraylist&lt;string 
  &gt; (); 
  for (int i = 0; i &lt; i++) {Items.Add ("Here is Item" + i); 
  } adapter = new Myadapter (this, items); 
  Alv.setadapter (adapter); Alv.setonitemlongclicklistener (New Onitemlongclicklistener () {@Override public boolean OnITemlongclick (adapterview&lt;?&gt; Parent, view view, int position, long id) {Toast.maketext (Mainactivity.this, " 
    Longclick on "+ Parent.getadapter (). Getitemid (position), Toast.length_short). Show (); 
   return true; 
  } 
  });  Alv.setonitemclicklistener (New Onitemclicklistener () {@Override public void Onitemclick (adapterview&lt;?&gt; Parent, view view, int position, long id) {Toast.maketext (Mainactivity.this, "click on" + Parent.getadapter () 
   . Getitemid (position), Toast.length_short). Show (); 
 } 
  }); /** * Expandablelistview Initialization method */private void Initexpandablelistview () {(Expandablelistview) ALV). Set 
  Adapter (This) (new Expandablelistadapter); ((Expandablelistview) ALV). Setonchildclicklistener (New Onchildclicklistener () {@Override public boolean onch Ildclick (expandablelistview parent, View v, int groupposition, int childposition, long id) {Toast.maketext (MainA Ctivity.this, "click on Group" + GroUpposition + "Item" + Childposition, Toast.length_short). Show (); 
   return true; 
  } 
  }); ((Expandablelistview) ALV). Setonitemlongclicklistener (New Onitemlongclicklistener () {@Override public Boolea N Onitemlongclick (adapterview&lt;?&gt; parent, view view, int position, long id) {Toast.maketext (mainactivity.th 
    IS, ' longclick on ' + Parent.getadapter (). Getitemid (position), Toast.length_short). Show (); 
   return true; 
  } 
  }); ((Expandablelistview) ALV). Setongroupclicklistener (New Ongroupclicklistener () {@Override public boolean Ongr Oupclick (expandablelistview parent, View v, int groupposition, long id) {if (parent.isgroupexpanded grouppositio 
    N)) {///If the expansion closes Parent.collapsegroup (groupposition); 
    else {//if turned off, note that this is manually open do not default scrolling otherwise there will be a bug Parent.expandgroup (groupposition); 
   return true; 
 } 
  }); @Override public void Onrefresh () {//Drop-down refresh Operation New Handler () 
  {@Override public void Handlemessage (msg) {refreshlayout.refreshfinish (pulltorefreshlayout). 
   Refresh_succeed); 
 }}.sendemptymessagedelayed (0, 5000); @Override public void OnClick (View v) {switch (V.getid ()) {Case R.id.loadmore_layout:if (!isload 
    ing) {loading.setvisibility (view.visible); 
    Loading.startanimation (loadinganimation); 
    Loadtextview.settext (r.string.loading); 
   IsLoading = true; 
  } break; 
  Default:break; } class Expandablelistadapter extends Baseexpandablelistadapter {private string[] groupsstrings;//= new S 
  Tring[] {"This is group 0",//"This is group 1", "This is group 2"}; 
  Private string[][] GroupItems; 
 
  private context; 
   Public Expandablelistadapter {this.context = context; 
   Groupsstrings = new String[8]; for (int i = 0; i &lt; groupsstrings.length i++) {groupsstrings[i] = new String ("Here is group" +i); 
   } GroupItems = new string[8][8]; for (int i = 0; i &lt; groupitems.length i++) for (int j = 0; J &lt; Groupitems[i].length; J +) {Groupit 
    EMS[I][J] = new String ("Here is the item" in Group + i + "+ j"); 
  @Override public int GetGroupCount () {return groupsstrings.length; 
  @Override public int Getchildrencount (int groupposition) {return groupitems[groupposition].length; 
  @Override public Object getgroup (int groupposition) {return groupsstrings[groupposition]; @Override public Object getchild (int groupposition, int childposition) {return groupitems[groupposition] 
  [Childposition]; 
  @Override public long getgroupid (int groupposition) {return groupposition; 
  @Override public long Getchildid (int groupposition, int childposition) {return childposition; 
  @Override public boolean Hasstableids () {true; } @OverridE public View getgroupview (int groupposition, Boolean isexpanded, View Convertview, ViewGroup parent) {View Vie 
   W = layoutinflater.from (context). Inflate (r.layout.list_item_layout, NULL); 
   TextView TV = (TextView) View.findviewbyid (R.ID.NAME_TV); 
   Tv.settext (Groupsstrings[groupposition]); 
  return view; @Override public View getchildview (int groupposition, int childposition, Boolean islastchild, View Convertview, 
   ViewGroup parent) {View view = Layoutinflater.from (context). Inflate (r.layout.list_item_layout, NULL); 
   TextView TV = (TextView) View.findviewbyid (R.ID.NAME_TV); 
   Tv.settext (Groupitems[groupposition][childposition]); 
  return view; 
  @Override public boolean ischildselectable (int groupposition, int childposition) {return true; 
 } 
 
 } 
 
}

In mainactivity to Judge Contentview is ListView words to ListView added Footerview implementation Click Load More features. This is just a demo pulltorefreshlayout use of the demo, you can refer to the changes. I've written the Listview,gridview and Expandablelistview initialization method in it, calling it according to which I use it. So this is the ListView drop-down refresh and load more. What if I want the GridView to have a drop-down refresh function? Then replace the mainactivity layout with this:

<com.jingchen.pulltorefresh.pulltorefreshlayout xmlns:android= "Http://schemas.android.com/apk/res/android" 
 android:id= "@+id/refresh_view" 
 android:layout_width= "match_parent" 
 android:layout_height= "Match_" Parent "> 
 
 <include layout=" @layout/refresh_head "/> 
 <!--all subclasses that support Abslistview--> 
 < The GridView 
  android:id= "@+id/content_view" 
  android:layout_width= "match_parent" 
  android:layout_height= "Match_parent" 
  android:background= "@color/white" 
  android:columnwidth= "90DP" 
  android:gravity= " Center " 
  android:horizontalspacing=" 10DP " 
  android:numcolumns=" Auto_fit " 
  android:stretchmode=" ColumnWidth " 
  android:verticalspacing=" 15DP "> 
 </GridView> 
 
</ Com.jingchen.pulltorefresh.pulltorefreshlayout> 

If it's expandablelistview, change the layout to this:

<com.jingchen.pulltorefresh.pulltorefreshlayout xmlns:android= "Http://schemas.android.com/apk/res/android" 
 android:id= "@+id/refresh_view" 
 android:layout_width= "match_parent" 
 android:layout_height= "Match_" Parent "> 
 
 <include layout=" @layout/refresh_head "/> 
 <!--all subclasses that support Abslistview--> 
 < Expandablelistview 
  android:id= "@+id/content_view" 
  android:layout_width= "Match_parent" 
  android: layout_height= "Match_parent" 
  android:background= "@color/white" > 
 </ExpandableListView> 
 
</com.jingchen.pulltorefresh.PullToRefreshLayout> 

What do you think? It's simple, isn't it? Easy to use, no longer to inherit changes.

This article has been sorted into the "Android Drop-down refresh loading effect," Welcome to study.

Hopefully this article will help you learn about the Android Drop-down refresh control.

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.