WindowManager 實現懸浮窗 詳解


WindowManager 實現懸浮窗 詳解

一:對於想直接看效果的,可以看看我的demo app.

鏈接:http://sj.qq.com/myapp/detail.htm?apkName=com.inno.backdot

源碼:https://github.com/didikee/BackDot

二: Android 6.0 關於SYSTEM_ALERT_WINDOW權限申明直接報錯

// 設置window type 
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
        mWinParams.type = WindowManager.LayoutParams.TYPE_TOAST;
    } else {
        mWinParams.type = WindowManager.LayoutParams.TYPE_PHONE;
    }
//原因1:type為"TYPE_TOAST"在sdk19之前不接收事件,之后可以.
//原因12:type為"TYPE_PHONE"需要"SYSTEM_ALERT_WINDOW"權限.在sdk19之前不可以直接申明使用,之后不能直接申明使用.

三:用到的技術知識點:

1. OnTouch()的事件處理
2. WindowManager類及其LayoutParams的常見屬性的理解
3. Handler更新UI
4. 定時器(Timer + TimerTask)

1. OnTouch事件處理

這個網上的資料很多,這里說一些注意點:

1.獲取坐標

  • event.getRawX():獲取相對屏幕的坐標X(獲取Y的坐標同理)
  • event.getX():獲取相對於容器的坐標X(獲取Y的坐標同理)

2.返回值

  • return true:表示事件不往下傳遞了
  • return false:表示繼續傳遞事件

2. WindowManager類

獲取方式:

mWmManager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);

WindowManager.LayoutParams類

this.mWinParams = new WindowManager.LayoutParams();
	// 設置圖片格式,效果為背景透明
    mWinParams.format = PixelFormat.RGBA_8888;
    // 設置浮動窗口不可聚焦(實現操作除浮動窗口外的其他可見窗口的操作)
    mWinParams.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE;
    // 參考系為左上
    mWinParams.gravity= Gravity.LEFT | Gravity.TOP;
    mScreenHeight = mWmManager.getDefaultDisplay().getHeight();

    // 以屏幕左上角為原點,設置x、y初始值,相對於gravity
    mWinParams.x = mScreenWidth/4;
    mWinParams.y = mScreenHeight/4;

    // 設置懸浮窗口長寬數據
    mWinParams.width = FrameLayout.LayoutParams.WRAP_CONTENT;
    mWinParams.height = FrameLayout.LayoutParams.WRAP_CONTENT;

其中需要注意的是其Gravity屬性:

注意:Gravity不是說你添加到WindowManager中的View相對屏幕的幾種放置,而是說你可以設置你的 參 考 系 !

例如:mWinParams.gravity= Gravity.LEFT | Gravity.TOP;意思是以屏幕左上角為參考系,那么屏幕左上角的坐標就是(0,0),這是你后面擺放View位置的唯一依據.當你設置為mWinParams.gravity = Gravity.CENTER;那么你的屏幕中心為參考系,坐標(0,0).一般我們用屏幕左上角為參考系.

設置WindowManager中的View的透明度

使用:LayoutParams.alpha屬性(0.0f ~ 1.0f),1.0f不透明,0.0f全透明,源碼如下:

	/**
     * An alpha value to apply to this entire window.
     * An alpha of 1.0 means fully opaque and 0.0 means fully transparent
     */
    public float alpha = 1.0f;

Handler更新UI(略)

定時器

TimerTask timerTask = new TimerTask(){其實就是一個Runnable};
看他的類:
public abstract class TimerTask implements Runnable{...}

Timer mtimer=new Timer();

使用的時候:
mtimer.schedule(timerTask,0,3);//參數1:執行的任務;參數2:延遲0毫米執行;參數3:每隔3毫秒執行一次任務;


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM