1. 程式人生 > >android實現 桌面移動懸浮視窗實現

android實現 桌面移動懸浮視窗實現

現在很多應用都有這樣的功能,比如360等安全衛士,手機管家之內的應用。

效果圖:


一、實現原理及移動思路

呼叫WindowManager,並設定WindowManager.LayoutParams的相關屬性,通過WindowManager的addView方法建立View,這樣產生出來的View根據WindowManager.LayoutParams屬性不同,效果也就不同了。比如建立系統頂級視窗,實現懸浮視窗效果!然後通過覆寫懸浮View中onTouchEvent方法來改變windowMananager.LayoutParams中x和y的值來實現自由移動懸浮視窗。

二、示例程式碼

先看看懸浮View的程式碼把

package com.example.suspend;

import android.content.Context;
import android.util.Log;
import android.view.MotionEvent;
import android.view.WindowManager;
import android.widget.ImageView;

public class MyFloatView extends ImageView {
	private float mTouchStartX;
	private float mTouchStartY;
	private float x;
	private float y;

	private WindowManager wm = (WindowManager) getContext()
			.getApplicationContext().getSystemService("window");
	// 此wmParams變數為獲取的全域性變數,用以儲存懸浮視窗的屬性
	private WindowManager.LayoutParams wmParams = ((MyApplication) getContext()
			.getApplicationContext()).getMywmParams();

	public MyFloatView(Context context) {
		super(context);
	}

	@Override
	public boolean onTouchEvent(MotionEvent event) {
		// TODO Auto-generated method stub
		// 獲取相對螢幕的座標,即以螢幕左上角為原點
		x = event.getRawX();
		y = event.getRawY() - 25; // 25是系統狀態列的高度
		Log.i("currP", "currX" + x + "====currY" + y);

		switch (event.getAction()) {
		case MotionEvent.ACTION_DOWN: // 捕獲手指觸控按下動作
			// 獲取相對View的座標,即以此View左上角為原點
			mTouchStartX = event.getX();
			mTouchStartY = event.getY();
			Log.i("startP", "startX" + mTouchStartX + "====startY"
					+ mTouchStartY);
			break;
		case MotionEvent.ACTION_MOVE://捕獲手指觸控移動動作            
			updateViewPosition();  
			break;
		case MotionEvent.ACTION_UP://捕獲手指觸控離開動作  
			updateViewPosition();  
			mTouchStartX=mTouchStartY=0;  
			break;
		default:
			break;
		}
		return true;
	}

	private void updateViewPosition() {
		//更新浮動視窗位置引數  
		wmParams.x = (int)(x - mTouchStartX);
		wmParams.y = (int)(y - mTouchStartY);
		wm.updateViewLayout(this, wmParams);//重新整理顯示   
	}
}

上面的wmParams變數(即WindowManager.LayoutParams)的儲存採用了extends Application的方式來建立全域性變數,

示例程式碼如下:

package com.example.suspend;

import android.app.Application;
import android.view.WindowManager;

public class MyApplication extends Application {
	private WindowManager.LayoutParams wmParams = new WindowManager.LayoutParams();

	@Override
	public void onCreate() {
		// TODO Auto-generated method stub
		super.onCreate();
	}

	public WindowManager.LayoutParams getMywmParams() {
		return wmParams;

	}

}

再來看一看Activity中的程式碼:
package com.example.suspend;

import android.app.Activity;
import android.graphics.PixelFormat;
import android.os.Bundle;
import android.view.Gravity;
import android.view.WindowManager;
import android.view.WindowManager.LayoutParams;

