首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >在Android中如何更新小部件(使用AlarmManager)

在Android中如何更新小部件(使用AlarmManager)
EN

Stack Overflow用户
提问于 2021-09-07 14:47:40
回答 1查看 44关注 0票数 0

我的应用程序使用一个小部件,我想在一天的特定时间更新它。下面是代码:

代码语言:javascript
复制
package com.apps.app;

import android.app.AlarmManager;
import android.app.PendingIntent;
import android.appwidget.AppWidgetManager;
import android.appwidget.AppWidgetProvider;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
import android.widget.RemoteViews;

import com.snappydb.DB;
import com.snappydb.DBFactory;
import com.snappydb.SnappydbException;

import java.util.ArrayList;
import java.util.Calendar;

public class Widget extends AppWidgetProvider {

public static String ACTION_AUTO_UPDATE_WIDGET = "ACTION_AUTO_UPDATE_WIDGET";

@Override
public void onReceive(Context context, Intent intent) {
    super.onReceive(context, intent);

    if (ACTION_AUTO_UPDATE_WIDGET.equals(intent.getAction())) {
        Log.d("widget","received");
        onUpdate(context, AppWidgetManager.getInstance(context),
                AppWidgetManager.getInstance(context).getAppWidgetIds(new ComponentName(context, Widget.class)));
    }
}

@Override
public void onDisabled(Context context) {
    super.onDisabled(context);
    Intent intent = new Intent(context, Widget.class);
    intent.setAction(ACTION_AUTO_UPDATE_WIDGET);
    AlarmManager alarmMgr = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
    alarmMgr.cancel(PendingIntent.getBroadcast(context, 0, intent, 0));
}

@Override
public void onEnabled(Context context) {
    super.onEnabled(context);

    try {
        DB db = DBFactory.open(context, "notes");
        ArrayList <Note> noteArrayList = db.getObject("notes", ArrayList.class);
        for(Note note: noteArrayList) {
            setUpdateIntent(context, note.getHours(), note.getMinutes());
        }
    } catch (SnappydbException e) {
        e.printStackTrace();
    }
    
}

private void setUpdateIntent(Context context, int h, int m) {
    Intent intent1 = new Intent(context, Widget.class);
    intent1.setAction(ACTION_AUTO_UPDATE_WIDGET);
    PendingIntent alarmIntent = PendingIntent.getBroadcast(context, h*m, intent1, 0);

    Calendar c = Calendar.getInstance();
    c.set(Calendar.HOUR_OF_DAY, h);
    c.set(Calendar.MINUTE, m);

    AlarmManager alarmMgr = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
    alarmMgr.setRepeating(AlarmManager.RTC, c.getTimeInMillis(), AlarmManager.INTERVAL_DAY, alarmIntent);
}

@Override
public void onUpdate(Context context, AppWidgetManager appWidgetManager, int[] appWidgetIds) {
    super.onUpdate(context, appWidgetManager, appWidgetIds);
    for (int id : appWidgetIds) {
        updateWidget(context, appWidgetManager, id);
    }
}

private void updateWidget(Context context, AppWidgetManager manager, int widgetId) {
    RemoteViews widgetView = new RemoteViews(context.getPackageName(), R.layout.widget);
    widgetView.setTextViewText(R.id.dateTextView, TimeManager.getDay());
    widgetView.setTextViewText(R.id.curTimeTextView, TimeManager.getTime());
    widgetView.setTextViewText(R.id.weatherTextView,
            context.getSharedPreferences("weather", Context.MODE_PRIVATE).getString("weather", "default"));

    Intent configIntent = new Intent(context, MainActivity.class);
    configIntent.setAction(AppWidgetManager.ACTION_APPWIDGET_CONFIGURE);
    configIntent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, widgetId);
    PendingIntent pIntent = PendingIntent.getActivity(context, widgetId, configIntent, 0);
    widgetView.setOnClickPendingIntent(R.id.layoutId, pIntent);

    manager.updateAppWidget(widgetId, widgetView);
}

}

根据DB的数据,应该在17:37、17:40和17:42准确更新。这是我的更新日志:

代码语言:javascript
复制
2021-09-07 17:38:31.518 6787-6787/com.apps.app D/widget: received
2021-09-07 17:38:31.547 6787-6787/com.apps.app D/widget: received
2021-09-07 17:42:52.078 6787-6787/com.apps.app D/widget: received
2021-09-07 17:42:52.092 6787-6787/com.apps.app D/widget: received

我真的不明白小部件的更新是基于什么算法。有人能给我解释一下吗?

EN

回答 1

Stack Overflow用户

发布于 2021-12-10 03:04:23

如果您的应用程序希望允许传递时间漂移,以确保警报之间总是至少有一定的时间间隔,那么需要采取的方法是使用一次警报,在处理每个警报传递时自己调度下一个警报。

从API 19开始,所有重复的警报都是不准确的。如果您的应用程序需要精确的交付时间,那么它必须使用一次精确警报,重新安排每次发送时间。其targetSdkVersion早于API 19的遗留应用程序将继续将其所有警报(包括重复警报)作为精确处理。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/69090315

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档