前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >教你用Android自带统计服务一招制敌

教你用Android自带统计服务一招制敌

作者头像
开发者技术前线
发布2020-11-23 14:56:02
7560
发布2020-11-23 14:56:02
举报
文章被收录于专栏:开发者技术前线

Google从 API 21 新增了接口 android.app.usage , 通过这个api我们可以统计到每个app的使用情况,启动次数,启动时间等,也可以判断是否前后台,比较方便,今天就来深入的学习一下 。

Google从 API 21 新增了接口 android.app.usage , 通过这个api我们可以统计到每个app的使用情况,启动次数,启动时间等,也可以判断是否运行在前后台,比较方便,也可以用作埋点,统计框架中,今天就来深入的学习一下。

获取前后台

5.0以前做法是这样的:

代码语言:javascript
复制
 public String getForegroundApp(Context context) {        
    List<RunningAppProcesInfo> lr=context.getRunningAppProcesses();   

   if  (lr == null)  {     
       return null;   }   
 for (RunningAppProcessInfo ra : lr) {        
     if (ra.importance == RunningAppProcessInfo.IMPORTANCE_VISIBLE   || ra.importance == RunningAppProcessInfo.IMPORTANCE_FOREGROUND) {                return ra.processName;     
        }    
    }      
   return null; 

}

突然从5.0就不能用了。这就有点eggs pain, 很多人通过检查当前自己应用的界面做标记, 在可见和不可见的生命周期中分别做记录,来判断是否前台getRecentTasks( ) 也废弃使用了,我们在清单注册getTask权限已经被收回了,那怎么办,android api其实已经想好了替代品,那就是 AppUsageStatistics 需要用户授权才可以,好,就学学姿势吧。

5.0以后用AppUsageStatistics来获取

代码语言:javascript
复制
private String getForegroundApp() {  long ts = System.currentTimeMillis(); 
    List<UsageStats> queryUsageStats = 
usageStatsManager.queryUsageStats(UsageStatsManager.INTERVAL_BEST,ts-2000, ts);   
   if (queryUsageStats == null || queryUsageStats.isEmpty())  {     
       return null;   
    } 
  UsageStats recentStats = null; 
  for (UsageStats usageStats : queryUsageStats) { 
    if(recentStats == null || recentStats.getLastTimeUsed() < usageStats.getLastTimeUsed()) {       
     recentStats = usageStats;     
  }   
} 
  return recentStats.getPackageName; 
}

看是不是 很简单,或许你都没听过吧!好 follow me!

AppUasgeStatistics

1 首先清单申请权限

代码语言:javascript
复制
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.example.android.appusagestatistics"
    android:versionCode="1"
    android:versionName="1.0">

    <uses-permission android:name="android.permission.PACKAGE_USAGE_STATS"/>

    <application android:allowBackup="true"
        android:label="@string/app_name"
        android:icon="@drawable/ic_launcher"
        android:theme="@style/Theme.AppCompat.Light">

        <activity android:name=".AppUsageStatisticsActivity"
                  android:label="@string/app_name">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application></manifest>

2 获取UsageStatsManager

接着通过context GET到UsageStatsManager。

代码语言:javascript
复制
UsageStatsManager mUsageStatsManager = (UsageStatsManager) getActivity()                .getSystemService("usagestats"); //Context.USAGE_STATS_SERVICE

3 使用

我通过这个api获取一下每个app的使用情况intervalType是统计的周期,是统计区间UsageStatsManager 内部提供四个原则,有:年,月,周,日。

代码语言:javascript
复制
 DAILY("Daily", UsageStatsManager.INTERVAL_DAILY),
        WEEKLY("Weekly", UsageStatsManager.INTERVAL_WEEKLY),
        MONTHLY("Monthly", UsageStatsManager.INTERVAL_MONTHLY),
        YEARLY("Yearly", UsageStatsManager.INTERVAL_YEARLY);

为了拓展我定义一个CustomUsageStats, UsageStats是谷歌提供一个统计类,里面可以获取app的使用情况。