public class MainActivity extends Activity {
	private WindowManager wm;
	private WindowManager.LayoutParams wmParams;
	private MyFloatView myFV;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		// 建立懸浮視窗
		createFloatView();
	}

	private void createFloatView() {
		myFV = new MyFloatView(getApplicationContext());
		myFV.setImageResource(R.drawable.ic_launcher);
		// 獲取WindowManager
		wm = (WindowManager) getApplicationContext().getSystemService("window");
		// 設定LayoutParams(全域性變數)相關引數
		wmParams = ((MyApplication) getApplication()).getMywmParams();

		wmParams.type = LayoutParams.TYPE_PHONE;// 設定window type
		wmParams.format = PixelFormat.RGBA_8888;// 設定圖片格式,效果為背景透明
		// 設定Window flag
		wmParams.flags = LayoutParams.FLAG_NOT_TOUCH_MODAL
				| LayoutParams.FLAG_NOT_FOCUSABLE;
		/*
		 * 
		 * 下面的flags屬性的效果形同“鎖定”。
		 * 
		 * 懸浮窗不可觸控,不接受任何事件,同時不影響後面的事件響應。
		 * 
		 * wmParams.flags=LayoutParams.FLAG_NOT_TOUCH_MODAL
		 * 
		 * | LayoutParams.FLAG_NOT_FOCUSABLE
		 * 
		 * | LayoutParams.FLAG_NOT_TOUCHABLE;
		 */
		wmParams.gravity = Gravity.LEFT | Gravity.TOP;// 調整懸浮視窗至左上角,便於調整座標
		// 以螢幕左上角為原點,設定x、y初始值
		wmParams.x = 0;
		wmParams.y = 0;
		// 設定懸浮視窗長寬資料
		wmParams.width = 40;
		wmParams.height = 40;
		// 顯示myFloatView影象
		wm.addView(myFV, wmParams);
	}

	@Override
	protected void onDestroy() {
		// TODO Auto-generated method stub
		super.onDestroy();
		// 在程式退出(Activity銷燬)時銷燬懸浮視窗
		wm.removeView(myFV);
	}
}

最後,別忘了在AndroidManifest.xml中新增許可權:
<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />
    <uses-permission android:name="android.permission.SYSTEM_OVERLAY_WINDOW" />

最後,關於Android平臺下的懸浮視窗,有人說很不友好,有人很困惑哪裡會用到。事實上,在一些軟體裡面,懸浮視窗的設計給它們帶來了很大的優勢,比如流量監控,比如歌詞顯示。

相關推薦

android實現 桌面移動懸浮視窗實現

現在很多應用都有這樣的功能,比如360等安全衛士,手機管家之內的應用。 效果圖: 一、實現原理及移動思路呼叫WindowManager,並設定WindowManager.LayoutParams的相關屬性,通過WindowManager的addView方法建立View,這

Android中可自由移動懸浮視窗實現

本文為參加Google暑期大學生部落格分享大賽特別撰寫。 —————————————————————- 大家對懸浮窗概念不會陌生,相信每臺電腦桌面的右上角都會有這麼一個東西,它總是出現在所有頁面的頂端(Top Show)。但在Android平臺中如何實

懸浮佈局的最差實現方式,懸浮頭部實現,viewpager巢狀滑動

給部分程式碼看個大概實現,繼承 linearLayout,自己處理滑動,自己計運算元佈局中第一個佈局為摺疊部分。 其實,用scrollview,將listview以及懸浮部分高度設定為螢幕高度,效果直接,省事,滑動體驗更好。巢狀佈局也沒有滑動衝突 public class Scrollabl

Android仿騰訊手機管家實現桌面懸浮窗小火箭發射的動畫效果

無標題 服務 ice null obj activit 中間 ktr https 功能分析: 1、小火箭遊離在activity之外,不依附於任何activity,不管activity是否開啟,不影響小火箭的代碼邏輯,所以小火箭的代碼邏輯是要寫在服務中; 2、小火箭掛載在手機

android移動懸浮框的實現

    整個Android的視窗機制是基於一個叫做 WindowManager,這個介面可以新增view到螢幕,也可以從螢幕刪除view。它面向的物件一端是螢幕,另一端就是View,直接忽略我們以前的Activity或者Dialog之類的東東。其實我們的Activity或

Android懸浮視窗實現

最近在做一個流量統計的,有個懸浮窗會像樣點。所以稍微研究了下懸浮視窗的實現:效果圖如下:做了個透明背景。。。 懸浮視窗需要在主介面出現,就算APP被關閉了,因此懸浮視窗應該用一個service來控制; 既然懸浮視窗高於其他應用顯示在手機上,那控制懸浮視窗

Android 實現頂層視窗懸浮視窗

1、如圖片1所示,在一個Android應用中,除了標題欄和底層的ActionBar的區域,是我們可以操縱的UI區域,那是不是說我們就不能改變除了這兩個區域的UI呢?答案是否定的。 比如現在我們希望把一個View放在視窗的最低端顯示,通過hierarchyviewer工具我們

android懸浮實現各種功能、快速開發框架、單詞、筆記本、應用市場應用等源碼

