Service作为Android四大组件之一,一直默默无闻的在后台保证程序能正常运作。按照Google的定义,Service能在后台执行长时间的运行操作而不使用用户界面,它与后台线程的区别是它是整个程序的一部分,比如说Activity在运行的同时需要播放一些音乐,这完全可以通过开启一个后台线程来完成;但想要在应用进入后台运行时依然能播放音乐,则必须使用Service来完成了。
用户感知Service只能通过其弹出的Toast或者在通知栏的常驻通知,如果Service想向用户发送消息,除了以上这两项,就只能通过与Activity的通信来间接完成了。因此,我将平常看到的一些通信方式记录下来,以便以后学习和使用。
一、Activity绑定Service并调用Service中的方法
这是最简单最常用的方法,Activity通过Intent向服务发送消息并绑定,同时通过IBinder拿到Service的引用调用其公开的方法。
public class MyService extends Service {
private static final String TAG = "MyService";
public List<String> data = new ArrayList<>();
public MyService() {
data.add("This is some msg from " + TAG);
}
public class LocalBinder extends Binder {
MyService getService() {
return MyService.this;
}
List<String> getData() {
return data;
}
}
private final IBinder localBinder = new LocalBinder();
@Override
public IBinder onBind(Intent intent) {
String s = intent.getStringExtra("data");
Log.i(TAG,"onBind: 接收 " + s);
data.add(s);
return localBinder;
}
}
public class MainActivity extends AppCompatActivity {
private static final String TAG = "MainActivity";
private MyService mService;
private List<String> mData;
private boolean mBound = false;
private TextView textView;
private ServiceConnection serviceConnection = new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName name,IBinder service) {
Log.i(TAG,"onServiceConnected: ComponentName = " + name);
mService = ((MyService.LocalBinder) service).getService();
mData = ((MyService.LocalBinder) service).getData();
mBound = true;
}
@Override
public void onServiceDisconnected(ComponentName name) {
mService = null;
mBound = false;
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
textView = (TextView) findViewById(R.id.textView);
}
public void getData(View v) {
if (mBound) {