opr7pus相机悬浮球oppor7丢失怎么找回回

1699人阅读
Android 自定义系列(4)
这个案例就是在桌面上开启一个悬浮窗,悬浮窗里实时显示照相机的内容,可以自由拖动,当在非桌面状态下自动隐藏.如下图所示():
PS:gif都失真了,凑合看,实际中这个窗口是不会闪烁的
我做这个是因为公司项目里在android系统的NavigationBar里显示了行车记录仪,实时录像.我想把类似的思路分享出来.通过这个可以学习TextureView和自定义悬浮窗口的知识.
1、显示一个悬浮窗口
在MainActivity里启动一个服务,在服务里进行悬浮窗的操作
Button btn = (Button) findViewById(R.id.btn);
btn.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
Intent intent = new Intent(MainActivity.this,MyService.class);
startService(intent);
新建一个MyService继承自Service,在onCreate方法里加上如下代码
if (Build.VERSION.SDK_INT &= 23) {
if (Settings.canDrawOverlays(getApplicationContext())) {
showWindow();
Intent intent = new Intent(Settings.ACTION_MANAGE_OVERLAY_PERMISSION);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
getApplicationContext().startActivity(intent);
showWindow();
谷歌对于6.0以上的设备,默认是把悬浮窗功能给禁了,所以需要手动去打开.我用的小米就是这样,需要手动在设置里打开显示悬浮窗的权限.
- Settings.canDrawOverlays(context)方法是判断当前系统是否支持悬浮窗
- Settings.ACTION_MANAGE_OVERLAY_PERMISSION 是跳转到打开悬浮窗的ACTION
以上两个都是在6.0以上的SDK里才有.
对于6.0一下的设备可以直接显示.
看下showWindow()里的代码
private void showWindow() {
myWindow = new MyWindow(getApplicationContext());
mWindowManager = (WindowManager) getSystemService(Service.WINDOW_SERVICE);
Params = new WindowManager.LayoutParams();
Params.x = 0;
Params.y = 0;
Params.type = WindowManager.LayoutParams.TYPE_SYSTEM_ALERT;
Params.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE;
Params.flags = Params.flags | WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH;
Params.flags = Params.flags | WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS;
Params.flags |= WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED;
Params.gravity = Gravity.LEFT | Gravity.TOP;
Params.width =
Params.height = 500;
myWindow.setOnTouchListener(new OnTouchListener() {
public boolean onTouch(View v, MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_MOVE:
Params.x = (int) event.getRawX() - myWindow.getWidth() / 2;
Params.y = (int) event.getRawY() - myWindow.getHeight() / 2;
mWindowManager.updateViewLayout(myWindow, Params);
return false;
首先创建了MyWindow实例,这是一个自定义布局
public class MyWindow extends LinearLayout implements SurfaceTextureListener {
public MyWindow(Context context) {
super(context);
LayoutInflater.from(context).inflate(R.layout.window, this);
this.context =
initView();
加载布局文件进来,这个布局里放了一个Textureview和一个TextView.
创建MyWindow 实例后,获取WindowManager和布局参数LayoutParams.
- 设置LayoutParams的坐标x,y
- 设置LayoutParams的类型为TYPE_SYSTEM_ALERT
- 设置LayoutParams的flags
- 设置LayoutParams的gravity
- 设置LayoutParams的宽和高
这样一个Window的属性设置完了.
最后设置一个触摸监听,让悬浮窗跟随手指移动.
public class MyService extends Service {
myWindow.setOnTouchListener(new OnTouchListener() {
public boolean onTouch(View v, MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_MOVE:
Params.x = (int) event.getRawX() - myWindow.getWidth() / 2;
Params.y = (int) event.getRawY() - myWindow.getHeight() / 2;
mWindowManager.updateViewLayout(myWindow, Params);
return false;
那么什么时候显示和隐藏悬浮窗呢?
我前面说了,会在非桌面界面隐藏该悬浮窗.在桌面界面显示悬浮窗.在这里我通过开启一个定时器每隔一秒发一个消息到Handler,在Handler里判断当前界面是否是桌面.
public class MyService extends Service {
Timer timer = new Timer();
timer.schedule(task, 1000, 1000);
public class MyService extends Service {
TimerTask task = new TimerTask() {
public void run() {
Message message = new Message();
handler.sendMessage(message);
public class MyService extends Service {
private Handler handler = new Handler() {
public void handleMessage(Message msg) {
if (isHome()) {
if (!myWindow.isAttachedToWindow()) {
mWindowManager.addView(myWindow, Params);
if (myWindow.isAttachedToWindow()) {
mWindowManager.removeView(myWindow);
super.handleMessage(msg);
这样就完成了一个悬浮窗的显示和隐藏.进入其他应用时会隐藏该悬浮窗,回到桌面时又会自动显示出来.这里用到了两个方法.
- 获取桌面(Launcher)的包名的方法getHomes
- 判断当前是否是桌面的方法isHome
* 获取桌面(Launcher)的包名
private List&String& getHomes() {
List&String& names = new ArrayList&String&();
PackageManager packageManager = this.getPackageManager();
Intent intent = new Intent(Intent.ACTION_MAIN);
intent.addCategory(Intent.CATEGORY_HOME);
List&ResolveInfo& resolveInfo = packageManager.queryIntentActivities(intent, PackageManager.MATCH_DEFAULT_ONLY);
for (ResolveInfo info : resolveInfo) {
names.add(info.activityInfo.packageName);
* 判断当前是否是桌面
public boolean isHome() {
ActivityManager mActivityManager = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);
List&RunningTaskInfo& rti = mActivityManager.getRunningTasks(1);
List&String& strs = getHomes();
if (strs != null && strs.size() & 0) {
return strs.contains(rti.get(0).topActivity.getPackageName());
return false;
2、在窗口里显示照相机
这里要用到TextureView这个控件,它和SurfaceView是 “兄弟”.
与SurfaceView相比,TextureView并没有创建一个单独的Surface用来绘制,这使得它可以像一般的View一样执行一些变换操作,设置透明度等。另外,Textureview必须在硬件加速开启的窗口中。对应的就是这条属性
Params.flags |= WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED
以下代码是在MyWindow里实现的
private void initView() {
textureView = (TextureView) findViewById(R.id.textureView);
textureView.setSurfaceTextureListener(this);
mWindowManager = (WindowManager) context.getSystemService(Service.WINDOW_SERVICE);
设置监听需要实现SurfaceTextureListener接口,会重载下面4个方法
- onSurfaceTextureAvailable 可用时候执行
- onSurfaceTextureDestroyed 销毁的时候执行
- onSurfaceTextureSizeChanged 尺寸改变时执行
- onSurfaceTextureUpdated 更新的时候执行
这里在onSurfaceTextureAvailable方法执行一下操作.
1.创建Camera实例(我这里用的是旧版本的Camera,已经过时了).
2.通过setPreviewTexture把内容渲染到SurfaceTexture 上
3.通过.setDisplayOrientation设置角度
这里用到了SetDegree(context)方法
private int SetDegree(MyWindow myWindow) {
int rotation = mWindowManager.getDefaultDisplay().getRotation();
int degree = 0;
switch (rotation) {
case Surface.ROTATION_0:
degree = 90;
case Surface.ROTATION_90:
degree = 0;
case Surface.ROTATION_180:
degree = 270;
case Surface.ROTATION_270:
degree = 180;
4.通过startPreviewd开始渲染
public void onSurfaceTextureAvailable(SurfaceTexture surface, int width, int height) {
if (myCamera == null) {
myCamera = Camera.open();
myCamera.setPreviewTexture(surface);
myCamera.setDisplayOrientation(SetDegree(MyWindow.this));
myCamera.startPreview();
} catch (IOException e) {
e.printStackTrace();
最后onSurfaceTextureDestroyed方法里进行停止渲染和释放资源操作.
public boolean onSurfaceTextureDestroyed(SurfaceTexture surface) {
myCamera.stopPreview();
myCamera.release();
myCamera = null;
return false;
最后别忘了加上这三个权限:
android:name="android.permission.SYSTEM_ALERT_WINDOW" /&
android:name="android.permission.GET_TASKS" /&
android:name="android.permission.CAMERA" /&
有兴趣可以自己去丰富内容,比如加拍照的功能等等.最后附上Demo:
密码:362r
参考知识库
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
访问:55063次
排名:千里之外
原创:43篇
评论:94条
微信: Dennis
文章:10篇
阅读:9351
文章:10篇
阅读:11160
(1)(3)(10)(4)(12)(5)(6)(2)孩子被绑在父亲腰间,骑摩托车400多公里跋涉回家。
得知儿子即将与她团聚,老人感动的泣不成声。
声明:本文由入驻搜狐公众平台的作者撰写,除搜狐官方账号外,观点仅代表作者本人,不代表搜狐立场。
  据英国《每日邮报》报道,这是有趣的一幕:一名宇航员将一颗泡腾片丢进一滴掺入了颜料,并且正在空中漂浮的水滴中。
  这是科学家们在国际空间站上进行的一项实验内容,实验的目的是测试美国宇航局开发的一款新型高清摄影装置,其分辨率可以达到普通高清镜头的4倍。这台相机还可以每秒摄制达300帧的画面,从而使其非常适合捕捉快速变动的画面。
  从视频中可以看到一滴处于失重状态下的水滴悬浮在国际空间站内,随后一名宇航员朝其中注射了一些蓝色食用色素,随后又加入一些红色,这样一来这颗悬浮水滴便呈现出一种绿色。随后一名宇航员把一颗泡腾片丢进这颗悬浮的水滴之中。这种药片一般是用来缓解消化不良和胃绞痛之类病痛。
  随着药片在水体中逐渐融化,可以看到大量气泡的产生。另外药片还在水滴里剧烈移动,就像马上要从这个“水球”中跳出来一样,非常有意思。
  一般情况下宇航员们是不会允许液体在国际空间站内漂浮的,这是为了防止空间站内精密的设备受到沾染液体的破坏,为此他们还配备了专门的长吸管,在他们平常喝水喝饮料的时候吸走飘出来的液滴。
  这些画面都被使用新型相机拍摄了下来,美国宇航局计划未来就使用这种相机拍摄空间站上的各种事件,如飞船与空间站的对接和分离,或是空间站内开展的科学实验等等。
  美国宇航局表示该局希望能够向公众呈现更多空间站内部与外部的高清影像。从轨道上,这台相机还将能够提供我们居住的这颗星球有史以来最为清晰的图像。
  这款相机是由美国RED公司制造的,名为“Epic Dragon”,其拍摄模式可以从传统的HDTV模式一直转换为6K高清模式,像素值高达6144 x 3160。
  相比之下,常规的高清电视显示屏分辨率为1920 x 1080像素,而数码相机的这一数字则一般在之间。2015年1月份,由SpaceX公司执行的第五次空间站补给任务期间将这台相机设备送到了国际空间站。
  ―――――――分割线――――――――
  更多秘籍、宝典、美图知识、趣闻,家居发财好风水...
  尽在:zxbzw315(装修保障网)
欢迎举报抄袭、转载、暴力色情及含有欺诈和虚假信息的不良文章。
请先登录再操作
请先登录再操作
微信扫一扫分享至朋友圈
搜狐公众平台官方账号
生活时尚&搭配博主 /生活时尚自媒体 /时尚类书籍作者
搜狐网教育频道官方账号
全球最大华文占星网站-专业研究星座命理及测算服务机构
家居技术宅男!各种家居知识、天文地理,科学技术,奇门遁甲,...
主演:黄晓明/陈乔恩/乔任梁/谢君豪/吕佳容/戚迹
主演:陈晓/陈妍希/张馨予/杨明娜/毛晓彤/孙耀琦
主演:陈键锋/李依晓/张迪/郑亦桐/张明明/何彦霓
主演:尚格?云顿/乔?弗拉尼甘/Bianca Bree
主演:艾斯?库珀/ 查宁?塔图姆/ 乔纳?希尔
baby14岁写真曝光
李冰冰向成龙撒娇争宠
李湘遭闺蜜曝光旧爱
美女模特教老板走秀
曝搬砖男神奇葩择偶观
柳岩被迫成赚钱工具
大屁小P虐心恋
匆匆那年大结局
乔杉遭粉丝骚扰
男闺蜜的尴尬初夜
客服热线:86-10-
客服邮箱:欢迎来到火星做客,可惜我们这儿找不到你需要的应用。
请尝试以下操作:}

我要回帖

更多关于 oppor7手机找回 的文章

更多推荐

版权声明:文章内容来源于网络,版权归原作者所有,如有侵权请点击这里与我们联系,我们将及时删除。

点击添加站长微信