怎么通过Unity和谷歌纸盒做一个VR游戏?(译)

原文链接:点击打开链接

作者是用iPhone适配的,我是用的Android手机且由于SDK版本的关系所以会有些小细节不一样。

游戏工程地址:忍者飞镖

GoogleVR SDK for Unity:SDK 或 https://developers.google.com/vr/

                                                                                           怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第1张图片

欢迎……来到三维空间!

可以很负责任的说每个人都在期待着虚拟现实体验,自从现代经典电影《割草者》的上映,向我们预示了一个可喜的未来……额,通过虚拟现实

我们可以拥有心灵感应类似的力量。

在这篇指导内,你会通过谷歌纸盒学习将一个简单的Unity游戏变成一个VR游戏来帮助人类准备好心灵感应的能力和虚拟现实。此文,你会学习到:

1.集成一个VR摄像机到你的工程

2.修改UI元素让它们工作在VR模式

3.让按钮在VR模式下可以选中

4.在运行中以编程的方式完成VR和普通模式的切换

Note:在写的时候,通过VR拥有思维控制和成为超人一般的能力不是一个可行的科技,不管《割草者》展示给我们的那些。因此,直到有了思维控制API,

坚持掌握先驱者(VR技术~_~)。


什么是谷歌纸盒?

原理上创建一个VR体验是很直接的。替换掉显示在你屏幕上的单个图片,变成两张图片~

他们来自两个摄像机隔开一点距离放置,用户通过左眼看左边的图片,反之亦然,创建出有深度的景象。

而且,通过正确的传感器数据,你可以检测到用户面朝哪个方向。结合到你创建的3D场景,你会得到一个沉浸式的体验。

通常,这需要一些相当复杂精妙的硬件去显示两个高分辨率的图像,连同追踪用户的头部,把所有的内容放进一个小且足够明亮设备中不会伤害你的颈部。

                                                                                                  怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第2张图片

然而,结果证明这样一个高科技先进设备正是你口袋的arm架构的手机。几乎所有的智能手机,它是纸盒之前的idea。你的手机有显示和传感器可以把他们变成

一个可用的VR设备,只需要一个纸盒子和两个塑料透镜。


开始吧


Note:你需要使用不少的UnityGUI的一些知识,如果你从来没有接触过,你可能需要学习一下UGUI


为了开始制作你自己的VR游戏,你需要以下内容:

1.5.x版本的Unity开发套件

2.一部智能手机,iPhone 5或Android 4.1以后。

3.一个装手机的VR设备


Note:如果你对Unity不熟悉也不了解相应借口,你可以去Unity官网进行学习。


没有VR设备我能否进行开发?

当然阔以,运行在手机上就是这样滴:

                                                                  怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第3张图片

当播放的时候如果你盯住屏幕,你可以近似的得到一个3D的体验。如果你移动你的手机,通过绑住你的头你可以控制它,模拟点击通过敲击屏幕(装进盒子

了怎么敲? 所以最好还是有个蓝牙手柄……当然不装进去点着玩儿也不错)~

尽管你可以通过使用VR一体机玩游戏去感受它是什么感觉,但并不意味着你应该这样做。有点像吃巧克力和听别人说巧克力是什么味道。当然,你会得到一般

的印象,但并不一样。

长话短说:如果你没有耐心等到VR设备的到来,你仍然可以学习这篇向导,但有正确的装备去操作你会得到更多。


例子游戏——忍者回旋镖

花点儿时间玩玩你的例子游戏,下载链接在文章开始处。

接下来打开你的Unity,选择Open Project打开StarterNinja文件夹,然后打开NinjaAttack工程。

选择Assets目录下的MainScene打开,然后开始玩游戏。

左边是你的忍者,怪物会穿过屏幕,点击屏幕上的任何地方发射忍者飞镖打倒他们!打倒20个怪物你就赢了,但是如果怪物到达了左边的红色区域,你就输了。

                                       怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第4张图片


从谷歌VR的SDK开始

首先你需要下载SDK,文章开始处有找寻相应SDK的方法,自行下载~

接下来导入到你的工程,从Unity的菜单处点击Asset\Import Package\Custom Package……之后选择GoogleVRForUnity.unitypackgage,也就是你下载的SDK。

