上一篇文章我们实现了:拾取。
这次我们来点摆放。
只要在上一次代码的基础上,获取一下hit point,在结合创建逻辑就可实现。
private Entity Create(float3 pos)
{
EntityManager entityManager = World.DefaultGameObjectInjectionWorld.EntityManager;
// 把 entityFromPrefab 在 MonoBehaviour 内存储起来了(成员变量). var instance = entityManager.Instantiate(entityFromPrefab);
#if UNITY_EDITOR entityManager.SetName(instance, prefab.name + instance.Index);
#endif
// 老样子,设置物理的Box, 暂时还没细化正确数据. BoxGeometry boxGeometry = new BoxGeometry();
boxGeometry.Size = 1;
boxGeometry.Center = float3.zero;
boxGeometry.Orientation = quaternion.identity;
entityManager.AddComponentData(instance, new PhysicsCollider
{
Value = Unity.Physics.BoxCollider.Create(boxGeometry)
}
);
// 这是一个有趣的地方. // pos.y += 1f; entityManager.SetComponentData(instance, new Translation {Value = pos}); //赋值新位置.
return instance;
}
private Entity Raycast(float3 fromPosition, float3 toPosition)
{
BuildPhysicsWorld buildPhysicsWorld =
World.DefaultGameObjectInjectionWorld.GetExistingSystem();
CollisionWorld collisionWorld = buildPhysicsWorld.PhysicsWorld.CollisionWorld;
RaycastInput raycastInput = new RaycastInput
{
Start = fromPosition,
End = toPosition,
Filter = new CollisionFilter
{
BelongsTo = ~0u,
CollidesWith = ~0u,
GroupIndex = 0,
}
};
Unity.Physics.RaycastHit raycastHit = new Unity.Physics.RaycastHit();
if (collisionWorld.CastRay(raycastInput, out raycastHit))
{
Entity hitEntity = buildPhysicsWorld.PhysicsWorld.
Bodies[raycastHit.RigidBodyIndex].Entity;
Create(raycastHit.Position); // 在这里得到点击位置.
return hitEntity;
}
else
{
return Entity.Null;
}
}
private void Update()
{
if (Input.GetMouseButtonUp(0))
{
UnityEngine.Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
float rayDistance = 1000f;
Debug.Log(Raycast(ray.origin, ray.origin + ray.direction * rayDistance));
}
}
运行起来,有趣的事情发生了(为了准确看出,我换成了Cube):Cube 先飞上去了,然后再落下来的
看到有趣的现象,再分析一下,很简单,因为射线检测得到的坐标是:鼠标拾取floor时,接触点的坐标,点在floor的表面; 而BoxGeometry的Pivot 是几何中心;
(这里是由于设置的 boxGeometry.Size = 1; 和是不是 Cube 无关)
相当于: Cube放上去时就已经和floor穿透叠加了,Cube自然会被"弹飞",然后因为重力落下。所以需要把Cube放置的位置"人为"的上提一点,也就是 0.5f 个高度。这样就“正好”摆在floor上。
我更喜欢我代码中后来加的: "// 这是一个有趣的地方." 给 "pos.y += 1f; " 这个效果比较有趣. (实际不改pos.y, 直接给Cube加重量,物体很"重",则也不会使物体被挤飞, 修改PhysicsBody-Mass)
让我们换回人,减低点高度 pos.y += 0.5f ,效果:运行效果
因为BoxGeometry我还是凑合用的最简单的,所以导致影子还有问题。慢慢改进~