http://blog.csdn.net/langresser_king/article/details/37760091?utm_source=tuicool&utm_medium=referral

Unity的新动画系统Mecanim出来也有一阵子了,我的第一个Unity项目就是使用这个动画系统。但是只是做了最基本的应用,没有做深入的研究。

Mecanim的好处有三点:1、动画重定向,可以最大程度的复用动画资源   2、可视化编辑的状态机    3、Blend Tree可以方便的做动画融合,例如一边跑一边攻击。

但是对于我而言,Mecanim在使用上感觉有些蹩脚,最大的问题就是在可视化的状态机编辑上了。 这个状态机让动画编辑变得容易了,不需要一行代码就可以控制动作的流转,像Temple Run这样的游戏可以轻松搞定。  但是问题是,一个大型的mmo动画文件成百上千,如果都依托于这个编辑器的话,那状态机会变得像蜘蛛网一样密密麻麻,不可维护。更何况,连几千条线来处理动画,只有脑子抽疯的人才会这么干。

举个例子,人物有站立动画,拿不同武器的时候站立动作不一样,比如双持站立、空手站立、拿枪站立、拿弓站立等等;同样,跑步的动画也有十几种;死亡动画亦然。最后再加上几十个技能动画。这里我们不考虑骑马、马上攻击、飞行等等情况,可以算是简化的ARPG,但是即便如此,动画文件依然可能有一百多个。如果是按正常情况的话,光站立动作到技能就可能需要一千条线,每条线还要选择好正确的参数。正常人都应该意识到,这是不合理的。

解决方案一:

使用Mecanim Control插件,这个插件使用Mecanim系统提供的接口来模拟老式动画系统的接口(Play CrossFade等等)。把动画文件(Animation Clip)拖动到脚本上,然后就可以正常的使用Play等接口来进行动画播放了。由于内部依然使用的是Mecanim系统,所以支持动画重定向。如果没有什么特殊需求的话,这个应该是相对完善的解决方案。

要说缺点的话,也有一些,就是动画文件的流转完全交由代码来控制,并且不支持BlendTree动画融合。

解决方案二:

这个我还在初步尝试,理论上可行。 这个方案完全依托于Mecanim的操作方式和思路。只不过通过一些小技巧和没有广为流传的知识点使得Mecanim的编辑操作大大简化。

Mecanim 的状态机之所以变得复杂是因为多个站立动作与跑步动作以及技能之间的流转,这需要添加上千条线,而之所以会变得那么多,是因为站立动作本身就有十几个。如果有一种方法能够让十几个休闲动作作为一个整体去跟技能动作进行交互,那么连线数目直接降至几十条。 事实上,在Unity5里面会提供State Machine到State Machine之间的连线交互,每个Sub State Machine都有一个入口和出口,这就是我想要的。  可以再Unity4里面,Sub State Machine只是一个类似文件夹的概念,我们只能处理State之间的连线。

第一个知识点,通过animator.runtimeAnimatorController动态的替换动画控制器,通过AnimatorOverrideController动态的替换一个动画文件。 这个技术就是Mecanim Control插件所使用的。所以,我们只需要在状态机中添加一个Idle状态,然后控制这个状态和技能之间的动作流转。在代码中根据装备的武器动态的改变Idle的对应动画,然后就可以达到我们的目的了。参考代码如下:

[csharp] view
plain
 copy

  1. private Animator animator;
  2. public AnimationClip clip;
  3. // Use this for initialization
  4. void Start () {
  5. animator = GetComponent<Animator>();
  6. AnimatorOverrideController col = new AnimatorOverrideController();
  7. col.runtimeAnimatorController = animator.runtimeAnimatorController;
  8. col["2HAxe1"] = clip;
  9. animator.runtimeAnimatorController = col;
  10. }

第二个知识点,我们可以通过UnityEditorInternal.AnimatorController在编辑器中使用代码来创建AnimatorController文件,理论上也可加载并编辑一个controller文件。所以添加参数,添加动画文件,动画文件之间的连线这些体力活都可以使用脚本自动化完成。具体参考雨松的博客:http://www.xuanyusong.com/archives/2811

参考代码如下:

[csharp] view
plain
 copy

  1. using UnityEngine;
  2. using UnityEditor;
  3. using UnityEditorInternal;
  4. using System.Collections;
  5. public class AutoCreateAnimator : Editor {
  6. [MenuItem("Tools/创建动画控制器")]
  7. static void CreateAnimator()
  8. {
  9. //创建animationController文件,保存在Assets路径下
  10. AnimatorController animatorController = AnimatorController.CreateAnimatorControllerAtPath("Assets/animation.controller");
  11. //得到它的Layer, 默认layer为base 你可以去拓展
  12. AnimatorControllerLayer layer = animatorController.GetLayer(0);
  13. //把动画文件保存在我们创建的AnimationController中
  14. AddStateTransition("Assets/Model/Media/player/human_f/attack/human_f_2haxe1.fbx",layer);
  15. AddStateTransition("Assets/Model/Media/player/human_f/attack/human_f_2haxe2.fbx",layer);
  16. AddStateTransition("Assets/Model/Media/player/human_f/attack/human_f_2haxe3.fbx",layer);
  17. }
  18. private static void AddStateTransition(string path, AnimatorControllerLayer layer)
  19. {
  20. UnityEditorInternal.StateMachine sm = layer.stateMachine;
  21. //根据动画文件读取它的AnimationClip对象
  22. AnimationClip newClip = AssetDatabase.LoadAssetAtPath(path, typeof(AnimationClip)) as AnimationClip;
  23. //取出动画名子 添加到state里面
  24. State  state = sm.AddState(newClip.name);
  25. state.SetAnimationClip(newClip,layer);
  26. //把state添加在layer里面
  27. sm.AddAnyStateTransition(state);
  28. }
  29. }

