这篇文章给大家分享的是有关Android如何实现360度摇杆的内容。小编觉得挺实用的,因此分享给大家做个参考,一起跟随小编过来看看吧。
新建一个类。举例为MySurfaceView
package com.example.blt;
import android.annotation.SuppressLint;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.PixelFormat;
import android.graphics.PorterDuff.Mode;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.SurfaceHolder.Callback;
public class MySurfaceView extends SurfaceView implements Callback {
private SurfaceHolder sfh;
private Canvas canvas;
private Paint paint;
private int coordinate;
// 固定摇杆背景圆形的半径
private int RockerCircleR, SmallRockerCircleR;
// 摇杆的X,Y坐标以及摇杆的半径
private float SmallRockerCircleX, SmallRockerCircleY;
private RudderListener listener = null; // 事件回调接口
public MySurfaceView(Context context) {
super(context);
}
public MySurfaceView(Context context, AttributeSet as) {
super(context, as);
this.setKeepScreenOn(true);
sfh = getHolder();
sfh.addCallback(this);
paint = new Paint();
paint.setColor(Color.GREEN);
paint.setAntiAlias(true);// 抗锯齿
setFocusable(true);
setFocusableInTouchMode(true);
setZOrderOnTop(true);
sfh.setFormat(PixelFormat.TRANSPARENT);// 设置背景透明
}
public void surfaceCreated(SurfaceHolder holder) {
// 获得控件最小值
int little = this.getWidth() < this.getHeight() ? this.getWidth()
: this.getHeight();
// 根据屏幕大小绘制
SmallRockerCircleX = SmallRockerCircleY = coordinate = little / 2;
// 固定摇杆背景圆形的半径
RockerCircleR = (int) (little * 0.35);
// 摇杆的半径
SmallRockerCircleR = (int) (little * 0.15);
draw();
}
/***
* 得到两点之间的弧度
*/
public double getRad(float px1, float py1, float px2, float py2) {
// 得到两点X的距离
float x = px2 - px1;
// 得到两点Y的距离
float y = py1 - py2;
// 算出斜边长
float xie = (float) Math.sqrt(Math.pow(x, 2) + Math.pow(y, 2));
// 得到这个角度的余弦值(通过三角函数中的定理 :邻边/斜边=角度余弦值)
float cosAngle = x / xie;
// 通过反余弦定理获取到其角度的弧度
float rad = (float) Math.acos(cosAngle);
// 注意:当触屏的位置Y坐标<摇杆的Y坐标我们要取反值-0~-180
if (py2 < py1) {
rad = -rad;
}
return rad;
}
@SuppressLint("ClickableViewAccessibility")
@Override
public boolean onTouchEvent(MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_DOWN
|| event.getAction() == MotionEvent.ACTION_MOVE) {
// 当触屏区域不在活动范围内
if (Math.sqrt(Math.pow((coordinate - (int) event.getX()), 2)
+ Math.pow((coordinate - (int) event.getY()), 2)) >= RockerCircleR) {
// 得到摇杆与触屏点所形成的角度
double tempRad = getRad(coordinate, coordinate, event.getX(),
event.getY());
// 保证内部小圆运动的长度限制
getXY(coordinate, coordinate, RockerCircleR, tempRad);
} else {// 如果小球中心点小于活动区域则随着用户触屏点移动即可
SmallRockerCircleX = (int) event.getX();
SmallRockerCircleY = (int) event.getY();
}
} else if (event.getAction() == MotionEvent.ACTION_UP) {
// 当释放按键时摇杆要恢复摇杆的位置为初始位置
SmallRockerCircleX = coordinate;
SmallRockerCircleY = coordinate;
}
draw();
if (listener != null) {
listener.onSteeringWheelChanged((SmallRockerCircleX - coordinate)
/ RockerCircleR, (coordinate - SmallRockerCircleY)
/ RockerCircleR);
}
return true;
}
/**
*
* @param R
* 圆周运动的旋转点
* @param centerX
* 旋转点X
* @param centerY
* 旋转点Y
* @param rad
* 旋转的弧度
*/
public void getXY(float centerX, float centerY, float R, double rad) {
// 获取圆周运动的X坐标
SmallRockerCircleX = (float) (R * Math.cos(rad)) + centerX;
// 获取圆周运动的Y坐标
SmallRockerCircleY = (float) (R * Math.sin(rad)) + centerY;
}
public void draw() {
try {
canvas = sfh.lockCanvas();
// canvas.drawColor(Color.WHITE);
canvas.drawColor(Color.TRANSPARENT, Mode.CLEAR);// 清除屏幕
// 设置透明度
paint.setColor(Color.CYAN);
// 绘制摇杆背景
canvas.drawCircle(coordinate, coordinate, RockerCircleR, paint);
paint.setColor(Color.RED);
// 绘制摇杆
canvas.drawCircle(SmallRockerCircleX, SmallRockerCircleY,
SmallRockerCircleR, paint);
} catch (Exception e) {
// TODO: handle exception
} finally {
try {
if (canvas != null)
sfh.unlockCanvasAndPost(canvas);
} catch (Exception e2) {
}
}
}
public void surfaceChanged(SurfaceHolder holder, int format, int width,
int height) {
}
public void surfaceDestroyed(SurfaceHolder holder) {
}
// 设置回调接口
public void setRudderListener(RudderListener rockerListener) {
listener = rockerListener;
}
// 回调接口
public interface RudderListener {
void onSteeringWheelChanged(float cross, float longitudinal);
}
}
主窗体中
package com.example.blt;
import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;
public class ControlActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_control);
MySurfaceView temp = (MySurfaceView) findViewById(R.id.rudder);
temp.setRudderListener(new MySurfaceView.RudderListener() {
@Override
public void onSteeringWheelChanged(float cross, float longitudinal) {
// TODO Auto-generated method stub
Log.v("change", "c" + cross + "l" + longitudinal);
((TextView) findViewById(R.id.textView2)).setText("c:" + cross
+ "l:" + longitudinal);
}
});
((Button) findViewById(R.id.button2))
.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
}
});
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
// getMenuInflater().inflate(R.menu.control, menu);
return false;
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
}
----------------------主窗体XML
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#ffffff"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin" >
<GridLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_alignParentLeft="true"
android:layout_alignParentTop="true"
android:columnCount="3" >
<com.example.blt.MySurfaceView
android:id="@+id/rudder"
android:layout_width="150dp"
android:layout_height="150dp"
android:layout_column="0"
android:layout_gravity="left|bottom" />
<TextView
android:id="@+id/textView2"
android:layout_column="1"
android:layout_gravity="left|top"
android:text="TextView" />
<TableLayout
android:layout_column="2"
android:layout_gravity="bottom"
android:layout_row="0" >
<TableRow
android:id="@+id/tableRow1"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >
<TextView
android:id="@+id/axis_x"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="TextView" />
</TableRow>
<TableRow
android:id="@+id/tableRow2"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >
<Button
android:id="@+id/button2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="自动" />
<Button
android:id="@+id/button3"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Button" />
</TableRow>
<TableRow
android:id="@+id/tableRow3"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >
<Button
android:id="@+id/button1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Button" />
<Button
android:id="@+id/button4"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Button" />
</TableRow>
<TableRow
android:id="@+id/tableRow4"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >
<Button
android:id="@+id/button5"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Button" />
<Button
android:id="@+id/button6"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Button" />
</TableRow>
</TableLayout>
</GridLayout>
</RelativeLayout>
感谢各位的阅读!关于“Android如何实现360度摇杆”这篇文章就分享到这里了,希望以上内容可以对大家有一定的帮助,让大家可以学到更多知识,如果觉得文章不错,可以把它分享出去让更多的人看到吧!