ARFoundation项目学习记录(六)--基于人脸识别的AR flappy bird
学习记录,可供参考,大佬嘴下留情QAQ
项目构思:
人脸识别是AR应用开发中比较重要的功能。本项目打算将原有的手机、PC端的应用改造成AR应用,并展示人脸识别的功能
项目设计:
把经典游戏FlappyBird如图所示,转变为由通过人脸识别用鼻子控制Bird的飞行躲避障碍物的游戏
项目实施:
新建项目,命名为AR_FlappyBird,分别导入ARFoundation和ARCore XR Plugin,进行Android平台的基本设置(在ARFoundation的基本环境配置已经介绍过了)
在文末素材链接中,将素材包FlappyBird.unitypackage导入项目,在Sence目录下找到Bird场景文件,按下Ctrl+D组合键创建该文件的副本,并命名为AR_FlappyBird,双击打开。
在Hierarachy窗口的空白处单击鼠标右键,在弹出的菜单中选择XR>AR Session Origin和XR>AR Session,如图所示。
首先是对摄像头的调整,FlappyBird用的是MainCamera,我们的AR应用要用的是ARCamera,所以要把ARCamera的属性调整成和MainCamera基本一致.
我们选择AR Session Origin下的ARCamera,如图所示,调整transform的position为(0,0,-20),调整Projection为Orthographic,设置Clipping Planes Near为0.3,Far为1000,如图所示,然后再为ARCamera添加GameState的脚本组件,如图所示,用于判断游戏是否结束。这时点击运行就能得到跟原项目一样的效果。
随后把整个原项目的游戏对象都挂载到ARCamera的层级之下,这样才能实现我们整体的游戏画面不会因AR摄像机的运动而发生变化。
摄像头是要检测人脸上的鼻子来进行Bird的控制,因此我们需要添加用于人脸识别的组件ARFaceManager,选择Hierarchy窗口的ARSessionOrigin对象,为其挂载ARFaceManager组件,如图所示
补充一下,ARFaceManager组件在检测到人脸时会使用人脸的姿态实例一个预制体,即图中的Face Prefab属性,这个属性可以不用设置。同时当使用该组件时,默认使用的就是前置摄像头了。
5不能让背景遮住人脸,我们把背景隐藏,如图所示
6注意当使用了前置摄像头,我们X轴的朝向是相反的,X轴是向左的,这是为了在人脸上挂载虚拟物体时,可以保持虚拟物体正确的三轴朝向,但我们的UI方向就相反了,如图所示,这是未调整的前置摄像头会看到的画面。
因此我们要把UI都旋转180度,选择GameOver、StartGame、Score,设置Transform组件的Rotation为(0,180,0),调整后的画面如图所示
接下来调整管道的生成,首先找到Pipe脚本,修改udate中的内容,代码如下,使管道向X轴移动,这样当开启前置摄像头时,管道就会从右边出来。
void Update ()
{
//若游戏处于运行中
if (!GameState.Instance.GameOver)
{
//物体向X方向移动
transform.Translate(new Vector3(Speed * Time.deltaTime, 0, 0));
}
}
}
再找到PipeLines脚本,由于现在用的是ARcamera,摄像机的位置不是固定的,因此要修改CreatePipe()函数中设置管道坐标的代码,让管道生成的位置再加上摄像机的偏移量,代码如下。
go.transform.position = new Vector3(InitPosX, Random.Range(-2.4f, 1.5f))+this.transform.position;
新建一个C#脚本,命名为NoseTipManager,代码如下,用于检测鼻子位置,并控制小鸟飞行。
using System.Collections;
using System.Collections.Generic;
using Unity.Collections;
using UnityEngine;
using UnityEngine.XR.ARCore;
using UnityEngine.XR.ARFoundation;
[RequireComponent(typeof(ARFaceManager))]
[RequireComponent(typeof(ARSessionOrigin))]
public class NoseTipManager : MonoBehaviour
{
private ARFaceManager mARFaceManager;
public GameObject mInstantiatedPrefab;
private ARSessionOrigin mSessionOrigin;
private NativeArray<ARCoreFaceRegionData> mFaceRegions;
private void Awake() {
mARFaceManager = GetComponent<ARFaceManager>();
mSessionOrigin = GetComponent<ARSessionOrigin>();
}
private void OnEnable()
{
mARFaceManager.facesChanged += OnFacesChanged;
}
void OnDisable() { mARFaceManager.facesChanged -= OnFacesChanged;
}
void OnFacesChanged(ARFacesChangedEventArgs eventArgs)
{
foreach (var trackedFace in eventArgs.added)
{
OnFaceChanged(trackedFace);
}
foreach (var trackedFace in eventArgs.updated)
{
OnFaceChanged(trackedFace);
}
}
private void OnFaceChanged(ARFace refFace)
{
var subsystem = (ARCoreFaceSubsystem)mARFaceManager.subsystem;
subsystem.GetRegionPoses(refFace.trackableId, Allocator.Persistent, ref mFaceRegions);
for (int i = 0; i<mFaceRegions.Length; ++i)
{
var regionType = mFaceRegions[i].region;
if (regionType == ARCoreFaceRegion.NoseTip)
{
mInstantiatedPrefab.transform.localPosition = mFaceRegions[i].pose.position;
mInstantiatedPrefab.transform.localRotation = mFaceRegions[i].pose.rotation;
}
}
}
void OnDestroy()
{
if (mFaceRegions.IsCreated)
mFaceRegions.Dispose();
}
}
regionType == ARCoreFaceRegion.NoseTip用于判断鼻尖的位置,通过OnFaceChanged进行事件监听,在added、update中实时更新bird的姿态。
随后把脚本挂载到ARSessionOrigin上,把原场景中的bird游戏对象赋值给NoseTipManager,如图所示
\
在Scripts文件夹中找到Bird脚本,Ctrl+D复制脚本,改名为AR_Bird,注释掉update中用鼠标控制小鸟运动的代码,如图所示,再挂载到游戏对象bird上。
设置bird游戏对象的Rigidbody2D组件的Gravity Scale设置为0,让他不受重力的影响,同时设置Scale为(0.1,0.1,0.1),如图所示,SpriteRender中勾选X的Filp,即把贴图水平翻转,保证其在前置摄像头的正确朝向,如图所示。
.还存在一个问题,Scripts文件夹中的Restart脚本中OnMouseDown()函数是通过射线碰撞到物体,就调用这个函数,如图所示。
但在ARFaceManager组件在检测到人脸后,射线被遮挡,无法接触到用于重新加载的UI对象,场景无法重新加载,无法所以我们要换种方式进行场景的重新加载,这是通过Invoke函数进行延迟调用,修改Restart脚本,代码如下。
using UnityEngine;
using UnityEngine.SceneManagement;
public class Restart : MonoBehaviour
{
void Start()
{
//设置挂载本脚本物体的父物体 初始状态为隐藏
//这里即是 初始时隐藏 “GameOver”物体
this.transform.parent.gameObject.SetActive(false);
}
private void Update()
{
if (GameState.Instance.GameOver) {
//当游戏结束后,3秒后重新开始游戏
Invoke("SceneManagerRestart", 3f);
}
}
private void SceneManagerRestart()
{
//重新加载本游戏场景
SceneManager.LoadScene("AR_FlappyBird", LoadSceneMode.Single);
}
}
项目测试:
打包成apk发布到手机运行,效果如下:
注:这里用了《VR AR MR项目开发实战》案例的随书资源
素材链接:
链接:https://pan.baidu.com/s/12BjOCMKFrCjXzB9bgRWmew?pwd=tudp
提取码:tudp
源码链接:
链接:https://pan.baidu.com/s/1p5oFq2cNpGPH6T-aSPj5uQ?pwd=83mc
提取码:83mc
安装包链接:
链接:https://pan.baidu.com/s/1eu_BKvCAB389NcH-oxrosw?pwd=fbfk
提取码:fbfk
注意去官网看手机是否支持arcore,不然就是闪退黑屏
ARFoundation项目学习记录(一)--配置环境-CSDN博客
官网链接:
更多推荐
所有评论(0)