在 Xamarin 中使用 BroadcastReceiver 从通知调用服务方法 Android
Call service method from notification with BroadcastReceiver in Xamarin Android
我启动一个服务并创建新线程(下载一个大文件)。同时我显示带有操作的通知(暂停按钮)。 当我按下这个按钮时 "WSTRZYMAJ" 我想从我的服务中调用 PauseDownload() 方法。 我该怎么做?我读过 BroadcastReceiver,创建这个 class 但是如何从 BroadcastReceiver class?
的服务中调用方法
通知屏幕:
我的服务片段:
class DownloadsService : Service
{
DownloadsBroadcastReceiver receiver;
Notification.Builder notificationBuilder;
DownloadsData downloadsData;
int uniqueNumber = 1000;
bool isStarted;
public override StartCommandResult OnStartCommand(Intent intent, StartCommandFlags flags, int startId)
{
RegisterReceiver(receiver, new IntentFilter("com.xamarin.example.TEST"));
downloadsData = JsonConvert.DeserializeObject<DownloadsData>(intent.GetStringExtra("downloadsData"));
if (isStarted)
Log.Info("DAMIAN", "Error start service");
else
{
Log.Info("DAMIAN", "Start service");
DispatchNotificationThatServiceIsRunning(downloadsData.Name, "Started");
new Thread(new ThreadStart(() =>
{
MakeDownload();
})).Start();
isStarted = true;
}
return StartCommandResult.NotSticky;
}
private void DispatchNotificationThatServiceIsRunning(string title, string content)
{
Intent stopIntent = new Intent(this, typeof(DownloadsBroadcastReceiver));
stopIntent.PutExtra("action", "actionName");
PendingIntent stopPi = PendingIntent.GetBroadcast(this, 4, stopIntent, PendingIntentFlags.UpdateCurrent);
Intent intent = new Intent(this, typeof(MainActivity));
TaskStackBuilder stackBuilder = TaskStackBuilder.Create(this);
stackBuilder.AddParentStack(Java.Lang.Class.FromType(typeof(MainActivity)));
stackBuilder.AddNextIntent(intent);
PendingIntent resultPendingIntent = stackBuilder.GetPendingIntent(0, PendingIntentFlags.UpdateCurrent);
Notification.Action pauseAction = new Notification.Action.Builder(Resource.Drawable.Pause, "WSTRZYMAJ", stopPi).Build();
notificationBuilder = new Notification.Builder(this)
.SetSmallIcon(Resource.Drawable.Icon)
.SetContentIntent(resultPendingIntent)
.SetContentTitle(title)
.SetContentText(content)
.AddAction(pauseAction);
var notificationManager = (NotificationManager)GetSystemService(NotificationService);
notificationManager.Notify(uniqueNumber, notificationBuilder.Build());
}
private void UpdateNotification(string content)
{
notificationBuilder.SetContentText(content);
var notificationManager = (NotificationManager)GetSystemService(NotificationService);
notificationManager.Notify(uniqueNumber, notificationBuilder.Build());
}
private void MakeDownload()
{
//downloading file
}
private void PauseDownload()
{
//pause downloading
}
}
以及完整代码 BroadcastReceiver class:
[BroadcastReceiver(Enabled = true, Exported = false)]
[IntentFilter(new[] { "com.xamarin.example.TEST" })]
class DownloadsBroadcastReceiver : BroadcastReceiver
{
public override void OnReceive(Context context, Intent intent)
{
String action = intent.GetStringExtra("action");
if (action.Equals("actionName"))
Log.Info("DAMIAN", "BROADCAST"); //it works, ie. I have text "BROADCAST" in log
}
}
how to call method from service from BroadcastReceiver class?
当您在 DownloadsBroadcastReceiver
中收到消息时,您可以重新开始 DownloadsService
。当你这样做的时候,因为你的 DownloadsService
已经创建,它会调用 OnStartCommand() 方法,所以你会在这个方法中收到消息,你可以在 OnStartCommand()
方法中调用 PauseDownload()
.
这样的用法:
[BroadcastReceiver(Enabled = true, Exported = false)]
[IntentFilter(new[] { "com.xamarin.example.TEST" })]
public class DownloadsBroadcastReceiver : BroadcastReceiver
{
public override void OnReceive(Context context, Intent intent)
{
String action = intent.GetStringExtra("action");
if ("actionName".Equals(action))
{
Intent intent2 = new Intent(Application.Context, typeof(DownloadsService));
intent2.PutExtra(action, "actionName");
Application.Context.StartService(intent2);
}
}
}
在你的 DownloadsService
class :
public override StartCommandResult OnStartCommand(Intent intent, StartCommandFlags flags, int startId)
{
String action = intent.GetStringExtra("action");
if ("actionName".Equals(action))
{
PauseDownload();
}
...
return StartCommandResult.NotSticky;
}
我启动一个服务并创建新线程(下载一个大文件)。同时我显示带有操作的通知(暂停按钮)。 当我按下这个按钮时 "WSTRZYMAJ" 我想从我的服务中调用 PauseDownload() 方法。 我该怎么做?我读过 BroadcastReceiver,创建这个 class 但是如何从 BroadcastReceiver class?
的服务中调用方法通知屏幕:
我的服务片段:
class DownloadsService : Service
{
DownloadsBroadcastReceiver receiver;
Notification.Builder notificationBuilder;
DownloadsData downloadsData;
int uniqueNumber = 1000;
bool isStarted;
public override StartCommandResult OnStartCommand(Intent intent, StartCommandFlags flags, int startId)
{
RegisterReceiver(receiver, new IntentFilter("com.xamarin.example.TEST"));
downloadsData = JsonConvert.DeserializeObject<DownloadsData>(intent.GetStringExtra("downloadsData"));
if (isStarted)
Log.Info("DAMIAN", "Error start service");
else
{
Log.Info("DAMIAN", "Start service");
DispatchNotificationThatServiceIsRunning(downloadsData.Name, "Started");
new Thread(new ThreadStart(() =>
{
MakeDownload();
})).Start();
isStarted = true;
}
return StartCommandResult.NotSticky;
}
private void DispatchNotificationThatServiceIsRunning(string title, string content)
{
Intent stopIntent = new Intent(this, typeof(DownloadsBroadcastReceiver));
stopIntent.PutExtra("action", "actionName");
PendingIntent stopPi = PendingIntent.GetBroadcast(this, 4, stopIntent, PendingIntentFlags.UpdateCurrent);
Intent intent = new Intent(this, typeof(MainActivity));
TaskStackBuilder stackBuilder = TaskStackBuilder.Create(this);
stackBuilder.AddParentStack(Java.Lang.Class.FromType(typeof(MainActivity)));
stackBuilder.AddNextIntent(intent);
PendingIntent resultPendingIntent = stackBuilder.GetPendingIntent(0, PendingIntentFlags.UpdateCurrent);
Notification.Action pauseAction = new Notification.Action.Builder(Resource.Drawable.Pause, "WSTRZYMAJ", stopPi).Build();
notificationBuilder = new Notification.Builder(this)
.SetSmallIcon(Resource.Drawable.Icon)
.SetContentIntent(resultPendingIntent)
.SetContentTitle(title)
.SetContentText(content)
.AddAction(pauseAction);
var notificationManager = (NotificationManager)GetSystemService(NotificationService);
notificationManager.Notify(uniqueNumber, notificationBuilder.Build());
}
private void UpdateNotification(string content)
{
notificationBuilder.SetContentText(content);
var notificationManager = (NotificationManager)GetSystemService(NotificationService);
notificationManager.Notify(uniqueNumber, notificationBuilder.Build());
}
private void MakeDownload()
{
//downloading file
}
private void PauseDownload()
{
//pause downloading
}
}
以及完整代码 BroadcastReceiver class:
[BroadcastReceiver(Enabled = true, Exported = false)]
[IntentFilter(new[] { "com.xamarin.example.TEST" })]
class DownloadsBroadcastReceiver : BroadcastReceiver
{
public override void OnReceive(Context context, Intent intent)
{
String action = intent.GetStringExtra("action");
if (action.Equals("actionName"))
Log.Info("DAMIAN", "BROADCAST"); //it works, ie. I have text "BROADCAST" in log
}
}
how to call method from service from BroadcastReceiver class?
当您在 DownloadsBroadcastReceiver
中收到消息时,您可以重新开始 DownloadsService
。当你这样做的时候,因为你的 DownloadsService
已经创建,它会调用 OnStartCommand() 方法,所以你会在这个方法中收到消息,你可以在 OnStartCommand()
方法中调用 PauseDownload()
.
这样的用法:
[BroadcastReceiver(Enabled = true, Exported = false)]
[IntentFilter(new[] { "com.xamarin.example.TEST" })]
public class DownloadsBroadcastReceiver : BroadcastReceiver
{
public override void OnReceive(Context context, Intent intent)
{
String action = intent.GetStringExtra("action");
if ("actionName".Equals(action))
{
Intent intent2 = new Intent(Application.Context, typeof(DownloadsService));
intent2.PutExtra(action, "actionName");
Application.Context.StartService(intent2);
}
}
}
在你的 DownloadsService
class :
public override StartCommandResult OnStartCommand(Intent intent, StartCommandFlags flags, int startId)
{
String action = intent.GetStringExtra("action");
if ("actionName".Equals(action))
{
PauseDownload();
}
...
return StartCommandResult.NotSticky;
}