我尝试实现Android AIDL通信策略 . 我有活动和服务 . 我的活动可以成功"talk"到我的服务,但反向过程似乎不起作用 .
总而言之,当Activity和Service在不同的进程中运行时,它们无法共享任何数据抛出 IBinder
接口 . 所以 onServiceConnected()
方法接收一个AIDL接口 . 此接口在服务端实现,旨在使用(称为)活动端 . 我使用这个界面 register()
另一个AIDL . 这个新的AIDL实现了Activity-side,并通过AIDL接口称为Service-side . 它就像一个倾听者 . 不幸的是,这个新的AIDL的方法似乎没有被调用 .
由于 AndroidManifest.xml
中的以下行,服务在其自己的进程中运行:
AndroidManifest.xml
<service android:name=".DemoService" android:process=":DemoServiceProcess" />
我有2个AIDL文件,一个知道另一个 .
IAidlActivity.aidl
package app.test.aidldemo;
interface IAidlActivity {
void publish(int count);
}
IAidlService.aidl
package app.test.aidldemo;
import app.test.aidldemo.IAidlActivity;
interface IAidlService {
void startCounter();
void register(IAidlActivity activity);
}
该服务实现 onBind()
并运行一个负责递增计数器的处理程序 .
DemoService.java
package app.test.aidldemo;
import [...]
public class DemoService extends Service
{
protected IAidlActivity aidlActivity;
@Override
public IBinder onBind(Intent intent)
{
return new IAidlService.Stub() {
@Override
public void startCounter() {
DemoService.this.startJob();
}
@Override
public void register(IAidlActivity activity) {
DemoService.this.aidlActivity = activity;
}
};
}
public void startJob() {
final Handler handler = new Handler();
handler.post(new Runnable() {
protected int count = 0;
@Override
public void run() {
if (count < 500) {
count++; // increment counter
try { // then publish it to view
DemoService.this.aidlActivity.publish(count); // interface, implemented activity-side
} catch (RemoteException e) {}
handler.postDelayed(this, 2000); // 2sec.
}
}
});
}
}
活动仅包含TextView . 它开始与服务绑定并不时更新视图 . 当调用 publish()
时,它也应该更新视图 . 但这不会发生 .
MainActivity.java
package app.test.aidldemo;
import [...]
public class MainActivity extends Activity {
protected TextView view;
protected ServiceConnection connection;
@Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
view = new TextView(this);
setContentView(view);
appendToView("Let's go!");
connection = new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
IAidlService aidlService = IAidlService.Stub.asInterface(service);
appendToView("IAidlService accessed");
IAidlActivity.Stub aidlActivity = new IAidlActivity.Stub() {
@Override
public void publish(int count) {
appendToView("*** Hey, new count is: " + count + "!! ***");
}
};
appendToView("IAidlActivity created");
try {
aidlService.register(aidlActivity);
aidlService.startCounter(); // interface, implemented service-side
}
catch (RemoteException e) { appendToView(e.toString()); }
}
@Override
public void onServiceDisconnected(ComponentName name) {}
};
Intent intent = new Intent(MainActivity.this, DemoService.class);
bindService(intent, connection, Context.BIND_AUTO_CREATE);
}
@Override
public void onDestroy() {
unbindService(connection);
super.onDestroy();
}
public void appendToView(String text) {
view.append(text + "\n");
}
}
我也尝试了一些变化,如:
-
将
appendToView("*** Hey...
运行到runOnUiThread()
-
使用另一个处理程序延迟
bindService()
postDelayed()
我的后备技术是只使用IAidlService并且有一个"watcher"活动端来不断检查计数器 . 但我宁愿理解为什么它不起作用,以及使用AIDL的正确方法是什么 .
2 回答
摘要
2个陈述要改变 .
DemoService.java
MainActivity.java
我用同样的方式做了 . 我能够注册活动实例 .
在
DemoService.java
.但是在调用下面的代码
你能帮我解决这个问题吗?