在日常开发中,我们可能需要实现全局悬浮窗的需求:
支持拖动,提供自动贴边等动画
内部自动进行权限申请操作
可自由指定要显示悬浮窗的界面
应用退到后台时,悬浮窗会自动隐藏
除小米外,4.4~7.0 无需权限申请
位置及宽高可设置百分比值,轻松适配各分辨率
支持权限申请结果、位置等状态监听
链式调用,简洁清爽
<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />
allprojects {
repositories {
...
maven { url 'https://jitpack.io' }
}
}
dependencies {
implementation 'com.github.yhaolpz:FloatWindow:1.0.9'
}
FloatWindow
.with(getApplicationContext())
.setView(view)
.setWidth(100) //设置控件宽高
.setHeight(Screen.width,0.2f)
.setX(100) //设置控件初始位置
.setY(Screen.height,0.3f)
.setDesktopShow(true) //桌面显示
.setViewStateListener(mViewStateListener) //监听悬浮控件状态改变
.setPermissionListener(mPermissionListener) //监听权限申请结果
.build();
宽高及位置可设像素值或屏幕宽/高百分比,默认宽高为 wrap_content;默认位置为屏幕左上角,x、y 为偏移量。
.setFilter(true, A_Activity.class, C_Activity.class)
此方法表示 A_Activity、C_Activity 显示悬浮窗,其他界面隐藏。
.setFilter(false, B_Activity.class)
此方法表示 B_Activity 隐藏悬浮窗,其他界面显示。
注意:setFilter 方法参数可以识别该 Activity 的子类
.setMoveType(MoveType.slide)
.setMoveStyle(500, new AccelerateInterpolator()) //贴边动画时长为500ms,加速插值器
共提供 4 种 MoveType :
MoveType.slide : 可拖动,释放后自动贴边 (默认)
MoveType.back : 可拖动,释放后自动回到原位置
MoveType.active : 可拖动
MoveType.inactive : 不可拖动
//手动控制
FloatWindow.get().show();
FloatWindow.get().hide();
//修改显示位置
FloatWindow.get().updateX(100);
FloatWindow.get().updateY(100);
//销毁
FloatWindow.destroy();
public class MyAPP extends Application {
private static final String TAG = "FloatWindow";
@Override
public void onCreate() {
super.onCreate();
ImageView imageView = new ImageView(getApplicationContext());
imageView.setImageResource(R.drawable.icon);
FloatWindow
.with(getApplicationContext())
.setView(imageView)
.setWidth(Screen.width, 0.2f) //设置悬浮控件宽高
.setHeight(Screen.width, 0.2f)
.setX(Screen.width, 0.8f)
.setY(Screen.height, 0.3f)
.setMoveType(MoveType.slide,100,-100)
.setMoveStyle(500, new BounceInterpolator())
.setFilter(true, A_Activity.class, C_Activity.class)
.setViewStateListener(mViewStateListener)
.setPermissionListener(mPermissionListener)
.setDesktopShow(true)
.build();
imageView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Toast.makeText(BaseApplication.this, "onClick", Toast.LENGTH_SHORT).show();
}
});
}
private PermissionListener mPermissionListener = new PermissionListener() {
@Override
public void onSuccess() {
Log.d(TAG, "onSuccess");
}
@Override
public void onFail() {
Log.d(TAG, "onFail");
}
};
private ViewStateListener mViewStateListener = new ViewStateListener() {
@Override
public void onPositionUpdate(int x, int y) {
Log.d(TAG, "onPositionUpdate: x=" + x + " y=" + y);
}
@Override
public void onShow() {
Log.d(TAG, "onShow");
}
@Override
public void onHide() {
Log.d(TAG, "onHide");
}
@Override
public void onDismiss() {
Log.d(TAG, "onDismiss");
}
@Override
public void onMoveAnimStart() {
Log.d(TAG, "onMoveAnimStart");
}
@Override
public void onMoveAnimEnd() {
Log.d(TAG, "onMoveAnimEnd");
}
@Override
public void onBackToDesktop() {
Log.d(TAG, "onBackToDesktop");
}
};
}