1.相比较之前的版本,多了一个Mode,如下所示:
2.两种Mode下的不同距离的效果:
3.获取depth和player的C#语言:
在上一篇的前提下(就是不改变XAML的情况下,修改后台程序),代码如下:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using Microsoft.Kinect;
namespace KinectSdkDemo
{
/// <summary>
/// MainWindow.xaml 的交互逻辑
/// </summary>
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
}
const float MaxDepthDistance = 4000;// max value returned
const float MinDepthDistance = 850;// min value returned
const float MaxDepthDistanceOffset = MaxDepthDistance - MinDepthDistance;
KinectSensor _sensor;
private void Window_Loaded(object sender, RoutedEventArgs e)
{
kinectSensorChooser1.KinectSensorChanged
+= new DependencyPropertyChangedEventHandler(kinectSensorChooser1_KinectSensorChanged);
if (KinectSensor.KinectSensors.Count > 0)
{
_sensor = KinectSensor.KinectSensors[0];
}
if (_sensor.Status == KinectStatus.Connected)
{
_sensor.ColorStream.Enable();
_sensor.DepthStream.Enable();
_sensor.SkeletonStream.Enable();
_sensor.AllFramesReady += new EventHandler<AllFramesReadyEventArgs>(_sensor_AllFramesReady);
_sensor.Start();
}
}
void _sensor_AllFramesReady(object sender, AllFramesReadyEventArgs e)
{
/*throw new NotImplementedException();*/
//using (ColorImageFrame colorFrame = e.OpenColorImageFrame())
//{
// if (colorFrame == null)
// {
// return;
// }
// byte[] pixels = new byte[colorFrame.PixelDataLength];
// colorFrame.CopyPixelDataTo(pixels);
// int stride = colorFrame.Width * 4;
////image1.Source =
//// BitmapSource.Create(colorFrame.Width, colorFrame.Height, 96, 96
//// , PixelFormats.Bgr32, null, pixels, stride);
//}
using (DepthImageFrame depthFrame = e.OpenDepthImageFrame())
{
if (depthFrame == null)
{
return;
}
byte[] depthPixels = GenerateColoredBytes(depthFrame);
int stride_depth = depthFrame.Width * 4;
image1.Source =
BitmapSource.Create(depthFrame.Width, depthFrame.Height, 96, 96
, PixelFormats.Bgr32, null, depthPixels, stride_depth);
}
}
private byte[] GenerateColoredBytes(DepthImageFrame depthFrame)
{
//get the raw data from kinect with the depth for every pixel
short[] rawDepthData = new short[depthFrame.PixelDataLength];
depthFrame.CopyPixelDataTo(rawDepthData);
//use depthFrame to create the image to display on-screen
//depthFrame contains color information for all pixels in image
//Height * Width * 4(Red, Green, Blue, empth byte)
Byte[] pixels = new byte[depthFrame.Height * depthFrame.Width * 4];
//Bgr32 - Blue, Green, Red, empth byte
//Bgra32 - Blue, Green, Red, transparency
//You must set transparency for Bgra as .NET defaults a byte to 0 = fully transparency
//hardcoded locations to Blue, Green, Red(RGB) index positions
const int BlueIndex = 0;
const int GreenIndex = 1;
const int RedIndex = 2;
//loop through all distances
//pick a RGB color based on distance
for (int depthIndex = 0, colorIndex = 0;
depthIndex < rawDepthData.Length && colorIndex < pixels.Length;
depthIndex++, colorIndex += 4)
{
//get the player(requires skeleton tracking enabled for values)
int player = rawDepthData[depthIndex] & DepthImageFrame.PlayerIndexBitmask;
//gets the depth value
int depth = rawDepthData[depthIndex] >> DepthImageFrame.PlayerIndexBitmaskWidth;
//.9M or 2.95'
if (depth <= 900)
{
//we are very close
pixels[colorIndex + BlueIndex] = 255;
pixels[colorIndex + GreenIndex] = 0;
pixels[colorIndex + RedIndex] = 0;
}
// 0.9M - 2, or 2.95' - 6.56'
else if (depth > 900 && depth < 2000)
{
//we are a bit further away
pixels[colorIndex + BlueIndex] = 0;
pixels[colorIndex + GreenIndex] = 255;
pixels[colorIndex + RedIndex] = 0;
}
else if (depth > 2000)
{
//we are the farthest
pixels[colorIndex + BlueIndex] = 0;
pixels[colorIndex + GreenIndex] = 0;
pixels[colorIndex + RedIndex] = 255;
}
//equal coloring for monochromatic histogram
byte intensity = calculateIntensityFromDepth(depth);
pixels[colorIndex + BlueIndex] = intensity;
pixels[colorIndex + GreenIndex] = intensity;
pixels[colorIndex + RedIndex] = intensity;
//Color all players "gold"
if (player > 0)
{
pixels[colorIndex + BlueIndex] = Colors.Gold.B;
pixels[colorIndex + GreenIndex] = Colors.Gold.G;
pixels[colorIndex + RedIndex] = Colors.Gold.R;
}
}
return pixels;
}
private byte calculateIntensityFromDepth(int depth)
{
//formula for calculating monochrome intensity for histogram
return (byte)(255 - (255 * Math.Max(depth - MinDepthDistance, 0)
/ (MaxDepthDistanceOffset)));
}
void StopKinect(KinectSensor sensor)
{
if (sensor != null)
{
sensor.Stop();
sensor.AudioSource.Stop();
}
}
private void Window_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{
StopKinect(kinectSensorChooser1.Kinect);
}
void kinectSensorChooser1_KinectSensorChanged(object sender, DependencyPropertyChangedEventArgs e)
{
KinectSensor oldSensor = (KinectSensor)e.OldValue;
StopKinect(oldSensor);
KinectSensor newSensor = (KinectSensor)e.NewValue;
newSensor.ColorStream.Enable();
newSensor.DepthStream.Enable();
newSensor.SkeletonStream.Enable();
// newSensor.AllFramesReady += new EventHandler<AllFramesReadyEventArgs>(_sensor_AllFramesReady);
try
{
newSensor.Start();
}
catch (System.IO.IOException)
{
kinectSensorChooser1.AppConflictOccurred();
}
}
}
}