Unity复刻Visage/Amnesia开门逻辑:半开后从另一侧关闭旋转重置问题求助
解决方案建议
跟踪门的实时旋转基准
原方案的核心问题是始终以初始0度作为旋转参考,而非门的当前实际角度。每次玩家触发门交互时,先记录门的当前Y轴旋转值作为新的基准点,后续所有鼠标拖动的旋转计算都基于这个实时基准,不再依赖固定初始值。
示例代码:private float currentBaseRotation; void OnStartInteract() { // 记录当前门的旋转作为基准 currentBaseRotation = transform.localEulerAngles.y; }判断玩家与门的相对侧
必须明确玩家处于门的正面还是背面,才能保证拖动方向与门的运动逻辑匹配。通过计算玩家位置与门正面法线的点积判断:点积为正表示在正面,为负则在背面。根据这个结果反转鼠标拖动对应的旋转方向,确保无论在哪一侧,“拖向自己”都是开门、“拖离自己”都是关门。
示例代码:bool IsPlayerOnFrontSide(Transform player) { Vector3 doorToPlayer = player.position - transform.position; float dot = Vector3.Dot(transform.forward, doorToPlayer.normalized); return dot > 0f; }基于当前角度设置旋转范围
给门设置合理的旋转上下限时,要以实时基准为中心(比如基准±90度),而非固定的0度±90度。同时用平滑插值更新旋转,避免跳变:// 计算目标旋转(基于基准和鼠标输入) float targetRotation = currentBaseRotation + (mouseInput * rotationSpeed * (isFrontSide ? 1 : -1)); // 限制在合理范围 targetRotation = Mathf.Clamp(targetRotation, currentBaseRotation - 90f, currentBaseRotation + 90f); // 平滑应用旋转 transform.localEulerAngles = Vector3.Lerp(transform.localEulerAngles, new Vector3(0, targetRotation, 0), Time.deltaTime * 5f);移除强制重置旋转的代码
检查原方案中是否存在交互开始时将门旋转强制重置为0度的逻辑(比如transform.localEulerAngles = Vector3.zero;),直接删除这类语句,替换为记录当前旋转基准的代码。
内容的提问来源于stack exchange,提问作者Gan
相关产品推荐
相关产品推荐

