news 2026/7/5 12:41:39

Android 14.0 framework监听某个app启动获取应用使用时长功能实现

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Android 14.0 framework监听某个app启动获取应用使用时长功能实现

1.前言

在进行14.0的系统定制开发中,在某些app的定制过程中,需要知道某个app的启动时候然后获取 应用使用时长的功能,所以就需要监听某个app的启动后就获取使用时长,需要在Activity的生命周期中来实现监听功能

2.frameworks监听某个app启动获取应用使用时长功能实现的核心类

frameworks\base\core\java\android\app\Activity.java

3.frameworks监听某个app启动获取应用使用时长功能实现的核心功能分析和实现

Android Activity生命周期是Android开发中非常重要的概念,它描述了一个Activity从创建到销毁的整个过程。Activity生命周期由一系列回调方法组成,开发者可以在这些方法中执行相应的操作。

1. Activity生命周期的状态
Activity在其生命周期中会经历以下几种状态:

运行(Running):Activity位于屏幕前台,用户可以与它交互。

暂停(Paused):Activity部分被遮挡,不再处于前台,但仍然可见(例如,有一个透明或非全屏的Activity覆盖在上面)。此时Activity不再接收用户输入。

停止(Stopped):Activity完全被遮挡,不可见。它仍然保留所有状态和成员信息,但可能被系统销毁。

销毁(Destroyed):Activity被系统销毁或从内存中移除。

2. 生命周期回调方法
Activity类提供了以下核心生命周期方法:

onCreate()
调用时机:Activity首次创建时调用。

作用:进行一次性初始化,如加载布局、绑定数据等。

后续状态:onStart()

onStart()
调用时机:Activity即将变为可见时调用(进入前台)。

作用:准备Activity进入前台,但尚未与用户交互。

后续状态:onResume()(如果Activity进入前台)或onStop()(如果Activity被隐藏)

onResume()
调用时机:Activity开始与用户交互之前调用。此时Activity位于Activity栈的顶部。

作用:启动动画、初始化相机等需要与用户交互的组件。

后续状态:onPause()

onPause()
调用时机:当Activity即将进入暂停状态时调用(例如,有另一个非全屏Activity覆盖)。

作用:提交未保存的更改、释放系统资源、停止动画等。注意,此方法应快速执行,否则会影响新Activity的显示。

后续状态:onResume()(如果Activity重新回到前台)或onStop()(如果Activity完全不可见)

onStop()
调用时机:Activity完全不可见时调用。

作用:释放不再需要的资源,保存数据。

后续状态:onRestart()(如果Activity重新显示)或onDestroy()(如果Activity被销毁)

onRestart()
调用时机:Activity从停止状态重新显示时调用,在onStart()之前。

作用:重新初始化在onStop()中释放的资源。

后续状态:onStart()

onDestroy()
调用时机:Activity被销毁之前调用。这可能是因为Activity结束(调用finish())或系统为节省空间而临时销毁该Activity。

作用:释放所有资源,包括线程、数据库连接等。

3. 生命周期图示
为了更好地理解,以下是一个经典的生命周期图示(描述性):

启动Activity:onCreate() -> onStart() -> onResume()

另一个Activity覆盖当前Activity(非全屏):onPause() -> (如果完全覆盖)onStop()

返回原Activity:onRestart() -> onStart() -> onResume()

回退或结束当前Activity:onPause() -> onStop() -> onDestroy()

注意:当系统资源不足时,可能会杀死后台的Activity。此时,当用户返回时,Activity会重新创建。

4. 保存和恢复状态
由于Activity可能被系统销毁,因此需要保存状态以便恢复。

onSaveInstanceState()
在Activity可能被销毁之前调用(例如,屏幕旋转、系统资源回收)。可以将临时数据保存到Bundle中。

onRestoreInstanceState()
在onStart()之后、onResume()之前调用,用于恢复保存的状态。也可以选择在onCreate()中恢复。

5. 实际开发中的注意事项
避免在onPause()和onStop()中执行耗时操作,否则会影响新Activity的响应。

在onResume()中重新获取资源(如相机),在onPause()中释放。

使用onSaveInstanceState()保存临时UI状态,使用onCreate()或onRestoreInstanceState()恢复。

