android10 系统定制:增加应用使用数据埋点,应用使用时长统计

需求意在统计应用的使用时长和开始结束时间,最终生成一个文件可以直观看出什么时候进入了哪个应用、什么时候退出,如图:
在这里插入图片描述
每行记录了应用的进入或退出,以逗号分割。分别记录了事件开始时间,应用包名,进入或退出(1或2),应用名称。
根据上面的数据记录可以看出:2024-08-12 09:52:54进入了设置,09:52:57退出设置回到了桌面,09:53:11进入了包名为com.example.intelligentsearch888名称为client1的应用… …
基本思路:当系统窗体焦点发生变化时,获取应用信息,如果进入了新的应用(同一个应用内不做记录,减少不必要的数据)则写入记录文件。
具体实现:
1.添加数据记录帮助类:
在frameworks/base/services/core/java/com/下添加自定义目录custom/buriedpoint,添加工具文件BuriedPointManager.java:

 package com.custom.buriedpoint;import android.content.Context;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageManager;
import android.provider.Settings;
import android.text.TextUtils;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;/*** @author : ljl  * @description:* @date :2024/8/9 下午5:35*/
public class BuriedPointManager {/*** Enter application buried point type*/private static final int TYPE_BURIED_POINT_DATA_ENTER = 1;/*** Exit application buried point type*/private static final int TYPE_BURIED_POINT_DATA_EXIT = 2;/*** Embedded point file path*/private static final String BURIED_POINT_FILE_PATH = "/data/system/UsageStats.txt";/*** Time conversion format** @param createTime* @return*/private String getSimpleDateTime(long createTime) {SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");try {long issueTime = new Date(createTime).getTime();String timeStamp = dateFormat.format(new Date(issueTime));return timeStamp;} catch (NumberFormatException e) {e.printStackTrace();}return "";}/*** Write buried point file** @param appName* @param packageName* @param type*/private void saveBuriedPointFile(String appName, String packageName, int type) {File file = new File(BURIED_POINT_FILE_PATH);if (!file.exists()) {try {file.createNewFile();} catch (IOException e) {e.printStackTrace();}}StringBuilder sb = new StringBuilder();sb.append(getSimpleDateTime(System.currentTimeMillis()));sb.append(",");sb.append(packageName);sb.append(",");sb.append(type);sb.append(",");sb.append(appName);android.util.Log.i("fzs-buried", "save content == " + sb.toString());FileWriter writer = null;try {writer = new FileWriter(BURIED_POINT_FILE_PATH, true);writer.write(sb.toString());writer.write("\n");} catch (IOException e) {e.printStackTrace();} finally {try {if (writer != null) {writer.close();}} catch (IOException e) {e.printStackTrace();}}}public void onNewFocusChange(String newPackageName, String newAppName, boolean isFocus) {saveBuriedPointFile(newPackageName, newAppName,isFocus ? TYPE_BURIED_POINT_DATA_ENTER : TYPE_BURIED_POINT_DATA_EXIT);}
}

代码比较简单,主要定义了日志文件的输出路径,进入或退出应用的常量和写入到文件的方法。
2.埋点数据的写入
系统窗口焦点的变化可以在WindowManagerService中获取到,所以主要在WMS中进行数据写入:

