PointCloudAggregator.cs 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160
  1. using System.Collections.Generic;
  2. using UnityEngine;
  3. using Windows.Kinect;
  4. public class PointCloudAggregator : MonoBehaviour {
  5. public float accuracy = 1000f;
  6. public ParticleSystem _particleSystem;
  7. private ParticleSystem.Particle[] particles;
  8. // Kinectsensor foo
  9. private MultiSourceManager _MultiManager;
  10. private KinectSensor _Sensor;
  11. private CoordinateMapper _Mapper;
  12. private int depthWidth;
  13. private int depthHeight;
  14. private FrameDescription depthFrameDesc;
  15. private CameraSpacePoint[] cameraSpacePoints;
  16. private ColorSpacePoint[] colorSpacePoints;
  17. private Texture2D cameraTexture;
  18. private Color[] cameraColor;
  19. Dictionary<Vector2Int, ColorHeight> data = new Dictionary<Vector2Int, ColorHeight>();
  20. struct ColorHeight
  21. {
  22. public float height;
  23. public Color color;
  24. float avgAbout;
  25. public ColorHeight(float inHeight, Color inColor)
  26. {
  27. height = inHeight;
  28. color = inColor;
  29. avgAbout = 1;
  30. }
  31. public void UpdateInfo(float newHeight, Color newColor)
  32. {
  33. color = (color * avgAbout / (avgAbout + 1)) + newColor / avgAbout;
  34. height = (height * avgAbout / (avgAbout + 1)) + newHeight / avgAbout;
  35. avgAbout++;
  36. }
  37. }
  38. void Start()
  39. {
  40. _Sensor = KinectSensor.GetDefault();
  41. if (_Sensor != null)
  42. {
  43. _MultiManager = GetComponent<MultiSourceManager>();
  44. _Mapper = _Sensor.CoordinateMapper;
  45. depthFrameDesc = _Sensor.DepthFrameSource.FrameDescription;
  46. depthWidth = depthFrameDesc.Width;
  47. depthHeight = depthFrameDesc.Height;
  48. if (!_Sensor.IsOpen)
  49. {
  50. _Sensor.Open();
  51. }
  52. cameraSpacePoints = new CameraSpacePoint[depthWidth * depthHeight];
  53. colorSpacePoints = new ColorSpacePoint[depthWidth * depthHeight];
  54. cameraColor = new Color[depthWidth * depthHeight];
  55. }
  56. }
  57. // Update is called once per frame
  58. void Update () {
  59. if (Input.GetKeyDown(KeyCode.Space))
  60. {
  61. Debug.Log("Snapshot");
  62. NewSnapshot();
  63. }
  64. if (Input.GetKeyDown(KeyCode.A))
  65. {
  66. Debug.Log("Cloud!");
  67. Debug.Log(data.Count);
  68. ShowAsPointCloud();
  69. }
  70. }
  71. void NewSnapshot()
  72. {
  73. Vector3 currentPoint;
  74. Vector2Int floorPosition;
  75. ushort[] rawdata = _MultiManager.GetDepthData();
  76. cameraTexture = _MultiManager.GetColorTexture();
  77. _Mapper.MapDepthFrameToCameraSpace(rawdata, cameraSpacePoints);
  78. _Mapper.MapDepthFrameToColorSpace(rawdata, colorSpacePoints);
  79. for(int i = 0; i < cameraSpacePoints.Length; i++)
  80. {
  81. currentPoint = KinectPointToVector3(cameraSpacePoints[i]);
  82. currentPoint = transform.InverseTransformPoint(currentPoint);
  83. floorPosition = new Vector2Int(Mathf.RoundToInt(currentPoint.x * (int)accuracy), Mathf.RoundToInt(currentPoint.z * (int)accuracy));
  84. if (data.ContainsKey(floorPosition))
  85. {
  86. ColorHeight values = data[floorPosition];
  87. values.UpdateInfo(currentPoint.y, GetColorAtIndex(i));
  88. data[floorPosition] = values;
  89. }
  90. else
  91. {
  92. data[floorPosition] = new ColorHeight(currentPoint.y, GetColorAtIndex(i));
  93. }
  94. }
  95. }
  96. Vector3 KinectPointToVector3(CameraSpacePoint point)
  97. {
  98. return new Vector3(-point.X, point.Y, point.Z);
  99. }
  100. Color GetColorAtIndex(int index)
  101. {
  102. Color result = cameraTexture.GetPixel(Mathf.RoundToInt(colorSpacePoints[index].X), Mathf.RoundToInt(colorSpacePoints[index].Y));
  103. return result;
  104. }
  105. void ShowAsPointCloud()
  106. {
  107. ColorHeight colorHeight;
  108. particles = new ParticleSystem.Particle[data.Count];
  109. int i = 0;
  110. foreach(Vector2Int floorPos in data.Keys)
  111. {
  112. colorHeight = data[floorPos];
  113. particles[i].position = new Vector3((float)floorPos.x/accuracy, (float)colorHeight.height, (float)floorPos.y/ accuracy);
  114. particles[i].startColor = colorHeight.color;
  115. particles[i].startSize = 0.02f;
  116. i++;
  117. }
  118. _particleSystem.SetParticles(particles, particles.Length);
  119. }
  120. }