This is the forum for miscellaneous technical/programming questions.
Moderator: 2ffat
Lena
BCBJ Master
Posts: 719 Joined: Sun Feb 06, 2011 1:28 pm
Post
by Lena » Fri Nov 27, 2020 8:54 am
Hello.
There is a foreground service code that works great on Android 8.1. In Android 7 the application crashes after a splash screen (I sent my apk). I don't have an Android 7 phone.
What's missing for Android 7? RAD 10.3
Thanks.
Code: Select all
interface
uses
System.SysUtils,
System.Classes,
System.Android.Service,
AndroidApi.JNI.GraphicsContentViewText,
Androidapi.JNI.Os,
Androidapi.JNI.App,
Androidapi.JNI.Support,
Androidapi.JNI.JavaTypes,
Androidapi.Helpers,
Androidapi.JNIBridge,
Androidapi.Jni;
type
TDM = class(TAndroidService)
function AndroidServiceStartCommand(const Sender: TObject;
const Intent: JIntent; Flags, StartId: Integer): Integer;
private
{ Private declarations }
public
{ Public declarations }
end;
var
DM: TDM;
implementation
{%CLASSGROUP 'FMX.Controls.TControl'}
{$R *.dfm}
function TDM.AndroidServiceStartCommand(const Sender: TObject;
const Intent: JIntent; Flags, StartId: Integer): Integer;
var
ServiceChannel: JNotificationChannel;
NotificationManager: JNotificationManager;
Obj: JObject;
NewIntent: JIntent;
ncb: JNotificationCompat_Builder;
ntf: JNotification;
PendingIntent: JPendingIntent;
begin
Result := TJService.JavaClass.START_NOT_STICKY;
ServiceChannel := TJNotificationChannel.JavaClass.init(
StringtoJString('com.radio.one'),
StrToJCharSequence('Public radio Channel'),
TJNotificationManager.JavaClass.IMPORTANCE_DEFAULT
);
Obj := TAndroidHelper.Context.getSystemService(
TJContext.JavaClass.NOTIFICATION_SERVICE);
NotificationManager := TJNotificationManager.Wrap(Obj);
NotificationManager.createNotificationChannel(ServiceChannel);
PendingIntent := TJPendingIntent.JavaClass.getActivity(
JavaService.getApplicationContext, 0, Intent, 0
);
ncb := TJNotificationCompat_Builder.JavaClass.init(
TAndroidHelper.Context,
StringToJString('com.radio.one')
);
ncb.setContentTitle(StrToJCharSequence('PublicRadio'));
// ncb.setTicker(StrToJCharSequence('Communications Service'));
ncb.setSmallIcon(JavaService.getApplicationInfo.icon);
ncb.setContentIntent(PendingIntent);
ncb.setOngoing(True);
ntf := ncb.build;
JavaService.startForeground(StartId, ntf);
end;
end.
rlebeau
BCBJ Author
Posts: 1795 Joined: Wed Jun 01, 2005 3:21 am
Location: California, USA
Contact:
Post
by rlebeau » Mon Nov 30, 2020 5:23 pm
Lena wrote: ↑ Fri Nov 27, 2020 8:54 am
In Android 7 the application crashes after a splash screen (I sent my apk).
Crashes HOW exactly? Please be more specific.
Lena wrote: ↑ Fri Nov 27, 2020 8:54 am
I don't have an Android 7 phone.
Have you tried using Android 7 in any simulators? Does the crash happen in them, too? Where in your code does the crash happen exactly?
Lena
BCBJ Master
Posts: 719 Joined: Sun Feb 06, 2011 1:28 pm
Post
by Lena » Wed Dec 02, 2020 10:26 am
Crashes HOW exactly? Please be more specific.
Debager does not work.
I think I have found a solution. It looks like it works:
Code: Select all
function TDM.AndroidServiceStartCommand(const Sender: TObject;
const Intent: JIntent; Flags, StartId: Integer): Integer;
var
//Android 8.1
ServiceChannel: JNotificationChannel;
NotificationManager: JNotificationManager;
Obj: JObject;
NewIntent: JIntent;
ncb: JNotificationCompat_Builder;
ntf: JNotification;
PendingIntent: JPendingIntent;
//Android 7.1
service : JService;
serviceObjectId : Pointer;
ntf2 : JNotification;
intent2 : JIntent;
PendingIntent2 : JPendingIntent;
begin
Result := TJService.JavaClass.START_NOT_STICKY;
// can't ref .O on earlier phones, must hardcode
if TJBuild_VERSION.JavaClass.SDK_INT > 26 then // JBuild_VERSION_CODES.JavaClass.O
begin
//Android 8.1
//new ways for SDK > 26 (won't be called when API < 26 anyways)
ServiceChannel := TJNotificationChannel.JavaClass.init(
StringtoJString('com.radio.one'), //CHANNEL_ID
StrToJCharSequence('Public radio Channel'),
TJNotificationManager.JavaClass.IMPORTANCE_DEFAULT
);
Obj := TAndroidHelper.Context.getSystemService(
TJContext.JavaClass.NOTIFICATION_SERVICE);
NotificationManager := TJNotificationManager.Wrap(Obj);
NotificationManager.createNotificationChannel(ServiceChannel);
NewIntent:= TAndroidHelper.Context.getPackageManager().getLaunchIntentForPackage(
TAndroidHelper.Context.getPackageName());
NewIntent.setAction(TJIntent.JavaClass.ACTION_MAIN);
NewIntent.addCategory(TJIntent.JavaClass.CATEGORY_LAUNCHER);
NewIntent.addFlags(TJIntent.JavaClass.FLAG_ACTIVITY_NEW_TASK);
PendingIntent := TJPendingIntent.JavaClass.getActivity(
TAndroidHelper.Context, 0, NewIntent,
TJIntent.JavaClass.FLAG_ACTIVITY_NEW_TASK
);
ncb := TJNotificationCompat_Builder.JavaClass.init(
TAndroidHelper.Context,
StringToJString('com.radio.one')
);
ncb.setContentTitle(StrToJCharSequence('PublicRadio Service'));
// ncb.setTicker(StrToJCharSequence('MyCommsService')); // can't remember why this is commented out to be honest
ncb.setSmallIcon(JavaService.getApplicationInfo.icon);
ncb.setContentIntent(PendingIntent);
ncb.setOngoing(True);
ntf := ncb.build;
JavaService.startForeground(StartId, ntf);
end
else
begin
//Android 7.1
serviceObjectId := (JavaService as ILocalObject).GetObjectID;
service := TJService.Wrap(serviceObjectId);
/////ntf2 := TJNotification.Create;
////ntf2.icon := service.getApplicationInfo.icon;
NewIntent:= TAndroidHelper.Context.getPackageManager().getLaunchIntentForPackage(
TAndroidHelper.Context.getPackageName());
NewIntent.setAction(TJIntent.JavaClass.ACTION_MAIN);
NewIntent.addCategory(TJIntent.JavaClass.CATEGORY_LAUNCHER);
NewIntent.addFlags(TJIntent.JavaClass.FLAG_ACTIVITY_NEW_TASK);
PendingIntent2 := TJPendingIntent.JavaClass.getActivity(
TAndroidHelper.Context, 0, NewIntent,
TJIntent.JavaClass.FLAG_ACTIVITY_NEW_TASK
);
ncb := TJNotificationCompat_Builder.JavaClass.init(
TAndroidHelper.Context,
StringToJString('com.radio.one')
);
//intent2 := TJIntent.Create;
//PendingIntent2 := TJPendingIntent.JavaClass.getActivity(service.getApplicationContext, 0, intent2, 0);
ncb.setContentTitle(StrToJCharSequence('PublicRadio'));
// ncb.setTicker(StrToJCharSequence('MyCommsService'));
ncb.setSmallIcon(JavaService.getApplicationInfo.icon);
ncb.setContentIntent(PendingIntent2);
ncb.setOngoing(True);
ntf2 := ncb.build;
ntf2.setLatestEventInfo(service.getApplicationContext, StrToJCharSequence('PublicRadio'), StrToJCharSequence('PublicRadio Service'), PendingIntent2);
service.startForeground(StartId, ntf2);
end;
end;
Source:
https://stackoverflow.com/questions/504 ... 6#50486556