2013-03-28 76 views
0

我一直在研究這個問題已經好幾天了,但沒有成功,看着其他問題,堆棧溢出是我的一個來源。 我正在使用Kinect for Windows創建一個程序,該程序將跟蹤用戶的關節,並在單獨的「屏幕」上繪製骨骼,我已經映射了關節本身,並使用圖像(紅點)來演示映射關節的位置。映射骨架關節以創建骨架

我的下一步是通過從一個關節繪製一條線來構建骨骼本身,我遇到的問題是如何繪製線...我有一種傾向於過度複雜的東西,所以我想知道是否我只是爲自己製造困難,而不是僅僅發現 最簡單的解決方案。

我覺得我有99%的路,但仍然遇到一個錯誤,我無法得到我的頭,請在下面找到錯誤消息和相關的C#代碼。

"cannot convert from 'Microsoft.Kinect.SkeletonPoint' to 'System.Windows.Point" 

代碼:

private void DrawBone (Joint jointFrom, Joint jointTo) 
{ 
    Brush centerPointBrush; 
    Pen trackedBonePen = new Pen(Brushes.White, TrackedBoneThickness); 
    inferredBonePen = new Pen(Brushes.Gray, InferredBoneThickness); 
    DrawingVisual visual = new DrawingVisual(); 
    DrawingContext context = visual.RenderOpen(); 

    centerPointBrush = Brushes.Red; 

    if (jointFrom.TrackingState == JointTrackingState.NotTracked 
     || jointTo.TrackingState == JointTrackingState.NotTracked) 
    { 
     return; 
    } 

    if (jointFrom.TrackingState == JointTrackingState.Inferred 
     || jointTo.TrackingState == JointTrackingState.Inferred) 
    {  
     context.DrawLine(inferredBonePen,jointFrom.Position, jointTo.Position); 
    } 

    if (jointFrom.TrackingState == JointTrackingState.Tracked 
     || jointTo.TrackingState == JointTrackingState.Tracked) 
    { 
     context.DrawLine(trackedBonePen, jointFrom.Position, jointTo.Position); 
    } 
} 

與啓動context.DrawLine的線條,這些都是不正確的參數爲DrawLine功能,我得到的一個伴隨的錯誤錯誤:

Error 4 The best overloaded method match for 
'System.Windows.Media.DrawingContext.DrawLine(System.Windows.Media.Pen, 
System.Windows.Point, System.Windows.Point)' has some invalid arguments 

回答

0

錯誤消息說明了這一切。而不是直接使用jointFrom.Position,您需要創建一個System.Windows.Point來表示jointFrom的座標,並將其傳遞給DrawLine

這同樣適用於jointTo ...

的複雜性在於,骨架的位置,並且因此fromJoint.Position,表示三維座標,而用於繪製直線的點是2D座標。所以直接轉換是不可能的。相反,您需要在2D中投影關節位置,並使用投影點畫出線條。

您的其他選擇是使用3D drawing in WPF,而不僅僅是繪製到視覺效果。

0

正如Miky Dinescu指出的那樣,您的直接問題是需要將Microsoft.Kinect.Joint.Position轉換爲System.Windows.Point

您可能不在意Z的值(深度),因此需要將XY標準化爲您窗口的大小。根據您希望繪製的骨架的行爲方式,可能會始終如此簡單,因爲始終將JointType.Spine放置在窗口的中央;或者您可能需要額外計算數據才能根據玩家在Kinect的FOV中的位置來翻譯骨骼需要顯示的窗口中的哪個位置。

根據Kinect的輸入繪製骨架的示例有多個示例,可從Kinect for Windows Toolkit獲取。 「骨架基礎」和「塑造遊戲」的例子是立即想到的兩個例子。您也可以在Kinect for Windows Samples CodePlex頁面找到代碼(這些示例代碼爲SDK 1.6,在SDK 1.7中這些代碼都可以正常工作)。

這裏是MainWindow.xaml.cs爲「骨架基礎」的例子。注意DrawBonesAndJoints' and DrawBone的功能來演示你想要做的事情。

0

也許我沒有正確理解,但你爲什麼要做一些已經完成的事情?以下是來自Kinect Developer Toolkit 1.8的示例代碼。

private void DrawBone(Skeleton skeleton, DrawingContext drawingContext, JointType jointType0, JointType jointType1) 
    { 
     Joint joint0 = skeleton.Joints[jointType0]; 
     Joint joint1 = skeleton.Joints[jointType1]; 

     // If we can't find either of these joints, exit 
     if (joint0.TrackingState == JointTrackingState.NotTracked || joint1.TrackingState == JointTrackingState.NotTracked) 
     { 
      return; 
     } 

     // Don't draw if both points are inferred 
     if (joint0.TrackingState == JointTrackingState.Inferred && joint1.TrackingState == JointTrackingState.Inferred) 
     { 
      return; 
     } 

     // We assume all drawn bones are inferred unless BOTH joints are tracked 
     Pen drawPen = this.inferredBonePen; 

     if (joint0.TrackingState == JointTrackingState.Tracked && joint1.TrackingState == JointTrackingState.Tracked) 
     { 
      drawPen = this.trackedBonePen; 
     } 

     drawingContext.DrawLine(drawPen, this.SkeletonPointToScreen(joint0.Position), this.SkeletonPointToScreen(joint1.Position)); 
    } 
1

不要重新發明輪子。微軟的傢伙在那裏做得很好。也許這段代碼可以幫助你:

private void DrawBonesAndJoints(Skeleton skeleton, DrawingContext drawingContext) 
     { 
      // Render Torso 
      this.DrawBone(skeleton, drawingContext, JointType.Head, JointType.ShoulderCenter); 
      this.DrawBone(skeleton, drawingContext, JointType.ShoulderCenter, JointType.ShoulderLeft); 
      this.DrawBone(skeleton, drawingContext, JointType.ShoulderCenter, JointType.ShoulderRight); 
      this.DrawBone(skeleton, drawingContext, JointType.ShoulderCenter, JointType.Spine); 
      this.DrawBone(skeleton, drawingContext, JointType.Spine, JointType.HipCenter); 
      this.DrawBone(skeleton, drawingContext, JointType.HipCenter, JointType.HipLeft); 
      this.DrawBone(skeleton, drawingContext, JointType.HipCenter, JointType.HipRight); 

      // Left Arm 
      this.DrawBone(skeleton, drawingContext, JointType.ShoulderLeft, JointType.ElbowLeft); 
      this.DrawBone(skeleton, drawingContext, JointType.ElbowLeft, JointType.WristLeft); 
      this.DrawBone(skeleton, drawingContext, JointType.WristLeft, JointType.HandLeft); 

      // Right Arm 
      this.DrawBone(skeleton, drawingContext, JointType.ShoulderRight, JointType.ElbowRight); 
      this.DrawBone(skeleton, drawingContext, JointType.ElbowRight, JointType.WristRight); 
      this.DrawBone(skeleton, drawingContext, JointType.WristRight, JointType.HandRight); 

      // Left Leg 
      this.DrawBone(skeleton, drawingContext, JointType.HipLeft, JointType.KneeLeft); 
      this.DrawBone(skeleton, drawingContext, JointType.KneeLeft, JointType.AnkleLeft); 
      this.DrawBone(skeleton, drawingContext, JointType.AnkleLeft, JointType.FootLeft); 

      // Right Leg 
      this.DrawBone(skeleton, drawingContext, JointType.HipRight, JointType.KneeRight); 
      this.DrawBone(skeleton, drawingContext, JointType.KneeRight, JointType.AnkleRight); 
      this.DrawBone(skeleton, drawingContext, JointType.AnkleRight, JointType.FootRight); 


      // Render Joints 
      foreach (Joint joint in skeleton.Joints) 
      { 
       Brush drawBrush = null; 

       if (joint.TrackingState == JointTrackingState.Tracked) 
       { 
        drawBrush = this.trackedJointBrush;      
       } 
       else if (joint.TrackingState == JointTrackingState.Inferred) 
       { 
        drawBrush = this.inferredJointBrush;      
       } 

       if (drawBrush != null) 
       { 
        drawingContext.DrawEllipse(drawBrush, null, this.SkeletonPointToScreen(joint.Position), JointThickness, JointThickness); 
       } 
      } 
     }