如何修复更新小部件的 ANR 错误
Posted
技术标签:
【中文标题】如何修复更新小部件的 ANR 错误【英文标题】:How to fix ANR error for updating widgets 【发布时间】:2018-05-23 14:14:28 【问题描述】:我有一个 JobScheduler 服务触发更新小部件 UI。
@Override
public boolean onStartJob(final JobParameters params)
//Offloading work to a new thread.
new Thread(() ->
try
// Here we receive updated data and store to SharedPreferences
...
MyWidgetProvider.updateWidgets(getApplicationContext());
catch (Exception e)
Log.e(TAG, "onStartJob: " + e.getMessage());
finally
jobFinished(params, false);
).start();
return true;
我的 AppWidgetProvider:
protected static void updateWidget(Context context)
try
ComponentName thisWidget = new ComponentName(context, MyWidgetProvider.class);
int[] appWidgetIds = AppWidgetManager.getInstance(context.getApplicationContext()).getAppWidgetIds(thisWidget);
if (appWidgetIds != null)
if (appWidgetIds.length > 0)
for (int appWidgetId : appWidgetIds)
try
Intent intent = new Intent(context, MyWidgetProvider.class);
intent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, appWidgetId);
intent.setAction(UPDATE_WIDGET);
context.sendBroadcast(intent);
catch (Exception e)
catch (Exception e)
Log.e(TAG, "error" + e.getMessage());
@Override
public void onReceive(Context context, Intent intent)
super.onReceive(context, intent);
try
Bundle extras = intent.getExtras();
String action = intent.getAction();
if (extras != null && !TextUtils.isEmpty(action))
int appWidgetId = extras.getInt(AppWidgetManager.EXTRA_APPWIDGET_ID, AppWidgetManager.INVALID_APPWIDGET_ID);
if (appWidgetId != AppWidgetManager.INVALID_APPWIDGET_ID)
if (action.equals(UPDATE_WIDGET))
RemoteViews remoteViews = getRemoteView(context);
// Here read from the SharedPreferences and updates the remoteViews
....
AppWidgetManager appWidgetManager = AppWidgetManager.getInstance(context);
appWidgetManager.partiallyUpdateAppWidget(appWidgetId, remoteViews);
catch (Exception e)
Log.e(TAG, "onReceive() error: " + e.getMessage());
我在广播意图 act=.....UPDATE_WIDGET
时收到 ANR 错误由于我无法在我的设备上复制,我不得不猜测解决方案是什么。
解决方案 #1 我可以传递将减少 UI 运行时的值,而不是保存到 SharedPreferences 并从 SharedPreferences 中读取。这个我可以马上做出改变。
解决方案 #2 我应该调用一个广播并传递所有小部件 ID,而不是循环每个小部件 ID 并调用每个小部件 ID 的广播?不会让 onReceive() 花费更长的时间来执行吗? (因为它必须更新所有小部件)。
解决方案 #2 是我不确定的。这种改变会有帮助吗?还是导致 ANR 更频繁地发生?
【问题讨论】:
问题解决了吗?我在某些三星设备上遇到了同样的问题。我认为这是邪恶的电池管理员。 【参考方案1】:回答我自己的问题。
解决方案 #1 通过意图传递数据值以避免从 SharedPreferences 加载数据和/或从 WorkerThread 加载 SharedPreferences 消除了 ANR 错误。
我已经尝试了解决方案 #2,但我不确定它是否有助于消除 ANR。
【讨论】:
以上是关于如何修复更新小部件的 ANR 错误的主要内容,如果未能解决你的问题,请参考以下文章