class MyService : Service(){
class MyBinder : Binder(){
fun funA(arg: Int){
}
}
override fun onBind(p0: Intent?): IBinder? {
return MyBinder()
}
}
val connection: ServiceConnection = object : ServiceConnection{
override fun onServiceConnected(p0: ComponentName?, p1: IBinder?) {
serviceBinder = p1 as MyService.MyBinder
}
override fun onServiceDisconnected(p0: ComponentName?) {
}
}
serviceBinder.funA()
class MyService : Service(){
lateinit var messenger: Messenger
internal class IncomingHandler(
context : Context,
private val applicationContext: Context = context.applicationContext
) : Handler(Looper.getMainLooper()){
override fun handleMessage(msg: Message) {
when(msg.what) {
10 -> Toast.makeText(applicationContext, "${msg.obj}", Toast.LENGTH_SHORT).show()
20 -> Toast.makeText(applicationContext, "${msg.obj}", Toast.LENGTH_SHORT).show()
else -> super.handleMessage(msg)
}
}
}
override fun onBind(p0: Intent?): IBinder? {
messenger = Messenger(IncomingHandler(this))
return messenger.binder
}
}
class MainActivity : AppCompatActivity() {
lateinit var messenger: Messenger
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val intent = Intent(this, MyService::class.java)
bindService(intent, connection, Context.BIND_AUTO_CREATE)
}
val connection : ServiceConnection = object : ServiceConnection {
override fun onServiceConnected(p0: ComponentName?, p1: IBinder?) {
messenger = Messenger(p1)
}
override fun onServiceDisconnected(p0: ComponentName?) {
}
}
}
val msg = Message()
msg.what = 10
msg.obj = "hello"
messenger.send(msg)
<service>
에 intent-filter가 적용되어 있어야 한다.<queries>
를 통해 패키지 공개 상태를 적용해야 한다. <queries>
<package android:name="com.example.test_outter"/>
</queries>
val intent = Intent("ACTION_OUTER_SERVICE")
intent.setPackage("com.example.test_outter")
bindService(intent, connection, Context.BIND_AUTO_CREATE)
val bundle = Bundle()
bundle.putString("data1", "hello")
val msg = Message()
msg.what = 10
msg.obj = bundle
messenger.send(msg)
AIDL(Android Interface Definition Language)
두 프로세스 간 데이터를 주고받는 프로세스 간 통신을 구현할 때 사용하는 기법으로 bindService() 함수를 사용한다.
메신저 대비 AIDL 의 장점
interface IMyAidlInterface {
void funA(String data);
int funB();
}
class MyService : Service() {
override fun onBind(intent: Intent): IBinder {
return object : IMyAidlInterface.Stub(){
override fun funA(data: String?) {
}
override fun funB(): Int {
return 10
}
}
}
}
<service
android:name=".MyService"
android:enabled="true"
android:exported="true">
<intent-filter>
<action android:name="ACTION_AIDL_SERVICE"/>
</intent-filter>
</service>
class MainActivity : AppCompatActivity() {
lateinit var aidlService: IMyAidlInterface
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val intent = Intent("ACTION_AIDL_SERVICE")
intent.setPackage("com.example.test_outter")
bindService(intent, connection, Context.BIND_AUTO_CREATE)
}
val connection: ServiceConnection = object : ServiceConnection{
override fun onServiceConnected(p0: ComponentName?, p1: IBinder?) {
aidlService = IMyAidlInterface.Stub.asInterface(p1)
}
override fun onServiceDisconnected(p0: ComponentName?) {
}
}
}
aidlService.funA("hello")