确认所有的都选中了,去掉选中DemoScenes文件夹(就是一些例子导不导入随意),然后点击导入按钮。

                                                             怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第5张图片

乘热打铁

为了让你的游戏成为VR模式,你需要展示一些快速的暗招。

在GoogleVR\Prefabs文件夹中,将GvrViewerMain预制体拖到Hierachy中。设置它的坐标几乎是你忍者角色的坐标(-5.53, 1.13, 0.122)

和Y轴旋转90度

                                                           怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第6张图片

你会意识到这个坐标比忍者的中心位置高一点,实际上你是通过它的眼睛看出去的。GvrViewerMain默认以第一个主相机为目标来进行相机的分身

处理所以你需要将主相机也调整到对应的位置,让主相机刚好渲染出角色视角看到的场景(可以通过修改之前的相机到Perspective模式,推荐新建

一个相机然后关闭正交相机,之后动态切换相机的时候还需要默认的相机)。

现在在你的编辑器中运行游戏,你应该看到场景被重新组装成了3D的!如果此时你按住Alt键然后晃动你的鼠标,相机会像你转动你的头一样运动。

                                                             怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第7张图片

把这个场景在你的安卓设备上跑起来

在你的编辑器里运行游戏是好的,但是我最后一次检查了没有合适的VR设备和好的电脑这样运行起来是痛苦的,因此我们工作在手机上。

                                                                                             怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第8张图片

1.选中File\Build Settings——Android应该被选择为你的默认平台

2.点击Player Settings到达inspector界面

3.在Resolution and Presentation下选择Default Orientation为Landscape Left

4.在Other Settings里把Bundle Identifier改成合适的组织名称(com.xxx.xxxx   默认的编译会报错)

                                                              怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第9张图片

连接上你的手机和电脑之后,选择Build and Run之后选择输出文件夹,随意路径。

Unity会导出你的工程,之后会将会发布到你的手机上,装进你的VR设备调节好视距之类的就开始体验吧。

                                                                                            怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第10张图片

Note:如果发布到手机,手机启动应用时出现了什么错误,你可以用Android的IDE查看相应的log信息,或者adb logcat > d:\logcat.txt

将运行的log抓取出来然后判断是哪里出错了。


重新制作这个游戏!

总的来说可以观看你的游戏世界是很棒的,但是你需要玩儿它。独特的讲,你想要往面朝的地方发射忍者飞镖,那是你刚开始玩儿游戏所体会到的。

UI层面,纸盒支持一个按钮(我用的淘宝上买的,有蓝牙手柄~),会感受到限制,但是结合到你头部的动作跟踪,它允许你更加完整的交互。

在游戏中,你会检测用户的GvrViewer.Instance.VRModeEnabled属性。你会检查GvrViewer.Instance.Triggered按钮是否

按下的属性。如果都为true,你就会在面朝的方向发射一个飞镖。

打开你的 NinjaStarLauncher.cs 脚本,你可以在GameLogic 游戏物体上找到。

创建一个新的私有变量:

private Vector3 _vrShooterOffset;

  Start()方法中初始化它:

_vrShooterOffset = new Vector3(0.0f, -0.4f, 1.0f);
用以下代码替换你的 Update()

void Update () {
  //1 
  if (GvrViewer.Instance.VRModeEnabled && GvrViewer.Instance.Triggered && !_gameController.isGameOver) {  
    GameObject vrLauncher = GvrViewer.Instance.GetComponentInChildren().gameObject;
    // 2
    LaunchNinjaStarFrom(vrLauncher, _vrShooterOffset);
  } else if (!GvrViewer.Instance.VRModeEnabled && Input.GetButtonDown("Fire1") && 
    !_gameController.isGameOver) {
    // This is the same code as before
    Vector3 mouseLoc = Input.mousePosition;
    Vector3 worldMouseLoc = Camera.main.ScreenToWorldPoint(mouseLoc);
    worldMouseLoc.y = ninja.transform.position.y;
    ninja.transform.LookAt(worldMouseLoc);
    LaunchNinjaStarFrom(ninja, _shooterOffset);
  }
}
它你会让你的游戏运行起来,看看Update方法做了啥:

1.首先检测你是否处于VR模式且用户点击了按钮被单例模式的GvrViewer.Instance 检测属性的变化。

2.之后你可以调用LaunchNinjaStarFrom() 方法去实例化一个忍者飞镖,传进去两个参数:

A.首先是你的头部游戏对象,谷歌VR库为你准备好了,应该已经指向了正确的方向.

B.第二个是一个轻度的偏移,因此这个方法实例化一个忍者飞镖在你的前面一点下方一点,看起来更加的正常,总不希望飞镖

从你的眼睛里面发射出来吧?很酷,但很奇怪~


你的飞镖在被生成出来的时候就注定要在你面朝的方向飞走,它会朝着正确的地方开火~

换个方式尝试!在这个点上,你可以旋转你的头部去射击坏人,输还是赢逻辑仍然有用。

                                                             怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第11张图片

修复Game Over菜单

正如你所观察到的那样,当游戏结束的时候留下的还是之前的游戏结束菜单。没有以正确的3D模式去显示,所以没法去点击它。

                                                            怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第12张图片

游戏当前使用的是画布显示——UGUI里面的——去显示Game Over,总是显示在游戏窗口的最上层。

这个画布对很多的游戏都是很实用的,它会自动缩放自身去适应你的屏幕,不管你的游戏摄像机在做什么,它对不同的屏幕尺寸是友好的。

但在这种情况下,你需要一个GUI画布存在于世界坐标中,会被3D场景渲染,同样因为你不想让它随着摄像机的移动而没有变化。

你想要你的用户可以朝上看朝下看,看向不同的UI元素通过点击按钮激活它。


创建一个新的Canvas

在Hierachy中选中并复制一份GameOverCanvas

将副本重命名为VRGameOverCanvas,为了与原始的作区分把其子对象GameOverTxt重命名成 VRGameOverTxt.

                                                                                   

VRGameOverCanvas的组件Canvas中,把Render Mode变成World Space

Rect Transform组件中,改变属性Position(-2.24, 1.1, 0.07),Y Rotation90.

最后,把X和Y的缩放为0.009.所有设置好了之后为像这样滴:

                                                                       怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第13张图片  

之后,你应该看见两个画布会重叠(游戏没有运行的时候):

                                                                  怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第14张图片

这些值是从哪里来的?老实说,我也是瞎搞了很久直到把他们弄起来在纸盒内看起来比较好。

有时候编程更像是一门艺术而不是科学……


支持两种画布

接下来,你要修改GameController.cs去意识到两种画布的存在。打开脚本并修改,这个脚本同样挂载在GameLogic游戏物体上。

在类中加上这两个公有变量:

public Canvas VRGameOverCanvas;
public Text VRGameOverTxt;
GameOver()
方法替换为:
public void GameOver(bool didIWin) {
    isGameOver = true;
    _didIWin = didIWin;
    string finalTxt = (_didIWin) ? "You won!" : "Too bad";
    if (GvrViewer.Instance.VRModeEnabled) {
        VRGameOverCanvas.enabled = true;
        VRGameOverTxt.text = finalTxt;
    } else {
        gameOverCanvas.enabled = true;
        gameOverTxt.text = finalTxt;
    }
}
这会显示合适的画布和文字对象,取决于你是否处于VR模式 ( GvrViewer.Instance.VRModeEnabled ).

在你保存了你的脚本之后,你需要为你的新变量赋上正确的值。

找到GameController 脚本,像下图一样赋值。

                                                               怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第15张图片

Note:你是否在想你为什么要支持两种画布而不是只是替换到现在有的呢?因为最终你需要支持两种模式,调整状态!


如果你现在运行你的游戏,你会看见合适的VR模式游戏结束界面。可以朝上看朝下看,看不同的部分,当你点击Play Again按钮时就会消失。

                                                        怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第16张图片


Note:至少,理论上看起来应该是这样的。

练习中,5.3.4p2的Unity会有一个BUG,世界坐标系的GUI画布不会渲染到RenderTexture(这啥?),所以谷歌的SDK使用扭曲修正——你在

两个摄像机中看见的鱼眼效果。