 final class H extends android.os.Handler {private BuriedPointManager buriedPointManager;private String lastPackageName=""; //记录上个应用包名private String lastAppName=""; //记录上个应用名称...public void handleMessage(Message msg) {switch (msg.what) {case REPORT_FOCUS_CHANGE: {if (lastFocus == newFocus) {// Focus is not changing, so nothing to do.return;}if (buriedPointManager == null) {//实例化工具类buriedPointManager = new BuriedPointManager();}PackageManager packageManager = mContext.getPackageManager();if (lastFocus != null){try {ApplicationInfo applicationInfoLastFocus = packageManager.getApplicationInfo(lastFocus.getOwningPackage(),PackageManager.GET_META_DATA);if (applicationInfoLastFocus!=null){//获取lastFocus 对应的包名和应用名称,记录到全局变量lastPackageName = packageManager.getApplicationLabel(applicationInfoLastFocus).toString();lastAppName = lastFocus.getOwningPackage();}} catch (PackageManager.NameNotFoundException e) {e.printStackTrace();}}if (newFocus != null){try {ApplicationInfo applicationInfoNewFocus = packageManager.getApplicationInfo(newFocus.getOwningPackage(),PackageManager.GET_META_DATA);if (applicationInfoNewFocus!=null){String newPackageName = packageManager.getApplicationLabel(applicationInfoNewFocus).toString();if (!TextUtils.equals(newPackageName, lastPackageName)) {//发生了应用切换if (!TextUtils.isEmpty(lastPackageName)) {//记录退出了上个应用buriedPointManager.onNewFocusChange(lastPackageName,lastAppName,false);}if (!TextUtils.isEmpty(newPackageName)) {// 记录进入了新的应用buriedPointManager.onNewFocusChange(newPackageName,newFocus.getOwningPackage(),newFocus.isFocused());}}}} catch (PackageManager.NameNotFoundException e) {e.printStackTrace();}}synchronized (mGlobalLock) {displayContent.mLastFocus = newFocus;if (DEBUG_FOCUS_LIGHT) Slog.i(TAG_WM, "Focus moving from " + lastFocus +" to " + newFocus + " displayId=" + displayContent.getDisplayId());if (newFocus != null && lastFocus != null && !newFocus.isDisplayedLw()) {if (DEBUG_FOCUS_LIGHT) Slog.i(TAG_WM, "Delaying loss of focus...");displayContent.mLosingFocus.add(lastFocus);lastFocus = null;}}...break;}...}...}

系统窗口焦点发生变化会调用Handler的REPORT_FOCUS_CHANGE,里面有lastFocus和newFocus记录了新旧Window的状态。
因为执行到这里lastFocus可能为null只存在newFocus,因此在Handler定义了全局变量lastPackageName和lastAppName来记录上次的应用包名及名称。根据lastFocus获取到上个窗体的应用包名及名称。当新的窗体到来(newFocus!=null)时,判断新的包名与旧的是否相同,如果不同说明进行了应用切换,记录退出了上个应用和进入了新的应用。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/1539551.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

51单片机——直流电机驱动

1、直流电机介绍 直流电机是一种将电能转换为机械能的装置。一般的直流电机有两个电极,当电极正接时,电机正转,当电极反接时,电机反转。 直流电机主要由永磁体(定子)、线圈(转子)和…

YoloV10改进策略:BackBone改进|Next-ViT主干赋能下的革命性改进

摘要 Next-ViT(下一代视觉Transformer)是专为解决传统ViT模型在工业部署中遇到的推理速度慢、计算复杂度高等问题而设计的。它巧妙地结合了高效的Next Convolution Block(NCB)和Next Transformer Block(NTB),通过创新的混合策略(NHS)堆叠这些模块,从而在各种视觉任务…

驱动---动态模块编译

动态模块编译 ctags 用法 创建文件 ------- ctags -R 一定要在顶层目录下 1. ctags –R * 2. vi –t tag (请把tag替换为您欲查找的变量或函数名) 3. Ctrl ] (跳转到要找的目标) 4. Ctrl T (回跳) 5. set tag/p…

计算机的错误计算(九十八)

摘要 探讨 的计算精度问题。 由计算机的错误计算(九十六)知,IEEE 754-2019标准中含有 运算。 另外,似乎没有语言直接编程实现内置了该运算。 例1. 已知 x-0.9999999999321 . 计算 不妨用Java编程计算: import…

【linux】基础IO(上)

1. 共识原理 文件 内容 属性文件分为 打开的文件 没打开的文件打开的文件 : 是进程打开的 ----- 本质是要研究文件和进程的关系没打开的文件 : 没打开的文件储存在磁盘上,由于没打开的文件很多,所以需要分门别类的防止好&…

【Linux实用教程】-03-用户权限命令

点个关注吧 🌴 3.1 Linux 的用户和组 🌾3.1.1 用户的管理 添加用户 useradd 添加一个用户useradd test 添加 test 用户useradd test -d /home/t1 指定用户 home 目录 注意: 用户操作需要使用管理员权限操作,可以先使用…

8583 顺序栈的基本操作

### 思路 1. **初始化栈**:分配初始大小为 STACK_INIT_SIZE 的内存空间,并将 base 和 top 指针指向该空间的起始位置。 2. **入栈**:检查栈是否已满,如果已满则扩展栈的存储空间。将新元素插入栈顶,并更新 top 指针。 …

用pod部署prometheus

用pod部署prometheus node_exporter 节点数据收集器 daemonset ————> 保证每个节点都有一个收集器 prometheus————>监控主程序 grafana————>图形化 altermanager————>告警模块 [rootmaster01 ~]# kubectl create ns monitor-sa namespace/moni…

【天怡AI-注册安全分析报告-无验证方式导致安全隐患】

前言 由于网站注册入口容易被黑客攻击,存在如下安全问题: 1. 暴力破解密码,造成用户信息泄露 2. 短信盗刷的安全问题,影响业务及导致用户投诉 3. 带来经济损失,尤其是后付费客户,风险巨大,造…

使用SpringCloud构建可伸缩的微服务架构

Spring Cloud是一个用于构建分布式系统的开源框架。它基于Spring Boot构建,并提供了一系列的工具和组件,用于简化开发分布式系统的难度。Spring Cloud可以帮助开发人员快速构建可伸缩的微服务架构。 要使用Spring Cloud构建可伸缩的微服务架构&#xff0…

外国药品位置检测系统源码分享

外国药品位置检测检测系统源码分享 [一条龙教学YOLOV8标注好的数据集一键训练_70全套改进创新点发刊_Web前端展示] 1.研究背景与意义 项目参考AAAI Association for the Advancement of Artificial Intelligence 项目来源AACV Association for the Advancement of Computer…

office2016 增强版 KMS

第一步: 用管理员权限登陆:Windows PowerShell (安装最新的 PowerShell,了解新功能和改进!https://aka.ms/PSWindows) 第二步: C:\Windows\system32> cd C:\Program Files\Microsoft Off…

OpenCv(一)

计算机视觉和机器视觉的区别 计算机视觉(Computer Vision)和机器视觉(Machine Vision)是两个密切相关但又有区别的领域。两者在应用、技术和目标上都有所不同。 **计算机视觉:**主要是研究如何使计算机能够理解和处理…

cadence SPB17.4 - allegro - 用板子外形创建整板铺铜

文章目录 cadence SPB17.4 - allegro - 用板子外形创建整板铺铜概述笔记先确定自己板子的 board Geometry/Design_Outline 是否有外形shape为了将软件提示看得更清楚,在每个操作之前,先将命令提示区内容先删了用Z-copy从外形层生成整板的铺铜备注END cad…

[PTA]7-6 整数分解为若干项之和

[PTA]7-6 整数分解为若干项之和 将一个正整数N分解成几个正整数相加,可以有多种分解方法,例如761,752,7511,…。编程求出正整数N的所有整数分解式子。 输入格式: 每个输入包含一个测试用例,即…

Oracle 19c 安装教程学习

Oracle 19c 安装教程学习 (最新) 很久没有用Oracle 我记得用的时候还是 2021年 ,那个时候用的 Oralce 11g 。 今天本人实测安装 。 今天的学习目标就是教大家怎么安装 。直接上图 19c下载地址:https://www.oracle.com/cn/databa…

【高级编程】网络编程 基于 TCPUDP 协议的 Socket 编程

文章目录 IP地址Socket基于 TCP 协议的 Socket 编程基于 UDP 协议的 Socket 编程 IP地址 IP地址(Internet Protocol):唯一标识网络上的每一台计算机 IP地址的组成:32位,由4个8位二进制数组成 11000000.10101000.000…

TMStarget学习——Functional Connectivity

今天基于结构像和功能像数据试验操作TMStarget 的第二个功能模块Functional Connectivity。参考季老师的文档PPT来学习的,整个处理过程蛮长的,可能配置原因一路上报错也比较多,下面还是逐步记录吧,后面采用连更的方式直到跑通后再…

微服务注册中⼼2

5.Nacos配置管理 Nacos除了可以做注册中⼼,同样可以做配置管理来使⽤ 5.1 统⼀配置管理 当微服务部署的实例越来越多,达到数⼗、数百时,逐个修改微服务配置就会让⼈抓狂,⽽且很容易出错。我们需要⼀种统⼀配置管理⽅案&#xf…

怎样把PPT上顽固的图标删了

例如: 解决: 首先打开下载好的PPT模板,然后在视图选项卡里面找到幻灯片母版。 进入幻灯片母版后,找到第一页母版页就会看到LOGO了,这时使用鼠标就可以选中删除啦。