代码语言:javascript
复制
public class CustomUsageStats {   
  public UsageStats usageStats;    
  public Drawable appIcon;
}

面这段代码就是获取每个app的使用情况的。

代码语言:javascript
复制
public List<UsageStats> getUsageStatistics(int intervalType) {        // Get the app statistics since one year ago from the current time.
        Calendar cal = Calendar.getInstance();
        cal.add(Calendar.YEAR, -1);

        List<UsageStats> queryUsageStats = mUsageStatsManager
                .queryUsageStats(intervalType, cal.getTimeInMillis(),
                        System.currentTimeMillis());        if (queryUsageStats.size() == 0) {
            Log.i(TAG, "The user may not allow the access to apps usage. ");
            Toast.makeText(getActivity(),
                    getString(R.string.explanation_access_to_appusage_is_not_enabled),
                    Toast.LENGTH_LONG).show();
            mOpenUsageSettingButton.setVisibility(View.VISIBLE);
            mOpenUsageSettingButton.setOnClickListener(new View.OnClickListener() {
                @Override                public void onClick(View v) {
                    startActivity(new Intent(Settings.ACTION_USAGE_ACCESS_SETTINGS));
                }
            });
        }        return queryUsageStats;
    }

当然上面代码只是获取app的使用情况,来写个列表,用适配器用来展现app的包名,最后使用的时间,以及图标icon。

代码语言:javascript
复制
public class UsageListAdapter extends RecyclerView.Adapter<UsageListAdapter.ViewHolder> {    
  private List<CustomUsageStats> mCustomUsageStatsList = new ArrayList<>();    
  private DateFormat mDateFormat = new SimpleDateFormat();   
   /**
     * Provide a reference to the type of views that you are using (custom ViewHolder)
     */
    public static class ViewHolder extends RecyclerView.ViewHolder {        
    private final TextView mPackageName;        
    private final TextView mLastTimeUsed;        
    private final ImageView mAppIcon;        
    public ViewHolder(View v) {            
       super(v);
            mPackageName = (TextView) v.findViewById(R.id.textview_package_name);
            mLastTimeUsed = (TextView) v.findViewById(R.id.textview_last_time_used);
            mAppIcon = (ImageView) v.findViewById(R.id.app_icon);
        }        
        public TextView getLastTimeUsed() {            
           return mLastTimeUsed;
        }        
        public TextView getPackageName() {            
           return mPackageName;
        }        
        public ImageView getAppIcon() {            
          return mAppIcon;
        }
    }    
    public UsageListAdapter() {
    }    
    
    @Override
    public ViewHolder onCreateViewHolder(ViewGroup viewGroup, int viewType) {
        View v = LayoutInflater.from(viewGroup.getContext())
                .inflate(R.layout.usage_row, viewGroup, false);        return new ViewHolder(v);
    }    
    @Override
    public void onBindViewHolder(ViewHolder viewHolder, final int position) {
        viewHolder.getPackageName().setText(
                mCustomUsageStatsList.get(position).usageStats.getPackageName());        long lastTimeUsed = mCustomUsageStatsList.get(position).usageStats.getLastTimeUsed();
        viewHolder.getLastTimeUsed().setText(mDateFormat.format(new Date(lastTimeUsed)));
        viewHolder.getAppIcon().setImageDrawable(mCustomUsageStatsList.get(position).appIcon);
    }    
    @Override
    public int getItemCount() {        
       return mCustomUsageStatsList.size();
    }    
    public void setCustomUsageStatsList(List<CustomUsageStats> customUsageStats) {
        mCustomUsageStatsList = customUsageStats;
    }
}

后记

这个api不是说想用就能用,必须用户授权了才能统计到。所以我们在做移动端埋点时可以加入这个api,方便我们更精确的搜集app的使用情况。更多技巧请继续关注。

技术 - 资讯 - 感悟

END

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2017-03-29,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 开发者技术前线 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 5.0以前做法是这样的:
  • 5.0以后用AppUsageStatistics来获取
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档