Home Technical Talk

Consolidate Materials into a MultiSub Materials - 3ds Max

Hi Folks, I have a model with several separate materials. Is there a script for Max 2012 that will condense or consolidate them into one Multi-Sub material and update the model with the relevant material ids?

I have a bunch of models to do this for and it would really speed me up.

Thank you!

Replies

  • leechdemon
    Options
    Offline / Send Message
    leechdemon polycounter lvl 11
    I'm not sure about a script, but if you attach them all with edit poly, you'll get a "merge IDs" dialogue that'll combine them for you. I'm sure it's scriptable, but if you can live with them as one object, you may not need to even do that much.
  • WhiteNorthStar
    thank you! yes, agreed, but I may need to keep the objects separate... which is why I'm looking for a script
  • leechdemon
    Options
    Offline / Send Message
    leechdemon polycounter lvl 11
    You could clone everything, merge the clones, then put that material on the originals. You'd have to re-ID after, but you could always "select by material" or "select similar" and do them in waves.
  • WhiteNorthStar
    very creative! however, I may have quite a few models and that's why I'm looking for a script to save time... it will help me avoid attaching the objects of each model, and especially save me from re-IDing.
  • Bryan Cavett
    Options
    Offline / Send Message
    Bryan Cavett polycounter lvl 19
    Here's a real quick script I wrote. It doesn't have a lot of error checking but I dont have the time to spend on it. Just select some geometry and run the script. It will loop through the selection, add a material modifier, sets the mat id of that modifier to a number, takes the current material and adds it to a multisub material, and then adds that mutlti sub material to the object. It will show up under the category "BCTools" and is called "objectsToMultiSub"
    macroscript objectsToMultiSub
    category:"BCTools"
    (
    	if selection.count >= 1 then
    	(
    		local selectedGeom = selection as array
    		local newMat = multisubmaterial()
    		newMat.name = "newMat"
    		newMat.count = selectedGeom.count
    		meditMaterials[1] = newMat
    		for i in 1 to selectedGeom.count do
    		(
    			addModifier selectedGeom[i] (Materialmodifier ())
    			selectedGeom[i].modifiers[#Material].materialID = i
    			newMat.material[i] = selectedGeom[i].material
    			selectedGeom[i].material = newMat
    		)
    	)
    )
    
  • WhiteNorthStar
    Bryan, you are a flipping genius, thank you!

    :-D
  • Bryan Cavett
    Options
    Offline / Send Message
    Bryan Cavett polycounter lvl 19
    No problem.

    I should mention that this script assumes that each object has a different material and there are not any duplicates. If you have duplicates then I would need to check for those to see if they are already in the multi/sub or not and then assign the right matid.
  • WhiteNorthStar
    Bryan, I seem to keep coming back to needing this solution, and there are often duplicate materials in my scenes.

    If you have time, I'd be very grateful if you would add this functionality to your script.

    Again, thank you for your awesomeness :D
  • Bryan Cavett
    Options
    Offline / Send Message
    Bryan Cavett polycounter lvl 19
    See if this new script suits your needs. I've also fixed a bug that added duplicate material IDs to the multisub if you selected objects in a certain way. Objects that had the same material applied to them that were selected right after one another would cause this.
    macroscript objectsToMultiSub
    category:"BCTools"
    (
    	if selection.count >= 1 then
    	(
    		local selectedGeom = selection as array
    		local newMat = multisubmaterial()
    		newMat.name = "newMat"
    		newMat.count = 0
    		meditMaterials[1] = newMat
    		
    		addModifier selectedGeom[1] (Materialmodifier ())
    		selectedGeom[1].modifiers[#Material].materialID = 1
    		newMat.material[1] = selectedGeom[1].material
    		selectedGeom[1].material = newMat
    			
    		for i in 2 to selectedGeom.count do
    		(
    			doesMatExist = findItem newMat.material selectedGeom[i].material
    
    			if doesMatExist == 0 then
    			(
    				addModifier selectedGeom[i] (Materialmodifier ())
    				selectedGeom[i].modifiers[#Material].materialID = i
    				newMat.material[newMat.material.count+1] = selectedGeom[i].material
    				selectedGeom[i].material = newMat
    			)
    			else
    			(
    				addModifier selectedGeom[i] (Materialmodifier ())
    				selectedGeom[i].modifiers[#Material].materialID = doesMatExist
    				selectedGeom[i].material = newMat
    			)
    			
    		)
    	)
    )
    
  • WhiteNorthStar
    Wow, that was fast!

    It's almost perfect, but it is assigning the incorrect material id to objects
  • Bryan Cavett
    Options
    Offline / Send Message
    Bryan Cavett polycounter lvl 19
    Sorry small bug... This should work but again its not bullet proof. I just dont have the time to get it to that point but I hope this helps.
    macroscript objectsToMultiSub
    category:"BCTools"
    (
    	if selection.count >= 1 then
    	(
    		local selectedGeom = selection as array
    		local newMat = multisubmaterial()
    		newMat.name = "newMat"
    		newMat.count = 0
    		meditMaterials[1] = newMat
    		
    		addModifier selectedGeom[1] (Materialmodifier ())
    		selectedGeom[1].modifiers[#Material].materialID = 1
    		newMat.material[1] = selectedGeom[1].material
    		selectedGeom[1].material = newMat
    			
    		for i in 2 to selectedGeom.count do
    		(
    			doesMatExist = findItem newMat.material selectedGeom[i].material
    			
    			--print doesMatExist
    			if doesMatExist == 0 then
    			(
    				addModifier selectedGeom[i] (Materialmodifier ())
    				selectedGeom[i].modifiers[#Material].materialID = newMat.material.count+1
    				newMat.material[newMat.material.count+1] = selectedGeom[i].material
    				selectedGeom[i].material = newMat
    			)
    			else
    			(
    				addModifier selectedGeom[i] (Materialmodifier ())
    				selectedGeom[i].modifiers[#Material].materialID = doesMatExist
    				selectedGeom[i].material = newMat
    			)
    		)
    	)
    )
    
  • WhiteNorthStar
    Bryan, you are a beacon of awesomeness :D

    it's creating the multisub material perfectly, but still assigning the wrong material to the objects.

    anyway, I understand that you have better things to do, anyway it's progress! :D

    EDIT: Actually, it is right about 60% of the time, so that's a big help combined with auto multisub, the rest I can drag and drop manually
  • Bryan Cavett
    Options
    Offline / Send Message
    Bryan Cavett polycounter lvl 19
    Sorry WhiteNorthStar but I cant replicate this in my test scene. Its possible that you have something in your scene that im not accounting for. Do you have anymore info you can give me on how this is being used in your scene? Types of materials? or objects that already have multiple mat IDs?

    I am assuming that all the objects in the scene have one mat ID and one standard material applied to them and its very likely this script will fail if none of the criteria is met. Thats what I meant about it not being bullet proof :)
  • WhiteNorthStar
    Bryan, you've been great

    I'm not sure what is causing it, but my scene materials are a bit of a mess... after all my experimenting, it could be anything.

    On a fresh scene, with normal conditions, maybe it will work perfectly. Anyway, I really appreciate the time you put into this... do you have a paypal so I can buy you a virtual coffee... feel free to PM me with it :D
Sign In or Register to comment.