作为一个暂时的变通方案,你可以在GvrViewerMain对象的Gvr Viewer组件上改变Distortion Correction为None。

                                                         怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第17张图片

这意味着你可能会看见轻微的扭曲,当你把游戏放入你的VR设备区看的时候,但至少你能够看见你的GUI。


添加凝视输入

幸运滴,Unity内置支持相机中心点作为一个鼠标,当使用世界坐标系的GUI的时候,但你需要提供一个附加的脚本让其在VR模式下工作。

首先,把你的主相机放置在GvrViewerMain对象的子节点上:

                                                                                             怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第18张图片

选择你的VRGameOverCanvas 对象,你会看见Event Camera选项,将VR Main Camera选中(之前你修改的主相机)

                                                                        怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第19张图片

点击在Hierachy中的EventSystem  对象,添加GazeInputModule 脚本。这是一个让UGUI明白谷歌VR相机是怎么工作的。

选中VR Mode Only选项框,因为你只是想要工作在VR模式而不是普通的版本。

最终把你的Gaze InputModule往上移保证它的优先级,最终看起来会像这样:

                                                                     怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第20张图片

现在尝试一下!当你聚焦到PlayAgain按钮上,它应该变成绿色,然后点击一下屏幕就会开始新的游戏!

                                                      怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第21张图片

细微的游戏调整

因此,也许你发现在VR模式的这个版本很难。这个部分是因为在VR模式下你减小了视野,在你看向错误的方向的时候敌人也更容易溜走。

同时,你不能和以前一样快速的转变你的方向去瞄准,物理上被你的脖子转动速度所限制。

                                                                                                怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第22张图片

你不想让选择玩VR模式的玩家遭罪!所有你怎么修正这个呢?

                                                                                          怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第23张图片

额,我会建议减少敌人的速度。你会怎么想?

选中你在Prefab文件夹内的EvilSlimeEnemy预制体,打开挂载上面的EnemyMover.cs脚本。加上以下代码,

正好在之前设置thisSpeed的地方:

if (GvrViewer.Instance.VRModeEnabled) { 
  thisSpeed *= 0.85f; 
}
这会让你的敌人更集中一点,如果你想让它们空出一些空间,找到 EnemySpawner.cs
——它挂载在你的 GameLogic游戏物体上——添加以下代码行在 SetNextLaunch()方法中,

在你设置了launchInterval之后:

if (GvrViewer.Instance.VRModeEnabled) { 
  launchInterval *= 1.1f;
}
这会让你的VR游戏更加容易尝试——足够让你的玩家选择这样玩儿不感到坑爹。


修改屏幕上显示的分数
其他的UI元素你需要在屏幕上定位的是分数对象,你将尝试轻微的不同方式。仍然需要出现在在合适的VR模式,你想要修改它

在你的摄像机看向任何地方的时候。


想象把你的分数投影在一片持续运动的玻璃上,因此它总是与你看向的地方保持2米远的距离。这是你将要创建的效果。

你将要实现它通过另一个渲染在3D世界的画布,将它变成GoogleVR Head 对象的子物体(这是原文作者的实现方式,我没弄成

不知道原文作者的效果是不是分数面板跟着头一起动的,我的是固定在一个地方的。因为它的SDK貌似是有一个相机的,可以放置到

头部跟踪,而我的SDK是没有相机,通过渲染主相机达到的,没法去跟踪头部运动~)。


然后在GvrViewerMain中右击新建一个Canvas,重命名为VRScoreCanvas将Render Mode变为World Space。

设置以下值:

1.Position:(0,1,2.5)

2.Width:400, Height: 100

3.Rotation:(0,0,0)

4.Scale:(0.0115, 0.0115, 1)

当你设置好了之后,应该像下面一样:

                                                                     怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第24张图片

在你的VRScoreCanvas右击添加UI\Text子物体,重命名为VRScoreTxt。把锚点设置为左上方,Position的值为(150, -65, 0)和Width为60。

在文本组件中,设置字体大小为18对其方式为右对齐,值为999,完成后像这样:

                                                                           怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第25张图片

它也许看起来很奇怪的位于你屏幕的中央,但是在VR模式,你看见的比你实际世界要少很多,所以结果上这文字是很靠近你的视野边界的。

