在U3D中用正则表达式实现FBX文件的自动分割

来源:互联网 发布:从新网代理商转出域名 编辑:程序博客网 时间:2024/05/18 21:12
1.前言
MAX制作角色动画还是很便利的,cs骨骼系统加上自带的bone骨骼就能胜任基本的绝大部分的多足动物骨骼的构建。
导出为FBX的时候有时候会提示进行动画烘焙,类似法线烘焙之类的求解过程,实际上magic spring插件的原理也和这里差不多吧。
将导出的FBX直接导入U3D的时候,常常会出现材质丢失的问题,这个时候重新导入材质就好。
然后就到了分割的时候了。
2.普通的分割方式
 在FBX文件的动画选项卡中新建一个剪辑,然后制定起始和结束的帧号,设定勾选有关的参数即可。
虽然操作上是很方便,但是实际流程中,需要在MAX中记录帧号,然后对着记录下来的信息一点一点设定,还是觉得有点麻烦……
之前没有接触U3D的时候,甚至还需要把信息传给其他人员来进行操作,这样出错的环节就增多了。
3.利用正则的快速分割
因为记录帧号的时候会遵照一定的格式,所以用正则来做的话会很方便。
U3D特殊文件夹中Editor文件夹中的脚本可以调用U3D自带的部分API,尝试以这个为突破口来进行下去吧!
using UnityEngine;using UnityEditor;using System.Collections;using System.IO;using System.Text.RegularExpressions;using System;using System.IO;public class FbxAnimListPostprocessor : AssetPostprocessor{public void OnPreprocessModel(){if (Path.GetExtension(assetPath) == ".FBX")//判断拓展名FBX{try{string fileAnim;if (DragAndDrop.paths.Length <= 0)//若文件名合法性{return;}fileAnim = DragAndDrop.paths[0];string ClipText = Path.ChangeExtension(fileAnim, ".txt");//按照相同文件名寻找txt文件StreamReader file = new StreamReader(ClipText);string sAnimList = file.ReadToEnd();//处理后的动画列表,file.Close();//关闭文件//if (EditorUtility.DisplayDialog("是否从下列文件中导入已关联的FBX动画?",fileAnim, "导入", "取消"))//标题、正文、选项卡{System.Collections.ArrayList List = new ArrayList();ParseAnimFile(sAnimList, ref List);//自定义的parse方法ModelImporter modelImporter = assetImporter as ModelImporter;//modelImporter.clipAnimations. = true;modelImporter.clipAnimations = (ModelImporterClipAnimation[])List.ToArray(typeof(ModelImporterClipAnimation));//转换正则捕捉到的结果EditorUtility.DisplayDialog("已导入动画","已导入剪辑数量 "+ modelImporter.clipAnimations.GetLength(0).ToString(), "OK");}}catch { }}void ParseAnimFile(string sAnimList, ref System.Collections.ArrayList List){Regex regexString = new Regex(" *(?<firstFrame>[0-9]+) *- *(?<lastFrame>[0-9]+) *(?<loop>(loop|noloop| )) *(?<name>[^\r^\n]*[^\r^\n^ ])",RegexOptions.Compiled | RegexOptions.ExplicitCapture);Match match = regexString.Match(sAnimList, 0);//逐条获取while (match.Success){ModelImporterClipAnimation clip = new ModelImporterClipAnimation();if (match.Groups["firstFrame"].Success)//写入firstName{clip.firstFrame = System.Convert.ToInt32(match.Groups["firstFrame"].Value, 10);}if (match.Groups["lastFrame"].Success)//写入lastName{clip.lastFrame = System.Convert.ToInt32(match.Groups["lastFrame"].Value, 10);}if (match.Groups["loop"].Success)//写入loop信息{clip.loop = match.Groups["loop"].Value == "loop";}if (match.Groups["name"].Success)//写入name{clip.name = match.Groups["name"].Value;}List.Add(clip);//在输出结果的List中增加定义完成的clipmatch = regexString.Match(sAnimList, match.Index + match.Length);//读取下一节内容}}}
在Asset文件夹下创建Editor文件夹,然后新建一个Divider.cs文件使用以上代码。
在FBX文件的同一目录下创建同名的txt文档,内容格式如下:
起始帧号-结束帧号 循环信息 剪辑名
然后拖动文件进入U3D中指定的文件夹下,会弹出是否导入关联动画的窗体,此时选择取消的话就会正常导入。
如图,对应上面txt文件中的内容,模型导入的时候自动生成了剪辑列表!

4.后话
不过,其实最本质的解决方法不应该是在MAX中吗??
像是老Flash8那样指定帧标签,给帧制定帧名,用一个字符串来表示特定的帧,这样的话后期调整就会更加灵活,如果FBX文件中带有这种信息并且U3D中可以识别,那么完全不需要这样做。
阅读全文
0 0
原创粉丝点击