public static Vector2[] GetStencilMask() { HiddenAreaMesh_t leftMesh = m_vrSystem.GetHiddenAreaMesh(EVREye.Eye_Left); HiddenAreaMesh_t rightMesh = m_vrSystem.GetHiddenAreaMesh(EVREye.Eye_Right); uint leftVertsCount = leftMesh.unTriangleCount * 3; uint rightVertsCount = rightMesh.unTriangleCount * 3; Vector2[] verts = new Vector2[leftVertsCount + rightVertsCount]; unsafe { uint index = 0; for (int i = 0, j = 0; i < leftMesh.unTriangleCount * 3; i++) { Vector2 vertex; float x = ((float *)leftMesh.pVertexData.ToPointer())[j++]; float y = ((float *)leftMesh.pVertexData.ToPointer())[j++]; vertex.X = -1 + 2 * x; vertex.Y = -1 + 2 * y; vertex.X = vertex.X / 2 - 0.5f; verts[index++] = vertex; } for (int i = 0, j = 0; i < rightMesh.unTriangleCount * 3; i++) { Vector2 vertex; float x = ((float *)rightMesh.pVertexData.ToPointer())[j++]; float y = ((float *)rightMesh.pVertexData.ToPointer())[j++]; vertex.X = -1 + 2 * x; vertex.Y = -1 + 2 * y; vertex.X = vertex.X / 2 + 0.5f; verts[index++] = vertex; } } return(verts); }
void GetMeshData(HiddenAreaMesh_t meshData, ISpread <float> ret) { var floatCount = (int)meshData.unTriangleCount * 3 * 2; ret.SliceCount = floatCount; Marshal.Copy(meshData.pVertexData, ret.Stream.Buffer, 0, floatCount); }
public static HiddenAreaMesh Make(Device device, EVREye eye) { HiddenAreaMesh_t hiddenAreaMeshDefinition = OpenVR.System.GetHiddenAreaMesh(eye, EHiddenAreaMeshType.k_eHiddenAreaMesh_Standard); int triangleCount = (int)hiddenAreaMeshDefinition.unTriangleCount; if (triangleCount == 0) { return(null); } int vertexCount = triangleCount * 3; Buffer vertexBuffer = new Buffer(device, hiddenAreaMeshDefinition.pVertexData, new BufferDescription { SizeInBytes = vertexCount * Vector2.SizeInBytes, BindFlags = BindFlags.VertexBuffer, Usage = ResourceUsage.Immutable }); VertexBufferBinding vertexBufferBinding = new VertexBufferBinding(vertexBuffer, Vector2.SizeInBytes, 0); return(new HiddenAreaMesh(vertexCount, vertexBufferBinding)); }
public static Mesh CreateHiddenAreaMesh(HiddenAreaMesh_t src, VRTextureBounds_t bounds) { if (src.unTriangleCount == 0) { return(null); } var data = new float[src.unTriangleCount * 3 * 2]; //HmdVector2_t Marshal.Copy(src.pVertexData, data, 0, data.Length); var vertices = new Vector3[src.unTriangleCount * 3 + 12]; var indices = new int[src.unTriangleCount * 3 + 24]; var x0 = 2.0f * bounds.uMin - 1.0f; var x1 = 2.0f * bounds.uMax - 1.0f; var y0 = 2.0f * bounds.vMin - 1.0f; var y1 = 2.0f * bounds.vMax - 1.0f; for (int i = 0, j = 0; i < src.unTriangleCount * 3; i++) { var x = Lerp(x0, x1, data[j++]); var y = Lerp(y0, y1, data[j++]); vertices[i] = new Vector3(x, y, 0.0f); indices[i] = i; } // Add border var offset = (int)src.unTriangleCount * 3; var iVert = offset; vertices[iVert++] = new Vector3(-1, -1, 0); vertices[iVert++] = new Vector3(x0, -1, 0); vertices[iVert++] = new Vector3(-1, 1, 0); vertices[iVert++] = new Vector3(x0, 1, 0); vertices[iVert++] = new Vector3(x1, -1, 0); vertices[iVert++] = new Vector3(1, -1, 0); vertices[iVert++] = new Vector3(x1, 1, 0); vertices[iVert++] = new Vector3(1, 1, 0); vertices[iVert++] = new Vector3(x0, y0, 0); vertices[iVert++] = new Vector3(x1, y0, 0); vertices[iVert++] = new Vector3(x0, y1, 0); vertices[iVert++] = new Vector3(x1, y1, 0); var iTri = offset; indices[iTri++] = offset + 0; indices[iTri++] = offset + 1; indices[iTri++] = offset + 2; indices[iTri++] = offset + 2; indices[iTri++] = offset + 1; indices[iTri++] = offset + 3; indices[iTri++] = offset + 4; indices[iTri++] = offset + 5; indices[iTri++] = offset + 6; indices[iTri++] = offset + 6; indices[iTri++] = offset + 5; indices[iTri++] = offset + 7; indices[iTri++] = offset + 1; indices[iTri++] = offset + 4; indices[iTri++] = offset + 8; indices[iTri++] = offset + 8; indices[iTri++] = offset + 4; indices[iTri++] = offset + 9; indices[iTri++] = offset + 10; indices[iTri++] = offset + 11; indices[iTri++] = offset + 3; indices[iTri++] = offset + 3; indices[iTri++] = offset + 11; indices[iTri++] = offset + 6; var mesh = new Mesh(); mesh.vertices = vertices; mesh.triangles = indices; mesh.bounds = new Bounds(Vector3.zero, new Vector3(float.MaxValue, float.MaxValue, float.MaxValue)); // Prevent frustum culling from culling this mesh return(mesh); }
public static Mesh CreateHiddenAreaMesh(HiddenAreaMesh_t src, VRTextureBounds_t bounds) { if (src.unTriangleCount == 0u) { return(null); } float[] array = new float[src.unTriangleCount * 3u * 2u]; Marshal.Copy(src.pVertexData, array, 0, array.Length); Vector3[] array2 = new Vector3[src.unTriangleCount * 3u + 12u]; int[] array3 = new int[src.unTriangleCount * 3u + 24u]; float num = 2f * bounds.uMin - 1f; float num2 = 2f * bounds.uMax - 1f; float num3 = 2f * bounds.vMin - 1f; float num4 = 2f * bounds.vMax - 1f; int num5 = 0; int num6 = 0; while ((long)num5 < (long)((ulong)(src.unTriangleCount * 3u))) { float x = SteamVR_Utils.Lerp(num, num2, array[num6++]); float y = SteamVR_Utils.Lerp(num3, num4, array[num6++]); array2[num5] = new Vector3(x, y, 0f); array3[num5] = num5; num5++; } int num7 = (int)(src.unTriangleCount * 3u); int num8 = num7; array2[num8++] = new Vector3(-1f, -1f, 0f); array2[num8++] = new Vector3(num, -1f, 0f); array2[num8++] = new Vector3(-1f, 1f, 0f); array2[num8++] = new Vector3(num, 1f, 0f); array2[num8++] = new Vector3(num2, -1f, 0f); array2[num8++] = new Vector3(1f, -1f, 0f); array2[num8++] = new Vector3(num2, 1f, 0f); array2[num8++] = new Vector3(1f, 1f, 0f); array2[num8++] = new Vector3(num, num3, 0f); array2[num8++] = new Vector3(num2, num3, 0f); array2[num8++] = new Vector3(num, num4, 0f); array2[num8++] = new Vector3(num2, num4, 0f); int num9 = num7; array3[num9++] = num7; array3[num9++] = num7 + 1; array3[num9++] = num7 + 2; array3[num9++] = num7 + 2; array3[num9++] = num7 + 1; array3[num9++] = num7 + 3; array3[num9++] = num7 + 4; array3[num9++] = num7 + 5; array3[num9++] = num7 + 6; array3[num9++] = num7 + 6; array3[num9++] = num7 + 5; array3[num9++] = num7 + 7; array3[num9++] = num7 + 1; array3[num9++] = num7 + 4; array3[num9++] = num7 + 8; array3[num9++] = num7 + 8; array3[num9++] = num7 + 4; array3[num9++] = num7 + 9; array3[num9++] = num7 + 10; array3[num9++] = num7 + 11; array3[num9++] = num7 + 3; array3[num9++] = num7 + 3; array3[num9++] = num7 + 11; array3[num9++] = num7 + 6; return(new Mesh { vertices = array2, triangles = array3, bounds = new Bounds(Vector3.zero, new Vector3(float.MaxValue, float.MaxValue, float.MaxValue)) }); }
/// <summary> /// Initialize HMD using OpenVR API calls. /// </summary> /// <returns>True on success, false otherwise. Errors logged.</returns> bool InitHMD() { bool retVal = false; // return if HMD has already been initialized if (hmdIsInitialized) { return(true); } // check if HMD is connected on the system retVal = OpenVR.IsHmdPresent(); if (!retVal) { Debug.Log("[KerbalVR] HMD not found on this system."); return(retVal); } // check if SteamVR runtime is installed. // For this plugin, MAKE SURE IT IS ALREADY RUNNING. retVal = OpenVR.IsRuntimeInstalled(); if (!retVal) { Debug.Log("[KerbalVR] SteamVR runtime not found on this system."); return(retVal); } // initialize HMD EVRInitError hmdInitErrorCode = EVRInitError.None; vrSystem = OpenVR.Init(ref hmdInitErrorCode, EVRApplicationType.VRApplication_Scene); // return if failure retVal = (hmdInitErrorCode == EVRInitError.None); if (!retVal) { Debug.Log("[KerbalVR] Failed to initialize HMD. Init returned: " + OpenVR.GetStringForHmdError(hmdInitErrorCode)); return(retVal); } else { Debug.Log("[KerbalVR] OpenVR.Init passed."); } // reset "seated position" and capture initial position. this means you should hold the HMD in // the position you would like to consider "seated", before running this code. hmdIsInitialized = true; ResetInitialHmdPosition(); // initialize Compositor vrCompositor = OpenVR.Compositor; // initialize render textures (for displaying on HMD) uint renderTextureWidth = 0; uint renderTextureHeight = 0; vrSystem.GetRecommendedRenderTargetSize(ref renderTextureWidth, ref renderTextureHeight); //renderTextureWidth /= 2; //renderTextureHeight /= 2; Debug.Log("[KerbalVR] Render Texture size: " + renderTextureWidth + " x " + renderTextureHeight); hmdLeftEyeRenderTexture = new RenderTexture((int)renderTextureWidth, (int)renderTextureHeight, 24, RenderTextureFormat.ARGB32); hmdLeftEyeRenderTexture.antiAliasing = 1; hmdLeftEyeRenderTexture.Create(); hmdRightEyeRenderTexture = new RenderTexture((int)renderTextureWidth, (int)renderTextureHeight, 24, RenderTextureFormat.ARGB32); hmdRightEyeRenderTexture.Create(); hmdLeftEyeTexture.handle = hmdLeftEyeRenderTexture.GetNativeTexturePtr(); hmdLeftEyeTexture.eType = EGraphicsAPIConvention.API_OpenGL; //hmdLeftEyeTexture.eType = EGraphicsAPIConvention.API_DirectX; // this doesn't seem to work hmdLeftEyeTexture.eColorSpace = EColorSpace.Auto; hmdRightEyeTexture.handle = hmdRightEyeRenderTexture.GetNativeTexturePtr(); hmdRightEyeTexture.eType = EGraphicsAPIConvention.API_OpenGL; //hmdRightEyeTexture.eType = EGraphicsAPIConvention.API_DirectX; // this doesn't seem to work hmdRightEyeTexture.eColorSpace = EColorSpace.Auto; // Set rendering bounds on texture to render? // I assume min=0.0 and max=1.0 renders to the full extent of the texture hmdTextureBounds.uMin = 0.0f; hmdTextureBounds.uMax = 1.0f; hmdTextureBounds.vMin = 0.0f; hmdTextureBounds.vMax = 1.0f; // create the hidden area mask meshes HiddenAreaMesh_t vrHiddenAreaMesh = vrSystem.GetHiddenAreaMesh(EVREye.Eye_Left); hmdHiddenAreaMeshLeft = SteamVR_Utils.CreateHiddenAreaMesh(vrHiddenAreaMesh, hmdTextureBounds); vrHiddenAreaMesh = vrSystem.GetHiddenAreaMesh(EVREye.Eye_Right); hmdHiddenAreaMeshRight = SteamVR_Utils.CreateHiddenAreaMesh(vrHiddenAreaMesh, hmdTextureBounds); // TODO: Need to understand better how to create render targets and incorporate hidden area mask mesh // search for camera objects to render foreach (string cameraName in cameraNamesToRender) { foreach (Camera camera in Camera.allCameras) { if (cameraName.Equals(camera.name)) { float nearClipPlane = (camera.name.Equals(cameraNames[3])) ? 0.05f : camera.nearClipPlane; HmdMatrix44_t projLeft = vrSystem.GetProjectionMatrix(EVREye.Eye_Left, nearClipPlane, camera.farClipPlane, EGraphicsAPIConvention.API_OpenGL); HmdMatrix44_t projRight = vrSystem.GetProjectionMatrix(EVREye.Eye_Right, nearClipPlane, camera.farClipPlane, EGraphicsAPIConvention.API_OpenGL); //HmdMatrix44_t projLeft = vrSystem.GetProjectionMatrix(EVREye.Eye_Left, nearClipPlane, camera.farClipPlane, EGraphicsAPIConvention.API_DirectX); // this doesn't seem to work //HmdMatrix44_t projRight = vrSystem.GetProjectionMatrix(EVREye.Eye_Right, nearClipPlane, camera.farClipPlane, EGraphicsAPIConvention.API_DirectX); // this doesn't seem to work camerasToRender.Add(new CameraProperties(camera, camera.projectionMatrix, MathUtils.Matrix4x4_OpenVr2UnityFormat(ref projLeft), MathUtils.Matrix4x4_OpenVr2UnityFormat(ref projRight))); break; } } } foreach (Camera camera in Camera.allCameras) { if (cameraNames[5].Equals(camera.name)) { uiCamera = camera; } } // detect controllers for (uint idx = 0; idx < OpenVR.k_unMaxTrackedDeviceCount; idx++) { if ((ctrlIndexLeft == 0) && (vrSystem.GetTrackedDeviceClass(idx) == ETrackedDeviceClass.Controller)) { ctrlIndexLeft = idx; } else if ((ctrlIndexRight == 0) && (vrSystem.GetTrackedDeviceClass(idx) == ETrackedDeviceClass.Controller)) { ctrlIndexRight = idx; } } bool ctrlFocusCaptured = vrSystem.CaptureInputFocus(); if (!ctrlFocusCaptured) { Debug.LogWarning("[KerbalVR] Controller input focus was not captured"); } return(retVal); }