ソースを参照

new XTRA support in FBX user props (will deprecate xtra file soon)

ncannasse 10 年 前
コミット
90d8669088
2 ファイル変更65 行追加57 行削除
  1. 24 0
      hxd/fmt/fbx/BaseLibrary.hx
  2. 41 57
      tools/xtra/xtraExporter.ms

+ 24 - 0
hxd/fmt/fbx/BaseLibrary.hx

@@ -143,6 +143,29 @@ class BaseLibrary {
 		this.root = root;
 		for( c in root.childs )
 			init(c);
+
+		// init properties
+		for( m in this.root.getAll("Objects.Model") ) {
+			for( p in m.getAll("Properties70.P") )
+				switch( p.props[0].toString() ) {
+				case "UDP3DSMAX":
+					var userProps = p.props[4].toString().split("&cr;&lf;");
+					for( p in userProps ) {
+						var pl = p.split("=");
+						var pname = StringTools.trim(pl.shift());
+						var pval = StringTools.trim(pl.join("="));
+						switch( pname ) {
+						case "UV" if( pval != "" ):
+							var xml = try Xml.parse(pval) catch( e : Dynamic ) throw "Invalid UV data in " + m.getName();
+							var frames = [for( f in new haxe.xml.Fast(xml.firstElement()).elements ) { var f = f.innerData.split(" ");  { t : Std.parseFloat(f[0]) * 9622116.25, u : Std.parseFloat(f[1]), v : Std.parseFloat(f[2]) }} ];
+							if( uvAnims == null ) uvAnims = new Map();
+							uvAnims.set(m.getName(), frames);
+						default:
+						}
+					}
+				default:
+				}
+		}
 	}
 
 	public function loadXtra( data : String ) {
@@ -595,6 +618,7 @@ class BaseLibrary {
 				animNode = getChild(a, "AnimationLayer");
 				break;
 			}
+
 		if( animNode == null ) {
 			if( animName != null )
 				throw "Animation not found " + animName;

+ 41 - 57
tools/xtra/xtraExporter.ms

@@ -1,66 +1,50 @@
-macroScript XtraExport Category:"Shiro" tooltip:"Xtra Export" buttontext:"XTRA"
+macroScript XtraExport Category:"Shiro" tooltip:"Add Extra Infos" buttontext:"XTRA"
 (
 
-fn f_URLEncode _STR =
-(
-dotnet.loadassembly "System.Web"
-dotnet.loadassembly "System.Text"
-local httpUtility = dotnetClass "System.Web.HttpUtility"
-local enc = dotnetClass "System.Text.Encoding"
-local urlEncodedString = httpUtility.UrlEncode _STR enc.UTF8
-return urlEncodedString
-)
-
-	function export file = (
-		format "Exporting %\n" file
-		deleteFile file
-		local f = createFile file
-		local somethingDone = false
-		format "<xtra>\n" to:f
-		local sel = getCurrentSelection()
-		if sel.count == 0 then sel = Geometry
-		for m in sel do (
-			if m.material == undefined then continue
-			local diffuse = m.material.diffuseMap
-			if diffuse == undefined then continue
-			local coords = diffuse.coords
-			local hasUVAnim = false
-			local curU = 0.
-			local curV = 0.
-			local flip = 1
-			/*
-				when inverting faces, we have no way to tell that culling was flip and UV anim will go another way.
-				Let's mark such objects with backfaceCull
-			*/
-			if m.backfaceCull then flip = -1
-			local timeVal = animationRange.start.ticks
-			for frame = animationRange.start to animationRange.end do (
-				at time frame (			
-					if curU != coords.U_offset or curV != coords.V_offset then (
-						if not hasUVAnim then (
-							somethingDone = true
-							hasUVAnim = true
-							local name = f_URLEncode(m.name)
-							format "<uv name='%'>\n" name to:f
-							if timeVal != frame.ticks then format "<f>% % %</f>\n" timeVal curU curV to:f
-						)
-						timeVal = frame.ticks
-						curU = coords.U_offset * flip
-						curV = coords.V_offset	* flip
-						format "<f>% % %</f>\n" timeVal curU curV to:f
+	local somethingDone = false
+	for m in Geometry do (
+		if m.material == undefined then continue
+		local diffuse = m.material.diffuseMap
+		if diffuse == undefined then continue
+		local coords = diffuse.coords
+		local hasUVAnim = false
+		local curU = 0.
+		local curV = 0.
+		local flip = 1
+		/*
+			when inverting faces, we have no way to tell that culling was flip and UV anim will go another way.
+			Let's mark such objects with backfaceCull
+		*/
+		if m.backfaceCull then flip = -1
+		local timeVal = animationRange.start.ticks
+		local uvData = undefined
+		for frame = animationRange.start to animationRange.end do (
+			at time frame (			
+				if curU != coords.U_offset or curV != coords.V_offset then (
+					if not hasUVAnim then (
+						somethingDone = true
+						hasUVAnim = true
+						uvData = "<uv>"					
+						if timeVal != frame.ticks then uvData = uvData + "<f>"+(timeVal as string)+" "+(curU as string)+" "+(curV as string)+"</f>";
 					)
+					timeVal = frame.ticks
+					curU = coords.U_offset * flip
+					curV = coords.V_offset	* flip
+					uvData = uvData + "<f>"+(timeVal as string)+" "+(curU as string)+" "+(curV as string)+"</f>";
 				)
 			)
-			if hasUVAnim then format "</uv>\n" to:f
 		)
-		format "</xtra>" to:f
-		close f
-		if not somethingDone then (
-			messageBox "No UV animation has been found"
-			deleteFile file
+
+		if hasUVAnim then (
+			setUserProp m "UV" (uvData+"</uv>");
+		) else if getUserProp m "UV" != undefined then (
+			local buf = getUserPropBuffer m
+			setUserProp m "UV" "";
+			buf = substituteString buf "UV = \r\n" ""
+			setUserPropBuffer m buf
 		)
 	)
-
-	local fileName = getSaveFileName caption:"Save XTRA to:" types:"Xtra file(*.xtra)|*.xtra" filename:(substituteString maxFileName ".max" ".xtra")
-	if fileName != undefined then export fileName
+	if not somethingDone then (
+		messageBox "No UV animation has been found"
+	)
 )