Android截屏功能是一个常用的功能,可以方便的用来分享或者发送给好友,本文介绍了如何实现应用内截屏监控功能,当发现用户在我们的应用程序内进行了截屏操作时,进行对图片的二次操作,例如添加二维码,公司标志等一系列*。
项目地址
android系统并没有提供截屏通知相关的API,需要我们自己利用系统能提供的相关特性变通实现.Android系统有一个媒体数据库,每拍一张照片,或使用系统截屏截取一张图片,都会把这张图片的详细信息加入到这个媒体数据库,并发出内容改变通知,我们可以利用内容观察者(ContentObserver)监听媒体数据库的变化,当数据库有变化时,获取最后插入的一条图片数据,如果该图片符合特定的规则,则认为被截屏了。
当ContentObserver监听到媒体数据库的数据改变,在有数据改变时获取最后插入数据库的一条图片数据,如果符合以下规则,则认为截屏了:
-
<李>时间判断,图片的生成时间在开始监听之后,并与当前时间相隔10秒内:开始监听后生成的图片才有意义,相隔10秒内说明是刚刚生成的李>
<李>尺寸判断,图片的尺寸没有超过屏幕的尺寸:图片尺寸超过屏幕尺寸,不可能是截屏图片李>
<李>路径判断,图片路径符合包含特定的关键词:这一点是关键,截屏图片的保存路径通常包含“截图”李>
这些判断是为了增加截屏检测结果的可靠性,防止误报,防止遗漏。其中截屏图片的路径正常Android系统保存的路径格式,例如我的是:“外部存储器/存储/模拟/0/图片/截图/screenshot_2017 - 08 - 03 - 15 - 42 - 58. - png”,但Android系统碎片化严重,加上其他第三方截屏软件等,所以路径关键字除了检查是否包含“截图”外,还可以适当增加其他关键字,详见最后的监听器完整代码。这种监听截屏的方法也不是100%准确,例如某些被根的机器使用第三方截屏应用自定义保存路径,还比如通过亚行命令在电脑上获取手机屏幕快照均不能监听的到,但这也是目前可行性最高的方法,对于绝大多数用户都比较靠谱。
<>强监听截屏强>
公开课ScreenShotListenManager { 私有静态最终字符串标签=癝creenShotListenManager”;/* * *读取媒体数据库时需要读取的列 */私有静态最终String [] MEDIA_PROJECTIONS={ MediaStore.Images.ImageColumns.DATA, MediaStore.Images.ImageColumns.DATE_TAKEN, };/* * *读取媒体数据库时需要读取的列,其中宽度和高度字段在API 16以后才有 */私有静态最终String [] MEDIA_PROJECTIONS_API_16={ MediaStore.Images.ImageColumns.DATA, MediaStore.Images.ImageColumns.DATE_TAKEN, MediaStore.Images.ImageColumns.WIDTH, MediaStore.Images.ImageColumns.HEIGHT, };/* * *截屏依据中的路径判断关键字 */私有静态最终={String[]关键词 “截屏”、“screen_shot”、“截图”、“截屏”, “screencapture”、“screen_capture”、“抓屏”、“屏幕截图”, “screencap”、“screen_cap”、“屏幕图”、“屏幕帽” }; 私有静态点sScreenRealSize;/* * *已回调过的路径 */私人最终静态ListsHasCallbackPaths=new ArrayList (); 私人上下文mContext; 私人> @Override 保护无效onResume () { super.onResume (); startScreenShotListen (); } @Override 保护无效onPause () { super.onPause (); stopScreenShotListen (); }/* * *监听 */私人空间startScreenShotListen () { 如果(!isHasScreenShotListener,,screenShotListenManager !=null) { screenShotListenManager。setListener(新ScreenShotListenManager.OnScreenShotListener () { @Override 公共空间onShot(字符串imagePath) { 路径=imagePath; 日志。d(“味精”、“BaseActivity→onShot:“+”获得截图路径:”+ imagePath); MyDialog ksDialog=MyDialog.getInstance () .init (BaseActivity。这一点,R.layout.dialog_layout) .setCancelButton(“取消”,零) .setPositiveButton(“查”看,新MyDialog.OnClickListener () { @Override 公共空间OnClick(查看视图){ 位图screenShotBitmap=screenShotListenManager。createScreenShotBitmap (mContext、路径);//此处只要分享这个合成的位图图片就行了//为了演示,故写下面代码 screenShotIv.setImageBitmap (screenShotBitmap); } }); screenShotIv=(ImageView) ksDialog.getView (R.id.iv); progressBar=(progressBar) ksDialog.getView (R.id.avLoad); mHandler。postDelayed(新Runnable () { @Override 公共空间run () { progressBar.setVisibility (View.GONE); Glide.with (mContext) .load(路径).into (screenShotIv); } },1500); } }); screenShotListenManager.startListen (); isHasScreenShotListener=true; } }/* * *停止监听 */私人空间stopScreenShotListen () { 如果(isHasScreenShotListener,,screenShotListenManager !=null) { screenShotListenManager.stopListen (); isHasScreenShotListener=false; } } Android应用程序内监听截图加二维码功能代码