最近公司PC项目需要串流到Piconec3上运行,HTC手柄是圆盘键按下移动还可以,但是Piconeo3是摇杆,按下移动的话显得不科学,所以写了一套基于圆盘键,使用摇杆移动的方法

第一步:编写摇杆左右旋转功能

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using HTC.UnityPlugin.Vive;
using UnityEngine.UI;
using DG.Tweening;

public class RockerTest : MonoBehaviour {

	public Text hint;
	public Transform VR_Head;
	public GameObject rightRay;
	// Use this for initialization
	void Start () {
		
	}

	bool isRotate = true;
	// Update is called once per frame
	void Update () {
		Vector2 rightPos = ViveInput.GetPadAxis(HandRole.RightHand);

		if (isRotate && Mathf.Abs(rightPos.x)>.7f)
		{
			rightRay.SetActive(false);
			isRotate = false;
			Invoke("ResetRotate",1);
			if (rightPos.x>0)
			{
				hint.text += "—向右旋转";
				Debug.Log("向右旋转");
				VR_Head.rotation = Quaternion.AngleAxis(30, Vector3.up) * VR_Head.rotation;
				//VR_Head.DORotateQuaternion(Quaternion.AngleAxis(30, Vector3.up) * VR_Head.transform.rotation,1);
			}
			else
			{
				hint.text += "—向左旋转";
				Debug.Log("向左旋转");
				VR_Head.rotation = Quaternion.AngleAxis(-30, Vector3.up) * VR_Head.rotation;
				//VR_Head.DORotateQuaternion(Quaternion.AngleAxis(-30, Vector3.up) * VR_Head.transform.rotation, 1);
			}
		}
		
	}
	void ResetRotate() {
		isRotate = true;
		rightRay.SetActive(true);
	}
}

第二步:移动功能,修改原HTC自带的脚本ViveInputVirtualButton

 

第二步修改完以后发现它只是能够显示与隐藏射线,真实的移动在Teleportable脚本里边

第三步,修改移动脚本如下,Unity属性面板选择PadTouch选项

//========= Copyright 2016-2017, HTC Corporation. All rights reserved. ===========

using HTC.UnityPlugin.Vive;
using System.Collections;
using UnityEngine;
using UnityEngine.EventSystems;

public class Teleportable : MonoBehaviour
    , IPointerExitHandler
{
    public enum TeleportButton
    {
        Trigger,
        Pad,
        Grip,
        PadTouch,
    }

    public Transform target;  // The actual transfrom that will be moved Ex. CameraRig
    public Transform pivot;  // The actual pivot point that want to be teleported to the pointed location Ex. CameraHead
    public float fadeDuration = 0.3f;

    public TeleportButton teleportButton = TeleportButton.Pad;

    private Coroutine teleportCoroutine;

    public ControllerButton teleportViveButton
    {
        get
        {
            switch (teleportButton)
            {
                case TeleportButton.PadTouch:
                    return ControllerButton.PadTouch;

                case TeleportButton.Pad:
                    return ControllerButton.Pad;

                case TeleportButton.Grip:
                    return ControllerButton.Grip;

                case TeleportButton.Trigger:
                default:
                    return ControllerButton.Trigger;
            }
        }
    }
#if UNITY_EDITOR
    private void Reset()
    {
        FindTeleportPivotAndTarget();
    }
#endif
    private void FindTeleportPivotAndTarget()
    {
        foreach (var cam in Camera.allCameras)
        {
            if (!cam.enabled) { continue; }
#if UNITY_5_4_OR_NEWER
            // try find vr camera eye
            if (cam.stereoTargetEye != StereoTargetEyeMask.Both) { continue; }
#endif
            pivot = cam.transform;
            target = cam.transform.root == null ? cam.transform : cam.transform.root;
        }
    }

    public void OnPointerExit(PointerEventData eventData)
    {
        Debug.Log("释放触摸");
        // skip if it was teleporting
        if (teleportCoroutine != null) { return; }

        // don't teleport if it was not releasing the button
        //if (eventData.eligibleForClick) { return; }

        //VivePointerEventData viveEventData;
        //if (!eventData.TryGetViveButtonEventData(out viveEventData)) { return; }

        //if (viveEventData.viveButton != teleportViveButton) { return; }

        var hitResult = eventData.pointerCurrentRaycast;
        if (!hitResult.isValid) { return; }

        if (target == null || pivot == null)
        {
            FindTeleportPivotAndTarget();
        }

        var headVector = Vector3.ProjectOnPlane(pivot.position - target.position, target.up);
        var targetPos = hitResult.worldPosition - headVector;

        teleportCoroutine = StartCoroutine(StartTeleport(targetPos, fadeDuration));
    }
#if VIU_STEAMVR
    private bool m_steamVRFadeInitialized;

    public IEnumerator StartTeleport(Vector3 position, float duration)
    {
        var halfDuration = Mathf.Max(0f, duration * 0.5f);

        if (!Mathf.Approximately(halfDuration, 0f))
        {
            if (!m_steamVRFadeInitialized)
            {
                // add SteamVR_Fade to the last rendered stereo camera
                var fadeScripts = FindObjectsOfType<SteamVR_Fade>();
                if (fadeScripts == null || fadeScripts.Length <= 0)
                {
                    var topCam = SteamVR_Render.Top().gameObject;
                    if (topCam != null)
                    {
                        topCam.gameObject.AddComponent<SteamVR_Fade>();
                    }
                }

                m_steamVRFadeInitialized = true;
            }

            SteamVR_Fade.Start(new Color(0f, 0f, 0f, 1f), halfDuration);
            yield return new WaitForSeconds(halfDuration);
            yield return new WaitForEndOfFrame(); // to avoid from rendering guideline in wrong position
            target.position = position;
            SteamVR_Fade.Start(new Color(0f, 0f, 0f, 0f), halfDuration);
            yield return new WaitForSeconds(halfDuration);
        }
        else
        {
            yield return new WaitForEndOfFrame(); // to avoid from rendering guideline in wrong position
            target.position = position;
        }

        teleportCoroutine = null;
    }
#else
    public IEnumerator StartTeleport(Vector3 position, float duration)
    {
        var halfDuration = Mathf.Max(0f, duration * 0.5f);

        if (!Mathf.Approximately(halfDuration, 0f))
        {
            Debug.LogWarning("SteamVR plugin not found! install it to enable SteamVR_Fade!");
            fadeDuration = 0f;
        }

        yield return new WaitForEndOfFrame(); // to avoid from rendering guideline in wrong position
        target.position = position;

        teleportCoroutine = null;
    }
#endif
}
//进行测试,旋转与移动都可以正常运行了
posted on 2021-12-13 18:49  陌洛  阅读(460)  评论(0编辑  收藏  举报