阅读 417

EasyAR4.0使用说明(Unity3D)三----平面图像跟踪扩展

播放视频

平面图像识别以后播放视频也是一种经常被用到的增强现实的表现方式。通常是截取视频第一帧的图片作为识别图片,识别以后播放视频。这样就给人一个图片动起来的错觉。

  • 在场景中设置Main Camera的Clear Flags属性为Solid Color。
  • 将EasyAR/Prefabs/Composites目录下的EasyAR_ImageTracker-1预制件拖到场景中。
  • 将EasyAR/Prefabs/Primitives目录下的ImageTarget预制件拖到场景中。
  • 设置“ImageTarget”的识别图片。

播放视频

  • 选中一个“ImageTarget”,点击鼠标右键,在弹出菜单中选择3D Object--Plane,为“ImageTarget”对象添加一个平面作为其子游戏对象。
  • 设置Plane游戏对象的角度为“90,0,180”,并修改其Scale属性将其大小设置的和视频图片大小一样。

播放视频

  • 选中Plane游戏对象,点击菜单Component--Video--Video Player,为其添加一个视频播放组件。
  • 将一段视频拖到目录EasyAR4Learn/Videos下,导入为资源,并将其拖动到Video Player组件的Video Clip属性中为其赋值。

播放视频

运行效果:

播放视频

视频不仅可以在平面上播放,也可以在其他形状的3D物体上播放。

在另外一个“ImageTarget”对象下,添加一个方块作为视频播放的游戏对象,设置方块的大小和角度,添加Video Player组件并设置组件的Video Clip属性。

播放视频

运行效果:

当识别出图片以后,就可以看见一个方块,在方块的表面在播放视频。

播放视频

涂涂乐

导入资源

从官方示例导入小熊模型。

播放视频

从官方示例中导入【Coloring3D】着色器。

播放视频

从官方示例中导入【Sample_TextureSample】材质。同时设置材质对应的着色器是【Sample/Coloring3D】。

播放视频

导入脚本。这个脚本是用官方示例脚本改写的,区别只是去掉了对按钮的绑定。

播放视频

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using easyar;

public class Coloring3D : MonoBehaviour
{
    public CameraImageRenderer CameraRenderer;
    private Material material;
    private ImageTargetController imageTarget;
    private RenderTexture renderTexture;
    private Optional<bool> freezed;
    private RenderTexture freezedTexture;

    void Awake()
    {
        material = GetComponent<MeshRenderer>().material;
        imageTarget = GetComponentInParent<ImageTargetController>();
        CameraRenderer.RequestTargetTexture((camera, texture) =>
         {
             renderTexture = texture;
         });
        imageTarget.TargetFound += () =>
       {
           if (freezed.OnNone)
           {
               freezed = false;
           }
       };
    }

    public void Freeze()
    {
        freezed = true;
        if (freezedTexture)
        {
            Destroy(freezedTexture);
        }
        if (renderTexture)
        {
            freezedTexture = new RenderTexture(renderTexture.width, renderTexture.height, 0);
            Graphics.Blit(renderTexture, freezedTexture);
        }
        material.SetTexture("_MainTex", freezedTexture);
    }

    public void Thaw()
    {
        if (freezedTexture)
        {
            Destroy(freezedTexture);
        }
    }

