我只停留在Oreo +设备中2个应用之间的同步实时数据上,就像如果其他用户登录到该应用,那么它应该立即在其他应用中生效,并且也应该在其他应用中更改(例如Facebook和Facebook) Messenger,如果您从Facebook登出,它将自动从FB Messenger登出,或者,如果您登录到Facebook,那么它将自动登录FB Messenger,反之亦然)我在两个应用程序中都创建了广播接收器,并且如果一个应用程序的登录更改了,则发送广播到其他应用程序,它将完成其余工作。
我在Google上进行了搜索,发现了一些方法。
我已经阅读了这份文件
https://developer.android.com/about/versions/oreo/background
已经通过此链接
Broadcast receiver not working in oreo
Oreo: Broadcast receiver Not working
Broadcast receiver registered in manifest not getting called in Android Oreo
Receiver stopped receiving in Oreo
但是应该实现这种方式。
1)创建前台服务并将接收者注册到其中。 -这样,我需要一个运行前台服务所需的通知。而且我做不到。我无法显示不必要的通知。
2)计划的工作: -我无法使用它,因为我需要一直在后台运行服务。
到目前为止,我已经尝试过:
1)应用程序类中的注册接收者:由于上下文被杀死,应用程序被杀死后,此接收器不起作用。
2)在FireBase通知服务中注册接收器,但仅在通知到达时才初始化。
代码:
在Application类中注册接收者
ASampleActionReceiver mASampleActionReceiver = new ASampleActionReceiver();
IntentFilter filterAction = new IntentFilter();
filterAction.addAction("com.sample.example.receiver.operation");
registerReceiver(mASampleActionReceiver, filterAction);
在清单中
<receiver android:name=".receiver.ASampleActionReceiver">
<intent-filter>
<action android:name="com.sample.example.receiver.operation" />
</intent-filter>
</receiver>
意图服务将由接收方开始
<service
android:name="com.sample.example.services.SampleOperationService"
android:enabled="true"
android:exported="false" />
还有一个Receiver ASampleActionReceiver.java
public class ASampleActionReceiver extends BroadcastReceiver {
Context mContext;
@Override
public void onReceive(Context context, Intent intent) {
mContext = context;
AdoddleLog.d("LOG", intent.getExtras().getString("loginData"));
Intent mIntent = new Intent(mContext, SampleOperationService.class);
mIntent.putExtras(intent);
mContext.startService(mIntent);
}
}
请问有人可以提出更好的解决方案吗?
我可以使用AIDL进行应用通信吗?如果有任何一个应用程序处于空闲状态或未在后台运行,是否可以正常工作?
答案 0 :(得分:0)
最后,我找到了解决方法,我想发表详细的答案。
我使用AIDL在2个应用之间共享数据
在Both应用程序中,使用相同的包名称创建AIDL文件,例如com.common.app,并在其中创建一个辅助文件。
// IRemoteService.aidl
package com.common.app;
// Declare any non-default types here with import statements
interface IRemoteService {
void onReceive(String data);
}
在两个应用程序中,都需要创建意图服务SampleOperationService.java,它将在从另一个应用程序接收数据后完成其余工作。您可以改用JobIntentService。
public class SampleOperationService extends IntentService{
private String DEBUG_LOG = "SampleOperationService";
/**
* Creates an IntentService. Invoked by your subclass's constructor.
*/
public SampleOperationService() {
super("SampleOperationService Service");
}
@Override
protected void onHandleIntent(@Nullable Intent intent) {
//here you will get data in intent extra, in "data" key, Which is send from another app. You can do rest of work here
}
}
在“两个应用程序”中,创建服务都不需要添加相同的程序包,例如aidl。它包含一个服务绑定程序,该服务绑定程序扩展了AIDL Stub。在这里您将从其他应用程序获取数据。
public class RemoteService extends Service {
@Override
public IBinder onBind(Intent intent) {
return (new RemoteServiceBinder());
}
private class RemoteServiceBinder extends IRemoteService.Stub {
@Override
public void onReceive(String data) {
Intent mIntent = new Intent(RemoteService.this, SampleOperationService.class);
mIntent.putExtra("data", data); // you will get data from the second app
startService(mIntent);
}
}
}
Manifest.xml
对于第一个应用
<service
android:name="com.firstapp.app.service.SampleOperationService"
android:enabled="true"
android:exported="false" />
<service android:name="com.firstapp.app.RemoteService"> // this is service
<intent-filter>
<action android:name="com.common.app.IRemoteService" />// this is the path of aidl file
</intent-filter>
</service>
对于第二个应用
<service
android:name="com.secondapp.app.service.SampleOperationService"
android:enabled="true"
android:exported="false" />
<service android:name="com.secondapp.app.RemoteService">
<intent-filter>
<action android:name="com.common.app.IRemoteService" />// this is the path of aidl file which will on same place for both app
</intent-filter>
</service>
数据传递:
在Both应用程序中,我们需要绑定远程服务。
如果是Activity,请在onCreate中绑定服务
public class SampleActivity extends AppCompatActivity implements ServiceConnection {
private IRemoteService bindingRemoteService;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_login);
bindRemoteService();
}
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
bindingRemoteService = IRemoteService.Stub.asInterface(service);
}
@Override
public void onServiceDisconnected(ComponentName name) {
bindingRemoteService = null;
}
private void bindRemoteService() {
Intent implicit = new Intent(IRemoteService.class.getName());
List<ResolveInfo> matches = getPackageManager()
.queryIntentServices(implicit, 0);
for (ResolveInfo mResolveInfo : matches) {
if (mResolveInfo.serviceInfo.packageName.equalsIgnoreCase("com.secondapp.app")) {// for second app it will be "com.firstapp.app"
Intent explicit = new Intent(implicit);
ServiceInfo svcInfo = mResolveInfo.serviceInfo;
ComponentName cn = new ComponentName(svcInfo.applicationInfo.packageName,
svcInfo.name);
explicit.setComponent(cn);
getApplicationContext().bindService(explicit, this, Context.BIND_AUTO_CREATE);
break;
}
}
}
}
这里只是绑定其他应用程序服务。因此它不会接收数据 相同的应用。并出于安全目的将服务绑定到特定的软件包
向其他应用发送数据
public void sendDataToOtherApp(){
if (bindingRemoteService != null) {
try {
HashMap map = new HashMap();
map.put("data", data);// data will be string
bindingRemoteService.onReceive(new Gson().toJson(map));
} catch (RemoteException e) {
e.printStackTrace();
}
}
}
数据将在另一个应用程序的 RemoteService 中接收。