jpeg 源碼 新聞 thread 並不是 類型 and 所有 大小 Android精選源碼 懸浮球,實現一鍵靜音,一鍵鎖頻,一鍵截屏等功能 一個Android快速開發框架,MVP架構 Android QQ小紅點的實現源碼 android一款單詞應用完整app源碼

使用electron實現百度網盤懸浮視窗功能的示例程式碼

相關依賴 裡面使用了vuex vue vue-route storeJs storeJs 用來持久化vuex狀態 展示 相關依賴 裡面使用了vuex vue vue-route storeJs storeJs 用來持久化vuex狀態 展示 介紹說明

用JS實現移動視窗

                很簡單的,關鍵的我用紅色標註了:<html><head><title>移動的視窗</title><script language="javascript">var timer;var x = 0;var y = 0;f

Android——自由拖動並顯示文字的懸浮實現

專案中需要實現一個狀態顯示的懸浮框,要求可以設定兩種模式:拖動模式和不可拖動模式。 實現效果圖如下: 實現步驟: 1.首先要設定該懸浮框的基本屬性: /** * 顯示彈出框 * * @param context */ @Su

Android 簡單實現ListView頂部懸浮效果

首先上效果圖,實現如下效果:起初在網上搜了下實現這樣的效果,美團網,大眾點評的“購買框”懸浮效果也是這樣的,不過作者實現比較麻煩,自己想了想就根據ListView提供的一些特性進行了簡單實現。整個主要佈局就是一個ListView,如果listview的上面有內容且高度比較高,可以把它當做listview的he

Android 實現控制元件懸浮效果

隨著移動網際網路的快速發展,它已經和我們的生活息息相關了,在公交地鐵裡面都能看到很多人的人低頭看著自己的手機螢幕,從此“低頭族”一詞就產生了,作為一名移動行業的開發人員,我自己也是一名“低頭族”,上下班時間在公交地鐵上看看新聞來打發下時間,有時候也會看看那些受歡迎

Android桌面懸浮視窗舉例

概述 Android專案開發時,有時候需要開發一些懸浮在桌面上的檢視。比如桌面小精靈,各種音樂播放器的懸浮播放控制欄等等。本文就藉助一個小的demo,用程式碼的方式大概進行介紹。 原理 開發桌面懸浮視窗一般遵循兩個大的原則。 1.最根本的原則是採用W

Android開發中實現桌面小部件App Widget

在Android開發中,有時候我們的App設計的功能比較多的時候,需要根據需要更簡潔的為使用者提供清晰已用的某些功能的時候,用桌面小部件就是一個很好的選擇,即App Widget,下面我們就用Android studio來建立一個簡單的桌面小部件: 選擇New->Widge

Winform視窗去邊框實現可以移動

Windows自帶的邊框很影響我們個性化定製視窗UI的美觀程式。 首選選擇視窗,屬性裡的FormBorderStyle設定為None。 邊框去掉之後 會發現視窗無法最大最小化和移動。 1 在標題欄

android 超炫的懸浮窗設計與實現

現在很多軟體都有懸浮框功能,比如Facebook,體驗效果極佳。 其他不說,直接步入正題看看具體的實現吧。 一、效果圖: 二、實現知識點: 1.     WindowManager addView(View view, LayoutParams params)

Android不依賴Activity的全域性懸浮實現

Android懸浮窗實現  實現基礎 Android懸浮窗實現使用WindowManager ,WindowManager介紹   通過Context.getSystemService(Context.WINDOW_SERVICE)可以獲得 WindowManager物件。

android 使用Scroller實現美團懸浮框,網易左右滑動選單效果

Scroller類其實就是對View的scrollTo()以及ScrollBy()方法封裝以及優化,比如我們熟悉的網易客戶端主介面的側滑選單,如果要實現當滑動超過一半的時候回彈的效果,而不是一下子就回到了最終點,view的scrollTo(),scrollBy()方法是沒

Android關於小米相簿懸浮標題欄、凍結標題欄的實現方式(巢狀型RecycleView)

效果圖如下: 網上完全查詢不到關於凍結標題欄的實現方式,經過幾天的摸索嘗試,終於實現了這種效果;當然在過程中遇到了很多問題拖延了進度,關鍵是沒有摸清思路。 本文的實現方式已經盡了本人最大的能力進行簡化,並解決了快速滑動造成的錯亂問題,具體思路如下: