Unity Kinect应用

Kinect Manager

KinectManager:脚本说明

 

属性:

[Tooltip("离地面有多高的传感器(单位:米)。")]

    public float sensorHeight = 1.0f;

 

    [Tooltip("Kinect仰角(度)。可能是积极的还是消极的。")]

    public float sensorAngle = 0f;

 

    public enum AutoHeightAngle : int { DontUse, ShowInfoOnly, AutoUpdate, AutoUpdateAndShowInfo }

    [Tooltip("是否自动设置传感器高度和角度。用户必须在前面的传感器,为了自动检测工作。")]

    public AutoHeightAngle autoHeightAngle = AutoHeightAngle.DontUse;

 

    public enum UserMapType : int { None, RawUserDepth, BodyTexture, UserTexture, CutOutTexture }

    [Tooltip("是否以及如何利用用户和深度地图。")]

    public UserMapType computeUserMap = UserMapType.RawUserDepth;

 

    [Tooltip("是否利用彩色摄像机图像。")]

    public bool computeColorMap = false;

 

    [Tooltip("是否利用红外摄像机的图像。")]

    public bool computeInfraredMap = false;

 

    [Tooltip("是否显示屏幕上的用户映射。")]

    public bool displayUserMap = false;

 

    [Tooltip("是否显示彩色摄像机图像在屏幕上。")]

    public bool displayColorMap = false;

 

    [Tooltip("是否显示用户地图上骨架线。")]

    public bool displaySkeletonLines = false;

 

    // 如果百分比是零,这是计算内部以匹配所选的深度图像的宽度和高度

    [Tooltip("深度和宽度彩色图像在屏幕上,相机宽度的百分比。图像高度取决于计算宽度。")]

    public float DisplayMapsWidthPercent = 20f;

 

    [Tooltip("是否要使用多源阅读器,如果有可用的(K2-only特性)。")]

    public bool useMultiSourceReader = false;

 

    // Public Bool to determine whether to use sensor's audio source, if available

    //public bool useAudioSource = false;

 

    [Tooltip("最小距离用户,为了考虑骨骼数据处理。")]

    public float minUserDistance = 0.5f;

 

    [Tooltip("最大距离用户,为了考虑骨骼数据处理。值为0时表示没有最大距离限制。")]

    public float maxUserDistance = 0f;

 

    [Tooltip("最大用户向左或向右的距离,为了考虑骨骼数据处理。值为0时表示没有左/右的距离限制。")]

    public float maxLeftRightDistance = 0f;

 

    [Tooltip("最大数量的用户,这可能是同时跟踪。")]

    public int maxTrackedUsers = 6;

 

    [Tooltip("是否显示跟踪用户只允许的范围内,或所有用户(fps)。")]

    public bool showTrackedUsersOnly = true;

 

    [Tooltip("是否先检测只有最接近用户。")]

    public bool detectClosestUser = true;

 

    [Tooltip("是否只利用跟踪关节(而忽略推断的)。")]

    public bool ignoreInferredJoints = false;

 

    [Tooltip("是否忽略关节的z坐标(即在2 d场景)中使用它们。")]

    public bool ignoreZCoordinates = false;

 

    [Tooltip("是否更新AvatarControllers LateUpdate(),而不是更新()。所需Mocap-Mecanim混合。")]

    public bool lateUpdateAvatars = false;

 

    public enum Smoothing : int { None, Default, Medium, Aggressive }

    [Tooltip("联合平滑参数集。")]

    public Smoothing smoothing = Smoothing.Default;

 

    [Tooltip("是否应用骨方向约束。")]

    public bool useBoneOrientationConstraints = false;

    //public bool useBoneOrientationsFilter = false;

 

    [Tooltip("是否允许检测身体的运作周期。")]

    public bool allowTurnArounds = false;

 

    public enum AllowedRotations : int { None = 0, Default = 1, All = 2 }

    [Tooltip("允许他们的手和手腕旋转。没有——没有手旋转,允许违约——手旋转除了扭曲,所有——所有转动是允许的。")]

    public AllowedRotations allowedHandRotations = AllowedRotations.Default;

 

    [Tooltip("场景中的控制化身的列表。如果列表为空时,可用的《阿凡达》控制器将在启动检测。")]

    public List<AvatarController> avatarControllers = new List<AvatarController>();

 

    [Tooltip("玩家姿势校准")]

    public KinectGestures.Gestures playerCalibrationPose;

 

    [Tooltip("手势为每个球员被探测到的列表。")]

    public List<KinectGestures.Gestures> playerCommonGestures = new List<KinectGestures.Gestures>();

 

    [Tooltip("最低手势检测间隔时间(以秒为单位)。")]

    public float minTimeBetweenGestures = 0.7f;

 

    [Tooltip("手势经理,用于检测编程Kinect动作。")]

    public KinectGestures gestureManager;

 

    [Tooltip("列出可用的姿态听众。他们必须实现KinectGestures.GestureListenerInterface。如果列表是空的,可用手势听众会发现启动。")]

    public List<MonoBehaviour> gestureListeners = new List<MonoBehaviour>();

 

    [Tooltip("gui文本来显示用户检测消息。")]

    public GUIText calibrationText;

 

    [Tooltip("gui文本显示为当前手势跟踪调试消息。")]

    public GUIText gesturesDebugText;

 

===============================================================================

部分方法解析:

//体感设备是否初始化完成

public bool IsInitialized()

//程序捕获的人物个数

public int GetBodyCount()

//程序捕获的关节个数

public int GetJointCount()

//返回骨骼节点的索引

public int GetJointIndex(KinectInterop.JointType joint)

//返回骨骼节点的类型

public KinectInterop.JointType GetParentJoint(KinectInterop.JointType joint)

//设备返回彩色图片的宽度

public int GetColorImageWidth()

//设备返回彩色图片的高度

public int GetColorImageHeight()

//设备返回深度图的宽度

public int GetDepthImageWidth()

//设备返回深度图的高度

public int GetDepthImageHeight()

//获取最原始的深度图

public ushort[] GetRawInfraredMap()

//获取深度图像

public Texture2D GetUsersLblTex()

//获取彩色数据图

public Texture2D GetUsersClrTex()

//是否检测到用户

public bool IsUserDetected()

//指定的用户是否被检测到

public bool IsUserTracked(Int64 userId)

//获取用户的个数

public int GetUsersCount()

//获取主要检测的用户

public Int64 GetPrimaryUserID()

//返回用户相对于体感探头的位置

public Vector3 GetUserPosition(Int64 userId)

//返回用户相对于体感探头的旋转

public Quaternion GetUserOrientation(Int64 userId, bool flip)

//获取关节的捕获状态

public KinectInterop.TrackingState GetJointTrackingState(Int64 userId, int joint)

//关节是否被检测追踪

public bool IsJointTracked(Int64 userId, int joint)

//返回关节相对于Kinect的位置

public Vector3 GetJointKinectPosition(Int64 userId, int joint)

//返回关节相对于场景摄像头的位置

public Vector3 GetJointPosition(Int64 userId, int joint)

//得到的三维叠加位置给depth-image联合。

public Vector3 GetJointPosDepthOverlay(Int64 userId, int joint, Camera camera, Rect imageRect)

//得到了3 d覆盖给定的联合在彩色图像的位置。

public Vector3 GetJointPosColorOverlay(Int64 userId, int joint, Camera camera, Rect imageRect)

//获取左手的状态(握拳,伸开,yes)

public KinectInterop.HandState GetLeftHandState(Int64 userId)

//获取右手的状态(握拳,伸开,yes)

public KinectInterop.HandState GetRightHandState(Int64 userId)

//坐标转换

//空间坐标转换到深度坐标

public Vector3 MapDepthPointToSpaceCoords(Vector2 posPoint, ushort depthValue, bool bWorldCoords)

//空间坐标转换到深度坐标

public Vector2 MapSpacePointToDepthCoords(Vector3 posPoint)

//深度坐标转换到彩色坐标

public Vector2 MapDepthPointToColorCoords(Vector2 posPoint, ushort depthValue)

//添加监听的手势

public void DetectGesture(Int64 UserId, KinectGestures.Gestures gesture)

//删除监听的手势

public bool DeleteGesture(Int64 UserId, KinectGestures.Gestures gesture)

//检测某个手势是否完成

public bool IsGestureComplete(Int64 UserId, KinectGestures.Gestures gesture, bool bResetOnComplete)

*************************************************************************************************************************

Kinect 功能的实现

开发部分实现方法:

===============================================================================

获取人物关节点的注意事项:

//1.先检查人物是否被检测

if (_manager.IsUserDetected())

//2.获取人物ID

long userId = _manager.GetPrimaryUserID();

//3.关节索引

int jointIndex = (int)KinectInterop.JointType.HandLeft;

//4.判断需要跟踪的关节点是否已经被识别

if (_manager.IsJointTracked(userId, jointIndex))

//5.获取骨骼节点信息

Vector3 leftHandPos = _manager.GetJointKinectPosition(userId, jointIndex);

 

===============================================================================

获取手势信息

 //获取右手状态

KinectInterop.HandState rightHandState = _manager.GetRightHandState(userId);

//判断右手状态值

if (rightHandState == KinectInterop.HandState.Closed)

{

debugText.text = "右手握拳";

}

else if (rightHandState == KinectInterop.HandState.Open)

{

debugText.text = "右手展开";

}

else if (rightHandState == KinectInterop.HandState.Lasso)

{

debugText.text = "yes 手势";

}

===============================================================================

Kinect坐标到屏幕坐标的转换

//1.获取骨骼节点坐标

Vector3 jointKinectPos = _manager.GetJointKinectPosition(userId, jointIndex);

//2.空间坐标转换成深度坐标

Vector2 posDepth = _manager.MapSpacePointToDepthCoords(jointKinectPos);

//3.根据深度坐标获取深度值

ushort depthValue = _manager.GetDepthForPixel((int)posDepth.x, (int)posDepth.y);

if (depthValue > 0)//深度值大于0

{

//4.深度图像转换成彩色图像

Vector2 posColor = _manager.MapDepthPointToColorCoords(posDepth, depthValue);

//5.按彩色图像转换坐标

float xNorm = (float)posColor.x / _manager.GetColorImageWidth();

float yNorm = (float)posColor.y / _manager.GetColorImageHeight();

 

if (overlayObject)

{

//将视口坐标转换为空间坐标

    Vector3 vpos = Camera.main.ViewportToWorldPoint(xNorm, yNorm, distanceToCamera);

    overlayObject.transform.position = Vector3.Lerp(overlayObject.transform.position, vpos, Time.deltaTime * 5);

}

}

===============================================================================

//UI点击的实现

1.获取右手(左手/关节点)的3D坐标

Vector3 rightHandPos = _manager.GetJointKinectPosition(userId, jointIndex);//右手坐标

2.3D坐标转换成屏幕坐标

Vector3 rightScreenPos = Camera.main.WorldToScreenPoint(rightHandPos);//转换成屏幕坐标

Vector2 screenPosTemp = new Vector2(rightScreenPos.x, rightScreenPos.y);//屏幕坐标

3.屏幕坐标转换成UGUI坐标(得到手的位置在UGUI的位置)

 Vector2 uguiPos;

if (RectTransformUtility.ScreenPointToLocalPointInRectangle(canvas, screenPosTemp, null, out uguiPos))

{

hand.anchoredPosition = uguiPos;

}

4.判断手的位置是否在UGUI控件上方

bool isOverBtn1 = RectTransformUtility.RectangleContainsScreenPoint(btn1, screenPosTemp, null);

5.手如果在控件上方,判断是否握拳

 //获取右手状态

KinectInterop.HandState rightHandState = _manager.GetRightHandState(userId);

//判断右手状态值

if (rightHandState == KinectInterop.HandState.Closed)

{

if (isOverBtn1)

print("握住btn1");

}

else if (rightHandState == KinectInterop.HandState.Open){}

else if (rightHandState == KinectInterop.HandState.Lasso){}

***********************************************************************************

Kinect 骨骼数据和姿势监听

Kinect骨骼分析:

 

人物的数据

public struct BodyData

{

public Int64 liTrackingID;//人物是否被追踪

public Vector3 position;//人物的位置

public Quaternion orientation;

public JointData[] joint;//骨骼节点的数据

 

// KM calculated parameters

public Quaternion normalRotation;

public Quaternion mirroredRotation;

public Vector3 hipsDirection;

public Vector3 shouldersDirection;

public float bodyTurnAngle;

//public float bodyFullAngle;

public bool isTurnedAround;

public float turnAroundFactor;

 

public Quaternion leftHandOrientation;

public Quaternion rightHandOrientation;

 

public Quaternion headOrientation;

 

//public Vector3 leftArmDirection;

//public Vector3 leftThumbForward;

//public Vector3 leftThumbDirection;

////public float leftThumbAngle;

//

//public Vector3 rightArmDirection;

//public Vector3 rightThumbForward;

//public Vector3 rightThumbDirection;

////public float rightThumbAngle;

 

//public Vector3 leftLegDirection;

//public Vector3 leftFootDirection;

//public Vector3 rightLegDirection;

//public Vector3 rightFootDirection;

 

public HandState leftHandState;//左手状态

public TrackingConfidence leftHandConfidence;

public HandState rightHandState;//右手状态

public TrackingConfidence rightHandConfidence;

public uint dwClippedEdges;

public short bIsTracked;

public short bIsRestricted;

}

 

//骨骼点信息

public struct JointData

{

     public TrackingState trackingState;

     public Vector3 kinectPos;

     public Vector3 position;

public Quaternion orientation;  // deprecated

 

public Vector3 posPrev;

public Vector3 posRel;

public Vector3 posDrv;

 

// KM calculated parameters

public Vector3 direction;

public Quaternion normalRotation;

public Quaternion mirroredRotation;

// Constraint parameters

public float lastAngle;

}

//姿势检测的结构

public struct GestureData

{

public long userId;//要检测的用户ID

public Gestures gesture;//要检测的姿势类型

public int state;//姿势检测的状态,姿势是否正在检测

public float timestamp;

public int joint;

public Vector3 jointPos;

public Vector3 screenPos;

public float tagFloat;

public Vector3 tagVector;

public Vector3 tagVector2;

public float progress;

public bool complete;

public bool cancelled;

public List<Gestures> checkForGestures;

public float startTrackingAtTime;


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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值