Android self-defined component family "5"--Advanced Practices (1)

Source: Internet
Author: User
Tags gety

In the next few articles will be the teacher's blog post, "You can pull down Pinnedheaderexpandablelistview implementation," the concrete implementation. Take a look at the code of the Great God and record it.

Original source: http://blog.csdn.net/singwhatiwanna/article/details/25546871

Let's take a look at the results:

watermark/2/text/ahr0cdovl2jsb2cuy3nkbi5uzxqvc2luz3doyxrpd2fubme=/font/5a6l5l2t/fontsize/400/fill/i0jbqkfcma== /dissolve/70/gravity/southeast "/>

Create a new Activity_main.xml file

<relativelayout xmlns:android= "http://schemas.android.com/apk/res/android" android:layout_width= "Fill_parent" android:layout_height= "Fill_parent" ><com.example.testexpandablelistview.ui.stickylayout android:id= "@+id/ Sticky_layout "android:layout_width=" match_parent "android:layout_height=" Match_parent "android:layout_marginTop= "0DP" android:orientation= "vertical" > <linearlayout android:id= "@+id/header" Android:layout_wid         Th= "Match_parent" android:layout_height= "100DP" android:gravity= "center" android:background= "#78a524"        android:orientation= "vertical" > </LinearLayout> <linearlayout android:id= "@+id/content" Android:layout_width= "Match_parent" android:layout_height= "match_parent" android:orientation= "Vertica L "> </LinearLayout></com.example.testexpandablelistview.ui.StickyLayout></RelativeLayout>
The above Stickylayout class is our own definition of the linearlayout, the idea is actually very easy, first get stickylayout in the header and content two view, code such as the following:

