当前位置: 编程技术>移动开发
本页文章导读:
▪部分控件使用方法及效果简介 一部分控件使用方法及效果简介
http://filod.net/jqm/docs/lists/docs-lists.html
......
▪ OpenGL学习二 OpenGL学习2
绘制多边形
1.glVertexPointer (int size, int type, int stride, Buffer pointer)
第一个参数表示坐标的维数,可以是2或者3,如果是2,则坐标为(x,y),z轴默认为0;如果是3,则坐标为(x,y,z)
.........
▪ 关于旋旋动画效果 关于旋转动画效果
好久没有写过blog了,5.1还在继续劳动,:( 刚研究完一个旋转动画的,困扰了我很久的一个问题,现在终于解决了,放在这里给大家分享,避免大家走我一样的弯路,:) Main.java: Java.........
[1]部分控件使用方法及效果简介
来源: 互联网 发布时间: 2014-02-18
一部分控件使用方法及效果简介
http://filod.net/jqm/docs/lists/docs-lists.html
[2] OpenGL学习二
来源: 互联网 发布时间: 2014-02-18
OpenGL学习2
绘制多边形
1.glVertexPointer (int size, int type, int stride, Buffer pointer)
第一个参数表示坐标的维数,可以是2或者3,如果是2,则坐标为(x,y),z轴默认为0;如果是3,则坐标为(x,y,z)
第二个参数可以是GL10.GL_FIXED或者GL10.GL_FLOAT,如果是GL10.GL_FIXED,则第四个参数为IntBuffer类 型,如果为GL10.GL_FLOAT,则第四个参数为FloatBuffer类型
第三个参数表示步长
2.glDrawArrays (int mode, int first, int count)
第一个参数有三种类型GL10.GL_TRIANGLES、GL10.GL_TRIANGLE_FAN、GL10.GL_TRIANGLE_STRIP
GL_TRIANGLES:每三个顶之间绘制三角形,之间不连接
GL_TRIANGLE_FAN:以V0V1V2,V0V2V3,V0V3V4,……的形式绘制三角形
GL_TRIANGLE_STRIP:顺序在每三个顶点之间均绘制三角形。这个方法可以保证从相同的方向上所有以三角形均被绘制。以V0V1V2,V1V2V3,V2V3V4……的形式绘制三角形
3.代码
package com.lanhuidong.opengl; import java.nio.FloatBuffer; import java.nio.IntBuffer; import javax.microedition.khronos.egl.EGLConfig; import javax.microedition.khronos.opengles.GL10; import android.opengl.GLSurfaceView.Renderer; import com.lanhuidong.opengl.util.BufferToNativeOrder; public class OpenGLRender implements Renderer { private static int x = 0x10000 / 4; private static float f = 0.5f; private static float[] array = new float[] { -f, 0, 0, 0, (float) (f * Math.sqrt(3) / 2), 0, f, 0, 0 }; private static int[] array2 = new int[] { x, x, 0, x, -x, 0, -x, -x, 0, -x, x, 0 }; private static int[] array3 = new int[] { x, x, 0, -x, x, 0, -2 * x, 0, 0, -x, -x, 0, x, -x, 0, 2 * x, 0, 0 }; private static float[] colorarray = new float[] { 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1 }; /** * 调用此方法绘制当前窗口 */ @Override public void onDrawFrame(GL10 gl) { gl.glClear(GL10.GL_COLOR_BUFFER_BIT | GL10.GL_DEPTH_BUFFER_BIT); gl.glLoadIdentity(); gl.glTranslatef(-0.5f, 0.5f, -1.0f); // 画三角行 gl.glEnableClientState(GL10.GL_VERTEX_ARRAY); FloatBuffer triangleBuffer = BufferToNativeOrder.getNativeOrderFloatBuffer(array); gl.glVertexPointer(3, GL10.GL_FLOAT, 0, triangleBuffer);// gl.glDrawArrays(GL10.GL_TRIANGLES, 0, 3); gl.glLoadIdentity(); gl.glTranslatef(0.5f, 0.5f, -1.0f); // 画矩形 IntBuffer quadrangleBuffer = BufferToNativeOrder.getNativeOrderIntBuffer(array2); gl.glVertexPointer(3, GL10.GL_FIXED, 0, quadrangleBuffer); gl.glDrawArrays(GL10.GL_TRIANGLE_STRIP, 0, 4); gl.glLoadIdentity(); gl.glTranslatef(-0.5f, -0.5f, -1.0f); // 六边形 gl.glVertexPointer(3, GL10.GL_FIXED, 0, BufferToNativeOrder.getNativeOrderIntBuffer(array3)); gl.glDrawArrays(GL10.GL_TRIANGLE_FAN, 0, 6); gl.glDisableClientState(GL10.GL_VERTEX_ARRAY); } /** * 窗口被创建或者窗口大小改变时被调用 */ @Override public void onSurfaceChanged(GL10 gl, int width, int height) { gl.glViewport(0, 0, width, height); float ratio = (float) width / height; gl.glMatrixMode(GL10.GL_PROJECTION); gl.glLoadIdentity(); gl.glFrustumf(-ratio, ratio, -1, 1, 1, 10); } /** * 窗口被创建或者被重新创建时调用,做初始化工作 */ @Override public void onSurfaceCreated(GL10 gl, EGLConfig config) { gl.glClearColor(0, 0, 1.0f, 0.5f); } }
package com.lanhuidong.opengl.util; import java.nio.ByteBuffer; import java.nio.ByteOrder; import java.nio.FloatBuffer; import java.nio.IntBuffer; public class BufferToNativeOrder { public static IntBuffer getNativeOrderIntBuffer(int[] array){ ByteBuffer buffer = ByteBuffer.allocateDirect(array.length * 4); buffer.order(ByteOrder.nativeOrder()); IntBuffer intBuffer = buffer.asIntBuffer(); intBuffer.put(array); intBuffer.position(0); return intBuffer; } public static FloatBuffer getNativeOrderFloatBuffer(float[] array){ ByteBuffer buffer = ByteBuffer.allocateDirect(array.length * 4); buffer.order(ByteOrder.nativeOrder()); FloatBuffer floatBuffer = buffer.asFloatBuffer(); floatBuffer.put(array); floatBuffer.position(0); return floatBuffer; } }
效果:
[3] 关于旋旋动画效果
来源: 互联网 发布时间: 2014-02-18
关于旋转动画效果
好久没有写过blog了,5.1还在继续劳动,:(
刚研究完一个旋转动画的,困扰了我很久的一个问题,现在终于解决了,放在这里给大家分享,避免大家走我一样的弯路,:)
Main.java:
Java代码
public class Main extends Activity {
private com.example.view.RoundSpinView mSelfView;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
mSelfView = (com.example.view.RoundSpinView) findViewById(R.id.mSelfView);
mSelfView.setmPointX(160);
mSelfView.setmPointY(150);
mSelfView.setmRadius(80);
mSelfView.fixBoxPosition();
}
}
public class Main extends Activity {
private com.example.view.RoundSpinView mSelfView;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
mSelfView = (com.example.view.RoundSpinView) findViewById(R.id.mSelfView);
mSelfView.setmPointX(160);
mSelfView.setmPointY(150);
mSelfView.setmRadius(80);
mSelfView.fixBoxPosition();
}
}
自定义View,实现旋转动画:
RoundSpinView.java:
Java代码
public class RoundSpinView extends View {
private Paint mPaint = new Paint();
private static final int STONE_COUNT = 4;
/** 4张图片分布的角度均值 */
private int mDegreeDelta;
private float mDown_x, mDown_y;
private int[] mResourceId = { R.drawable.customer, R.drawable.product,
R.drawable.order, R.drawable.info };
public RoundSpinView(Context context, AttributeSet attrs) {
super(context, attrs);
mPaint.setColor(Color.RED);
mPaint.setStrokeWidth(2);
setupStones();
computeCoordinates();
}
/** 初始化每个旋转图片的坐标位置及图片资源 */
private void setupStones() {
mStones = new BigStone[STONE_COUNT];
BigStone stone;
int angle = 0;
mDegreeDelta = 360 / STONE_COUNT;
for (int index = 0; index < STONE_COUNT; index++) {
stone = new BigStone();
stone.angle = angle;
stone.bitmap = BitmapFactory.decodeResource(getResources(),
mResourceId[index]);
angle += mDegreeDelta;
mStones[index] = stone;
}
}
/** 计算每个旋转图片坐标 */
private void computeCoordinates() {
BigStone stone;
for (int index = 0; index < STONE_COUNT; index++) {
stone = mStones[index];
if (stone.angle >= 360) {
stone.angle -= 360;
}
stone.x = mPointX
+ (float) (mRadius * Math.cos(stone.angle * Math.PI / 180));
stone.y = mPointY
+ (float) (mRadius * Math.sin(stone.angle * Math.PI / 180));
}
}
public RoundSpinView(Context context) {
super(context);
}
private BigStone[] mStones;
/** 旋转的中心点 */
private int mPointX = 0, mPointY = 0;
/** 旋转半径 */
private int mRadius = 0;
private int[] mInts = new int[] { 0, 0, 0, 0 };
/** 标识那个图片应该位于正中间 */
private int mIn;
public int getmRadius() {
return mRadius;
}
public void setmRadius(int mRadius) {
this.mRadius = mRadius;
}
public int getmPointX() {
return mPointX;
}
public void setmPointX(int mPointX) {
this.mPointX = mPointX;
}
public int getmPointY() {
return mPointY;
}
public void setmPointY(int mPointY) {
this.mPointY = mPointY;
}
/** Sort the elements in one array. */
public static void sort(int[] data) {
int len = data.length;
for (int i = 0; i < len - 1; i++) {
int temp = 0;
boolean isExchanged = false;
for (int j = len - 1; j > i; j--) {
if (data[j] < data[j - 1]) {
temp = data[j];
data[j] = data[j - 1];
data[j - 1] = temp;
/** 发生了交换,故将交换标志置为真 */
isExchanged = true;
}
}
/** 本趟排序未发生交换,提前终止算法,提高效率 */
if (!isExchanged) {
return;
}
}
}
public void fixBoxPosition() {
for (int i = 0; i < 4; i++) {
mInts[i] = Math.abs(mStones[i].angle - 90);
}
RoundSpinView.sort(mInts);
for (int i = 0; i < 4; i++) {
if (Math.abs(mStones[i].angle - 90) == mInts[0]) {
mIn = i;
break;
}
}
int mO = 0;
do {
mStones[mIn].angle = mO * 90 + 90;
mIn++;
if (mIn == 4) {
mIn = 0;
}
mO++;
} while (mO < 4);
computeCoordinates();
invalidate();
}
public void catchClickEvent(float mX, float mY) {
System.out.println("mDown_x__________" + mDown_x);
System.out.println("mDown_y__________" + mDown_y);
for (int i = 0; i < mStones.length; i++) {
if (mStones[i].angle == 90) {
mStones[i].bitmap = BitmapFactory.decodeResource(
getResources(), R.drawable.icon);
}
}
invalidate();
}
@Override
public boolean dispatchTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
mDown_x = event.getX();
mDown_y = event.getY();
// catchClickEvent(mDown_x, mDown_y);
break;
case MotionEvent.ACTION_MOVE:
float mDistance_x = event.getX() - mDown_x;
float mDistance_y = event.getY() - mDown_y;
computeAngle(mDistance_x, mDistance_y);
computeCoordinates();
invalidate();
break;
case MotionEvent.ACTION_UP:
fixBoxPosition();
break;
}
return true;
}
public void computeAngle(float mX, float mY) {
int angle = (int) (mX * 0.1);
if (mX < 0) {
for (int index = 0; index < STONE_COUNT; index++) {
mStones[index].angle = mStones[index].angle - angle;
}
} else if (mX > 0) {
for (int index = 0; index < STONE_COUNT; index++) {
mStones[index].angle = mStones[index].angle - angle;
}
}
}
/** 计算一次滑动的角度 */
public int computeCurrentAngle(float x, float y) {
float distance = (float) Math
.sqrt(((x - mPointX) * (x - mPointX) + (y - mPointY)
* (y - mPointY)));
int degree = (int) (Math.acos((x - mPointX) / distance) * 180 / Math.PI);
return degree;
}
@Override
public void onDraw(Canvas canvas) {
canvas.drawPoint(mPointX, mPointY, mPaint);
for (int index = 0; index < STONE_COUNT; index++) {
if (!mStones[index].isVisible)
continue;
drawInCenter(canvas, mStones[index].bitmap, mStones[index].x,
mStones[index].y);
// 不想有红线,就注掉下面这句
// canvas.drawLine(mPointX, mPointY, mStones[index].x,
// mStones[index].y, mPaint);
}
}
/**
* 把中心点放到中心处
*
* @param canvas
* @param bitmap
* @param left
* @param top
*/
void drawInCenter(Canvas canvas, Bitmap bitmap, float left, float top) {
canvas.drawPoint(left, top, mPaint);
canvas.drawBitmap(bitmap, left - bitmap.getWidth() / 2,
top - bitmap.getHeight() / 2, null);
}
class BigStone {
Bitmap bitmap;
int angle;
float x;
float y;
boolean isVisible = true;
}
}
public class RoundSpinView extends View {
private Paint mPaint = new Paint();
private static final int STONE_COUNT = 4;
/** 4张图片分布的角度均值 */
private int mDegreeDelta;
private float mDown_x, mDown_y;
private int[] mResourceId = { R.drawable.customer, R.drawable.product,
R.drawable.order, R.drawable.info };
public RoundSpinView(Context context, AttributeSet attrs) {
super(context, attrs);
mPaint.setColor(Color.RED);
mPaint.setStrokeWidth(2);
setupStones();
computeCoordinates();
}
/** 初始化每个旋转图片的坐标位置及图片资源 */
private void setupStones() {
mStones = new BigStone[STONE_COUNT];
BigStone stone;
int angle = 0;
mDegreeDelta = 360 / STONE_COUNT;
for (int index = 0; index < STONE_COUNT; index++) {
stone = new BigStone();
stone.angle = angle;
stone.bitmap = BitmapFactory.decodeResource(getResources(),
mResourceId[index]);
angle += mDegreeDelta;
mStones[index] = stone;
}
}
/** 计算每个旋转图片坐标 */
private void computeCoordinates() {
BigStone stone;
for (int index = 0; index < STONE_COUNT; index++) {
stone = mStones[index];
if (stone.angle >= 360) {
stone.angle -= 360;
}
stone.x = mPointX
+ (float) (mRadius * Math.cos(stone.angle * Math.PI / 180));
stone.y = mPointY
+ (float) (mRadius * Math.sin(stone.angle * Math.PI / 180));
}
}
public RoundSpinView(Context context) {
super(context);
}
private BigStone[] mStones;
/** 旋转的中心点 */
private int mPointX = 0, mPointY = 0;
/** 旋转半径 */
private int mRadius = 0;
private int[] mInts = new int[] { 0, 0, 0, 0 };
/** 标识那个图片应该位于正中间 */
private int mIn;
public int getmRadius() {
return mRadius;
}
public void setmRadius(int mRadius) {
this.mRadius = mRadius;
}
public int getmPointX() {
return mPointX;
}
public void setmPointX(int mPointX) {
this.mPointX = mPointX;
}
public int getmPointY() {
return mPointY;
}
public void setmPointY(int mPointY) {
this.mPointY = mPointY;
}
/** Sort the elements in one array. */
public static void sort(int[] data) {
int len = data.length;
for (int i = 0; i < len - 1; i++) {
int temp = 0;
boolean isExchanged = false;
for (int j = len - 1; j > i; j--) {
if (data[j] < data[j - 1]) {
temp = data[j];
data[j] = data[j - 1];
data[j - 1] = temp;
/** 发生了交换,故将交换标志置为真 */
isExchanged = true;
}
}
/** 本趟排序未发生交换,提前终止算法,提高效率 */
if (!isExchanged) {
return;
}
}
}
public void fixBoxPosition() {
for (int i = 0; i < 4; i++) {
mInts[i] = Math.abs(mStones[i].angle - 90);
}
RoundSpinView.sort(mInts);
for (int i = 0; i < 4; i++) {
if (Math.abs(mStones[i].angle - 90) == mInts[0]) {
mIn = i;
break;
}
}
int mO = 0;
do {
mStones[mIn].angle = mO * 90 + 90;
mIn++;
if (mIn == 4) {
mIn = 0;
}
mO++;
} while (mO < 4);
computeCoordinates();
invalidate();
}
public void catchClickEvent(float mX, float mY) {
System.out.println("mDown_x__________" + mDown_x);
System.out.println("mDown_y__________" + mDown_y);
for (int i = 0; i < mStones.length; i++) {
if (mStones[i].angle == 90) {
mStones[i].bitmap = BitmapFactory.decodeResource(
getResources(), R.drawable.icon);
}
}
invalidate();
}
@Override
public boolean dispatchTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
mDown_x = event.getX();
mDown_y = event.getY();
// catchClickEvent(mDown_x, mDown_y);
break;
case MotionEvent.ACTION_MOVE:
float mDistance_x = event.getX() - mDown_x;
float mDistance_y = event.getY() - mDown_y;
computeAngle(mDistance_x, mDistance_y);
computeCoordinates();
invalidate();
break;
case MotionEvent.ACTION_UP:
fixBoxPosition();
break;
}
return true;
}
public void computeAngle(float mX, float mY) {
int angle = (int) (mX * 0.1);
if (mX < 0) {
for (int index = 0; index < STONE_COUNT; index++) {
mStones[index].angle = mStones[index].angle - angle;
}
} else if (mX > 0) {
for (int index = 0; index < STONE_COUNT; index++) {
mStones[index].angle = mStones[index].angle - angle;
}
}
}
/** 计算一次滑动的角度 */
public int computeCurrentAngle(float x, float y) {
float distance = (float) Math
.sqrt(((x - mPointX) * (x - mPointX) + (y - mPointY)
* (y - mPointY)));
int degree = (int) (Math.acos((x - mPointX) / distance) * 180 / Math.PI);
return degree;
}
@Override
public void onDraw(Canvas canvas) {
canvas.drawPoint(mPointX, mPointY, mPaint);
for (int index = 0; index < STONE_COUNT; index++) {
if (!mStones[index].isVisible)
continue;
drawInCenter(canvas, mStones[index].bitmap, mStones[index].x,
mStones[index].y);
// 不想有红线,就注掉下面这句
// canvas.drawLine(mPointX, mPointY, mStones[index].x,
// mStones[index].y, mPaint);
}
}
/**
* 把中心点放到中心处
*
* @param canvas
* @param bitmap
* @param left
* @param top
*/
void drawInCenter(Canvas canvas, Bitmap bitmap, float left, float top) {
canvas.drawPoint(left, top, mPaint);
canvas.drawBitmap(bitmap, left - bitmap.getWidth() / 2,
top - bitmap.getHeight() / 2, null);
}
class BigStone {
Bitmap bitmap;
int angle;
float x;
float y;
boolean isVisible = true;
}
}
代码有点长,各位可以建个工程运行看下效果.
main.xml:
Java代码
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent" android:layout_height="fill_parent"
android:background="@drawable/bg">
<TextView android:layout_width="fill_parent"
android:layout_height="wrap_content" android:text="The animation is solved." />
<com.example.view.RoundSpinView
android:layout_width="320dp" android:layout_height="300dp" android:id="@+id/mSelfView"
android:layout_alignParentBottom="true" />
</RelativeLayout>
好久没有写过blog了,5.1还在继续劳动,:(
刚研究完一个旋转动画的,困扰了我很久的一个问题,现在终于解决了,放在这里给大家分享,避免大家走我一样的弯路,:)
Main.java:
Java代码
public class Main extends Activity {
private com.example.view.RoundSpinView mSelfView;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
mSelfView = (com.example.view.RoundSpinView) findViewById(R.id.mSelfView);
mSelfView.setmPointX(160);
mSelfView.setmPointY(150);
mSelfView.setmRadius(80);
mSelfView.fixBoxPosition();
}
}
public class Main extends Activity {
private com.example.view.RoundSpinView mSelfView;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
mSelfView = (com.example.view.RoundSpinView) findViewById(R.id.mSelfView);
mSelfView.setmPointX(160);
mSelfView.setmPointY(150);
mSelfView.setmRadius(80);
mSelfView.fixBoxPosition();
}
}
自定义View,实现旋转动画:
RoundSpinView.java:
Java代码
public class RoundSpinView extends View {
private Paint mPaint = new Paint();
private static final int STONE_COUNT = 4;
/** 4张图片分布的角度均值 */
private int mDegreeDelta;
private float mDown_x, mDown_y;
private int[] mResourceId = { R.drawable.customer, R.drawable.product,
R.drawable.order, R.drawable.info };
public RoundSpinView(Context context, AttributeSet attrs) {
super(context, attrs);
mPaint.setColor(Color.RED);
mPaint.setStrokeWidth(2);
setupStones();
computeCoordinates();
}
/** 初始化每个旋转图片的坐标位置及图片资源 */
private void setupStones() {
mStones = new BigStone[STONE_COUNT];
BigStone stone;
int angle = 0;
mDegreeDelta = 360 / STONE_COUNT;
for (int index = 0; index < STONE_COUNT; index++) {
stone = new BigStone();
stone.angle = angle;
stone.bitmap = BitmapFactory.decodeResource(getResources(),
mResourceId[index]);
angle += mDegreeDelta;
mStones[index] = stone;
}
}
/** 计算每个旋转图片坐标 */
private void computeCoordinates() {
BigStone stone;
for (int index = 0; index < STONE_COUNT; index++) {
stone = mStones[index];
if (stone.angle >= 360) {
stone.angle -= 360;
}
stone.x = mPointX
+ (float) (mRadius * Math.cos(stone.angle * Math.PI / 180));
stone.y = mPointY
+ (float) (mRadius * Math.sin(stone.angle * Math.PI / 180));
}
}
public RoundSpinView(Context context) {
super(context);
}
private BigStone[] mStones;
/** 旋转的中心点 */
private int mPointX = 0, mPointY = 0;
/** 旋转半径 */
private int mRadius = 0;
private int[] mInts = new int[] { 0, 0, 0, 0 };
/** 标识那个图片应该位于正中间 */
private int mIn;
public int getmRadius() {
return mRadius;
}
public void setmRadius(int mRadius) {
this.mRadius = mRadius;
}
public int getmPointX() {
return mPointX;
}
public void setmPointX(int mPointX) {
this.mPointX = mPointX;
}
public int getmPointY() {
return mPointY;
}
public void setmPointY(int mPointY) {
this.mPointY = mPointY;
}
/** Sort the elements in one array. */
public static void sort(int[] data) {
int len = data.length;
for (int i = 0; i < len - 1; i++) {
int temp = 0;
boolean isExchanged = false;
for (int j = len - 1; j > i; j--) {
if (data[j] < data[j - 1]) {
temp = data[j];
data[j] = data[j - 1];
data[j - 1] = temp;
/** 发生了交换,故将交换标志置为真 */
isExchanged = true;
}
}
/** 本趟排序未发生交换,提前终止算法,提高效率 */
if (!isExchanged) {
return;
}
}
}
public void fixBoxPosition() {
for (int i = 0; i < 4; i++) {
mInts[i] = Math.abs(mStones[i].angle - 90);
}
RoundSpinView.sort(mInts);
for (int i = 0; i < 4; i++) {
if (Math.abs(mStones[i].angle - 90) == mInts[0]) {
mIn = i;
break;
}
}
int mO = 0;
do {
mStones[mIn].angle = mO * 90 + 90;
mIn++;
if (mIn == 4) {
mIn = 0;
}
mO++;
} while (mO < 4);
computeCoordinates();
invalidate();
}
public void catchClickEvent(float mX, float mY) {
System.out.println("mDown_x__________" + mDown_x);
System.out.println("mDown_y__________" + mDown_y);
for (int i = 0; i < mStones.length; i++) {
if (mStones[i].angle == 90) {
mStones[i].bitmap = BitmapFactory.decodeResource(
getResources(), R.drawable.icon);
}
}
invalidate();
}
@Override
public boolean dispatchTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
mDown_x = event.getX();
mDown_y = event.getY();
// catchClickEvent(mDown_x, mDown_y);
break;
case MotionEvent.ACTION_MOVE:
float mDistance_x = event.getX() - mDown_x;
float mDistance_y = event.getY() - mDown_y;
computeAngle(mDistance_x, mDistance_y);
computeCoordinates();
invalidate();
break;
case MotionEvent.ACTION_UP:
fixBoxPosition();
break;
}
return true;
}
public void computeAngle(float mX, float mY) {
int angle = (int) (mX * 0.1);
if (mX < 0) {
for (int index = 0; index < STONE_COUNT; index++) {
mStones[index].angle = mStones[index].angle - angle;
}
} else if (mX > 0) {
for (int index = 0; index < STONE_COUNT; index++) {
mStones[index].angle = mStones[index].angle - angle;
}
}
}
/** 计算一次滑动的角度 */
public int computeCurrentAngle(float x, float y) {
float distance = (float) Math
.sqrt(((x - mPointX) * (x - mPointX) + (y - mPointY)
* (y - mPointY)));
int degree = (int) (Math.acos((x - mPointX) / distance) * 180 / Math.PI);
return degree;
}
@Override
public void onDraw(Canvas canvas) {
canvas.drawPoint(mPointX, mPointY, mPaint);
for (int index = 0; index < STONE_COUNT; index++) {
if (!mStones[index].isVisible)
continue;
drawInCenter(canvas, mStones[index].bitmap, mStones[index].x,
mStones[index].y);
// 不想有红线,就注掉下面这句
// canvas.drawLine(mPointX, mPointY, mStones[index].x,
// mStones[index].y, mPaint);
}
}
/**
* 把中心点放到中心处
*
* @param canvas
* @param bitmap
* @param left
* @param top
*/
void drawInCenter(Canvas canvas, Bitmap bitmap, float left, float top) {
canvas.drawPoint(left, top, mPaint);
canvas.drawBitmap(bitmap, left - bitmap.getWidth() / 2,
top - bitmap.getHeight() / 2, null);
}
class BigStone {
Bitmap bitmap;
int angle;
float x;
float y;
boolean isVisible = true;
}
}
public class RoundSpinView extends View {
private Paint mPaint = new Paint();
private static final int STONE_COUNT = 4;
/** 4张图片分布的角度均值 */
private int mDegreeDelta;
private float mDown_x, mDown_y;
private int[] mResourceId = { R.drawable.customer, R.drawable.product,
R.drawable.order, R.drawable.info };
public RoundSpinView(Context context, AttributeSet attrs) {
super(context, attrs);
mPaint.setColor(Color.RED);
mPaint.setStrokeWidth(2);
setupStones();
computeCoordinates();
}
/** 初始化每个旋转图片的坐标位置及图片资源 */
private void setupStones() {
mStones = new BigStone[STONE_COUNT];
BigStone stone;
int angle = 0;
mDegreeDelta = 360 / STONE_COUNT;
for (int index = 0; index < STONE_COUNT; index++) {
stone = new BigStone();
stone.angle = angle;
stone.bitmap = BitmapFactory.decodeResource(getResources(),
mResourceId[index]);
angle += mDegreeDelta;
mStones[index] = stone;
}
}
/** 计算每个旋转图片坐标 */
private void computeCoordinates() {
BigStone stone;
for (int index = 0; index < STONE_COUNT; index++) {
stone = mStones[index];
if (stone.angle >= 360) {
stone.angle -= 360;
}
stone.x = mPointX
+ (float) (mRadius * Math.cos(stone.angle * Math.PI / 180));
stone.y = mPointY
+ (float) (mRadius * Math.sin(stone.angle * Math.PI / 180));
}
}
public RoundSpinView(Context context) {
super(context);
}
private BigStone[] mStones;
/** 旋转的中心点 */
private int mPointX = 0, mPointY = 0;
/** 旋转半径 */
private int mRadius = 0;
private int[] mInts = new int[] { 0, 0, 0, 0 };
/** 标识那个图片应该位于正中间 */
private int mIn;
public int getmRadius() {
return mRadius;
}
public void setmRadius(int mRadius) {
this.mRadius = mRadius;
}
public int getmPointX() {
return mPointX;
}
public void setmPointX(int mPointX) {
this.mPointX = mPointX;
}
public int getmPointY() {
return mPointY;
}
public void setmPointY(int mPointY) {
this.mPointY = mPointY;
}
/** Sort the elements in one array. */
public static void sort(int[] data) {
int len = data.length;
for (int i = 0; i < len - 1; i++) {
int temp = 0;
boolean isExchanged = false;
for (int j = len - 1; j > i; j--) {
if (data[j] < data[j - 1]) {
temp = data[j];
data[j] = data[j - 1];
data[j - 1] = temp;
/** 发生了交换,故将交换标志置为真 */
isExchanged = true;
}
}
/** 本趟排序未发生交换,提前终止算法,提高效率 */
if (!isExchanged) {
return;
}
}
}
public void fixBoxPosition() {
for (int i = 0; i < 4; i++) {
mInts[i] = Math.abs(mStones[i].angle - 90);
}
RoundSpinView.sort(mInts);
for (int i = 0; i < 4; i++) {
if (Math.abs(mStones[i].angle - 90) == mInts[0]) {
mIn = i;
break;
}
}
int mO = 0;
do {
mStones[mIn].angle = mO * 90 + 90;
mIn++;
if (mIn == 4) {
mIn = 0;
}
mO++;
} while (mO < 4);
computeCoordinates();
invalidate();
}
public void catchClickEvent(float mX, float mY) {
System.out.println("mDown_x__________" + mDown_x);
System.out.println("mDown_y__________" + mDown_y);
for (int i = 0; i < mStones.length; i++) {
if (mStones[i].angle == 90) {
mStones[i].bitmap = BitmapFactory.decodeResource(
getResources(), R.drawable.icon);
}
}
invalidate();
}
@Override
public boolean dispatchTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
mDown_x = event.getX();
mDown_y = event.getY();
// catchClickEvent(mDown_x, mDown_y);
break;
case MotionEvent.ACTION_MOVE:
float mDistance_x = event.getX() - mDown_x;
float mDistance_y = event.getY() - mDown_y;
computeAngle(mDistance_x, mDistance_y);
computeCoordinates();
invalidate();
break;
case MotionEvent.ACTION_UP:
fixBoxPosition();
break;
}
return true;
}
public void computeAngle(float mX, float mY) {
int angle = (int) (mX * 0.1);
if (mX < 0) {
for (int index = 0; index < STONE_COUNT; index++) {
mStones[index].angle = mStones[index].angle - angle;
}
} else if (mX > 0) {
for (int index = 0; index < STONE_COUNT; index++) {
mStones[index].angle = mStones[index].angle - angle;
}
}
}
/** 计算一次滑动的角度 */
public int computeCurrentAngle(float x, float y) {
float distance = (float) Math
.sqrt(((x - mPointX) * (x - mPointX) + (y - mPointY)
* (y - mPointY)));
int degree = (int) (Math.acos((x - mPointX) / distance) * 180 / Math.PI);
return degree;
}
@Override
public void onDraw(Canvas canvas) {
canvas.drawPoint(mPointX, mPointY, mPaint);
for (int index = 0; index < STONE_COUNT; index++) {
if (!mStones[index].isVisible)
continue;
drawInCenter(canvas, mStones[index].bitmap, mStones[index].x,
mStones[index].y);
// 不想有红线,就注掉下面这句
// canvas.drawLine(mPointX, mPointY, mStones[index].x,
// mStones[index].y, mPaint);
}
}
/**
* 把中心点放到中心处
*
* @param canvas
* @param bitmap
* @param left
* @param top
*/
void drawInCenter(Canvas canvas, Bitmap bitmap, float left, float top) {
canvas.drawPoint(left, top, mPaint);
canvas.drawBitmap(bitmap, left - bitmap.getWidth() / 2,
top - bitmap.getHeight() / 2, null);
}
class BigStone {
Bitmap bitmap;
int angle;
float x;
float y;
boolean isVisible = true;
}
}
代码有点长,各位可以建个工程运行看下效果.
main.xml:
Java代码
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent" android:layout_height="fill_parent"
android:background="@drawable/bg">
<TextView android:layout_width="fill_parent"
android:layout_height="wrap_content" android:text="The animation is solved." />
<com.example.view.RoundSpinView
android:layout_width="320dp" android:layout_height="300dp" android:id="@+id/mSelfView"
android:layout_alignParentBottom="true" />
</RelativeLayout>
最新技术文章: