一、看协议文档
网上资料挺少的,求人不如求己,打铁还需自身硬,啃文档是最直接的学习方式。国标28181对ptz信令这块,有确切的描述。
其实文档里已经说的很清楚了,就是一些字节方面的移位操作,当然实现方式很多种。我下面列出我实现的一种方式。
二、具体代码实现
云台请求相关接口:
bool GB28181Srv::RequestPTZ(stuDev *pDev, ePTZCmd eCmd, int iSpeed, int iSpeed2)
{
if (pDev == NULL)
return false;
QString sCmd = GetStrFromPTZCmd(eCmd, iSpeed, iSpeed2);
QString sBody;
sBody.sprintf(
"<?xml version=\"1.0\"?>\r\n"
"<Control>\r\n"
" <CmdType>DeviceControl</CmdType>\r\n"
" <SN>%d</SN>\r\n"
" <DeviceID>%s</DeviceID>\r\n"
" <PTZCmd>%s</PTZCmd>\r\n"
"</Control>\r\n"
, ++m_iRequestMessageSN, pDev->m_sDevCode.toStdString().data(), sCmd.toStdString().data());
int ret = SendRequestMessage(pDev->m_sDevCode, pDev->m_sDevIp, pDev->m_iDevPort, "Application/MANSCDP+xml", sBody);
return !ret;
}
关键部分,写的比较挫,各位看官将就看下:
QString GB28181Srv::GetStrFromPTZCmd(ePTZCmd eCmd, quint8 iSpeed, quint8 iSpeed2)
{
QString sCmd = "A50F00";
switch (eCmd)
{
case ePTZUp:
case ePTZUpStop:
sCmd += eCmd == ePTZUp ? "0800" : "0000";
sCmd += eCmd == ePTZUp ? GetHexFromInt(iSpeed) : "00";
sCmd += "00";
sCmd += eCmd == ePTZUp ? GetCrcFromPTZCmd(165 + 15 + 0 + 8 + 0 + iSpeed + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 0 + 0 + 0 + 0);
break;
case ePTZDown:
case ePTZDownStop:
sCmd += eCmd == ePTZDown ? "0400" : "0000";
sCmd += eCmd == ePTZDown ? GetHexFromInt(iSpeed) : "00";
sCmd += "00";
sCmd += eCmd == ePTZDown ? GetCrcFromPTZCmd(165 + 15 + 0 + 4 + 0 + iSpeed + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 0 + 0 + 0 + 0);
break;
case ePTZLeft:
case ePTZLeftStop:
sCmd += eCmd == ePTZLeft ? "02" : "00";
sCmd += eCmd == ePTZLeft ? GetHexFromInt(iSpeed) : "00";
sCmd += "0000";
sCmd += eCmd == ePTZLeft ? GetCrcFromPTZCmd(165 + 15 + 0 + 2 + iSpeed + 0 + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 0 + 0 + 0 + 0);
break;
case ePTZRight:
case ePTZRightStop:
sCmd += eCmd == ePTZRight ? "01" : "00";
sCmd += eCmd == ePTZRight ? GetHexFromInt(iSpeed) : "00";
sCmd += "0000";
sCmd += eCmd == ePTZRight ? GetCrcFromPTZCmd(165 + 15 + 0 + 1 + iSpeed + 0 + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 0 + 0 + 0 + 0);
break;
case ePTZUpLeft:
case ePTZUpLeftStop:
sCmd += eCmd == ePTZUpLeft ? "0A" : "00";
sCmd += eCmd == ePTZUpLeft ? GetHexFromInt(iSpeed) : "00";
sCmd += eCmd == ePTZUpLeft ? GetHexFromInt(iSpeed2) : "00";
sCmd += "00";
sCmd += eCmd == ePTZUpLeft ? GetCrcFromPTZCmd(165 + 15 + 0 + 10 + iSpeed + iSpeed2 + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 0 + 0 + 0 + 0);
break;
case ePTZUpRight:
case ePTZUpRightStop:
sCmd += eCmd == ePTZUpRight ? "09" : "00";
sCmd += eCmd == ePTZUpRight ? GetHexFromInt(iSpeed) : "00";
sCmd += eCmd == ePTZUpRight ? GetHexFromInt(iSpeed2) : "00";
sCmd += "00";
sCmd += eCmd == ePTZUpRight ? GetCrcFromPTZCmd(165 + 15 + 0 + 9 + iSpeed + iSpeed2 + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 0 + 0 + 0 + 0);
break;
case ePTZDownLeft:
case ePTZDownLeftStop:
sCmd += eCmd == ePTZDownLeft ? "06" : "00";
sCmd += eCmd == ePTZDownLeft ? GetHexFromInt(iSpeed) : "00";
sCmd += eCmd == ePTZDownLeft ? GetHexFromInt(iSpeed2) : "00";
sCmd += "00";
sCmd += eCmd == ePTZDownLeft ? GetCrcFromPTZCmd(165 + 15 + 0 + 6 + iSpeed + iSpeed2 + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 0 + 0 + 0 + 0);
break;
case ePTZDownRight:
case ePTZDownRightStop:
sCmd += eCmd == ePTZDownRight ? "05" : "00";
sCmd += eCmd == ePTZDownRight ? GetHexFromInt(iSpeed) : "00";
sCmd += eCmd == ePTZDownRight ? GetHexFromInt(iSpeed2) : "00";
sCmd += "00";
sCmd += eCmd == ePTZDownRight ? GetCrcFromPTZCmd(165 + 15 + 0 + 5 + iSpeed + iSpeed2 + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 0 + 0 + 0 + 0);
break;
case ePTZZoomIn:
case ePTZZoomInStop:
sCmd += eCmd == ePTZZoomIn ? "100000" : "000000";
sCmd += eCmd == ePTZZoomIn ? GetHexFromInt(iSpeed * 16) : "00";
sCmd += eCmd == ePTZZoomIn ? GetCrcFromPTZCmd(165 + 15 + 0 + 16 + 0 + 0 + iSpeed * 16) : GetCrcFromPTZCmd(165 + 15 + 0 + 0 + 0 + 0 + 0);
break;
case ePTZZoomOut:
case ePTZZoomOutStop:
sCmd += eCmd == ePTZZoomOut ? "200000" : "000000";
sCmd += eCmd == ePTZZoomOut ? GetHexFromInt(iSpeed * 16) : "00";
sCmd += eCmd == ePTZZoomOut ? GetCrcFromPTZCmd(165 + 15 + 0 + 32 + 0 + 0 + iSpeed * 16) : GetCrcFromPTZCmd(165 + 15 + 0 + 0 + 0 + 0 + 0);
break;
case ePTZFocusFar:
case ePTZFocusFarStop:
sCmd += eCmd == ePTZFocusFar ? "41": "40";
sCmd += eCmd == ePTZFocusFar ? GetHexFromInt(iSpeed) : "00";
sCmd += "0000";
sCmd += eCmd == ePTZFocusFar ? GetCrcFromPTZCmd(165 + 15 + 0 + 65 + iSpeed + 0 + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 64 + 0 + 0 + 0);
break;
case ePTZFocusNear:
case ePTZFocusNearStop:
sCmd += eCmd == ePTZFocusNear ? "42" : "40";
sCmd += eCmd == ePTZFocusNear ? GetHexFromInt(iSpeed) : "00";
sCmd += "0000";
sCmd += eCmd == ePTZFocusNear ? GetCrcFromPTZCmd(165 + 15 + 0 + 66 + iSpeed + 0 + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 64 + 0 + 0 + 0);
break;
case ePTZIrisIn:
case ePTZIrisInStop:
sCmd += eCmd == ePTZIrisIn ? "4400" : "4000";
sCmd += eCmd == ePTZIrisIn ? GetHexFromInt(iSpeed) : "00";
sCmd += "00";
sCmd += eCmd == ePTZIrisIn ? GetCrcFromPTZCmd(165 + 15 + 0 + 68 + 0 + iSpeed + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 64 + 0 + 0 + 0);
break;
case ePTZIrisOut:
case ePTZIrisOutStop:
sCmd += eCmd == ePTZIrisOut ? "4800" : "4000";
sCmd += eCmd == ePTZIrisOut ? GetHexFromInt(iSpeed) : "00";
sCmd += "00";
sCmd += eCmd == ePTZIrisOut ? GetCrcFromPTZCmd(165 + 15 + 0 + 72 + 0 + iSpeed + 0) : GetCrcFromPTZCmd(165 + 15 + 0 + 64 + 0 + 0 + 0);
break;
default:
break;
}
return sCmd;
}
先这样,该睡了。不懂的再联系