    void Update()
    {
        if (freezed.OnNone || freezed.Value || imageTarget.Target == null)
        {
            return;
        }
        var halfWidth = 0.5f;
        var halfHeight = 0.5f / imageTarget.Target.aspectRatio();
        Matrix4x4 points = Matrix4x4.identity;
        Vector3 targetAnglePoint1 = imageTarget.transform.TransformPoint(new Vector3(-halfWidth, halfHeight, 0));
        Vector3 targetAnglePoint2 = imageTarget.transform.TransformPoint(new Vector3(-halfWidth, -halfHeight, 0));
        Vector3 targetAnglePoint3 = imageTarget.transform.TransformPoint(new Vector3(halfWidth, halfHeight, 0));
        Vector3 targetAnglePoint4 = imageTarget.transform.TransformPoint(new Vector3(halfWidth, -halfHeight, 0));
        points.SetRow(0, new Vector4(targetAnglePoint1.x, targetAnglePoint1.y, targetAnglePoint1.z, 1f));
        points.SetRow(1, new Vector4(targetAnglePoint2.x, targetAnglePoint2.y, targetAnglePoint2.z, 1f));
        points.SetRow(2, new Vector4(targetAnglePoint3.x, targetAnglePoint3.y, targetAnglePoint3.z, 1f));
        points.SetRow(3, new Vector4(targetAnglePoint4.x, targetAnglePoint4.y, targetAnglePoint4.z, 1f));
        material.SetMatrix("_UvPints", points);
        material.SetMatrix("_RenderingViewMatrix", Camera.main.worldToCameraMatrix);
        material.SetMatrix("_RenderingProjectMatrix", GL.GetGPUProjectionMatrix(Camera.main.projectionMatrix, false));
        material.SetTexture("_MainTex", renderTexture);
    }

    void OnDestroy()
    {
        if (freezedTexture) { Destroy(freezedTexture); }
    }
}
复制代码

实现

  • 在场景中设置Main Camera的Clear Flags属性为Solid Color。
  • 将EasyAR/Prefabs/Composites目录下的EasyAR_ImageTracker-1预制件拖到场景中。
  • 将EasyAR/Prefabs/Primitives目录下的ImgaeTarget预制件拖到场景中。
  • 导入识别图片并设置“ImageTarget”的识别图片为“coloring3d-bear.jpg”,这里的识别图片必须和3D模型对应,是一个特殊UV展开后的纹理贴图。

涂涂乐

在ImageTarget游戏对象下添加模型bear。设置模型的方向和位置。修改模型的材质为Sample_TextureSample。

涂涂乐

将Coloring3D脚本拖到模型上成为其组件,将RenderCamera游戏对象拖到脚本组件的Camera Renderer属性中为其赋值。

涂涂乐

运行效果:

修改识别图片中小熊的颜色,对应模型的颜色也会随之修改。

涂涂乐

自定义实现

涂涂乐本质是将一个3D模型的UV展开图作为识别图片,然后动态的将识别作为贴图贴到模型上。

在Unity商城里面找一个合适的模型,不要太复杂,关键是,贴图只能是一副图片,而且需要有一些留白。这里选取的是下面这个卡通汽车模型。在Unity商城中导入资源包。

涂涂乐

导入资源以后,在CartoonCarFree/models/Materials目录下找到模型的贴图。

涂涂乐

涂涂乐

用图片编辑器,修改贴图,去掉贴图的主要颜色并把边界线留出来。为了提高贴图的识别率,在空白处添加文字内容。

涂涂乐

  • 设置场景中的Main Camera的Clear Flags属性为Solid Color。
  • 将EasyAR/Prefabs/Composites目录下的EasyAR_VideoCamera预制件拖到场景中。
  • 将EasyAR/Prefabs/Primitives目录下的ImageTarget预制件拖到场景中。
  • 将修改好的贴图命名为“car.jpg”,拖到StreamingAssets目录下。
  • 设置识别图片是StreamingAssets目录下的“car.jpg”。

涂涂乐

将FreeCar模型拖到ImageTarget游戏对象下。设置模型的大小位置和角度到合适的情况。

涂涂乐

选中FreeCar游戏对象,将目录EasyAR4Learn/Materials下的Sample_TextureSample贴图拖到Materials属性下为其赋值。

涂涂乐

  • 将Coloring3D脚本拖到FreeCar游戏对象下成为其组件。
  • 将RenderCamera游戏对象拖到Camera Renderer属性中为其赋值。

涂涂乐

运行效果:

识别图片以后,在图片对于位置填色或绘制内容,模型对应位置也会一起变化。

涂涂乐

如果需要做一个像官方例子那样的涂涂乐,首先需要选择模型并重新展开UV,重新设计贴图。

视频版链接:www.bilibili.com/video/BV1ct…