【C#】UDP接收摄像头PTZ数据并解析

前言

        最近遇到一个需求,需要同步摄像机画面并在摄像机画面上叠加虚拟图像,有点虚拟演播室的需求。于是对摄像头Free-D协议传回的UDP协议进行解析。

参考文献

FreeD协议说明

大佬文章

设备和环境

硬件:Lumens VC-H717KN

Visual Studio(数据接收)

摄像机设置

按照说明书捣鼓捣鼓(不同摄像机设置不一样)

Lumens的话,通讯笔者的话,关闭NDI才能接收到FreeD协议传输的数据。不知道为什么会冲突,官方没说明。

UDP获取PTZ数据

UDP直接采集的数据是29字节的十六进制数据。

数据包一共有 29字节 (尖括号的内容为一字节), 包括了摄像机的八个参数数据,这八个参数主要包括摄像机的六个外部参数和两个内部参数。外部的六个参数为:摄像机的空间位置( x,y,z),摄像机自身水平(pan)、垂直(tilt)和自身旋转 (roll)的数值。内部两个参数包括摄像机镜头的缩放(zoom)和对焦(focus)数值。

<D1> 消息类型
<CA> 摄像机 ID
<PH><PM><PL> 水平 Pan 角度
<TH><TM><TL> 垂直 Tilt 角度
<RH><RM><RL> 旋转 Roll 角度
<XH><XM><XL> 摄像机的 X 坐标
<YH><YM><YL> 摄像机的 Y 坐标
<HH><HM><HL> 摄像机的 H 坐标 (Z 坐标)
<ZH><ZM><ZL> 缩放(zoom)数值
<FH><FM><FL> 对焦时的焦点(focus)数值
<SH><SL> 由用户保留,以做它用
<CK> 校验位

我们主要解析的是第三和第四项数据。

B.2 摄像机平移角度

摄像机平移角度定义为 Y 轴与摄像机光轴在水平 (XY) 平面上的投影之间的角度。零值

对应于相机在正 Y 方向上看和一个正值

表示向右平移(即从以上)。

该值以度数表示为 24 位二进制补码有符号数,其中最高有效位(位 23)是符号位,接下来的 8 位(位 22 到 15)是

整数部分和其余位(位 14 到 0)是小数部分;或者,

这可以被认为是一个以 1/32768 度为单位的有符号整数值。值的范围是从 -180.0 度(A60000 hex)到 +180.0 度(5A0000 hex)。

以水平Pan角度解析为例:

我测试过:直接按照官方解析会存在一定的偏差。

然后我就根据寻找规律,如下:

        //将三位十六进制合并成一个完整的十六进制数
         //转成2进制数,第0位为符号位 1表示正数 0表示负数  1010 1010 1111 1111 1111 1111
        //负数直接转十进制除于32768                     0101 0101 0000 0000 0000 0000
        //正数去除符号位 得补码后转十进制除于32768       0011 0001 0011 0011 0011

具体实现,默认得到UDP中的三字节Pan的十六进制数据。

        static void Main(string[] args)
        {
            int[] num1 = DecToBin(170);
            int[] num2 = DecToBin(255);
            int[] num3 = DecToBin(255);

            int[] binSlice = SpliceBin(num1, num2, num3);
            //判断符号位正负  
            if (binSlice[0] == 0)
            {
                double num = BinToDec(binSlice);
                Console.Write(-num);
            }
            else
            {
                //补码
                for (int i = 0; i < 24; i++)
                {
                    binSlice[i] = binSlice[i] == 0 ? 1 : 0;
                }
                int len = binSlice.Length;
                binSlice[len - 1] += 1;
                for (int i = 0; i < len; i++)
                {
                    if (binSlice[len - 1 - i] > 1)
                    {
                        binSlice[len - 1 - i] = 0;
                        binSlice[len - i] += 1;
                    }
                }


                double num = BinToDec(binSlice);
                Console.Write(num);
            }
        }
       

        /// <summary>
        /// 拼接三个二进制数据
        /// </summary>
        /// <returns>返回一个二十四位的二进制数据</returns>     
        static int[] SpliceBin(int[] bin1, int[] bin2, int[] bin3)
        {
            int[] bin = new int[24];
            for (int i = 0; i < 8; i++)
            {
                bin[i] = bin1[i];
            }
            for (int i = 0; i < 8; i++)
            {
                bin[i + 8] = bin2[i];
            }
            for (int i = 0; i < 8; i++)
            {
                bin[i + 16] = bin3[i];
            }
            return bin;
        }

        /// <summary>
        /// 十进制转八位的二进制 以二进制倒序数组返回
        /// </summary>
        /// <param name="value"></param>
        /// <returns></returns>
        static int[] DecToBin(int value)
        {
            int temp = value;
            int index = 0;
            int[] tempInt = new int[8];
            int[] result = new int[8];

            while (temp > 0)
            {
                tempInt[index] = temp % 2;
                temp /= 2;
                index++;
            }

            for (int i = 0; i < 8; i++)
            {
                result[i] = tempInt[7 - i];
            }


            return result;


        }

        /// <summary>
        /// 二进制转十进制
        /// </summary>
        /// <param name="value"></param>
        /// <returns></returns>
        static double BinToDec(int[] value)
        {
            int num = 0;
            for (int i = 0; i < value.Length; i++)
            {
                num += (int)(value[i] * Math.Pow(2, 23 - i));
            }


            return (float)num / 32768;
        }

猜你喜欢

转载自blog.csdn.net/weixin_44263579/article/details/126142636
今日推荐