限制 Android 小部件在设备上仅有一个实例

12

如何限制Android小部件,以便用户在任何时候只能创建一个实例?

一种可能的方法是存储包括计数器变量的SharedPreference,并在计数为1时崩溃,但很明显我不赞成这种解决方案。 ;-)

2个回答

7

如何限制Android小部件,使用户始终只能创建一个实例?

你做不到。

然而,仅因为用户请求多个应用程序小部件的实例并不意味着您必须为每个实例管理单独的数据。忽略ID并使用不带任何ID的updateAppWidget()方法即可。


@CommonsWare - 你有没有想过如何发送一个通用的广播,而不需要任何WidgetIds?因为我从一个Service中接收到某些信号,并且不想将服务操作与Widget / View代码混合在一起。 - Sebastian Roth
@CommonsWare,完成了。实际上我现在已经找到了一种方法。抽象地说:定义一个计数器变量,添加一个android:configure活动并管理小部件。如果它已经可见(counter == 1),那么使用AppWidgetHost ah = new AppWidgetHost(this, 1024); ah.deleteAppWidgetId(mAppWidgetId);。1024是Android Launcher的魔法数字。该配置活动可以是透明的或者根本没有任何视图,但它可以做我们需要准备的任何事情。 - Sebastian Roth
@Sebastian Roth:你的代码很可能无法在多个设备上运行,因为我怀疑1024不是每个主屏幕实现的“魔数”。而且据我所知,你不应该有权限在硬件上这样做——如果你确实有这样的权限,那就是一个安全漏洞,我会尽力修复它。请允许你的用户拥有尽可能多的应用程序小部件实例,即使它们都具有相同的内容。 - CommonsWare
@Sebastian Roth:关于1024,并不是每个主屏幕都使用Launcher.java。关于那个其他的SO问题,Android在一年前左右改变了应用程序小部件配置规则,我还没有花时间去尝试解决所有组合的问题。关于安全漏洞,我将在一个星期左右进行更多实验,即新年后发布。现在,您需要一个应用程序小部件实例ID才能造成很大的损害。AppWidgetManager允许您获取ComponentName的ID,如果这不足以保护,应用程序可以从任何人那里删除任何应用程序小部件。 - CommonsWare
好的。明白了。那么首先祝您新年快乐。 :-) - Sebastian Roth
显示剩余4条评论

1
我这样做:
在小部件 onUpdate 方法中,当用户创建第一个小部件时,我保存小部件的 ID 并更新小部件,第二次调用 onUpdate(当添加的小部件被更新时),我检查小部件的相同 ID 并更新它,否则告诉用户只允许一个小部件。
 @Override
    public void onUpdate(Context context, AppWidgetManager appWidgetManager, int[] appWidgetIds) {

        for (int appWidgetId : appWidgetIds) {

            //TinyDb is SharedPreferences Class
            TinyDB tinydb = new TinyDB(context);
            int WidgetId= tinydb.getInt("WidgetID",-1);

            //Check if WidgetID is same as Added ID if yes UPDATE
            if (WidgetId == appWidgetId){
                updateAppWidget(context, appWidgetManager, appWidgetId);
                return;
            //Check if no widget is added then add widget and save widget ID to sharedPreferences
            } else if (WidgetId == -1){
                tinydb.putInt("WidgetID", appWidgetId);
                updateAppWidget(context, appWidgetManager, appWidgetId);
                return;
            }
            else
                {
                //Make toast to tell the user that only one widget is allowed
                Toast.makeText(context, context.getResources().getString(R.string.Only_one_widget_allowed), Toast.LENGTH_SHORT).show();
                }
        }
    }

不要忘记:如果用户删除所有小部件并将其保存到共享首选项中,则我使用int -1,因此我使用此代码:

  @Override
    public void onDisabled(Context context) {
        // Enter relevant functionality for when the last widget is disabled
            TinyDB tinydb = new TinyDB(context);
            tinydb.putInt("WidgetID", -1);
    }

并且它像魔法一样运行!Wholaa!

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接