Unity Prefab未在预期位置实例化

时间:2017-11-17 16:51:39

标签: unity3d navigation transform unity5

Hello stackoverflow社区。
我有一个脚本在位置实例化NPC,保存在特殊列表中。 NPC Prefabs上有一个NavMeshAgent,并放置在普通的NavMesh上。在实例化Prefab之后,我将父对象以及新对象的位置和旋转设置为名为“DynamicObjects”的空对象(仅用于在场景视图中进行分组)。父项Transform在0/0/0处为零旋转,因此设置正常位置应该没有问题。问题是,对象不是在给定坐标处创建的。例如,给定的位置是193 / 6.2 / 87但是NPC将是170 / 6.4 / 87而不是193 / 6.2 / 87。 这是我的脚本(下面的详细说明):

GameObject npcPrefab = Resources.Load<GameObject>("Prefabs/NPC/NPC_default");
foreach (NPC_Wrapper wrapper in npc_wrappers) {
    if (wrapper.position.map != mapID)
        continue;

    GameObject npcObject = Instantiate(npcPrefab);
    npcObject.transform.SetParent(dynamicObjects);

    NPCBase npcBase = npcObject.GetComponent<NPCBase>();
    npcBase.SetPosition(new Vector3(wrapper.position.x, wrapper.position.y, wrapper.position.z));
    npcBase.SetRotation(new Vector3(wrapper.position.rotX, wrapper.position.rotY, wrapper.position.rotZ));
    npcBase.SetEntityID(wrapper.npcID);
    npcBase.SetWorldPosition(wrapper.position);

    Debug.Log("Spawn NPC " + wrapper.npcID + " at " + wrapper.position.x + "/" + wrapper.position.y + "/" + wrapper.position.z);
}

解释
第一步是加载预制件。我有一个包含NPC_Wrapper对象的列表。那些包装包含NPC的位置。我检查每个NPC,如果它在这个地图中(mapID)。如果它在此映射中,则实例化预制件并将父级设置为dynamicObjects(我的空对象的变换)。现在我从Instantiated对象中获取我的NPCBase类,并使用SetPosition和SetRotation方法设置transform.position和transform.rotation(它只是这样做,但是在NPCBase类中)。 SetEntityID和SetWorldPosition没有效果,所以我们可以跳过它们。当我完成后,我将它应该的位置记录到控制台。虽然我设置了正确的坐标,但GameObject不会位于wrapper.position.xyz中的位置。

我尝试了什么:

  • 用transform.localPosition
  • 替换transform.position
  • 使用NavMeshAgent.nextPosition代替transform.position
  • 设置为0/0/0(似乎工作正常)
  • 实例化而不设置父级(无差异)
  • 直接在此方法中设置位置:npcObject.transform.position = ...(无差异)
  • 搜索互联网和这个论坛(但无法找到一个好的答案或解决我的问题的答案)

我试着自己搞清楚了一段时间,但我真的很沮丧,所以我想我会问是否有人知道可能是什么问题。
提前感谢您,我将很乐意回答您的任何问题!

1 个答案:

答案 0 :(得分:0)

经过2天的调试后,我明白了!

因此,实例化的GameObject上有一个NavMeshAgent。我实例化它并将位置设置到我想要的位置。问题是,NavMeshAgent将在产生后的第一帧中更改GameObject的位置。那是因为虽然对象在有效的NavMesh上,但是Agent会以某种方式调整它的初始位置。

我如何解决它:
老实说,像这样的大多数问题都有相当简单的解决方案。在这种情况下,请不要使用 transform.position = newVector 设置对象的位置,而是使用 navmeshagent.Warp(newVector)。这适用于所有测试案例 希望有这个问题的其他人也可以从中获益:)