我正在使用Android网站上的蓝牙聊天示例应用。我想传递完整的传入消息,(下面的代码中包含的消息格式,因为这个网站正在解析我的消息,这也是我在代码中的工作,一个删除标签并提取消息名称和值的函数,使用它进行进一步的操作。readMessage
字符串(在切换案例中为Message_Read)发送所选字符并省略一些特殊字符。以下是蓝牙聊天应用程序(来自Android网站)的代码。
我无法以我在代码中提到的格式收到完整的消息。它以多行显示,许多字符被删除。有什么建议为什么会发生这种情况?
// The Handler that gets information back from the BluetoothChatService
private final Handler mHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case MESSAGE_STATE_CHANGE:
if(D) Log.i(TAG, "MESSAGE_STATE_CHANGE: " + msg.arg1);
switch (msg.arg1) {
case BluetoothChatService.STATE_CONNECTED:
mTitle.setText(R.string.title_connected_to);
mTitle.append(mConnectedDeviceName);
mConversationArrayAdapter.clear();
break;
case BluetoothChatService.STATE_CONNECTING:
mTitle.setText(R.string.title_connecting);
break;
case BluetoothChatService.STATE_LISTEN:
case BluetoothChatService.STATE_NONE:
mTitle.setText(R.string.title_not_connected);
break;
}
break;
case MESSAGE_WRITE:
byte[] writeBuf = (byte[]) msg.obj;
// construct a string from the buffer
String writeMessage = new String(writeBuf);
mConversationArrayAdapter.add("Me: " + writeMessage);
break;
case MESSAGE_READ:
byte[] readBuf = (byte[]) msg.obj;
// construct a string from the valid bytes in the buffer
String readMessage = new String(readBuf, 0, msg.arg1);
mConversationArrayAdapter.add(mConnectedDeviceName+": " + readMessage);
//Make sure there is a received message. Extract it's name and value
//int msgLen = readMessage.length();
//if( msgLen!= 0)
// Message format is <MSG><N>shiftDirection<!N><V>1<!V><!MSG>
if (readBuf.equals("<MSG><N>.*<!N><V>.*<!V><!MSG>"))
extractData(readMessage);
else mTitle.setText(R.string.floor_it);
break;
case MESSAGE_DEVICE_NAME:
// save the connected device's name
mConnectedDeviceName = msg.getData().getString(DEVICE_NAME);
Toast.makeText(getApplicationContext(), "Connected to "
+ mConnectedDeviceName, Toast.LENGTH_SHORT).show();
break;
case MESSAGE_TOAST:
Toast.makeText(getApplicationContext(), msg.getData().getString(TOAST),
Toast.LENGTH_SHORT).show();
break;
}
}
};
代码的一部分,它将输入的字节流读入缓冲区并传递缓冲区对象以供显示。
public void run() {
Log.i(TAG, "BEGIN mConnectedThread");
byte[] buffer = new byte[1024];
int bytes;
// Keep listening to the InputStream while connected
while (true) {
try {
// Read from the InputStream
bytes = mmInStream.read(buffer);
//String Incoming = new String(buffer);
//Pass "Incoming" instead of "buffer"
// Send the obtained bytes to the UI Activity
mHandler.obtainMessage(BluetoothChat.MESSAGE_READ, bytes, -1, buffer)
.sendToTarget();
} catch (IOException e) {
Log.e(TAG, "disconnected", e);
connectionLost();
break;
}
}
}
答案 0 :(得分:1)
我认为问题在于,case MESSAGE_READ:
不仅在收到完整的Packet
时被调用,如果收到一个小片段,也会调用readMessage
。因此,您应将mNewBuf += readMessage
放在单独的缓冲区(即mNewBuf
)中,检查{{1}}中是否有完整的数据包。如果是,则解析您的消息,然后清除缓冲区。它对我有用。
答案 1 :(得分:0)
if (readBuf.equals("<MSG><N>.*<!N><V>.*<!V><!MSG>"))
extractData(readMessage);
equals()
不应用正则表达式。如果您想匹配.*
,请使用java.util.regex
中的类来帮助您。答案 2 :(得分:0)
我遇到了同样的问题,我不是百分之百,这将永远有效,但我在javadoc上发现了这个:
read(byte[] b, int off, int len)
Reads up to len bytes of data from the input stream into an array of bytes.
如果您知道您期望的字节数,那么您可以尝试使用
bytes = mmInStream.read(buffer, 0, lengthYouWant);
但是,如果传入的数据长度可变,则无法使用。