private void _UpdateDepthArray <T>( ref T[] dataArray, AcquireDepthImageDelegate acquireImageDelegate) { // The native session provides the session and frame handles. var nativeSession = LifecycleManager.Instance.NativeSession; if (nativeSession == null) { Debug.LogError("NativeSession is null."); return; } // Gets the current depth image. IntPtr imageHandle = IntPtr.Zero; if (acquireImageDelegate( nativeSession.SessionHandle, nativeSession.FrameHandle, ref imageHandle) == false) { return; } // Gets the size of the depth data. int width = 0; int height = 0; ExternApi.ArImage_getWidth( nativeSession.SessionHandle, imageHandle, out width); ExternApi.ArImage_getHeight(nativeSession.SessionHandle, imageHandle, out height); // Accesses the depth image surface data. IntPtr planeDoublePtr = IntPtr.Zero; int planeSize = 0; ExternApi.ArImage_getPlaneData( nativeSession.SessionHandle, imageHandle, /*plane_index=*/ 0, ref planeDoublePtr, ref planeSize); IntPtr planeDataPtr = new IntPtr(planeDoublePtr.ToInt32()); int depthPixelCount = width * height; // Resizes the CPU depth array based on the updated size. if (dataArray.Length != depthPixelCount) { Array.Resize(ref dataArray, depthPixelCount); } int pixelStride = 0; ExternApi.ArImage_getPlanePixelStride(nativeSession.SessionHandle, imageHandle, /*plane_index*/ 0, ref pixelStride); // Copies the depth data into the provided CPU depth array. if (pixelStride == 1) { Marshal.Copy(planeDataPtr, dataArray as byte[], 0, dataArray.Length); } else { Marshal.Copy(planeDataPtr, dataArray as short[], 0, dataArray.Length); } // Releases the depth image. LifecycleManager.Instance.NativeSession.ImageApi.Release(imageHandle); return; }
/// <summary> /// Queries the image delegate for a texture data and updates the given array and texture. /// </summary> /// <typeparam name="T">Can be either short (for depth) or byte (for confidence).</typeparam> /// <param name="texture">The texture to update with new data.</param> /// <param name="dataArray">The CPU array to update with new data.</param> /// <param name="acquireImageDelegate">The function to call to obtain data.</param> private void _UpdateTexture <T>( ref Texture2D texture, ref T[] dataArray, AcquireDepthImageDelegate acquireImageDelegate) { // The native session provides the session and frame handles. var nativeSession = LifecycleManager.Instance.NativeSession; if (nativeSession == null) { Debug.LogError("NativeSession is null."); return; } // Get the current depth image. IntPtr imageHandle = IntPtr.Zero; if (acquireImageDelegate( nativeSession.SessionHandle, nativeSession.FrameHandle, ref imageHandle) == false) { return; } int previousDepthWidth = m_DepthWidth; int previousDepthHeight = m_DepthHeight; // Gets the size of the depth data. ExternApi.ArImage_getWidth( nativeSession.SessionHandle, imageHandle, out m_DepthWidth); ExternApi.ArImage_getHeight(nativeSession.SessionHandle, imageHandle, out m_DepthHeight); if (previousDepthWidth != m_DepthWidth || previousDepthHeight != m_DepthHeight) { _InitializeCameraIntrinsics(); } // Accesses the depth image surface data. IntPtr planeDoublePtr = IntPtr.Zero; int planeSize = 0; ExternApi.ArImage_getPlaneData( nativeSession.SessionHandle, imageHandle, /*plane_index*/ 0, ref planeDoublePtr, ref planeSize); IntPtr planeDataPtr = new IntPtr(planeDoublePtr.ToInt64()); int pixelStride = 0; ExternApi.ArImage_getPlanePixelStride(nativeSession.SessionHandle, imageHandle, /*plane_index*/ 0, ref pixelStride); // Resizes the CPU data array based on the updated size. if (dataArray.Length != planeSize / pixelStride) { Array.Resize(ref dataArray, planeSize / pixelStride); } // Copies the depth data into the provided CPU data array. if (pixelStride == 1) { // Pixel stride is 2, used for confidence data. Marshal.Copy(planeDataPtr, dataArray as byte[], 0, dataArray.Length); } else { // Pixel stride is 2, used for depth data. Marshal.Copy(planeDataPtr, dataArray as short[], 0, dataArray.Length); } // Resize the depth texture if needed. if (m_DepthWidth != texture.width || m_DepthHeight != texture.height) { if (pixelStride == 1) { texture.Resize(m_DepthWidth, m_DepthHeight, TextureFormat.R8, false); } else { texture.Resize(m_DepthWidth, m_DepthHeight, TextureFormat.RGB565, false); } } // Copies the raw depth data to the texture. texture.LoadRawTextureData(planeDataPtr, planeSize); texture.Apply(); // Releases the depth image. LifecycleManager.Instance.NativeSession.ImageApi.Release(imageHandle); return; }