对于Vive,我们可以正常使用,运动追踪功能是 HTC Vive 的一大亮点,这也让很多适配 HTC Vive 的游戏能够让用户动起来,听起来很酷,体验起来也很酷。在小范围移动1:·1的范围内活动或固定位置的游戏中,定位精确,并且延迟很低,各种优点不一而足。 
  但是空间问题,让想在小空间大场景的游戏中的玩家排在了门外,HTC官方建议:HTC 建议消费者在至少 20 平米空间使用全套装备,这也意味着你的游戏房要足够大。土豪就不用往下看了!!!   但是对于想要开疆扩土的用户,在实际中场地大小就成为了局限,用户没有恰好游戏场景大小的场地,游戏场地过大,而玩家场地太小,怎么解决呢? 
  还有就是要是1:1的场地,会有一种游戏场景非常局促,感觉没有走多远就到了边际,让玩家十分不爽。   
  所以这里给出了变比空间的HTC头盔的移动问题的解决方案。 
  当然,若你有更好的办法,也欢迎讨论。 
  我们重点来说,游戏场景过大,而实际场地台较小,需要对位移进行比例加速问题。 
我们要解决问题有三个: 
  1、边界放大 
  2、起点位置平移 
  3、 游戏空间与场地非等比空间速度缩放
 
一、边界放大
  首先,来看看官方SteamVR给出的预制体的顶视图: 
 
泰课在线
 发现没有。 
  在HTC 头盔的游戏中,玩家总在蓝色框的中间位置。而对于需要从(0,0)作为起点的游戏,需要在房间内到处移动,并且根据游戏剧情,需要空间移动的游戏,这个就只可以用原有场地的1/4的场地了,更造成了场地的浪费。 
  我们首先解决的就是位置需要偏移问题。 
  其次,看到蓝色边框的大小了没有。其实蓝色框范围很小, 
 
 
  看代码:
 
 
 
 
 
 
 
public enum Size
{
    Calibrated,
    _400x300,
    _300x225,
    _200x150
}
  这个面积小,不满足需求,怎么办呢? 自己来增加啊,搞大场地!! 
  我就自己做了一个区域标识。
 
 
  小的蓝色框为它原本的400*300的,大的为我自己缩放的区域。 
  选择Size为Calibrated这个选项,缩放即可。特地添加了一个父节点,以防止在直接节点上缩放出问题,xz均缩放为4,Y仍旧为1。 
  这个标识就基本满足游戏中场地大小为9*9米的一个大场地了。
 
二、起点位置平移
  好了。现在回来说,起点的平移问题。 
  分两部: 
  一个是视觉上,就是在游戏编辑器模式下,让玩家在蓝色区域的起点角点位置。这个容易,就是还是平移。平移谁呢,平移蓝色区域,把刚才缩放的那个预制体的父节点做了平移,项目中的平移位置为(4.2,0,4.2)即可。 
  这部分就搞定了。 
  第二部分,就是比较繁琐一点了。 
  说这个问题之前,需要稍微说下SteamVR插件的运行时和编辑状态的相机差别。
 
泰课在线
 
  这个是编辑器模式下的相机状态。 
  但是在运行时候,相机的层级结构会发生较大的变化。  
 
泰课在线
 
  可以看到eye作为父节点,ears作为子节点,而head则被隐藏了。 
  具体代码处理是在SteamVR_Camera.cs中的OnEnable中处理。
  部分代码:
可以看到eye作为父节点,ears作为子节点,而head则被隐藏了。 
  具体代码处理是在SteamVR_Camera.cs中的OnEnable中处理。
  部分代码: 
if (head != t)
{
    Expand();

    t.parent = origin;

    while (head.childCount > 0)
        head.GetChild(0).parent = t;

    // Keep the head around, but parent to the camera now since it moves with the hmd
    // but existing content may still have references to this object.
    head.parent = t;
    head.localPosition = Vector3.zero;
    head.localRotation = Quaternion.identity;
    head.localScale = Vector3.one;
    head.gameObject.SetActive(false);

    _head = t;
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19


还有ears的处理代码,设置ears的相机参数:

if (ears == null)
{
    var e = transform.GetComponentInChildren<SteamVR_Ears>();
    if (e != null)
        _ears = e.transform;
      }

if (ears != null)
    ears.GetComponent<SteamVR_Ears>().vrcam = this;
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9

为什么讲了这么多结构呢?因为它影响到了玩家起点平移的算法和处理。 
怎么处理呢? 
其实是蛮简单。给相机的父节点在初始化时候,重置一个与相机初始化一个相反的参数。 
为什么呢?这正是为了抵消相机在场景中从(0,0)点作为起点的变化啊. 
具体代码:

using UnityEngine;
using System.Collections;

public class PlayerPosIntitial : MonoBehaviour
{
    private bool bUseOnce = false;
    public Transform eye;

    private float starttime;
    private float delaytime = 4.0f;
    // Use this for initialization
    void Start ()
    {
        starttime = Time.time;  
    }

    // Update is called once per frame
    void Update () 
    {
        if (!bUseOnce && (Input.GetMouseButton(0) || Input.GetKey(KeyCode.JoystickButton0) || Time.time - starttime >= delaytime))
        {

            bUseOnce = true;
            if (null != eye) 
            {               
                this.transform.localPosition = new Vector3(-eye.transform.localPosition.x,0,-eye.transform.localPosition.z);
                Debug.Log ("set player initila position");
            }
        }
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6