为什么OnReceive功能在我的Xamarin Android Widget上不起作用?

csga3l58  于 2023-06-03  发布在  Android
关注(0)|答案(1)|浏览(361)

我正在为android做一个小部件,我在一个简单的表单上有一个按钮。由于某种原因,按钮一直工作,然后不工作;即使我没有修改代码或项目。在调试状态下,单击小部件上的按钮后,我会继续检查onReceive函数是否正在触发。我可以让它工作,然后通过删除意图过滤器或更改意图过滤器上的标签来不随机工作。这很奇怪,而且androidmanifest是自动生成的,所以在manifest中显示的内容并不是在manifest中实际运行的内容。
WidgetProvider.cs类

using Android.App;
using Android.Appwidget;
using Android.Content;
using Android.OS;
using Android.Runtime;
using Android.Support.V4.App;
using Android.Views;
using Android.Widget;

using Terminal;

namespace MultiApp
{
    [Activity(Label = "WidgetProvider")]
    [BroadcastReceiver(Label = "Terminal",Exported = true, Enabled = true)]
    [IntentFilter(new string[] { "android.appwidget.action.APPWIDGET_UPDATE", "WIDGET_BUTTON_CLICK" })]
    [MetaData("android.appwidget.provider", Resource = "@xml/my_widget")]
    public class WidgetProvider : AppWidgetProvider
    {

       public static int Counter = 0;

        public override void OnUpdate(Context context, AppWidgetManager appWidgetManager, int[] appWidgetIds)
        {
       
            base.OnUpdate(context, appWidgetManager, appWidgetIds);

            foreach(int appwidgetId in appWidgetIds)
            {
                // Build the remote views for the widget
                var remoteViews = BuildRemoteViews(context, appwidgetId);


                // Update all instances of the widget with the new remote views
                appWidgetManager.UpdateAppWidget(appwidgetId, remoteViews);
            }
         



        }

        public RemoteViews BuildRemoteViews(Context context, int appWidgetIds)
        {
            //Initialize our widget view, basically pointing to our main widget layout xml
            var widgetView = new RemoteViews(context.PackageName, Resource.Layout.widget_layout);



            //Initializing a new Intent variable, within our current context, and widget provider class
            var clickIntent = new Intent(context, typeof(WidgetProvider));

            //Settings that clickIntents action to be 'Widget_Button_Click'
            clickIntent.SetAction("WIDGET_BUTTON_CLICK");

            //Initializing a pending intent variable, basically saying that the button will be clicked at some point
            var pendingIntent = PendingIntent.GetBroadcast(context, 0, clickIntent, PendingIntentFlags.Immutable);

            //Associating the pending intent, to our widget_button pointer in our xml file
            widgetView.SetOnClickPendingIntent(Resource.Id.widget_button, pendingIntent);


            return widgetView;
        }







        public override void OnReceive(Context context, Intent intent)
        {
            base.OnReceive(context, intent);

            //If Intent Receive is our widget button click
            if (intent.Action == "WIDGET_BUTTON_CLICK")
            {
                Toast.MakeText(context, "Congrats", ToastLength.Short).Show();
            }
        }

    }
}

小部件布局类

<?xml version="1.0" encoding="utf-8"?>

<FrameLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:padding="8dp"
    android:background="@drawable/widgetbackGround">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:gravity="top|left"
        android:orientation="vertical"
        android:layout_margin="5dp"
        >

        <LinearLayout
            android:orientation="vertical"
            android:layout_width="150dp"
            android:layout_height="150dp"
            android:layout_margin="3dp">


            <ListView
                android:minWidth="25px"
                android:minHeight="25px"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:layout_weight="1"
                android:background="@drawable/terminalViewDraw"
                android:id="@+id/listView1"
                android:layout_marginRight="13.0dp" />


            </LinearLayout>

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="horizontal">

        

            <Button
                android:layout_width="60dp"
                android:layout_height="35dp"
                
                android:textAllCaps="false"
                android:id="@+id/widget_button"/>

        </LinearLayout>

    </LinearLayout>

</FrameLayout>

Android Manifest

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android" android:versionCode="1" android:versionName="1.0" package="com.companyname.terminal">
    <uses-sdk android:minSdkVersion="21" android:targetSdkVersion="33" />
    <application android:allowBackup="true" android:icon="@mipmap/ic_launcher" android:label="@string/app_name" android:supportsRtl="true" android:theme="@style/AppTheme">
    </application>
    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
</manifest>

我可以让它工作,然后通过删除意图过滤器或更改意图过滤器上的标签来不随机工作。太奇怪了

sg3maiej

sg3maiej1#

首先,我看到您在项目中使用了Android.Support.V4.App名称空间。我建议您将支持包迁移到AndroidX package with Xamarin
然后,您可以删除类WidgetProvider[Activity(Label = "WidgetProvider")],因为它不是Activity。
此外,我创建了一个新项目来测试您的代码。我可以重现这个问题:
由于某种原因,按钮一直工作,然后不工作;即使我没有修改代码或项目。在调试状态下,单击小部件上的按钮后,我会继续检查onReceive函数是否正在触发。我可以让它工作,然后通过移除意图过滤器或更改意图过滤器上的标签来使其不随机工作
如果在调试模式下重新启动项目,设备上现有的小部件将突然停止工作。您需要创建一个新的小部件并删除旧的小部件。然后,当您单击该按钮时,OnReceive将始终被触发。
删除旧的并添加新的对我来说很有用。最后,我在android 13上进行了测试,发现即使执行Toast.MakeText(context, "Congrats", ToastLength.Short).Show();,吐司也不会显示。

相关问题