Android Circular rotation menu, and support for mobile conversion feature

Source: Internet
Author: User
Tags event listener gety

LZ the company recently took over a project that needed to write a round rotation menu, and the menu moves between the transposition support, I would have thought such a demo if the Internet is very. Think your mother can not help me, empty rotation, but it can not change the position, so LZ we can only rely on their own groping.

The online section of the last LZ reference code. A self-defined view that ultimately implements this seemingly very hanging. But there is no meaningful function.

In this contribution to the vast numbers of farmers to share.

Words not much to say, first on the code:

Define the View class yourself:

public class Roundspinview extends View {private Paint mpaint = new Paint ();p rivate paintflagsdrawfilter pfd;private int S   Tartmenu; The first picture of the menu resources id//STONE List Private bigstone[] mstones;//number private static final int stone_count = 3;//Center coordinate private int Mpoin TX = 0, Mpointy = 0;//radius private int mradius = 0;//angle of every two point interval private int mdegreedelta;private int Menuradius; The radius of the menu private int mcur =-1;   Menu;private boolean[] quadranttouched that is being moved;  A record of each quadrant touch situation//Touch detectionprivate gesturedetector mgesturedetector;private onroundspinviewlistener mListener;  Define your own event listener private final static int to_rotate_button = 0; Rotate button;private Handler Handler = new Handler () {public void Handlemessage (Message msg) {switch (msg.what) {case To_rota Te_button:float velocity = float.parsefloat (msg.obj.toString ()); Rotatebuttons (velocity/75); Velocity/= 1.0666f;new Thread (new flingrunnable (velocity)). Start (); break;default:break;}};}; public interface Onroundspinviewlistener{public void Onsingletapup (int position); Listen for each menu click event}public roundspinview (Context context,attributeset attrs) {super (CONTEXT,ATTRS); if (attrs!=null) { TypedArray a = GetContext (). Obtainstyledattributes (Attrs,r.styleable.roundspinview); startmenu = A.getresourceid ( R.styleable.roundspinview_menustart, 0);} PFD = new Paintflagsdrawfilter (0, Paint.anti_alias_flag| Paint.filter_bitmap_flag); Mpaint.setcolor (Color.White); Mpaint.setstrokewidth (2); Mpaint.setantialias (true); Anti-aliasing Mpaint.setstyle (Paint.Style.STROKE);  Draw Hollow circle Patheffect effects = new Dashpatheffect (new float[]{5,5,5,5},1);  Mpaint.setpatheffect (effects); quadranttouched = new boolean[] {false, False, False, False, false};mgesturedetector = new Gesturedetector (GetContext (), New Mygesturelistener ()); Setupstones (); @Overrideprotected void onmeasure (int widthmeasurespec, int heightmeasurespec) {//TODO auto-generated method Stubsuper.onmeasure (Widthmeasurespec, heightmeasurespec); mpointx = This.getmeasuredwidth ()/2;mPointY = This.getmeasuredheight ()/2;//Initialize radius andMenu Radius Mradius = Mpointx-mpointx/5;menuradius = (int) (mpointx/5.5); Computecoordinates ();} /** * Initialize each point */private void Setupstones () {mstones = new Bigstone[stone_count]; Bigstone stone;int angle = 270;mdegreedelta = 360/stone_count;for (int index = 0; index < stone_count; index++) {ston E = new Bigstone (); if (angle >=) {angle-= 360;} else if (angle < 0) {angle + = 360;} Stone.angle = Angle;stone.bitmap = Bitmapfactory.decoderesource (Getresources (), StartMenu + index); angle + = Mdegreedelta;mstones[index] = stone;}} /** * Once again calculates the angle of each point */private void Resetstonesangle (float x, float y) {int angle = Computecurrentangle (x, y); LOG.D ("Roundspinview", "angle:" + angle); for (int index = 0; Index < Stone_count; index++) {Mstones[index].angle = Angle;angle + + Mdegreedelta;}} /** * Calculates coordinates for each point */private void Computecoordinates () {bigstone stone;for (int index = 0; index < stone_count; index++) { Stone = mstones[index];stone.x = mpointx+ (float) (Mradius * Math.Cos (Math.toradians (Stone.angle))); stone.y = mpointy+ (float) (Mradius * Math.sin (Math.toradians (Stone.angle)));}} /** * Calculates the angle of a point * * @param x * @param y * @return */private int Computecurrentangle (float x, float y) {Float distance = (fl  Oat) math.sqrt (((X-MPOINTX) * (X-MPOINTX) + (y-mpointy) * (y-mpointy)); int degree = (int) (Math.acos ((X-MPOINTX) /distance) * 180/math.pi); if (Y < mpointy) {degree =-degree;} LOG.D ("Roundspinview", "x:" + x + ", y:" + y + ", Degree:" + degree); return degree;} Private double startangle; @Overridepublic boolean dispatchtouchevent (Motionevent event) {//Resetstonesangle ( Event.getx (), event.gety ());//Computecoordinates ();//invalidate (); int x, Y;if (event.getaction () = = Motionevent.action_down) {x = (int) event.getx (); y = (int) event.gety (); mcur = Getincircle (x, y); if (mcur = =-1) {Startang Le = Computecurrentangle (x, y);}} else if (event.getaction () = = Motionevent.action_move) {x = (int) event.getx (); y = (int) event.gety (); if (mcur! =-1) {MSt ones[mcur].x = X;MSTONES[MCUR].Y =Y;invalidate ();} else {Double Currentangle = computecurrentangle (x, y); Rotatebuttons (startangle-currentangle); startangle = Currentangle;}} else if (event.getaction () = = motionevent.action_up) {x = (int) event.getx (); y = (int) event.gety (); if (mcur! =-1) {Compu Tecoordinates (); int cur = getincircle (x, y); if (cur! = mcur && cur! =-1) {int angle = Mstones[mcur].angle;mstones [Mcur].angle = Mstones[cur].angle;mstones[cur].angle = angle;} Computecoordinates (); invalidate (); mcur =-1;}} Set the touched quadrant to Truequadranttouched[getquadrant (Event.getx ()-mpointx,mpointy-event.gety ())] = True;mges Turedetector.ontouchevent (event); return true;} Private class Mygesturelistener extends Simpleongesturelistener {@Overridepublic boolean onfling (Motionevent E1, Motionevent E2, float velocityx,float velocityy) {//Get the quadrant of the start and the end of the flingint q1 = Getqua Drant (E1.getx ()-Mpointx, Mpointy-e1.gety ()); int q2 = Getquadrant (E2.getx ()-Mpointx, MPOINTY-E2.GEty ());//The inversed rotationsif (q1 = = 2 && q2 = 2 && math.abs (Velocityx) < Math.Abs (velocityy)) | | (Q1 = = 3 && q2 = 3) | | (q1 = = 1 && q2 = 3) | | (q1 = = 4 && q2 = 4 && math.abs (Velocityx) > Math.Abs (velocityy)) | | ((q1 = = 2 && q2 = 3) | | (Q1 = = 3 && q2 = 2)) | | ((q1 = = 3 && q2 = 4) | | (q1 = = 4 && q2 = 3)) | | (q1 = = 2 && q2 = 4 && quadranttouched[3]) | | (q1 = = 4 && q2 = = 2 && quadranttouched[3])) {//CircleLayout.this.post (New Flingrunnable ( -1//* (Velocityx + velocityy)); new Thread (New Flingrunnable (velocityx+ VELOCITYY). Start ();} else {//the normal rotation//circlelayout.this//. Post (new flingrunnable (Velocityx + velocityy)); new Thread (New Flingru Nnable (-(VELOCITYX+VELOCITYY))). Start ();} return true;} @Overridepublic Boolean onsingletapup (motionevent e) {int cur = getincircle (int) e.getx (), (int) e.gety ()), if (cur!=-1) { if (mlistener!=null) {Mlistener.onsingletapup (CUR);} Toast.maketext (GetContext (), "Position:" +cur, 0). Show (); return true;} return false;}} Private class Flingrunnable implements Runnable{private float velocity;public flingrunnable (float velocity) { this.velocity = velocity;} @Overridepublic void Run () {//TODO auto-generated method stubif (Math.Abs (velocity) >=200) {Message message = Message.obtain (); message.what = To_rotate_button;message.obj = velocity;handler.sendmessage (message);}} /** * @return the selected quadrant.  */private static int getquadrant (double x, double y) {if (x >= 0) {return y >= 0? 1:4;} else {}return y >= 0?

2:3;} /* * Rotate menu button */private void rotatebuttons (double degree) {for (int i = 0; i < Stone_count; i++) {Mstones[i].angle-= Degree;if (Mstones[i].angle < 0) {mstones[i].angle + = 360;} else if (Mstones[i].angle >=360) {mstones[i].angle-= 360;}} Computecoordinates (); invalidate ();} @Overridepublic void OnDraw (canvas canvas) {//Draw a white ring canvas.drawcircle (Mpointx, Mpointy, Mradius, mpaint);// Draw each menu out for (int index = 0; index < stone_count; index++) {if (!mstones[index].isvisible) Continue;drawincenter ( Canvas, Mstones[index].bitmap, MSTONES[INDEX].X,MSTONES[INDEX].Y);}} /** * Place Center point at CENTER * * @param canvas * @param bitmap * @param left * @param top */private void drawincenter (canvas canvas, B Itmap Bitmap, float left,float top) {Rect DST = new Rect ();d st.left = (int) (Left-menuradius);d st.right = (int) (left + Menuradius);d st.top = (int) (Top-menuradius);d st.bottom = (int) (top + Menuradius); Canvas.setdrawfilter (PFD); Canvas.drawbitmap (bitmap, NULL, DST, mpaint);} private int GetinCircle (int x, int y) {for (int i = 0; i < Stone_count; i++) {Bigstone STONE = mstones[i];int mx = (int) Stone.x;int my = (int) stone.y;if (((X-MX) * (X-MX) + (y-my) * (y-my)) < menuradius* Menuradius) {return i;}} return-1;} public void Setonroundspinviewlistener (Onroundspinviewlistener listener) {This.mlistener = listener;} Class Bigstone {//Picture bitmap bitmap;//angle int angle;//x coordinate float x;//y coordinate float y;//is visible boolean isVisible = True;}}

Layout file Code:

<linearlayout xmlns:android= "http://schemas.android.com/apk/res/android"    xmlns:app= "http// Schemas.android.com/apk/res-auto "    android:layout_width=" match_parent "    android:layout_height=" Match_ Parent "    android:orientation=" vertical "     >    <com.example.roundspinviewdemo.view.roundspinview        android:id= "@+id/rsv_test"        android:layout_width= "match_parent"        android:layout_height= "Match_ Parent "        android:layout_gravity=" center "        android:background=" @drawable/menubkground "        app: menustart= "@drawable/menu1"/></linearlayout>
Note: This must be added:
xmlns:app= "Http://schemas.android.com/apk/res-auto"


You must also include the attr file to set the corresponding self-defined attribute:

<?xml version= "1.0" encoding= "Utf-8"?><resources>    <!--set the corresponding first picture of the rotation menu--    < Declare-styleable name= "Roundspinview" >        <attr name= "Menustart" format= "reference"/>    </ Declare-styleable></resources>


The following is the application of the activity:

public class Mainactivity extends Activity implements Onroundspinviewlistener {private Roundspinview rsv_test;@ overrideprotected void OnCreate (Bundle savedinstancestate) {super.oncreate (savedinstancestate); Setcontentview ( R.layout.activity_main); Initview ();} private void Initview () {rsv_test = (Roundspinview) This.findviewbyid (r.id.rsv_test); rsv_ Test.setonroundspinviewlistener (this);} @Overridepublic void Onsingletapup (int position) {//TODO auto-generated method Stubswitch (position) {case 0:            Toast. Maketext (Mainactivity.this, "place:0", 0). Show (); Break;case 1:toast.maketext (Mainactivity.this, "Place:1", 0). Show ( ); Break;case 2:toast.maketext (Mainactivity.this, "Place:2", 0). Show (); break;default:break;}}}
Attention:
Rsv_test.setonroundspinviewlistener (this);
Assigning your own definition listener that defines a view


So far. Your project will be able to have a rotating transposition menu function that looks very big.

watermark/2/text/ahr0cdovl2jsb2cuy3nkbi5uzxqvc3a2njq1ntk3/font/5a6l5l2t/fontsize/400/fill/i0jbqkfcma==/ Dissolve/70/gravity/center ">

Here is a link to this demo resource: Click to open the link


Copyright notice: This article blog original articles, blogs, without consent, may not be reproduced.

Android Circular rotation menu, and support for mobile conversion feature

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.