1.添加权限
<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW"/>
2.自定义悬浮球
package com.example.administrator.ydxcfwpt.View; import android.content.Context; import android.content.SharedPreferences; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; import android.util.AttributeSet; import android.util.TypedValue; import android.view.View; import com.example.administrator.ydxcfwpt.Activity.MainActivity; import com.example.administrator.ydxcfwpt.Bean.Listener; import com.example.administrator.ydxcfwpt.R; import static android.content.Context.MODE_PRIVATE; /** * Created by Administrator on 2018/8/14. */ public class FloatBall extends View implements Listener { public int width = ((int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 40, getResources().getDisplayMetrics())); public int height = ((int)TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 40, getResources().getDisplayMetrics())); //默认显示的文本 private String text= ""; //是否在拖动 private boolean isDrag; private Paint ballPaint; private Paint textPaint; private Bitmap bitmap; public FloatBall(Context context) { super(context); init(); } public FloatBall(Context context, AttributeSet attrs) { super(context, attrs); init(); } public FloatBall(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); init(); } public void init() { ballPaint = new Paint(); ballPaint.setColor(Color.GRAY); ballPaint.setAntiAlias(true); textPaint = new Paint(); textPaint.setTextSize((int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 22, getResources().getDisplayMetrics())); textPaint.setColor(Color.WHITE); textPaint.setAntiAlias(true); textPaint.setFakeBoldText(true); Bitmap src = BitmapFactory.decodeResource(getResources(), R.drawable.meiyoushuju); //将图片裁剪到指定大小 bitmap = Bitmap.createScaledBitmap(src, width, height, true); } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { setMeasuredDimension(width, height); } @Override protected void onDraw(Canvas canvas) { if (!isDrag) { canvas.drawCircle(width / 2, height / 2, width / 2, ballPaint); text=MainActivity.shul; if (text!=null) { float textWidth = textPaint.measureText(MainActivity.shul); Paint.FontMetrics fontMetrics = textPaint.getFontMetrics(); float dy = -(fontMetrics.descent + fontMetrics.ascent) / 2; canvas.drawText(MainActivity.shul, width / 2 - textWidth / 2, height / 2 + dy, textPaint); }else { float textWidth = textPaint.measureText("0"); Paint.FontMetrics fontMetrics = textPaint.getFontMetrics(); float dy = -(fontMetrics.descent + fontMetrics.ascent) / 2; canvas.drawText("0", width / 2 - textWidth / 2, height / 2 + dy, textPaint); } } else { //正在被拖动时则显示指定图片 // canvas.drawBitmap(bitmap, 0, 0, null); } } //设置当前移动状态 public void setDragState(boolean isDrag) { this.isDrag = isDrag; invalidate(); } @Override public void send(String s) { } }
3.Service
package com.example.administrator.ydxcfwpt.Service; import android.accessibilityservice.AccessibilityService; import android.content.Intent; import android.util.Log; import android.view.accessibility.AccessibilityEvent; import org.greenrobot.eventbus.EventBus; import org.greenrobot.eventbus.Subscribe; /** * Created by Administrator on 2018/8/14. */ public class MyAccessibilityService extends AccessibilityService { public static final int BACK = 1; public static final int HOME = 2; private static final String TAG = "ICE"; @Override public void onCreate() { super.onCreate(); EventBus.getDefault().register(this); } @Override public int onStartCommand(Intent intent, int flags, int startId) { Log.d(TAG, "onStartCommand: 点击了"); return super.onStartCommand(intent, flags, startId); } @Override public void onAccessibilityEvent(AccessibilityEvent event) { } @Override public void onInterrupt() { } @Subscribe public void onReceive(Integer action){ switch (action){ case BACK: performGlobalAction(AccessibilityService.GLOBAL_ACTION_BACK); break; case HOME: performGlobalAction(AccessibilityService.GLOBAL_ACTION_HOME); break; } } }
在manifest里注册Service
<service android:name=".Service.MyAccessibilityService" android:permission="android.permission.BIND_ACCESSIBILITY_SERVICE"> <intent-filter> <action android:name="android.accessibilityservice.AccessibilityService"/> </intent-filter> <meta-data android:name="android.accessibilityservice" /> </service>
4. ViewManager
package com.example.administrator.ydxcfwpt.View; import android.content.Context; import android.content.Intent; import android.graphics.PixelFormat; import android.view.Gravity; import android.view.MotionEvent; import android.view.View; import android.view.WindowManager; import android.widget.Toast; import com.example.administrator.ydxcfwpt.Activity.MainActivity; import com.example.administrator.ydxcfwpt.Service.MyAccessibilityService; import org.greenrobot.eventbus.EventBus; /** * Created by Administrator on 2018/8/14. */ public class ViewManager { FloatBall floatBall; WindowManager windowManager; public static ViewManager manager; Context context; private WindowManager.LayoutParams floatBallParams; private ViewManager(Context context) { this.context = context; } public static ViewManager getInstance(Context context) { if (manager == null) { manager = new ViewManager(context); } return manager; } public void showFloatBall() { floatBall = new FloatBall(context); windowManager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE); if (floatBallParams == null) { floatBallParams = new WindowManager.LayoutParams(); floatBallParams.width = floatBall.width; floatBallParams.height = floatBall.height; floatBallParams.gravity = Gravity.TOP | Gravity.LEFT; floatBallParams.type = WindowManager.LayoutParams.TYPE_SYSTEM_ALERT; floatBallParams.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE | WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL; floatBallParams.format = PixelFormat.RGBA_8888; } windowManager.addView(floatBall, floatBallParams); floatBall.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { EventBus.getDefault().post(MyAccessibilityService.BACK); Intent intent = new Intent(context, MainActivity.class); context.startActivity(intent); } }); // floatBall.setOnLongClickListener(new View.OnLongClickListener() { // @Override // public boolean onLongClick(View v) { // EventBus.getDefault().post(MyAccessibilityService.HOME); // Intent intent = new Intent(context, MainActivity.class); // context.startActivity(intent); // // } // }); floatBall.setOnTouchListener(new View.OnTouchListener() { float startX; float startY; float tempX; float tempY; @Override public boolean onTouch(View v, MotionEvent event) { switch (event.getAction()) { case MotionEvent.ACTION_DOWN: startX = event.getRawX(); startY = event.getRawY(); tempX = event.getRawX(); tempY = event.getRawY(); break; case MotionEvent.ACTION_MOVE: float dx = event.getRawX() - startX; float dy = event.getRawY() - startY; //计算偏移量,刷新视图 floatBallParams.x += dx; floatBallParams.y += dy; windowManager.updateViewLayout(floatBall, floatBallParams); startX = event.getRawX(); startY = event.getRawY(); break; case MotionEvent.ACTION_UP: //判断松手时View的横坐标是靠近屏幕哪一侧,将View移动到依靠屏幕 float endX = event.getRawX(); float endY = event.getRawY(); if (endX < getScreenWidth() / 2) { endX = 0; } else { endX = getScreenWidth() - floatBall.width; } floatBallParams.x = (int) endX; windowManager.updateViewLayout(floatBall, floatBallParams); //如果初始落点与松手落点的坐标差值超过6个像素,则拦截该点击事件 //否则继续传递,将事件交给OnClickListener函数处理 if (Math.abs(endX - tempX) > 6 && Math.abs(endY - tempY) > 6) { return true; } break; } return false; } }); } public int getScreenWidth() { return windowManager.getDefaultDisplay().getWidth(); } }
5,在需要的地方启动悬浮球
ViewManager.getInstance(MainActivity.this).showFloatBall();