OpenNI 人体姿势识别

OpenNI简介

OpenNI (开放自然交互)是一个多语言,跨平台的框架,利用符合OpenNI标准的API进行编程,可以使我们与传感器和中间层的具体实现细节相脱离,同时OpenNI也允许我们获取和控制传感器层的数据。

OpenNI的中间件层是实现人体姿态的算法层,目前PrimeSense的NITE(Nature Interacte tecnoligy for End-User)提供了OpenNI标准规定的部分算法。

OpenNI使用分类器的设计概念,把传感器采集的数据逐层向上处理,产生更有用的数据。举例来说传感器采集的 原始数据---经过DepthGenerator-->产生DepthMap--经过GestureGenerator-->产生手势。

详细概念参考OpenNI文档。

程序简介

通过跟踪人的右手平移动作来控制下图中3D立方体的左右旋转。图中比较难看的小人用于显示被跟踪的人头,肩膀,肘和手的位置。程序只跟踪一个人,因为要显示多个人有点麻烦,跟踪一个更能直观的验证OpenNI各API的用法。

用法: 程序启动后,摆出Psi姿势,也就是图中小人的姿势:双手举起(缴枪投降的姿势),当图中的小人开始动时,说明已经被传感器跟踪了, 然后把右手伸出一定距离左右移动来控制立方体的左右旋转。功能比较简单,不过还是挺有意思的,有3D传感器的童鞋可以试试。

运行要求:

3D传感器(PrimeSense或Kinect)

OpenNI SDK

VS2010

代码说明

源代码在我空间里,点击下载

源代码中一个比较重要的类是UserTracker, 它封装了OpenNI的UserGenerator, 通过调用UserGenerator的SkeletonCapability的接口来跟踪人员,当有人进入传感器的可视区域后,开始寻找控制者--检测他是否摆出Psi姿势(可以换成其他的手势,不过这个调用起来比较方便。)。

        void userGenerator_NewUser(object sender, NewUserEventArgs e)
        {
            UserInfo user = new UserInfo() { ID = e.ID };
            userDict.Add(e.ID, user);
            //userGenerator.SkeletonCapability.StartTracking(e.ID);
            if(currentUser == -1)
                poseCap.StartPoseDetection("Psi", e.ID);
        }

当检测到被跟踪者摆出Psi姿势后,强制对他的骨骼进行校准。

	void poseCap_PoseDetected(object sender, PoseDetectedEventArgs e)
        {
            poseCap.StopPoseDetection(e.ID);
            if (currentUser == -1)
            {
                currentUser = e.ID;
                skeletonCap.RequestCalibration(e.ID, true);
            }
        }

校准成功后,开始跟踪该对象,并把他的骨骼位置信息发送给所有的观察者。

	void SkeletonCapability_CalibrationComplete(object sender, CalibrationProgressEventArgs e)
        {
            if (e.Status == CalibrationStatus.OK)
            {
                skeletonCap.StartTracking(e.ID);
            }
            else
            {
                poseCap.StartPoseDetection("Psi", e.ID);
            }

        }
        private void SkeletonThreadFunc()
        {
            while (bRunning)
            {
                try
                {
                    context.WaitAndUpdateAll();
                }
                catch (Exception)
                {
                }

                int[] userIDs = userGenerator.GetUsers();
                foreach (int i in userIDs)
                {
                    if (skeletonCap.IsTracking(i) && i == currentUser)
                    {
                        UpdateUser(i);
                    }
                }
         }
        }

主窗口的代码比较简单,就是接受UserTracker的位置信息,然后调整几个图形的位置,如果发现右手伸出一定距离,并开始左右移动,根据手的移动量进行旋转立方体。

  • 0
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值