新的 Android 程序员在这里。我有一个执行套接字管理和异步 I/O 的服务,我需要在它和我的应用程序中的 Activity 之间建立通信路径。
当前的方法是为服务和活动都配备广播接收器,并使用它们将“命令”意图从活动发送到服务,并将“警报”意图从服务发送到活动。
我的服务有一个可运行的,这是套接字 read() 发生的地方;当接收到数据时,runnable 会向 Service 发送一个“传入数据”意图,然后 Service 会向 Activity 发出警报:
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
super.onStartCommand(intent, flags, startId);
if (m_IsRunning == false) {
m_IsRunning = true;
(new Thread(new Runnable() {
byte[] inputBuffer = new byte[512];
public void run() {
while (m_IsRunning) {
if (m_IsConnected) {
try {
m_Nis = m_Socket.getInputStream();
m_Nis.read(inputBuffer, 0, 512);
Intent broadcast = new Intent();
Bundle bun = new Bundle();
bun.putString("ServiceCmd", "ALERT_INCOMING_DATA");
bun.putByteArray("MsgBuffer", inputBuffer);
broadcast.putExtras(bun);
broadcast.setAction(BROADCAST_TO_SERVICE);
sendBroadcast(broadcast);
} catch (IOException e) {
// Send fault to activity
}
}
}
}
})).start();
}
return START_STICKY;
}
我使用 BroadcastReceiver 的方法如下所示:
private BroadcastReceiver serviceReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
Bundle bun = intent.getExtras();
String cmdString = bun.getString("ServiceCmd");
if (cmdString.equals("CMD_SETHOSTINFO")) {
// The activity has requested us to set the host info
String hostAddr = bun.getString("HostAddressString");
int hostPort = bun.getInt("HostPortNumber");
processSetHostInfoCommand(hostAddr, hostPort);
}
else if (cmdString.equals("CMD_CONNECT")) {
// The activity has requested us to connect
if ((m_IsRunning) && (m_IsConnected == false)) {
// Attempt to connect
processConnectCommand();
}
}
else if (cmdString.equals("CMD_DISCONNECT")) {
// The activity has requested us to disconnect
if ((m_IsRunning) && (m_IsConnected == true)) {
// Attempt to disconnect
processDisconnectCommand();
}
}
else if (cmdString.equals("CMD_SENDDATA")) {
// The activity has requested us to send data
if ((m_IsRunning) && (m_IsConnected == true)) {
// Attempt to send data
byte[] msgBuffer = bun.getByteArray("MsgBuffer");
processSendDataCommand(msgBuffer);
}
}
else if (cmdString.equals("ALERT_INCOMING_DATA")) {
// Our TCP receiver thread has received data
if (m_IsRunning) {
byte[] msgBuffer = bun.getByteArray("MsgBuffer");
processIncomingDataAlert(msgBuffer);
}
}
}
};
(这些processWhatever()
方法一般都是做socket管理和数据传输。)
就像我说的,它似乎工作正常,但我想知道这是否不是使用消息和处理程序更合适的情况。
所以,具体的问题是:
在决定何时使用 BroadcastReceiver/Intents 或 Handler/Messages 时,“Android 之道”是什么?
在决定使用哪种方法时是否有任何跨线程考虑?
(而且,虽然它是题外话,最后一个问题):
- 服务是否适合做我正在尝试做的那种基于套接字的 I/O?