[英]Should I use Service or IntentService?
我必须创建两个Android应用程序。
App1 - 从用户处获取输入消息(即“Hello World”), App2将消息打印到可通过ADB Logcat查看的控制台。 来自App1的消息应通过Intents发送到App2。 App2应该是一个服务
我不确定是否为App2使用Service
或IntentService
。 如果我为App2创建服务。 我是否可以像这样使用Implicit Intent来使用它:
Intent serviceIntent = new Intent("com.example.vinitanilgaikwad.app2");
bindService(serviceIntent, myConnection, Context.BIND_AUTO_CREATE);
你能告诉我怎么办?
我的App1有以下源代码类。
App1 : DisplayMessageActivity
public class DisplayMessageActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_display_message);
Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
fab.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Snackbar.make(view, "Replace with your own action", Snackbar.LENGTH_LONG)
.setAction("Action", null).show();
}
});
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
Intent intent = getIntent();
String message = intent.getStringExtra(MainActivity.EXTRA_MESSAGE);
TextView textView = new TextView(this);
textView.setTextSize(40);
textView.setText(message);
RelativeLayout layout = (RelativeLayout) findViewById(R.id.content);
layout.addView(textView);
Intent serviceIntent = new Intent("com.example.vinitanilgaikwad.app2");
bindService(serviceIntent, myConnection, Context.BIND_AUTO_CREATE);
startService(serviceIntent);
}
Messenger myService = null;
boolean isBound;
private ServiceConnection myConnection = new ServiceConnection() {
public void onServiceConnected(ComponentName className,
IBinder service) {
myService = new Messenger(service);
isBound = true;
}
public void onServiceDisconnected(ComponentName className) {
myService = null;
isBound = false;
}
};
@Override
public void onDestroy() {
super.onDestroy();
unbindService(myConnection);
}
public void sendMessage(View view) {
// if (!isBound) return;
Message msg = Message.obtain();
Bundle bundle = new Bundle();
bundle.putString("MyString", "Vinit");
msg.setData(bundle);
try {
myService.send(msg);
} catch (RemoteException e) {
e.printStackTrace();
}
}
}
App2具有服务实现。
App2 : MessengerService
package com.example.vinitanilgaikwad.app2;
public class MessengerService extends Service {
class IncomingHandler extends Handler {
@Override
public void handleMessage(Message msg) {
Log.i("dddsds","fsdfdsfsfs");
Bundle data = msg.getData();
String dataString = data.getString("MyString");
Toast.makeText(getApplicationContext(),
dataString, Toast.LENGTH_SHORT).show();
Log.d("Me123",dataString);
}
}
final Messenger myMessenger = new Messenger(new IncomingHandler());
@Override
public IBinder onBind(Intent intent) {
return myMessenger.getBinder();
}
}
App2 : AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.vinitanilgaikwad.app2">
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:supportsRtl="true"
android:theme="@style/AppTheme">
<activity
android:name=".MainActivity"
android:label="@string/app_name"
android:theme="@style/AppTheme.NoActionBar">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<service
android:name=".MessengerService"
>
<intent-filter>
<action android:name="com.example.vinitanilgaikwad.app2"></action>
</intent-filter>
</service>
</application>
</manifest>
仍然App1 无法连接到App2中的服务。 Adb logcat不会打印邮件。
有人可以帮忙吗? 我是Android开发的新手。
来自JoséJuanoSánchez 答案 :
Tejas Lagvankar写了一篇关于这个主题的好文章 。 以下是Service和IntentService之间的一些主要区别。
什么时候用?
该服务可用于没有UI的任务,但不应太长。 如果需要执行长任务,则必须使用Service中的线程。
IntentService可用于长任务,通常不与主线程通信。 如果需要通信,可以使用主线程处理程序或广播意图。 另一种使用情况是需要回调时(Intent触发的任务)。
怎么触发?
通过调用方法startService()
来触发服务 。
使用Intent触发IntentService ,它生成一个新的工作线程,并在此线程上调用onHandleIntent()
方法。
触发来自
运行
服务在后台运行,但它在应用程序的主线程上运行。
IntentService在单独的工作线程上运行。
限制/缺点
服务可能会阻止应用程序的主线程。
IntentService无法并行运行任务。 因此,所有连续的意图将进入工作线程的消息队列,并将按顺序执行。
什么时候停?
如果您实现了服务 ,则通过调用stopSelf()
或stopService()
,您有责任在其工作完成后停止服务。 (如果您只想提供绑定,则不需要实现此方法)。
IntentService在处理完所有启动请求后停止服务,因此您永远不必调用stopSelf()
。
如果Activity或其他组件想要与服务通信,则可以使用LocalBroadcastManager 。 该服务可以通过活动将接收的本地广播发送消息。
阅读更多详情,这些应该可以帮助您:
正如@josemgu91所说,LocalBroadcastManager只能用于同一应用程序中的Activity和service。
我们可以通过Messenger和AIDL与其他应用程序或进程(称为IPC)进行通信。
由于使用AIDL传递数据是相当繁琐和冗长的,如果需要绑定通信,更有效的方法是使用方便的Messenger系统 ,它将绑定器包装成更易于使用的Handler对象。
阅读更多:
您应该在App2中使用Service
。
使用IntentService
的唯一原因是在UI线程以外的线程上执行工作。 根据您的帖子,您的要求是进程间通信,而不是工作线程。 ...所以你应该只使用一个Service
。
如果您只向App2发送信息(不期望返回),则也没有理由bind
其服务。 只需使用:
Intent svc = new Intent();
svc.setComponent(new ComponentName(
"com.wicked.cool.apps.app2", // App2's package
"com.wicked.cool.apps.app2.svc.App2Service")); // FQN of App2's service
svc.setStringExtra(STUFF_KEY, someStuff);
startService(svc)
...从App1向App2发起一个意图。
无需意图过滤器,广播管理器,IntentServices或Messengers。
(修改为添加明确的意图)
你想做什么样的任务? IntentService和Service都可以像你想要的那样处理Intent。 IntentService是一种特殊的服务,当接收到Intent然后在另一个线程中执行任务然后自行停止时。 如果你想做一个简单的一次性任务,那么你可以使用它。 另一方面,服务仍然有效,具体取决于您执行它的方式(绑定服务或非服务服务)。 如果您想要更灵活的方法,那么您可以使用服务并在onStartCommand方法中处理Intents。 如果您想要一种更灵活的方法来处理复杂的数据类型,那么您需要在服务中使用IPC技术(Messenger或AIDL)。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.