Browse Source

Fixed OBJ converter to handle edge case where MTL file has more materials than corresponding OBJ file.

Also half-baked broken vertex colors in Max exporter managed to sneak in this commit.
alteredq 14 years ago
parent
commit
40bbe28c40
2 changed files with 178 additions and 27 deletions
  1. 14 13
      utils/exporters/convert_obj_threejs_slim.py
  2. 164 14
      utils/exporters/max/ThreeJSExporter.ms

+ 14 - 13
utils/exporters/convert_obj_threejs_slim.py

@@ -662,19 +662,20 @@ def generate_materials(mtl, materials):
     
     mtl_array = []
     for m in mtl:
-        index = materials[m]
-        
-        # add debug information
-        #  materials should be sorted according to how
-        #  they appeared in OBJ file (for the first time)
-        #  this index is identifier used in face definitions
-        mtl[m]['DbgName'] = m
-        mtl[m]['DbgIndex'] = index
-        mtl[m]['DbgColor'] = generate_color(index)
-        
-        mtl_raw = ",\n".join(['\t"%s" : %s' % (n, value2string(v)) for n,v in sorted(mtl[m].items())])
-        mtl_string = "\t{\n%s\n\t}" % mtl_raw
-        mtl_array.append([index, mtl_string])
+        if m in materials:
+            index = materials[m]
+            
+            # add debug information
+            #  materials should be sorted according to how
+            #  they appeared in OBJ file (for the first time)
+            #  this index is identifier used in face definitions
+            mtl[m]['DbgName'] = m
+            mtl[m]['DbgIndex'] = index
+            mtl[m]['DbgColor'] = generate_color(index)
+            
+            mtl_raw = ",\n".join(['\t"%s" : %s' % (n, value2string(v)) for n,v in sorted(mtl[m].items())])
+            mtl_string = "\t{\n%s\n\t}" % mtl_raw
+            mtl_array.append([index, mtl_string])
         
     return ",\n\n".join([m for i,m in sorted(mtl_array)])
 

+ 164 - 14
utils/exporters/max/ThreeJSExporter.ms

@@ -13,6 +13,7 @@ rollout ThreeJSExporter "ThreeJSExporter"
 	headerFormat = "// Converted from: %
 //  vertices: %
 //  normals: %
+//  colors: %
 //  uvs: %
 //  triangles: %
 //  materials: %
@@ -38,24 +39,33 @@ rollout ThreeJSExporter "ThreeJSExporter"
 	-------------------------------------------------------------------------------------
 	-- User interface
 
-	group "ThreeJSExporter  v0.2" 
+
+	group "ThreeJSExporter  v0.4"
 	(
 
 		label msg "Exports selected meshes in Three.js ascii JSON format" align:#left
-		hyperLink lab1 "Original source at GitHub" address:"https://github.com/mrdoob/three.js" align:#left
+		hyperLink lab1 "Original source at GitHub" address:"https://github.com/alteredq/three.js/blob/master/utils/exporters/max/ThreeJSExporter.ms" color:(color 255 120 0) align:#left
 
+		label dummy1 "--------------------------------------------------------" align:#left
+		
+		checkbox exportColor "Export vertex colors" checked:false enabled:true
 		checkbox exportUv "Export uvs" checked:true enabled:true
 		checkbox exportNormal "Export normals" checked:true enabled:true
 		checkbox smoothNormal "Use vertex normals" checked:false enabled:true
-		checkbox exportColor "Export vertex colors" checked:false enabled:false
+		
+		label dummy2 "--------------------------------------------------------" align:#left
+		
 		checkbox flipYZ "Flip YZ" checked:true enabled:true
 		checkbox flipUV "Flip UV" checked:true enabled:true
 		checkbox flipFace "Flip all faces" checked:false enabled:true
 		checkbox autoflipFace "Try fixing flipped faces" checked:false enabled:true
 
+		label dummy3 "--------------------------------------------------------" align:#left
+		
+		button btn_export "Export selected objects"
+
 	)
 
-	button btn_export "Export selected objects"
 
 	-------------------------------------------------------------------------------------
 	-- Dump vertices
@@ -104,6 +114,50 @@ rollout ThreeJSExporter "ThreeJSExporter"
 		Format "],\n\n" to:ostream
 
 	)
+	
+	-------------------------------------------------------------------------------------
+	-- Dump colors
+
+	function SmallColor c = 
+	(
+
+		if c == 255 then 
+			return "1"
+		else 
+			return formattedPrint ( c / 255 ) format:".4f"
+
+	)
+	
+	function DumpColors src useColors = 
+	(
+
+		Format "'colors': [" to:ostream
+
+		num = src.count
+
+		if num > 0 and exportColor.checked and useColors then
+		(
+
+			for i = 1 to num do
+			(
+
+				col = src[i]
+				
+				r = SmallColor col.r
+				g = SmallColor col.g
+				b = SmallColor col.b
+				
+				Format "%,%,%" r g b to:ostream
+				
+				if i < num then Format "," to:ostream
+
+			)
+
+		)
+
+		Format "],\n\n" to:ostream
+
+	)	
 
 	-------------------------------------------------------------------------------------
 	-- Dump normals
@@ -479,7 +533,7 @@ rollout ThreeJSExporter "ThreeJSExporter"
 
 		n = obj.numVerts
 
-		for i = 1 to n do 
+		for i = 1 to n do
 		(
 
 			v = GetVert obj i
@@ -489,11 +543,64 @@ rollout ThreeJSExporter "ThreeJSExporter"
 
 	)
 
