Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/loops/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何创建Xamarin前台服务_C#_Android_Visual Studio_Xamarin_Xamarin.android - Fatal编程技术网

C# 如何创建Xamarin前台服务

C# 如何创建Xamarin前台服务,c#,android,visual-studio,xamarin,xamarin.android,C#,Android,Visual Studio,Xamarin,Xamarin.android,正在尝试创建我的第一个Xamarin前台服务,但找不到合适的示例。Microsoft文档中的示例似乎不完整或使用了折旧通知。生成器: 我发现了一个似乎是最新的代码示例,但通过查看代码,我很难理解它是如何工作的: 谁能给我一个如何创建基本前台服务的例子 问题可能是,“我应该如何找到Xamarin本机不常见功能的示例?” 如果您正在寻找不寻常功能的示例,您最好的朋友是GitHub: 只需登录到GitHub,在搜索栏中查找所有GitHub上的函数名,StartForegroundService

正在尝试创建我的第一个Xamarin前台服务,但找不到合适的示例。Microsoft文档中的示例似乎不完整或使用了折旧通知。生成器:

我发现了一个似乎是最新的代码示例,但通过查看代码,我很难理解它是如何工作的:


谁能给我一个如何创建基本前台服务的例子

问题可能是,“我应该如何找到Xamarin本机不常见功能的示例?”

如果您正在寻找不寻常功能的示例,您最好的朋友是GitHub:

  • 只需登录到GitHub,在搜索栏中查找所有GitHub上的函数名,
    StartForegroundServiceCompat
  • 瞧,你现在可以使用这个功能了

不要忘记写一篇文章,并提供一个最新的例子,解释它是如何工作的

我终于拼凑出了一个答案。以下是一个例子,供发现自己在这里的人参考:

创建依赖项服务,以便可以从共享代码中调用启动/停止服务方法

制作界面:

public interface IAndroidService
    {
        void StartService();

        void StopService();
    }
在使用该接口的android项目中实现一个类。请记住添加程序集引用

[assembly: Xamarin.Forms.Dependency(typeof(AndroidServiceHelper))]

namespace YourNameSpace.Droid
{
    internal class AndroidServiceHelper : IAndroidService
    {
        private static Context context = global::Android.App.Application.Context;

        public void StartService()
        {
            var intent = new Intent(context, typeof(DataSource));

            if (Android.OS.Build.VERSION.SdkInt >= Android.OS.BuildVersionCodes.O)
            {
                context.StartForegroundService(intent);
            }
            else
            {
                context.StartService(intent);
            }
        }

        public void StopService()
        {
            var intent = new Intent(context, typeof(DataSource));
            context.StopService(intent);
        }
    }
}
现在,我们在创建前台服务所需的通知方面做了几乎相同的工作(在android项目中创建接口并在类中实现):

用于创建通知的接口

public interface INotification
    {
        Notification ReturnNotif();
    }
在android项目中创建一个实现INotification的类,这样我们就可以创建并返回启动前台服务所需的通知对象。请记住添加程序集引用:

[assembly: Xamarin.Forms.Dependency(typeof(NotificationHelper))]

namespace MetroAlarmHandlerMobile.Droid
{
    internal class NotificationHelper : INotification
    {
        private static string foregroundChannelId = "9001";
        private static Context context = global::Android.App.Application.Context;