private void InitData () {///Use the Getidentifier () method to easily obtain the specified resource ID under each application package. See: Http://blog.sina.com.cn/s/blog_5da93c8f0100zlrx.htmlint Headerid = Getresources (). Getidentifier ("header", " ID ", GetContext (). Getpackagename ()), int contentId = Getresources (). Getidentifier (" Content "," id ", GetContext (). Getpackagename ()); if (Headerid! = 0 && ContentId! = 0) {Mheader = Findviewbyid (headerid); mcontent = Findviewbyid ( CONTENTID); moriginalheaderheight = Mheader.getmeasuredheight (); mheaderheight = moriginalheaderheight;//is a distance, When a slide is moved, the hand moves more than this distance to begin moving the control.

Mtouchslop = Viewconfiguration.get (GetContext ()). Getscaledtouchslop (); LOG.D (TAG, "mtouchslop =" + Mtouchslop);} Else{throw New Nosuchelementexception ("Did your view with \" Header\ "or \" content\ "exist?

");}}

The listener function of the re-processing screen

 @Overridepublic Boolean onintercepttouchevent (Motionevent event) {int intercepted = 0;int x = (int) event.getx (); int y = (int) event.gety (); switch (Event.getaction ()) {case MotionEvent.ACTION_DOWN:mLastXIntercept = x;mlastyintercept = Y;mlastx = X;mlasty = y ; intercepted = 0;break;case MotionEvent.ACTION_MOVE:int DeltaX = x-mlastxintercept;int DeltaY = y-mlastyintercept;if (M Status = = status_expanded && deltay <=-mtouchslop) {intercepted = 1;} else if (mgiveuptoucheventlistener! = null) {if (mgiveuptoucheventlistener.giveuptouchevent) && DeltaY >= mtouchslop) {intercepted = 1;}} Break;case motionevent.action_up:{intercepted = 0;mlastxintercept = Mlastyintercept = 0;break;} Default:break;} LOG.D (TAG, "intercepted =" + intercepted);//Assuming 1 returns true, passed to the current ontouchevent. Suppose that 0 returns false, passed to the child control return intercepted! = 0;} 
Onintercepttouchevent is defined in the ViewGroup, used to intercept gesture events, each gesture event will first call Onintercepttouchevent, assuming that the method returns true to intercept the event, The current ontouchevent is fired, assuming that false returns are passed to the child control.

@Overridepublic boolean ontouchevent (Motionevent event) {int x = (int) event.getx (); int y = (int) event.gety ();  LOG.D (TAG, "x=" + x + "y=" + y + "mlasty=" + mlasty); switch (Event.getaction ()) {case Motionevent.action_down:break;case MotionEvent.ACTION_MOVE:int DeltaX = X-mlastx;int DeltaY = y-mlasty; LOG.D (TAG, "mheaderheight=" + mheaderheight + "  deltay=" + DeltaY + "  mlasty=" + mlasty); Mheaderheight +=deltay;se Theaderheight (mheaderheight); break;case MotionEvent.ACTION_UP:int destheight = 0;if (mheaderheight <= Moriginalheaderheight * 0.5) {destheight = 0;mstatus = status_collapsed;} Else{destheight = Moriginalheaderheight;mstatus = status_expanded;} Slide slowly toward the end This.smoothsetheaderheight (Mheaderheight, Destheight, n); break;default:break;} MLASTX = X;mlasty = Y;return true;}
Passing events to ontouchevent when sliding

In the sliding event, the setheaderheight changes the height of the header section above, and when lifted it infers whether the original height is changed, and then slowly slides toward the end.

/* Change the height of the header */private void setheaderheight (int height) {if (height < 0) {height = 0;} else if (Height > moriginal Headerheight) {height = moriginalheaderheight;} if (mheaderheight! = Height | | true) {mheaderheight = Height;mheader.getlayoutparams (). height = mheaderheight; Mheader.requestlayout ();}}
public void Smoothsetheaderheight (final int from, final int to, long duration) {final int framecount = (int) (DURATION/1  000F * + 1;final float partation = (to-from)/(float) framecount;new Thread ("Thread#smoothsetheaderheight") {public void Ruan () {for (int i = 0; i < Framecount; i++) {Final Int. height;if (i = = frameCount-1) {height = to;} Else{height = (int) (from + partation * i);} Post (new Runnable () {@Overridepublic void run () {setheaderheight (height);}}); try {sleep];} catch (Interruptedexception e) {e.printstacktrace ();}}}}. Start ();}
The function of the View.post (Runnable) method above is to add the Runnable object to the UI thread to execute, altering the height of the header section.

The complete code for the Stickylayout class is as follows:

Package Com.example.testexpandablelistview.ui;import Java.util.nosuchelementexception;import Android.annotation.targetapi;import Android.content.context;import Android.os.build;import Android.util.attributeset;import Android.util.log;import Android.view.motionevent;import Android.view.View;import Android.view.viewconfiguration;import android.widget.linearlayout;/** * Own definition LinearLayout * @author turn from:/http blog.csdn.net/singwhatiwanna/article/details/25546871 * */public class Stickylayout extends Linearlayout{private Static final String TAG = "Stickylayout";p Ublic interface Ongiveuptouchenventlistener{public Boolean giveuptouchevent ( Motionevent event);}   Private View Mheader; The upper part.  The following becomes Headerprivate View mcontent;  The following sections private ongiveuptouchenventlistener mgiveuptoucheventlistener;private int mtouchslop; The height of the moving distance//header unit: Pxprivate int Moriginalheaderheight;//header Part of the original height private int mheaderheight;// The actual height of the header section today (as the gesture slide changes) private int mstatus = status_expanded;//Current state public STATic Final int status_expanded = 1;   Expand state public static final int status_collapsed = 2; Closed state//record last sliding coordinates private int mlastx = 0;private int mlasty = 0;//record last sliding coordinates (onintercepttouchevent) private int mlastxintercept = 0;private int mlastyintercept = 0;/* * Constructor 1 */public stickylayout (context context) {super (context);} /* Constructor 2 */public stickylayout (context context, AttributeSet Attrs) {Super (context, attrs);} /* Constructor 3 * The function of the TARGETAPI tag is to make the API code of the high version number in the low version number SDK without error */@TargetApi (build.version_codes. Honeycomb) Public stickylayout (context context, AttributeSet attrs, int defstyle) {Super (context, attrs, Defstyle); The}/** * Onwindowfocuschanged method is used to monitor whether an activity is loaded and completed. During the activity life cycle, * onStart, Onresume, oncreate are not real visible points of time, the real visible point is when the onwindowfocuschanged () function is executed. */@Overridepublic void onwindowfocuschanged (Boolean haswindowfocus) {super.onwindowfocuschanged (haswindowfocus); The assumption is that activity loading is complete, and Mheader and mcontent are not initialized. The initialization method is executed. if (Haswindowfocus && (Mheader = = NULL | | mcontent = = Null)) {InitData ();}} private void InitData () {///Use the Getidentifier () method to easily obtain the specified resource ID under each application package. See: Http://blog.sina.com.cn/s/blog_5da93c8f0100zlrx.htmlint Headerid = Getresources (). Getidentifier ("header", " ID ", GetContext (). Getpackagename ()), int contentId = Getresources (). Getidentifier (" Content "," id ", GetContext (). Getpackagename ()); if (Headerid! = 0 && ContentId! = 0) {Mheader = Findviewbyid (headerid); mcontent = Findviewbyid ( CONTENTID); moriginalheaderheight = Mheader.getmeasuredheight (); mheaderheight = moriginalheaderheight;//is a distance. When a slide is moved, the hand moves more than this distance to begin moving the control. Mtouchslop = Viewconfiguration.get (GetContext ()). Getscaledtouchslop (); LOG.D (TAG, "mtouchslop =" + Mtouchslop);} Else{throw New Nosuchelementexception ("Did your view with \" Header\ "or \" content\ "exist?");}} @Overridepublic boolean onintercepttouchevent (Motionevent event) {int intercepted = 0;int x = (int) event.getx (); int y = ( int) event.gety (); switch (Event.getaction ()) {Case MotionEvent.ACTION_DOWN:mLastXIntercept = X;mlastyintercePT = Y;MLASTX = X;mlasty = y;intercepted = 0;break;case MotionEvent.ACTION_MOVE:int deltax = x-mlastxintercept;int Delta Y = y-mlastyintercept;if (Mstatus = = status_expanded && deltay <=-mtouchslop) {intercepted = 1;} else if (mgiveuptoucheventlistener! = null) {if (mgiveuptoucheventlistener.giveuptouchevent) && DeltaY >= mtouchslop) {intercepted = 1;}} Break;case motionevent.action_up:{intercepted = 0;mlastxintercept = Mlastyintercept = 0;break;} Default:break;} LOG.D (TAG, "intercepted =" + intercepted);//Assuming 1 returns true, passed to the current ontouchevent. Suppose that 0 returns false, passed to the child control return intercepted! = 0;} @Overridepublic boolean ontouchevent (Motionevent event) {int x = (int) event.getx (); int y = (int) event.gety ();  LOG.D (TAG, "x=" + x + "y=" + y + "mlasty=" + mlasty); switch (Event.getaction ()) {case Motionevent.action_down:break;case MotionEvent.ACTION_MOVE:int DeltaX = X-mlastx;int DeltaY = y-mlasty; LOG.D (TAG, "mheaderheight=" + mheaderheight + "deltay=" + DeltaY + "mlasty=" + Mlasty); mheaderheight +=deltay;setheaderheight (mheaderheight); break;case MotionEvent.ACTION_UP:int destheight = 0;if (Mheaderheight <= moriginalheaderheight * 0.5) {destheight = 0;mstatus = status_collapsed;} Else{destheight = Moriginalheaderheight;mstatus = status_expanded;} Slide slowly toward the end This.smoothsetheaderheight (Mheaderheight, Destheight, n); break;default:break;} MLASTX = X;mlasty = Y;return true;} public void Smoothsetheaderheight (final int from, final int to, long duration) {final int framecount = (int) (DURATION/1  000F * + 1;final float partation = (to-from)/(float) framecount;new Thread ("Thread#smoothsetheaderheight") {public void Ruan () {for (int i = 0; i < Framecount; i++) {Final Int. height;if (i = = frameCount-1) {height = to;} Else{height = (int) (from + partation * i);} Post (new Runnable () {@Overridepublic void run () {setheaderheight (height);}}); try {sleep];} catch (Interruptedexception e) {e.printstacktrace ();}}}}. Start ();} /* Change the height of the header */private void Setheaderheight (int height) {if (height < 0) {height = 0;} else if (height > moriginalheaderheight) {height = moriginalheaderheight;} if (mheaderheight! = Height | | true) {mheaderheight = Height;mheader.getlayoutparams (). height = mheaderheight; Mheader.requestlayout ();}}}
Mainactivity.java

Package Com.example.testexpandablelistview;import Android.app.activity;import Android.os.bundle;import Com.example.testexpandablelistview.ui.stickylayout;public class Mainactivity extends activity{@Overrideprotected void OnCreate (Bundle savedinstancestate) {super.oncreate (savedinstancestate); Setcontentview (r.layout.activity_ main);}}
Execution effect:

Original address: http://blog.csdn.net/singwhatiwanna/article/details/25546871


Copyright notice: This article Bo Master original article. Blog, not reproduced without consent.

Android self-defined component family "5"--Advanced Practices (1)

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.