You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Unity3D(C#)玩家触碰LevelEnd1无法传送问题求助

问题排查与解决

日志能正常输出说明碰撞检测已经触发,但玩家没被传送,核心问题出在CharacterController组件的特性——直接修改transform.position会被CharacterController的内置移动逻辑覆盖,尤其是当玩家对象带有CharacterController时,它会在FixedUpdate阶段修正位置,导致你设置的坐标被重置。

下面是几种可行的解决方法:

方法1:临时禁用CharacterController再修改位置

先禁用CharacterController,修改坐标后再重新启用,避免内置逻辑干扰:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class PlayerTouched : MonoBehaviour
{
    public GameObject Player;
    private CharacterController _playerController;

    void Start()
    {
        // 提前获取玩家的CharacterController组件
        _playerController = Player.GetComponent<CharacterController>();
    }

    public void OnControllerColliderHit(ControllerColliderHit collision)
    {
        if (collision.gameObject.tag == "LevelEnd1")
        {
            // 禁用控制器
            _playerController.enabled = false;
            // 设置位置
            Player.transform.position = new Vector3(-193.5f, 5.860001f, 803.13f);
            // 延迟一帧再启用(确保位置生效)
            StartCoroutine(EnableControllerAfterFrame());
            Debug.Log("it worked!!");
        }
    }

    IEnumerator EnableControllerAfterFrame()
    {
        yield return null;
        _playerController.enabled = true;
    }
}

方法2:使用CharacterController的Teleport方法(Unity 2020+支持)

Unity 2020及以上版本给CharacterController加了Teleport方法,专门用来传送玩家,不会和内置逻辑冲突:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class PlayerTouched : MonoBehaviour
{
    public GameObject Player;
    private CharacterController _playerController;

    void Start()
    {
        _playerController = Player.GetComponent<CharacterController>();
    }

    public void OnControllerColliderHit(ControllerColliderHit collision)
    {
        if (collision.gameObject.tag == "LevelEnd1")
        {
            // 使用Teleport直接传送
            _playerController.Teleport(new Vector3(-193.5f, 5.860001f, 803.13f));
            Debug.Log("it worked!!");
        }
    }
}

额外检查点

  • 确认LevelEnd1对象的碰撞体不是触发器,如果是触发器,需要把OnControllerColliderHit换成OnTriggerEnter(Collider other),并确保玩家的CharacterController勾选了Trigger选项(或者碰撞体的IsTrigger设置和对应函数匹配)
  • 检查玩家是否有其他脚本在修改位置,比如移动脚本在FixedUpdate里持续更新坐标,导致传送位置被覆盖

内容的提问来源于stack exchange,提问作者berxiv

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.13 12:15:36