        public Notification ReturnNotif()
        {
            // Building intent
            var intent = new Intent(context, typeof(MainActivity));
            intent.AddFlags(ActivityFlags.SingleTop);
            intent.PutExtra("Title", "Message");

            var pendingIntent = PendingIntent.GetActivity(context, 0, intent, PendingIntentFlags.UpdateCurrent);

            var notifBuilder = new NotificationCompat.Builder(context, foregroundChannelId)
                .SetContentTitle("Your Title")
                .SetContentText("Main Text Body")
                .SetSmallIcon(Resource.Drawable.MetroIcon)
                .SetOngoing(true)
                .SetContentIntent(pendingIntent);

            // Building channel if API verion is 26 or above
            if (global::Android.OS.Build.VERSION.SdkInt >= BuildVersionCodes.O)
            {
                NotificationChannel notificationChannel = new NotificationChannel(foregroundChannelId, "Title", NotificationImportance.High);
                notificationChannel.Importance = NotificationImportance.High;
                notificationChannel.EnableLights(true);
                notificationChannel.EnableVibration(true);
                notificationChannel.SetShowBadge(true);
                notificationChannel.SetVibrationPattern(new long[] { 100, 200, 300, 400, 500, 400, 300, 200, 400 });

                var notifManager = context.GetSystemService(Context.NotificationService) as NotificationManager;
                if (notifManager != null)
                {
                    notifBuilder.SetChannelId(foregroundChannelId);
                    notifManager.CreateNotificationChannel(notificationChannel);
                }
            }

            return notifBuilder.Build();
        }
}
创建从服务继承和重写的类。这是在共享代码中创建的类,我们将在其中调用希望在前台服务上运行的方法

public class DataSource : Service
    {

        public override IBinder OnBind(Intent intent)
        {
            return null;
        }

        public const int ServiceRunningNotifID = 9000;

        public override StartCommandResult OnStartCommand(Intent intent, StartCommandFlags flags, int startId)
        {
            Notification notif = DependencyService.Get<INotification>().ReturnNotif();
            StartForeground(ServiceRunningNotifID, notif);

            _ = DoLongRunningOperationThings();

            return StartCommandResult.Sticky;
        }

        public override void OnDestroy()
        {
            base.OnDestroy();
        }

        public override bool StopService(Intent name)
        {
            return base.StopService(name);
        }


}
公共类数据源:服务
{
公共覆盖iBind OnBind(意图)
{
返回null;
}
公共const int ServiceRunningNotifID=9000;
公共覆盖StartCommandResult OnStartCommand(意图、StartCommandFlags标志、int-startId)
{
Notification notif=DependencyService.Get().ReturnNotif();
启动地面(服务运行通知,通知);
_=DoLongRunningOperationThings();
返回StartCommandResult.Sticky;
}
公共覆盖无效OnDestroy()
{
base.ondestory();
}
公共覆盖布尔停止服务(意图名称)
{
返回base.StopService(名称);
}
}
现在,您可以使用以下代码在共享代码中的任意位置使用依赖项服务启动和停止前台服务:

开始

DependencyService.Get().StartService();
停止

DependencyService.Get().StopService();

非常感谢您让我们提供另一个教程,为什么不就您发现的样本中不理解的具体内容提出一个问题呢?Jason样本很复杂,很难知道正确的问题,这就是为什么我要求提供一个我找不到的基本示例。请阅读Android前台服务文档。没有那么多运动部件。示例的形式是最纯粹的。@Cheesebaron示例使用Notification.Builder,该示例已过时,因此示例无法运行。它使用NotificationCompat。只需替换为通知。谢谢你的想法,伙计,我没有使用github,但根据你所说的,我可能应该!没问题!是的,在StackOverflow和MS Xamarin文档之后,它实际上是一个很好的资源@DavidDrewthorpe告诉我您是否能找到有用的东西,如果找到了,请解决这个问题。从服务继承必须在Android项目中完成,而不是在跨平台共享代码中完成。@MondQ DataSource是我创建的静态类的名称,它从服务继承并实现OnStartCommand等方法,StopService、OnDestroy等。。。所以,当它显示typeof(DataSource)时,您需要将“DataSource”替换为用于从服务继承的类。“如果未触发OnStartCommand,请尝试添加[Service]在数据源classIs之上,有没有一种方法可以知道服务是否已经启动?一种简单的方法是创建一个类似IsServiceStarted的bool,并在启动/停止它时将其设置为true/false。你只需要检查一下那个bool就知道它是否已经启动了
DependencyService.Get<IAndroidService>().StartService();
DependencyService.Get<IAndroidService>().StopService();