自由调试让它看起来在你的手机上合适。

接下来添加这个物体来显示你的分数,过程和你显示GameOver文字很类似。

打开GameController.cs然后添加一个公有变量:

public Text VRScoreTxt;
然后,你会每次更新你的VRScoreTxt去更新分数,在ResetGame()方法中添加这一行,刚好在你更新scoreTxt之后:

VRScoreTxt.text = "--";
接下来添加这一行在GotOne()方法里面,刚好在你更新scoreTxt之后:

VRScoreTxt.text = "" + _currScore;
保存你的脚本,回到Unity你会发现GameLogic游戏对象上的GameController组件有了空处,将VRScoreTxt赋值。
                                                              怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第26张图片

再次运行你的游戏,你会看见分数出现在了你的视野中,并且跟随你的头部运动。


进入和跳出VR模式

自从你的游戏工作在普通模式和VR模式,你需要让用户有能力去切换他们。

一个UI很直接就可以实现,你添加一个简单的按钮,可以切换VR模式和普通模式。福利来了,谷歌VR的SDK自己有一个返回按钮,你可以

用它来返回普通模式。

试一下!

首先,你将要添加一些代码去切换VR模式。选中GameLogic游戏物体,点击添加组件,新增CardboardSwapper脚本(我新增这个脚本会编译不过,

所以搞成了Changer脚本,不知道是不是命名被sdk的哪里重复了)。

打开,然后替换以下代码:

public class CardboardSwapper : MonoBehaviour {
 
  public GameObject[] cardboardObjects;
  public GameObject[] monoObjects;
 
  // Turn on or off VR mode
  void ActivateVRMode(bool goToVR) {
    foreach (GameObject cardboardThing in cardboardObjects) {
        cardboardThing.SetActive(goToVR);
    }
    foreach (GameObject monoThing in monoObjects) {
        monoThing.SetActive(!goToVR);
    }
    GvrViewer.Instance.VRModeEnabled = goToVR;
 
    // Tell the game over screen to redisplay itself if necessary
    gameObject.GetComponent().RefreshGameOver();
  }
 
  public void Switch() {
    ActivateVRMode(!GvrViewer.Instance.VRModeEnabled);
  }
 
  void Update () {
    if (GvrViewer.Instance.BackButtonPressed) {
      Switch();
    }
  }
 
  void Start() {
    ActivateVRMode(false);
  }
}
这个类中最重要的方法是ActivateVRMode当你改变了GvrViewr.Instance.VRModeEnable,就激活了VR模式。

剩下的逻辑就是激活或关闭在场景中不同的游戏物体,取决于你是否在VR模式。调用Start()方法中调用ActivateVRMode(false)

就会让你的游戏以普通模式开始。

你同样会意识到当点击返回按钮时会调用Switch()方法,你可以在编辑器中用esc键模式模拟GvrViewer.Instance.BackButtonPressed,一个

让你毫无疑问很趁手的测试特性。

你需要添加更多的一些游戏逻辑到你的GameController脚本里面让其正确选择游戏结束的模式。

打开GameController.cs添加如下方法:

public void RefreshGameOver() {
    gameOverCanvas.enabled = false;
    VRGameOverCanvas.enabled = false;
    if (isGameOver) {
        GameOver(_didIWin);
    }
}
保存所有,然后回到Unity给两种游戏物体数组赋值,就是你创建的转换开关类,挂在GameLogic上:
                                                   怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第27张图片
最后,你需要添加一个按钮在画布上供用户点击。节约时间,我已经准备好了。

在Prefabs文件夹下找到CardboardButton推到Canvas的子节点,设置Position(-50, 50, 0):

                      怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第28张图片

在你按钮的游戏物体的下方添加点击时间去调用CardboardSwapper.Switch()方法,如下:

                               

再次尝试你的游戏,就可以切换场景了:

                                怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第29张图片

祝贺!你像个老板样切换模式了!

                    怎么通过Unity和谷歌纸盒做一个VR游戏?(译)_第30张图片









你可能感兴趣的:(Unity和VR,Andriod,android,游戏,unity,google,VR)