(二)Kinect關節識別


基礎:添加KinectManager 組件

1)局部關節獲取(參考插件場景KinectOverlayDemo1)

要獲取局部某一關節及其位置,添加腳本JointOverlayer即可,通過Tracked joint參數可以分別獲取到相關關節位置以及坐標。

 

2)所有關節獲取(參考插件場景KinectOverlayDemo2)

 獲取所有關節,可用腳本SkeletonOverlayer

也可參考如下代碼

   /// <summary>
    /// 通過index獲取用戶的關節,並在每個關節點放置cube
    /// </summary>
    /// <param name="index"></param>
    private void GetBodyJoints(int index)
    {
        if(GetDetected())
        {
            long userId = kinectManger.GetUserIdByIndex(index);

            int jointsCount = kinectManger.GetJointCount();

            if(!isJointsCreated)
            {
                for (int i = 0; i < jointsCount; i++)
                {
                    joints.Add(Instantiate(jointGo));
                }
                isJointsCreated = true;
            }
            else
            {
                for (int i = 0; i < jointsCount; i++)
                {
                   joints[i].transform.position = kinectManger.GetJointKinectPosition(userId,i);
                   joints[i].name = i.ToString();
                }
            } 
        }
    }

 

3)交互功能(參考插件場景KinectOverlayDemo3)

交互功能即為通過手勢實現鼠標點擊功能需要InteractionManager以及HandOverlayer腳本,通過HandOverlayer/InteractionManager腳本上的參數帶texture的參數來實現抓取松開等樣式

如果要把手的位置反應到UI上則需要特殊處理,因為我們獲取的手的坐標單位為米,反應到unity中只是為數字(比如左手移動0.2m),但是如果分辨率為1920X1080,則手的移動0.2相對於分辨率來說幾乎為零,所以需要通過UICamera.ViewportToWorldPoint來轉化一下(或者   UICamera.ViewportToScreenPoint)下述腳本為在JointOverlayer中修改的update部分,通過獲取手移動的box(范圍),然后通過手實際位置轉換成相對坐標,然后轉化到實際分辨率下的位置。

    void Update () 
    {  
        KinectManager manager = KinectManager.Instance;
        
        if(manager && manager.IsInitialized() && foregroundCamera)
        {
            //backgroundImage.renderer.material.mainTexture = manager.GetUsersClrTex();
            if(backgroundImage && (backgroundImage.texture == null))
            {
                backgroundImage.texture = manager.GetUsersClrTex();
            }
            
            // get the background rectangle (use the portrait background, if available)
            Rect backgroundRect = foregroundCamera.pixelRect;
            PortraitBackground portraitBack = PortraitBackground.Instance;
            
            if(portraitBack && portraitBack.enabled)
            {
                backgroundRect = portraitBack.GetBackgroundRect();
            }

            // overlay the joint
            int iJointIndex = (int)trackedJoint;

            if (manager.IsUserDetected())
            {
                for (int i = 0; i < 6; i++)
                {
                    long userId = manager.GetUserIdByIndex(i);

                    //manager.IsUserTracked(userId);

                    if (manager.IsJointTracked(userId, iJointIndex))
                    {
                        //MainFunController.theController.OnDebug("Joint tracked\r\n" + GetPara(manager));

                        overlayObject.gameObject.SetActive(true);
                        Vector3 rightIboxRightBotBack = Vector3.zero, rightIboxRightTopFront = Vector3.zero, rightHandScreenPos = Vector3.zero;
                        bool isrightIboxValid = false;
                        isrightIboxValid = manager.GetRightHandInteractionBox(userId, ref rightIboxRightBotBack, ref rightIboxRightTopFront, isrightIboxValid);

                        if (isrightIboxValid && manager.GetJointTrackingState(userId, (int)KinectInterop.JointType.HandRight) != KinectInterop.TrackingState.NotTracked)
                        {
                            Vector3 rightHandPos = manager.GetJointPosition(userId, (int)KinectInterop.JointType.HandRight);

                            rightHandScreenPos.x = Mathf.Clamp01((rightHandPos.x - rightIboxRightBotBack.x) / (rightIboxRightTopFront.x - rightIboxRightBotBack.x));
                            rightHandScreenPos.y = Mathf.Clamp01((rightHandPos.y - rightIboxRightBotBack.y) / (rightIboxRightTopFront.y - rightIboxRightBotBack.y));
                            rightHandScreenPos.z = Mathf.Clamp01((rightIboxRightBotBack.z - rightHandPos.z) / (rightIboxRightBotBack.z - rightIboxRightTopFront.z));
                        }

                        Vector3 cursorTargetPos = UICamera.ViewportToWorldPoint(rightHandScreenPos);
                     
                        overlayObject.position = Vector2.Lerp(overlayObject.position, cursorTargetPos, 1f);
                        break;
                    }
                    else
                    {
                        overlayObject.gameObject.SetActive(false);
                        //MainFunController.theController.OnDebug("Joint miss");
                        //isFirstCatch = true;
                        //CollisionEvent.theEvent.OnStop();
                    }
                }
            }
            else
            {
                //debugText.text = "body miss";
            }

        }
    }

 

 

 

注:應用時建議復制此腳本,並修改名稱,然后做自己的修改


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM