Android 为你的应用添加悬浮窗功能不知道有没有童鞋用过QQ的Android版本中的一个高清版本,当你退出QQ的时
Android 为你的应用添加悬浮窗功能
不知道有没有童鞋用过QQ的Android版本中的一个高清版本,当你退出QQ的时候,会在你的屏幕上出现一个QQ图标的悬浮窗,就和PC上的迅雷的悬浮窗口一样,在所有应用的最上层,本来这个功能感觉还是挺好的,结果TX就给流氓了下,居然没有做隐藏掉这个悬浮窗的功能。
今天就来为大家简单介绍下这个悬浮窗的实现方法吧,不过记住至少还是给用户做一个隐藏掉这个悬浮窗的功能吧!其实实现原理还是挺简单的,就是利用WindowManager将你的图标View添加到窗口中,不知道大家知道WindowManager.LayoutParams中有一个type属性不,这里玄机挺大的,找了好久,终于给我试出来有一个TYPE_PHONE可以来实现这个功能的,该类型提供与用户交互,置于所有应用程序上方,但是在状态栏后面。至于其他的类型,大家还是去找API或者GG吧。
先看下效果图吧:
红框圈中得图标可以任意拖动哦,你可以根据自己的实际需要给图标添加功能。
核心代码如下:
package com.iaiai.activity;import android.app.Service;import android.content.Intent;import android.graphics.PixelFormat;import android.os.IBinder;import android.view.Gravity;import android.view.LayoutInflater;import android.view.MotionEvent;import android.view.View;import android.view.View.OnTouchListener;import android.view.WindowManager;/** * * <p> * Title: TopFloatService.java * </p> * <p> * E-Mail: 176291935@qq.com * </p> * <p> * QQ: 176291935 * </p> * <p> * Http: iaiai.iteye.com * </p> * <p> * Create time: 2012-2-10 上午9:31:54 * </p> * * @author 丸子 * @version 0.0.1 */public class TopFloatService extends Service {WindowManager wm = null;WindowManager.LayoutParams wmParams = null;View view;private float mTouchStartX;private float mTouchStartY;private float x;private float y;@Overridepublic void onCreate() {super.onCreate();view = LayoutInflater.from(this).inflate(R.layout.floating, null);createView();}private void createView() {// 获取WindowManagerwm = (WindowManager) getApplicationContext().getSystemService("window");// 设置LayoutParams(全局变量)相关参数wmParams = ((MyApplication) getApplication()).getMywmParams();wmParams.type = WindowManager.LayoutParams.TYPE_PHONE;// 该类型提供与用户交互,置于所有应用程序上方,但是在状态栏后面wmParams.flags |= WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE;// 不接受任何按键事件wmParams.gravity = Gravity.LEFT | Gravity.TOP; // 调整悬浮窗口至左上角// 以屏幕左上角为原点,设置x、y初始值wmParams.x = 0;wmParams.y = 0;// 设置悬浮窗口长宽数据wmParams.width = WindowManager.LayoutParams.WRAP_CONTENT;wmParams.height = WindowManager.LayoutParams.WRAP_CONTENT;wmParams.format = PixelFormat.RGBA_8888;wm.addView(view, wmParams);view.setOnTouchListener(new OnTouchListener() {public boolean onTouch(View v, MotionEvent event) {// 获取相对屏幕的坐标,即以屏幕左上角为原点x = event.getRawX();// 25是系统状态栏的高度,也可以通过方法得到准确的值,自己微调就是了y = event.getRawY()-25 ; switch (event.getAction()) {case MotionEvent.ACTION_DOWN:// 获取相对View的坐标,即以此View左上角为原点mTouchStartX = event.getX();mTouchStartY = event.getY()+view.getHeight()/2;break;case MotionEvent.ACTION_MOVE:updateViewPosition();break;case MotionEvent.ACTION_UP:updateViewPosition();mTouchStartX = mTouchStartY = 0;break;}return true;}});}private void updateViewPosition() {// 更新浮动窗口位置参数wmParams.x = (int) (x - mTouchStartX);wmParams.y = (int) (y - mTouchStartY);wm.updateViewLayout(view, wmParams);}@Overridepublic IBinder onBind(Intent intent) {return null;}}1 楼 xinyuetonghua 2012-04-28 请教个问题,怎么很好是区分是view的点击事件还是view的setOnTouchListener事件
