Android uses Viewpager for left and right loop sliding and carousel effects

Source: Internet
Author: User

Viewpager is a common Android component, but usually we do not use the Viewpager to achieve the left and right infinite loop sliding, when sliding to the boundary will see a page can not be animated, may affect the user experience. In addition, some culture viewpager (such as Viewpager for display ads or announcements) may require the effect of automatic carousel, where users can see information on other pages without swiping.

For this I looked at some of the existing network on the implementation of some examples of such effects, but are not very satisfied, after repeated experiments, summed up here and share to everyone, hope to be helpful.


The realization of the cyclic sliding effect: pageradapter

We know that the viewpager comes with a very good sliding effect, so we don't have to deal with this slide at all, only to handle the display of the content. The display of the content is controlled by adapter, so the focus here is the adapter. For simplicity's sake, each view in this example is directly a picture. Here is the code for adapter:

Private class imageadapter extends pageradapter{private arraylist<imageview>  viewlist;public imageadapter (arraylist<imageview> viewlist)  {this.viewlist =  viewlist;} @Overridepublic  int getcount ()  {//is set to maximum so that the user cannot see the boundary return integer.max_value;} @Overridepublic  boolean isviewfromobject (VIEW&NBSP;ARG0,&NBSP;OBJECT&NBSP;ARG1)  {return  ARG0==ARG1;}   @Override            public void  Destroyitem (viewgroup container, int position,                    object object)  {    Warning: Do not call removeview! here          }    @Override             public object instantiateitem (ViewGroup container, int position)  { position %= viewlist.size (); if  (position< 0) { position = viewlist.size () +position; } imageview view =  Viewlist.get (position);  //If the view has been previously added to a parent component, you must remove it first, or the illegalstateexception will be thrown.  viewparent vp =view.getparent (); if  (vp!=null) { viewgroup parent =   (ViewGroup) Vp; parent.removeview (view); }              container.addview (view);                //add listeners here if necessary              return view;            }  }

Here are a few places to note:

  • GetCount () The return value of the method: This value is directly related to the "boundary" of the Viewpager, so when we set it to Integer.max_value, the user basically does not see the boundary (the battery is already dead when the slide is down here o_o). Of course, it is usually possible to set it to 100 times times the actual number of content, and one of the previous implementations was to do so.

  • Span style= "font-family: ' italics ', ' italics _gb2312 ', simkai;font-size:16px;" >instantiateitem ()   method position Processing: As we set the count to  integer. max_value , So the value range of this position is very big, but we actually want to show the content is not so much (often only a few), so there is certainly a modulo operation. However, there is a problem with a simple modulo: if you consider the case where the user is sliding to the left, the position may appear negative. So we need to deal with negative values again, so that they fall within the correct interval.

  • Instantiateitem () methods The processing of parent components: usually we will addview directly, but if you write this directly, you will throw illegalstateexception. Assuming there are three view, the exception is triggered when the user slides to the fourth , because we are trying to add a view with a parent component to another component . However, if it is written directly as follows:

(ViewGroup) View.getparent (). Removeview (view);

It will also throw NullPointerExceptionbecause the component does not have a parent component at the beginning. Therefore, a judgement is required. That's the code above.

    • Destroyitem () method: As we are Instantiateitem () The remove logic has been processed in the method, so there is no need to deal with it. In fact, the experiment shows that if you add a call to remove, there is a case where the contents of the Viewpager are empty.


Implementation of the Carousel effect: Update with Handler

Here I define a handler to handle the Viewpager of the carousel 。 Note slide the viewpager manually with the carousel effect, so I think the user would want to view the specified page at this time, and the carousel should be canceled. The following is the implementation of this handler:

Private static class imagehandler extends handler{protected static final  int msg_update_image = 1;//Update Protected static final int msg_keep_ silent = 2;//Silent protected static final int msg_break_silent = 3;// Unblock Silent protected static final int msg_page_changed = 4;//page modification//Carousel interval Time protected  static final long msg_delay = 3000;//use weak references to avoid handler leaks private weakreference <MainActivity> weakReference;private int currentItem = 0;protected  ImageHandler (WEAKREFERENCE&LT;MAINACTIVITY&GT;&NBSP;WK) {weakreference = wk;} @Overridepublic  void handlemessage (message msg)  {super.handlemessage (msg); LOG.D (log_tag,  "receive message "  + msg.what); Mainactivity activity = weakreference.get ();if  (activity==null) {//activity has been recycled, No more UI to work on return ;} if  (Activity.handler.hasMessages (msg_update_image)) {activity.handler.removeMessages (msg_update_image);} switch  (msg.what)  {case msg_update_image:currentitem++;activity.viewpager.setcurrentitem ( CurrentItem); activity.handler.sendEmptyMessageDelayed (msg_update_image, msg_delay); break;case msg_ Keep_silent:break;case msg_break_silent:activity.handler.sendemptymessagedelayed (MSG_UPDATE_IMAGE,  Msg_delay); break;case msg_page_changed:currentitem = msg.arg1;break;default:break;}  }}


Integration code: Mainactivity

The following is the code for mainactivity, which mainly loads the view and initializes the Viewpager settings. Because the amount of code is less, the important part has been annotated, do not repeat the

public class mainactivity extends activity {private static final  string log_tag =  "Mainactivity";p rivate imagehandler handler = new  ImageHandler (new weakreference<mainactivity> (this));p rivate viewpager viewpager;@ Overrideprotected void oncreate (bundle savedinstancestate)  {super.oncreate ( Savedinstancestate); Setcontentview (r.layout.activity_main);//Initialize the contents of Iewpager viewpager =  (ViewPager)  findviewbyid (R.id.main_viewpager); Layoutinflater inflater = layoutinflater.from (This);imageview view1 =  (ImageView )  inflater.inflate (R.layout.item, null);imageview view2 =  (ImageView)   Inflater.inflate (r.layout.item, null);imageview view3 =  (ImageView)  inflater.inflate ( R.layout.item, null); View1.setimageresource (r.drawable.ics); View2.setimageresource (R.drawable.jellybean); View3.setimagEResource (R.drawable.kitkat); Arraylist<imageview> views = new arraylist<imageview> (); Views.add (View1); Views.add (VIEW2); Views.add (VIEW3); Viewpager.setadapter (New imageadapter (views)); Viewpager.setonpagechangelistener (New viewpager.onpagechangelistener ()  {// Set up with the CurrentItem field of the adapter. @Overridepublic  void onpageselected (int arg0)  {handler.sendmessage (Message.obtain (Handler,  imagehandler.msg_page_changed, arg0, 0));} @Overridepublic  void onpagescrolled (INT&NBSP;ARG0,&NBSP;FLOAT&NBSP;ARG1,&NBSP;INT&NBSP;ARG2)  {} Overwrite this method to realize the pause and resume of the Carousel effect @overridepublic void onpagescrollstatechanged (int arg0)  {switch  ( arg0)  {case viewpager.scroll_state_dragging:handler.sendemptymessage (imagehandler.msg_keep_silent); Break;case viewpager.scroll_state_idle:handler.sendemptymessagedelayed (ImageHandler.MSG_UPDATE_IMAGE,  imagehandler.msg_delay); break;default:break;}}); viewpager.seTcurrentitem (INTEGER.MAX_VALUE/2);//default in the middle, so that the user does not see the boundary//start Carousel effect handler.sendemptymessagedelayed (imagehandler.msg_ Update_image, imagehandler.msg_delay);}


The analysis on the code here, the example is relatively simple, if you need to download the code, please visit here: http://down.51cto.com/data/1898707. If there is any omission, please correct me.

This article is from the "Flying Cat" blog, be sure to keep this source http://flyingcat2013.blog.51cto.com/7061638/1575015

Android uses Viewpager for left and right loop sliding and carousel effects

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.