+	-------------------------------------------------------------------------------------
+	-- Extract vertex colors from mesh
+
+	function ExtractColors obj whereto =
+	(
+
+		-- white no-op fallback color for all vertices
+		
+		nVertices = obj.numVerts
+		
+		startOffset = whereto.count
+		
+		for i = 1 to nVertices do
+		(
+
+			append whereto (color 255 255 255)
+
+		)
+
+		nColors = GetNumCPVVerts obj
+		
+		if nColors > 0 then
+		(
+
+			nFaces = obj.numFaces
+			
+			for i = 1 to nFaces do 
+			(
+
+				f  = GetFace obj i
+				cf = GetVCFace obj i
+				
+				c1 = GetVertColor obj cf[1]
+				c2 = GetVertColor obj cf[2]
+				c3 = GetVertColor obj cf[3]
+				
+				-- set vertices to vertex colors
+				-- ( there is no guaranteed 1-1 correspondence
+				--   between vertices and vertex colors in max
+				--   so this may mess up things, but in Three
+				--   there is 1-1 correspondence, so we need this )
+				
+				whereto[ startOffset + f.x ] = c1
+				whereto[ startOffset + f.y ] = c2
+				whereto[ startOffset + f.z ] = c3
+
+			)
+
+		)		
+
+	)
+
 	-------------------------------------------------------------------------------------
 	-- Extract normals from mesh
 
 	function ExtractNormals obj whereto needsFlip =
 	(
+
 		if smoothNormal.checked then
 		(
 
@@ -773,13 +880,25 @@ rollout ThreeJSExporter "ThreeJSExporter"
 		if SuperClassOf node == GeometryClass then
 		(
 			needsFlip = false
+			hasVColors = false
+			
+			zmesh = SnapshotAsMesh node
 			
 			if autoflipFace.checked then
 			(
+
 				needsFlip = NeedsFaceFlip node
+
+			)
+			
+			if exportColor.checked and ( getNumCPVVerts zmesh ) > 0 then
+			(
+
+				hasVColors = true
+
 			)
 			
-			return #( SnapshotAsMesh node, node.name, node.material, needsFlip )
+			return #( zmesh, node.name, node.material, needsFlip, hasVColors )
 
 		)
 
@@ -801,23 +920,30 @@ rollout ThreeJSExporter "ThreeJSExporter"
 
 		mergedVertices = #()
 		mergedNormals = #()
+		mergedColors = #()
+		
 		mergedUvs = #()
 		mergedFaces = #()
 		mergedMaterials = #()
 		
+		sceneHasVColors = false
+		
 		for obj in selection do 
 		(
 
 			result = ExtractMesh obj
-
-			meshObj   	 = result[1]
-			meshName     = result[2]
-			meshMaterial = result[3]
-			needsFlip    = result[4]
+			meshObj = result[1]
 
 			if ClassOf meshObj == TriMesh then 
 			(
 
+				meshName     = result[2]
+				meshMaterial = result[3]
+				needsFlip    = result[4]
+				hasVColors   = result[5]
+				
+				sceneHasVColors = sceneHasVColors or hasVColors
+				
 				append meshObjects result
 
 				vertexOffset = mergedVertices.count
@@ -827,6 +953,8 @@ rollout ThreeJSExporter "ThreeJSExporter"
 
 				ExtractVertices meshObj mergedVertices
 				ExtractNormals meshObj mergedNormals needsFlip
+				ExtractColors meshObj mergedColors
+				
 				ExtractUvs meshObj mergedUvs
 
 				ExtractFaces meshObj meshMaterial mergedFaces mergedMaterials needsFlip vertexOffset uvOffset
@@ -838,23 +966,36 @@ rollout ThreeJSExporter "ThreeJSExporter"
 		totalVertices = mergedVertices.count
 		totalFaces = mergedFaces.count
 		totalMaterials = mergedMaterials.count
-
+		
+		totalColors = 0
 		totalNormals = 0
+		totalUvs = 0
+		
+		if sceneHasVColors then
+		(
+
+			totalColors = totalVertices
+
+		)
+
 		if exportNormal.checked then 
 		(
+
 			totalNormals = mergedNormals.count
+
 		)
 
-		totalUvs = 0
 		if exportUv.checked then
 		(
+
 			totalUvs = mergedUvs.count
+
 		)
 
 
 		-- Dump header
 
-		Format headerFormat maxFileName totalVertices totalNormals totalUvs totalFaces totalMaterials to:ostream
+		Format headerFormat maxFileName totalVertices totalNormals totalColors totalUvs totalFaces totalMaterials to:ostream
 
 		-- Dump objects (debug)
 
@@ -883,6 +1024,7 @@ rollout ThreeJSExporter "ThreeJSExporter"
 
 		DumpVertices mergedVertices
 		DumpNormals mergedNormals
+		DumpColors mergedColors sceneHasVColors
 		DumpUvs mergedUvs
 		DumpFaces mergedFaces
 
@@ -903,13 +1045,19 @@ rollout ThreeJSExporter "ThreeJSExporter"
 
 		fname = GetSaveFileName filename:zname types:"JavaScript file (*.js)|*.js|All Files(*.*)|*.*|"
 		if fname == undefined then
+		(
+
 			return undefined
 
+		)
+
 		ostream = CreateFile fname
 		if ostream == undefined then
 		(
+
 			MessageBox "Couldn't open file for writing !"
 			return undefined
+
 		)
 
 		return ostream
@@ -923,8 +1071,10 @@ rollout ThreeJSExporter "ThreeJSExporter"
 		ostream = GetSaveFileStream()
 		if ostream != undefined then
 		(
+
 			ExportScene()
 			close ostream
+
 		)
 
 	)