经过这两步操作,Mecanim的状态机编辑变得简化许多。就算依然要编个蜘蛛网出来,也是Hold住的蜘蛛网。由于直接使用Mecanim的功能,所以“边跑边打”“移动施法”这样的依托于动画融合的功能也可以方便的做出来。

Unity Mecanim在大型mmo中的应用的更多相关文章

  1. Spine with Unity Mecanim

    前言 最近这两天刚刚接触Spine,研究了一下Unity Mecanim Animator如何控制Spine,在此分享记录一下,如有不当之处,请留言指出,欢迎讨论. Unity & Spine ...

  2. 【分布式】Zookeeper在大型分布式系统中的应用

    一.前言 上一篇博文讲解了Zookeeper的典型应用场景,在大数据时代,各种分布式系统层出不穷,其中,有很多系统都直接或间接使用了Zookeeper,用来解决诸如配置管理.分布式通知/协调.集群管理 ...

  3. Unity在Android和iOS中如何调用Native API

    本文主要是对unity中如何在Android和iOS中调用Native API进行介绍. 首先unity支持在C#中调用C++ dll,这样可以在Android和iOS中提供C++接口在unity中调 ...

  4. Unity脚本在层级面板中的执行顺序测试3

    断断续续的写了3篇,以后有时间可以做成一个系列了 前面2篇测试了GameObject的顺序,以及Awake和OnEnable的时机: Unity脚本在层级面板中的执行顺序测试1 http://www. ...

  5. Unity脚本在层级面板中的执行顺序测试4-附加整理

    测试4为一些附加内容,后续的各种tips都加在此. 前几篇测试的链接: Unity脚本在层级面板中的执行顺序测试1 http://www.cnblogs.com/hont/p/4298110.html ...

  6. SLAM+语音机器人DIY系列:(二)ROS入门——8.理解roslaunch在大型项目中的作用

    摘要 ROS机器人操作系统在机器人应用领域很流行,依托代码开源和模块间协作等特性,给机器人开发者带来了很大的方便.我们的机器人“miiboo”中的大部分程序也采用ROS进行开发,所以本文就重点对ROS ...

  7. Session的原理,大型网站中Session方面应注意什么?

    一.Session和Cookie的区别Session是在服务器端保持会话数据的一种方法(通常用于pc端网站保持登录状态,手机端通常会使用token方式实现),存储在服务端. Cookie是在客户端保持 ...

  8. Kafka在大型应用中的 20 项最佳实践

    原标题:Kafka如何做到1秒处理1500万条消息? Apache Kafka 是一款流行的分布式数据流平台,它已经广泛地被诸如 New Relic(数据智能平台).Uber.Square(移动支付公 ...

  9. Egret的第三方库制作,以及在大型项目中的应用

    目录: 一 创建第三方库 二 TypeScript库 三 JavaScript库 四 第三方库制作在大型RPG中的实际应用 参考: 第三方库的使用方法 目标: 本文目的是将现有游戏的框架制作成第三方库 ...

随机推荐

  1. 最新wap手机agent

    名称 agent 铃声格式 和弦数 数据量 删除 LGE-CU8080  LGE-CU8080/1.0 UP.Browser/4.1.26l UP.Link/5.1.2.9  pmd2.0  40   ...

  2. CentOS 安装和配置 Mantis

    Mantis是一个基于PHP技术的轻量级的开源缺陷跟踪系统,以Web操作的形式提供项目管理及缺陷跟踪服务.在功能上.实用性上足以满足中小型项目的管理及跟踪.更重要的是其开源,不需要负担任何费用. 1. ...

  3. [省选]板块(shenben已经AFO!!!)

    shenben已经AFO!!! 部分摘抄自网络 同样的,加粗是重点,星号是选学 图论 网络流(dinic,ISAP选一个,费用流写EK就行.*zkw费用流),二分图 点分治,边分治,*动态点分治 树链 ...

  4. 2018-11-9-匿名函数&递归函数初识

    1.匿名函数(lambda) 2.递归函数初识

  5. win7下使用source insight,没有Courier字体

    http://hi.baidu.com/raoxj/item/0e3a3a3b2461c5be134b14fa 1. “控制面板:--->“字体”--->找到Courier New(建议用 ...

  6. Android:SQLiteOpenHelper类(SQLlite数据库操作)详细解析

    前言 SQLite数据库操作在Android开发中非常常用 今天我将带大家全面了解关于SQLite数据库的操作(增.删.查.改) 目录 1. SQLite数据库介绍 SQLite是Android内置的 ...

  7. hdu 1004 Let the Balloon Rise 解题报告

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1004 用STL 中的 Map 写的 #include <iostream> #includ ...

  8. 用margin还是用padding?(3)—— 负margin实战

    看过一篇文章是关于我知道你不知道的负Margin,里面对margin做了总结: 当margin四个值都为正数值的话,那么margin按照正常逻辑同周围元素产生边距.当元素margin的top和left ...

  9. 盈创动力之 JS校验方法

    var IS_NULL = 128; // 10000000var IS_FULL = 64; // 01000000var IS_HALF = 32; // 00100000var IS_ASCII ...

  10. 从Github上下载了项目,导入Android Studio,gradle 报错,应该怎么修改

    一.从Github上获取源代码 我这里是直接下载ZIP文件 二.在本机的Android Studio上新建一个空白项目,目的主要是与刚从Github上下载的项目文件结构做对比 三.替换gradle文件 ...