现在的位置: 首页 > 云计算 > 正文

updateperiodmillis属性是什么?桌面Widget动态刷新

2020年01月07日 云计算 ⁄ 共 3985字 ⁄ 字号 评论关闭

  关于桌面widget的动态刷新有这样一个配置,在res/xml下下有一个属性android:updatePeriodMillis="86400000"。

  updatePeriodMillis属性是什么

  updatePeriodMillis这个属性规定了AppWiget框架应该多久发送一次请求通过调用AppwidgetProvider的onUpdate()方法来更新,实际的更新并不能保证根据这个值准时的更新,我们建议尽可能频率少的进行更新操作,最好不要超过1个小时更新一次,为了保存电池的电量。你页可以给出配置允许用户来调整更新的频率,就像一些人希望股票行情追踪器每15分钟更新一次,或者仅仅一天更新4次

  如果屏幕是睡眠的,用updatePeriodMillis更新widget时,会唤醒屏幕。如果你不是每一次小时更新一次,那么你就有可能为电池的待机时间带来严重的影响。然而,如果你需要频繁的进行更新操作,但是或许你并不需要更新时唤醒屏幕,那么你可以在alarm的基础上进行更新操作而不用唤醒设备。像这样做,用AlarmManager设置一个携带intent的闹钟让你的AppwidgetProvider接受更新操作。将alarm的类型设置为ELAPSED_REALTIME或者RTC,这样就会仅仅在设备处于唤醒状态下才会传递alarm的intent。然后设置updatePeriodMillis=0.

  在实际的操作中会出现一些问题

  1、SDK在1.6以上时,当updatePeriodMillis的设置的值小于半个小时时,就会失效。

  2、使用service更新,或者alarm更新时也会出现一些问题

  下面说一下我个人的理解,有不对的地方,欢迎提出。

  先说appwidget创建的过程。

  1、长按桌面会出现一个列表,这个列表应该就是在manifest注册了AppWidgetProvider的应用列表

  android:name="android.appwidget.provider"

  android:resource="@xml/test_appwidget_info" />

  2、点击图标时候会触发android.appwidget.action.APPWIDGET_UPDATE这个intent,

  AppWidgetProvider的onReceive()方法执行。

  然后onUpdate()方法执行,这时会为该appWidget分配id。

  然后会调用AppWidgetConfigure这个Activity并且让你配置widget的大小。

  然后就是刷新的方法了,我先后试过几个方法都说一说。

  1、我最先用的是是在AppWidgetProvider的onUpate方法中用handler刷新,开一个线程10秒一次发消息

  这个方法有几个问题:1>应用升级时会发现问题。2>线程会挂掉

  2、用service,将appWidgetManager, appWidgetIds传给service然后在service内刷新,结果不行。不知道为什么。

  3、通过发android.appwidget.action.APPWIDGET_UPDATE这个广播刷新。用service发或者alarm发,相比较alarm更好,也是官方推荐的。下面就说用alarm做的过程

  这个方法刷新时最开始也出现了问题,我一直想的是在onUpdate方法里刷新,但事实是错误的。1>在onUpdate里面创建一个alarm然后每10秒发一次intent,那么每次onUpate刷新时又都会创建一个alarm发intent这样就是出问题了

  2>刷新时我都会将这个appwidget的id获取到然后appWidgetManager.updateAppWidget(appWidgetIds[0], views);刷新,结果出现了一个变态的情况我自己的widget和系统的桌面渲染的一个widget来回切换。没搞清楚什么情况。

  最后说下我现在在用的方法:

  在onUpdate中设置alarm

  AlarmManager alarmMgr = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);

  Intent intent = new Intent(AppWidgetManager.ACTION_APPWIDGET_UPDATE);

  int requestCode = 0;

  PendingIntent pendIntent = PendingIntent.getBroadcast(context, requestCode, intent, PendingIntent.FLAG_UPDATE_CURRENT);

  // 5秒后发送广播,然后每个10秒重复发广播。广播都是直接发到AlarmReceiver的

  long triggerAtTime = SystemClock.elapsedRealtime() + 10 * 1000;

  int interval = 10 * 1000;

  alarmMgr.setRepeating(AlarmManager.RTC, triggerAtTime, interval, pendIntent);

  然后在onReceive中刷新AppWidgetId是从AppWidgetConfigure里面拿的,把mAppWidgetId设为静态的了。

  [java]

  Intent intent = getIntent();

  Bundle extras = intent.getExtras();

  if (extras != null) {

  mAppWidgetId = extras.getInt(

  AppWidgetManager.EXTRA_APPWIDGET_ID,

  AppWidgetManager.INVALID_APPWIDGET_ID);

  }

  [java]

  AppWidgetManager.getInstance(context).updateAppWidget(TestAppWidgetConfigure.mAppWidgetId, views);

  关键:

  看一下TestAppWidgetProvider父类中的onReceive方法,在onUpdate中设置alarm时intent不用带参数,这样每次alarm刷新时只会调用onReceive方法也不会调用onUpate方法

  [java]

  /**

  * Implements {@link BroadcastReceiver#onReceive} to dispatch calls to the various

  * other methods on AppWidgetProvider.

  *

  * @param context The Context in which the receiver is running.

  * @param intent The Intent being received.

  */

  // BEGIN_INCLUDE(onReceive)

  public void onReceive(Context context, Intent intent) {

  // Protect against rogue update broadcasts (not really a security issue,

  // just filter bad broacasts out so subclasses are less likely to crash).

  String action = intent.getAction();

  if (AppWidgetManager.ACTION_APPWIDGET_UPDATE.equals(action)) {

  Bundle extras = intent.getExtras();

  if (extras != null) {

  int[] appWidgetIds = extras.getIntArray(AppWidgetManager.EXTRA_APPWIDGET_IDS);

  if (appWidgetIds != null && appWidgetIds.length > 0) {

  this.onUpdate(context, AppWidgetManager.getInstance(context), appWidgetIds);

  }

  }

  }

  else if (AppWidgetManager.ACTION_APPWIDGET_DELETED.equals(action)) {

  Bundle extras = intent.getExtras();

  if (extras != null && extras.containsKey(AppWidgetManager.EXTRA_APPWIDGET_ID)) {

  final int appWidgetId = extras.getInt(AppWidgetManager.EXTRA_APPWIDGET_ID);

  this.onDeleted(context, new int[] { appWidgetId });

  } www.2cto.com

  }

  else if (AppWidgetManager.ACTION_APPWIDGET_ENABLED.equals(action)) {

  this.onEnabled(context);

  }

  else if (AppWidgetManager.ACTION_APPWIDGET_DISABLED.equals(action)) {

  this.onDisabled(context);

  }

  }

抱歉!评论已关闭.