了解配置变更(如屏幕旋转)会销毁并重建Activity,因此需要妥善处理状态保存。

3.1 Activity.java中相关源码分析 ‌

Activity在‌Android应用程序中扮演着核心角色,主要负责展示用户界面、处理用户输入、管理生命周期以及与其他组件进行交互。 展示用户界面: Activity是用户可以看到的一个屏幕,它负责显示应用程序的用户界面,包括布局、按钮、文本框等元素。 用户可以通过与这些界面的交互来完成各种操作。

@MainThread @CallSuper protected void onCreate(@Nullable Bundle savedInstanceState) { if (DEBUG_LIFECYCLE) Slog.v(TAG, "onCreate " + this + ": " + savedInstanceState); if (mLastNonConfigurationInstances != null) { mFragments.restoreLoaderNonConfig(mLastNonConfigurationInstances.loaders); } if (mActivityInfo.parentActivityName != null) { if (mActionBar == null) { mEnableDefaultActionBarUp = true; } else { mActionBar.setDefaultDisplayHomeAsUpEnabled(true); } } .... mRestoredFromBundle = savedInstanceState != null; mCalled = true; } public void onCreate(@Nullable Bundle savedInstanceState, @Nullable PersistableBundle persistentState) { onCreate(savedInstanceState); } @CallSuper protected void onResume() { if (DEBUG_LIFECYCLE) Slog.v(TAG, "onResume " + this); dispatchActivityResumed(); mActivityTransitionState.onResume(this); enableAutofillCompatibilityIfNeeded(); if (mAutoFillResetNeeded) { if (!mAutoFillIgnoreFirstResumePause) { View focus = getCurrentFocus(); if (focus != null && focus.canNotifyAutofillEnterExitEvent()) { // TODO(b/148815880): Bring up keyboard if resumed from inline authentication. // TODO: in Activity killed/recreated case, i.e. SessionLifecycleTest# // testDatasetVisibleWhileAutofilledAppIsLifecycled: the View's initial // window visibility after recreation is INVISIBLE in onResume() and next frame // ViewRootImpl.performTraversals() changes window visibility to VISIBLE. // So we cannot call View.notifyEnterOrExited() which will do nothing // when View.isVisibleToUser() is false. getAutofillManager().notifyViewEntered(focus); } } } notifyContentCaptureManagerIfNeeded(CONTENT_CAPTURE_RESUME); mCalled = true; } //add core start public boolean isAppRunningState(@Nullable String appPackageName){ ActivityManager activities = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE); List<ActivityManager.RunningAppProcessInfo> appProcesses = activities.getRunningAppProcesses(); if (appProcesses == null) { return false; } for (ActivityManager.RunningAppProcessInfo appProcess : appProcesses) { Log.e("Activity_Main","appProcess.processName= "+appProcess.processName); if (appProcess.processName.equals(appPackageName)) { return true; } } return false; } private String getappusedtimes(@Nullable String appPackageName){ String usedtimes = ""; UsageStatsManager usageStatsManager = (UsageStatsManager) getSystemService(Context.USAGE_STATS_SERVICE); try { Calendar calendar = Calendar.getInstance(); calendar.set(Calendar.HOUR_OF_DAY, 0); calendar.set(Calendar.MINUTE, 0); calendar.set(Calendar.SECOND, 0); List<UsageStats> stats =usageStatsManager.queryUsageStats(UsageStatsManager.INTERVAL_DAILY, calendar.getTimeInMillis(), System.currentTimeMillis()); for(int i=0;i<stats.size();i++){ final android.app.usage.UsageStats pkgStats = stats.get(i); String package_name=pkgStats.getPackageName(); long time_begin= pkgStats.getFirstTimeStamp(); long time_end=pkgStats.getLastTimeStamp(); long time_used=pkgStats.getLastTimeUsed(); long time_totals=pkgStats.getTotalTimeInForeground(); if(time_total>0&&package_name.equals(appPackageName)) { Log.e("AppInfoDashboardFragment","package_name:"+package_name+"--time_begin:"+time_begin+"--time_used:"+time_used+"--time_total:"+time_total); return time_totals/1000+"s"; } } } catch (Exception e) { e.printStackTrace(); } return usedtimes; } //add core end @CallSuper protected void onPostResume() { //add core start boolean isRunning = isAppRunningState("com.tel.troops"); android.util.Log.e("Activity_Main","com.tel.troops is run="+isRunning); if(isRunning){ String run_time = getappusedtimes("com.tel.troops"); android.util.Log.e("Activity_Main","com.tel.troops is run_time="+ run_time); } //add core end final Window win = getWindow(); if (win != null) win.makeActive(); if (mActionBar != null) mActionBar.setShowHideAnimationEnabled(true); mCalled = true; }

在上述的Activity.java的相关源码中,在onCreate(@Nullable Bundle savedInstanceState) 中 的相关源码中,主要是初始化布局等功能,而在onPostResume()表示页面已经加载完毕后 调用的相关方法,所以就可以在onPostResume()中,来调用 isAppRunningState("com.tel.troops") 来利用ActivityManager.RunningAppProcessInfo当前置顶运行的进行是否是需要监听的app包名 如果返回true就可以监听到app已经启动了,这时候就可以调用getappusedtimes("com.tel.troops"); 来获取需要监听app的运行时间了,这样就可以监听app启动的时候,来获取这个app的运行时间了 从而来实现了相关的功能

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/7/3 12:03:10

C++编程实践——多线程变量共享问题展开分析

一、问题现象描述 在C编程的技术点中&#xff0c;多线&#xff08;进&#xff09;程的编程是一个非常让人上头的内容。这种情况其实还可以拓展到一些抽象的场景&#xff0c;比如信号、消息和异步等情况。它们看上去和多线程关系不大&#xff0c;但其实内部和多线程都有着密不可…

作者头像 李华
网站建设 2026/7/4 21:11:58

【Android FrameWork】第三十六天:随机数EntropyMixer

Android EntropyService 在 Android 系统中&#xff0c;EntropyService&#xff08;后更名为 EntropyMixer&#xff09; 是保障随机数安全性的核心服务之一。 它通过维护内核熵池&#xff08;Entropy Pool&#xff09;&#xff0c;解决了系统启动初期随机数可预测的问题&#x…

作者头像 李华
网站建设 2026/7/3 21:29:29

介观交通流仿真软件:VISSIM (介观模式)_(16).高级仿真技术

高级仿真技术 在上一节中&#xff0c;我们介绍了如何使用VISSIM进行基本的交通流仿真设置和运行。本节将深入探讨VISSIM的高级仿真技术&#xff0c;帮助用户在更复杂的交通场景中进行仿真分析。我们将重点介绍以下内容&#xff1a;自定义交通模型、交通事件的动态管理、信号控制…

作者头像 李华
网站建设 2026/7/3 12:47:55

安卓 之 PassthruPatchRecord

1. 类介绍 PassthruPatchRecord 是 Android AudioFlinger 中一个特殊的 patch。它的核心设计目标是实现一种 “直通” 模式,用于 AUDIO_SOURCE_VOICE_PERFORMANCE 等需要极低延迟的音频场景。 • 继承关系: PassthruPatchRecord -> PatchRecord -> RecordTrack ->…

作者头像 李华
网站建设 2026/6/30 0:24:37

YOLOv8 训练与检测系统智慧化交通公路上落石检测数据集 智慧道路交通路面障碍物检测数据集 智慧交通、山区公路监控、应急预警平台 YOLOv8 训练与检测系统

道路落石及障碍物检测数据集【共2套】 第一套&#xff1a; 智慧化道路落石检测数据集 nc一类:shitou1第二套&#xff1a;6类 道路障碍物检测数据集 落石 滑坡检测数据集 6 names: [‘Car’, ‘Motorcycle’, ‘People’, ‘shitou’, ‘Warning-Crash’, ‘landslide’]1111111…

作者头像 李华
网站建设 2026/7/5 3:20:04

基于django智慧农业管理系统设计开发实现

背景分析农业现代化转型需求日益迫切&#xff0c;传统农业依赖人工经验、资源利用率低、环境监测滞后等问题突出。全球气候变化加剧、人口增长导致的粮食安全压力&#xff0c;推动农业向精准化、数据化方向发展。物联网&#xff08;IoT&#xff09;、大数据、人工智能等技术的成…

作者头像 李华