private static PosRot GetTrackerWorldPosRot(XRNodeState tracker) { Vector3 pos = new Vector3(); Quaternion rot = new Quaternion(); try { var notes = new List <XRNodeState>(); InputTracking.GetNodeStates(notes); foreach (XRNodeState note in notes) { if (note.uniqueID != tracker.uniqueID) { continue; } if (note.TryGetPosition(out pos) && note.TryGetRotation(out rot)) { var roomCenter = BeatSaberUtil.GetRoomCenter(); var roomRotation = BeatSaberUtil.GetRoomRotation(); pos = roomRotation * pos; pos += roomCenter; rot = roomRotation * rot; } } } catch (Exception e) { Logger.Log(e.Message + "\n" + e.StackTrace, Logger.LogLevel.Error); } return(new PosRot(pos, rot)); }
public void ResizeAvatar(SpawnedAvatar avatar) { if (!avatar.customAvatar.descriptor.allowHeightCalibration) { return; } // compute scale float scale; AvatarResizeMode resizeMode = SettingsManager.settings.resizeMode; switch (resizeMode) { case AvatarResizeMode.ArmSpan: float playerArmLength = SettingsManager.settings.playerArmSpan; var avatarArmLength = avatar.customAvatar.GetArmSpan(); scale = playerArmLength / avatarArmLength; break; case AvatarResizeMode.Height: scale = BeatSaberUtil.GetPlayerEyeHeight() / avatar.customAvatar.eyeHeight; break; default: scale = 1.0f; break; } // apply scale avatar.behaviour.scale = scale; SharedCoroutineStarter.instance.StartCoroutine(FloorMendingWithDelay(avatar)); }
public void ResizeAvatar(SpawnedAvatar avatar) { if (!avatar.customAvatar.descriptor.allowHeightCalibration || !avatar.customAvatar.isIKAvatar) { return; } // compute scale float scale; AvatarResizeMode resizeMode = SettingsManager.settings.resizeMode; switch (resizeMode) { case AvatarResizeMode.ArmSpan: float avatarArmLength = avatar.customAvatar.GetArmSpan(); if (avatarArmLength > 0) { scale = SettingsManager.settings.playerArmSpan / avatarArmLength; } else { scale = 1.0f; } break; case AvatarResizeMode.Height: float avatarEyeHeight = avatar.customAvatar.eyeHeight; if (avatarEyeHeight > 0) { scale = BeatSaberUtil.GetPlayerEyeHeight() / avatarEyeHeight; } else { scale = 1.0f; } break; default: scale = 1.0f; break; } if (scale <= 0) { Plugin.logger.Warn("Calculated scale is <= 0; reverting to 1"); scale = 1.0f; } // apply scale avatar.tracking.scale = scale; SharedCoroutineStarter.instance.StartCoroutine(FloorMendingWithDelay(avatar)); }
private static PosRot GetXRNodeWorldPosRot(XRNode node) { var pos = InputTracking.GetLocalPosition(node); var rot = InputTracking.GetLocalRotation(node); var roomCenter = BeatSaberUtil.GetRoomCenter(); var roomRotation = BeatSaberUtil.GetRoomRotation(); pos = roomRotation * pos; pos += roomCenter; rot = roomRotation * rot; return(new PosRot(pos, rot)); }
private IEnumerator FloorMendingWithDelay(SpawnedAvatar avatar) { yield return(new WaitForEndOfFrame()); // wait for CustomFloorPlugin:PlatformManager:Start to hide original platform float floorOffset = 0f; if (SettingsManager.settings.enableFloorAdjust && avatar.customAvatar.isIKAvatar) { float playerEyeHeight = BeatSaberUtil.GetPlayerEyeHeight(); float avatarEyeHeight = avatar.customAvatar.eyeHeight; floorOffset = playerEyeHeight - avatarEyeHeight * avatar.tracking.scale; if (SettingsManager.settings.moveFloorWithRoomAdjust) { floorOffset += BeatSaberUtil.GetRoomCenter().y; } } floorOffset = (float)Math.Round(floorOffset, 3); // round to millimeter // apply offset avatar.tracking.verticalPosition = floorOffset; // ReSharper disable Unity.PerformanceCriticalCodeInvocation GameObject menuPlayersPlace = GameObject.Find("MenuPlayersPlace"); GameObject originalFloor = GameObject.Find("Environment/PlayersPlace"); GameObject customFloor = GameObject.Find("Platform Loader"); // ReSharper disable restore Unity.PerformanceCriticalCodeInvocation if (menuPlayersPlace) { Plugin.logger.Info($"Moving MenuPlayersPlace floor {Math.Abs(floorOffset)} m {(floorOffset >= 0 ? "up" : "down")}"); menuPlayersPlace.transform.position = new Vector3(0, floorOffset, 0); } if (originalFloor) { Plugin.logger.Info($"Moving PlayersPlace {Math.Abs(floorOffset)} m {(floorOffset >= 0 ? "up" : "down")}"); originalFloor.transform.position = new Vector3(0, floorOffset, 0); } if (customFloor) { Plugin.logger.Info($"Moving Custom Platforms floor {Math.Abs(floorOffset)} m {(floorOffset >= 0 ? "up" : "down")}"); _initialPlatformPosition = _initialPlatformPosition ?? customFloor.transform.position; customFloor.transform.position = (Vector3.up * floorOffset) + _initialPlatformPosition ?? Vector3.zero; } }
private void ResizePlayerAvatar() { if (_currentSpawnedPlayerAvatar?.GameObject == null) { return; } if (!_currentSpawnedPlayerAvatar.CustomAvatar.AllowHeightCalibration) { return; } var playerHeight = BeatSaberUtil.GetPlayerHeight(); if (playerHeight == _prevPlayerHeight) { return; } _prevPlayerHeight = playerHeight; _currentSpawnedPlayerAvatar.GameObject.transform.localScale = _startAvatarLocalScale * (playerHeight / _currentSpawnedPlayerAvatar.CustomAvatar.Height); Plugin.Log("Resizing avatar to " + (playerHeight / _currentSpawnedPlayerAvatar.CustomAvatar.Height) + "x scale"); }
private IEnumerator FloorMendingWithDelay(SpawnedAvatar avatar) { yield return(new WaitForEndOfFrame()); // wait for CustomFloorPlugin:PlatformManager:Start to hide original platform float floorOffset = 0f; if (SettingsManager.settings.enableFloorAdjust && avatar.customAvatar.isIKAvatar) { float playerViewPointHeight = BeatSaberUtil.GetPlayerEyeHeight(); float avatarViewPointHeight = avatar.customAvatar.viewPoint.position.y; floorOffset = playerViewPointHeight - avatarViewPointHeight * avatar.behaviour.scale; } // apply offset avatar.behaviour.position = new Vector3(0, floorOffset, 0); // ReSharper disable Unity.PerformanceCriticalCodeInvocation var originalFloor = GameObject.Find("MenuPlayersPlace") ?? GameObject.Find("Static/PlayersPlace"); var customFloor = GameObject.Find("Platform Loader"); // ReSharper disable restore Unity.PerformanceCriticalCodeInvocation if (originalFloor) { Plugin.logger.Info($"Moving original floor {Math.Abs(floorOffset)} m {(floorOffset >= 0 ? "up" : "down")}"); originalFloor.transform.position = new Vector3(0, floorOffset, 0); } if (customFloor) { Plugin.logger.Info($"Moving Custom Platforms floor {Math.Abs(floorOffset)} m {(floorOffset >= 0 ? "up" : "down")}"); _initialPlatformPosition = _initialPlatformPosition ?? customFloor.transform.position; customFloor.transform.position = (Vector3.up * floorOffset) + _initialPlatformPosition ?? Vector3.zero; } }
public void CalibrateFullBodyTracking() { Plugin.logger.Info("Calibrating full body tracking"); TrackedDeviceManager input = PersistentSingleton <TrackedDeviceManager> .instance; TrackedDeviceState head = input.head; TrackedDeviceState leftFoot = input.leftFoot; TrackedDeviceState rightFoot = input.rightFoot; TrackedDeviceState pelvis = input.waist; Vector3 floorNormal = Vector3.up; float floorPosition = SettingsManager.settings.moveFloorWithRoomAdjust ? BeatSaberUtil.GetRoomCenter().y : 0; if (leftFoot.found) { Vector3 leftFootForward = leftFoot.rotation * Vector3.up; // forward on feet trackers is y (up) Vector3 leftFootStraightForward = Vector3.ProjectOnPlane(leftFootForward, floorNormal); // get projection of forward vector on xz plane (floor) Quaternion leftRotationCorrection = Quaternion.Inverse(leftFoot.rotation) * Quaternion.LookRotation(Vector3.up, leftFootStraightForward); // get difference between world rotation and flat forward rotation SettingsManager.settings.fullBodyCalibration.leftLeg = new Pose((leftFoot.position.y - floorPosition) * Vector3.down, leftRotationCorrection); Plugin.logger.Info("Saved left foot pose correction " + SettingsManager.settings.fullBodyCalibration.leftLeg); } if (rightFoot.found) { Vector3 rightFootForward = rightFoot.rotation * Vector3.up; Vector3 rightFootStraightForward = Vector3.ProjectOnPlane(rightFootForward, floorNormal); Quaternion rightRotationCorrection = Quaternion.Inverse(rightFoot.rotation) * Quaternion.LookRotation(Vector3.up, rightFootStraightForward); SettingsManager.settings.fullBodyCalibration.rightLeg = new Pose((rightFoot.position.y - floorPosition) * Vector3.down, rightRotationCorrection); Plugin.logger.Info("Saved right foot pose correction " + SettingsManager.settings.fullBodyCalibration.rightLeg); } if (head.found && pelvis.found) { // using "standard" 8 head high body proportions w/ eyes at 1/2 head height // reference: https://miro.medium.com/max/3200/1*cqTRyEGl26l4CImEmWz68Q.jpeg float eyeHeight = head.position.y - floorPosition; Vector3 wantedPelvisPosition = new Vector3(0, eyeHeight / 15f * 10f, 0); Vector3 pelvisPositionCorrection = wantedPelvisPosition - Vector3.up * (pelvis.position.y - floorPosition); Vector3 pelvisForward = pelvis.rotation * Vector3.forward; Vector3 pelvisStraightForward = Vector3.ProjectOnPlane(pelvisForward, floorNormal); Quaternion pelvisRotationCorrection = Quaternion.Inverse(pelvis.rotation) * Quaternion.LookRotation(pelvisStraightForward, Vector3.up); SettingsManager.settings.fullBodyCalibration.pelvis = new Pose(pelvisPositionCorrection, pelvisRotationCorrection); Plugin.logger.Info("Saved pelvis pose correction " + SettingsManager.settings.fullBodyCalibration.pelvis); } }