转载请注明出处:http://blog.youkuaiyun.com/a512337862/article/details/79281648
最近,在接触onvif协议在Android端的实现。抓了无数的包,踩了无数的坑之后,利用取巧的方式也终于实现部分的功能,主要是搜索IPC设备,获取IPC设备的一些信息:rtsp地址,音视频编解码信息,云台信息等。关于onvif协议请自行百度。
思路
这里主要是将一些需要发送的关键指令以文件的形式保存在assets中,需要时直接从assets中读取指定的文件,然后将一些关键的字符填充进去发送给服务器即可。项目的流程如下:
1.发送广播包搜索局域网内的IPC。
2.通过IPC设备的serviceUrl获取IPC的能力集。
3.获取IPC的Profiles
4.获取IPC每个Profile的rtsp
代码实现
IPC设备搜索
IPC设备搜索主要是通过UDP广播包来发送Probe请求,IPC设备收到后会返回自己的设备部分信息。
搜索代码如下:
/**
* Author : BlackHao
* Time : 2018/1/8 14:38
* Description : 利用线程搜索局域网内设备
*/
public class FindDevicesThread extends Thread {
private byte[] sendData;
private boolean readResult = false, receiveTag = true;
//回调借口
private FindDevicesListener listener;
public FindDevicesThread(Context context, FindDevicesListener listener) {
this.listener = listener;
InputStream fis = null;
try {
//从assets读取文件
fis = context.getAssets().open("probe.xml");
sendData = new byte[fis.available()];
readResult = fis.read(sendData) > 0;
} catch (Exception e) {
e.printStackTrace();
} finally {
if (fis != null) {
try {
fis.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
@Override
public void run() {
super.run();
DatagramSocket udpSocket = null;
DatagramPacket receivePacket;
DatagramPacket sendPacket;
//设备列表集合
ArrayList<Device> devices = new ArrayList<>();
byte[] by = new byte[1024 * 3];
if (readResult) {
try {
//端口号
int BROADCAST_PORT = 3702;
//初始化
udpSocket = new DatagramSocket(BROADCAST_PORT);
udpSocket.setSoTimeout(4 * 1000);
udpSocket.setBroadcast(true);
//DatagramPacket
sendPacket = new DatagramPacket(sendData, sendData.length);
sendPacket.setAddress(InetAddress.getByName("239.255.255.250"));
sendPacket.setPort(BROADCAST_PORT);
//发送
udpSocket.send(sendPacket);
//接受数据
receivePacket = new DatagramPacket(by, by.length);