/*
*
*destPos, int length)
src:源数组;
srcPos:源数组要复制的起始位置;
dest:目的数组;
destPos:目的数组放置的起始位置;
length:复制的长度.
*/
public static void arraycopy(Object src, int srcPos, Object dest, int destPos, int length)
public static int bytesToInt(byte[] date, int start) {
if (date.length < start + 4) {
return 0;
}
return date[start] & 0xFF
| date[(start + 1)] << 8 & 0xFF00
| date[(start + 2)] << 16 & 0xFF0000
| date[(start + 3)] << 24 & 0xFF000000;
}
public static long bytesToLong(byte[] byteNum, int start) {
long l2;
if (byteNum.length < start + 8) {
l2 = 0L;
return l2;
}
long l1 = 0L;
int i = start;
for (; ; ) {
l2 = l1;
if (i >= start + 8) {
break;
}
l1 = l1 << 8 | byteNum[i] & 0xFF;
i += 1;
}
return l2;
}
public static byte[] longToBytes(long num) {
byte[] byteNum = new byte[8];
int i = 0;
while (i < 8) {
int offset = 64 - (i + 1) * 8;
byteNum[i] = ((byte) (int) ((num >> offset) & 0xFF));
//byteNum[i] = ((byte) (int) (num >> 64 - (i + 1) * 8 & 0xFF));
i += 1;
}
return byteNum;
}
public static String bytesToString(byte[] data, int start, int lenth) {
if (data == null) {
return null;
}
String str = "";
try {
str = new String(data, start, lenth, "utf-8");
int pos = str.indexOf(0);
if (pos > 0) {
str = str.substring(0, str.indexOf(0));
}
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
return str;
}
private static String fromBytes(byte[] buffer, int length) {
if (null == buffer) {
return "";
}
StringBuilder sb = new StringBuilder();
for (int i = 0; i < length; i++) {
String tempString = Integer.toHexString(0xFF & buffer[i]);
if (tempString.length() < 2) {
sb.append("0");
}
sb.append(tempString.toUpperCase());
if (i != length - 1) {
sb.append(" ");
}
}
return sb.toString();
}
private static String fromBytes(byte[] buffer, int start, int length) {
if (null == buffer) {
return "";
}
StringBuilder sb = new StringBuilder();
for (int i = 0; i < length; i++) {
String tempString = Integer.toHexString(0xFF & buffer[start + i]);
if (tempString.length() < 2) {
sb.append("0");
}
sb.append(tempString.toUpperCase());
if (i != length - 1) {
sb.append(" ");
}
}
return sb.toString();
}
比如我们一个完整的数据帧的结构是这样的。
字节 | 内容 | 说明 |
---|---|---|
0-3 | type | 数据类型 |
4-7 | sub_type | 数据子类型 |
8-11 | sub_type1 | 数据子类型(保留) |
12-15 | len | 数据长度 |
16-N | data | 数据内容 |
帧头:A1FF1AFF 帧尾:1AFFA1FF (帧头,帧尾,不包含在数据长度中)
比如要传递音乐的信息。音乐信息media(type = 0x13,subType = 0x03)的帧结构如下:
id | name | byte | meaning |
---|---|---|---|
1 | index | 4 | 位置 |
2 | type | 4 | 类 型 |
3 | id | 4 | id |
4 | title | 128 | 音乐 ID3 title |
5 | album | 128 | 专辑名 |
6 | artist | 128 | 歌手 |
7 | name | 128 | 文件名 |
音乐列表ListMedia帧组成(type = 0x03,sybType = 0x02)
id | name | byte | meaning |
---|---|---|---|
1 | start | 4 | 开始位置 |
2 | count | 4 | 条数 |
3 | media | 同media帧组成 |
具体的Java代码如下:
//media数据帧封装
public class MediaMetaData implements DataBase {
public static int bytesTotal = 524;
public int index;
public int type;
public int id;
public String title;
public String album;
public String artist;
public String name;
public int mSubType = 0x03;
public int mType = 0x13;
public void getDataFromBytes(byte[] data) {
this.index = Utils.bytesToInt(data, 0);
this.type = Utils.bytesToInt(data, 4);
this.id = Utils.bytesToInt(data, 8);
this.title = Utils.bytesToString(data, 12, 128);
this.album = Utils.bytesToString(data, 140, 128);
this.artist = Utils.bytesToString(data, 268, 128);
this.name = Utils.bytesToString(data, 396, 128);
}
public byte[] toBytes() {
byte[] data = new byte[bytesTotal];
System.arraycopy(Utils.intToBytes(index), 0, data, 0, 4);
System.arraycopy(Utils.intToBytes(type), 0, data, 4, 4);
System.arraycopy(Utils.intToBytes(id), 0, data, 8, 4);
if (title == null) {
title = "";
}
if (album == null) {
album = "";
}
if (artist == null) {
artist = "";
}
if (name == null) {
name = "";
}
byte[] title128 = new byte[128];
byte[] titleBytes = title.getBytes();
if (titleBytes.length <= 128) {
System.arraycopy(titleBytes, 0, title128, 0, titleBytes.length);
} else {
System.arraycopy(titleBytes, 0, title128, 0, 128);
}
System.arraycopy(title128, 0, data, 12, 128);
title128 = new byte[128];
titleBytes = this.album.getBytes();
if (titleBytes.length <= 128) {
System.arraycopy(titleBytes, 0, title128, 0, titleBytes.length);
} else {
System.arraycopy(titleBytes, 0, title128, 0, 128);
}
System.arraycopy(title128, 0, data, 140, 128);
title128 = new byte[128];
titleBytes = this.artist.getBytes();
if (titleBytes.length <= 128) {
System.arraycopy(titleBytes, 0, title128, 0, titleBytes.length);
} else {
System.arraycopy(titleBytes, 0, title128, 0, 128);
}
System.arraycopy(title128, 0, data, 268, 128);
title128 = new byte[128];
titleBytes = this.name.getBytes();
if (titleBytes.length <= 128) {
System.arraycopy(titleBytes, 0, title128, 0, titleBytes.length);
} else {
System.arraycopy(titleBytes, 0, title128, 0, 128);
}
System.arraycopy(title128, 0, data, 396, 128);
return data;
}
public byte[] toSendByte() {
return (byte[]) Utils.toSendBytes(this.mType, this.mSubType, toBytes());
}
public String toString() {
return "index=" + this.index + ",type=" + this.type + ",id=" + this.id + ",name=" + this.name;
}
//mediaList数据帧封装
public class MediaList implements DataBase {
public static int bytesTotal = 532;
public int start = 1;
public int count = 1;
public List<MediaMetaData> medias = new ArrayList();
private int subType = 0x02;
private int type = 0x03;
public void getDataFromBytes(byte[] data) {
this.start = Utils.bytesToInt(data, 0);
this.count = Utils.bytesToInt(data, 4);
int i = 0;
//循环遍历所有的数据
while (i < this.count) {
MediaMetaData Meta = new MediaMetaData();
byte[] mediadData = new byte[MediaMetaData.bytesTotal];
System.arraycopy(data, MediaMetaData.bytesTotal * i + 8, mediadData, 0, MediaMetaData.bytesTotal);
Meta.getDataFromBytes(mediadData);
this.medias.add(Meta);
i += 1;
}
}
public byte[] toBytes() {
byte[] data = new byte[this.medias.size() * MediaMetaData.bytesTotal + 8];
System.arraycopy(Utils.intToBytes(this.start), 0, data, 0, 4);
System.arraycopy(Utils.intToBytes(this.count), 0, data, 4, 4);
int i = 0;
while (i < this.medias.size()) {
System.arraycopy(((MediaMetaData) this.medias.get(i)).toBytes(), 0, data, MediaMetaData.bytesTotal * i + 8, MediaMetaData.bytesTotal);
i += 1;
}
return data;
}
public byte[] toSendByte() {
return Utils.toSendBytes(this.type, this.subType, toBytes());
}
public String toString() {
String str = "";
int i = 0;
while (i < this.medias.size()) {
str = str + "," + ((MediaMetaData) this.medias.get(i)).name;
i += 1;
}
return "musics =" + str;
}
}
// 完整帧组成
public static byte[] toSendBytes(int type, int subType, byte[] data) {
int allLength = byteHead.length + 4 + 4 + 4 + 4 + data.length + byteTail.length;
int dataLength = data.length;
byte[] subType1 = new byte[4];
byte[] sendData = new byte[allLength];
System.arraycopy(byteHead, 0, sendData, 0, 4);
System.arraycopy(intToBytes(type), 0, sendData, 4, 4);
System.arraycopy(intToBytes(subType), 0, sendData, 8, 4);
System.arraycopy(subType1, 0, sendData, 12, 4);
System.arraycopy(intToBytes(dataLength), 0, sendData, 16, 4);
System.arraycopy(data, 0, sendData, 20, dataLength);
System.arraycopy(byteTail, 0, sendData, dataLength + 20, 4);
return sendData;
}
主要是用System.arraycopy来截取字节数组,重新组合或者重新分离。