Batch saveto previous

Hi,

I'm thinking this may be simple, but have absolutely no maxscript skills whatsoever. I have a bunch of files saved in Max 2015, and I'd like to save them all back - as copies - to max 2013 versions. Anyone?

Thanks,

Phil

Comments

Comment viewing options

Select your preferred way to display the comments and click "Save settings" to activate your changes.
nnq2603's picture

How to add a custom script into this batch processing?

May I ask something about this batch processing.

I've got many *.max file in library that was provided as 2012 but actually was saved from higher version, so when use them in Xref object and Xref scene, annoying popup always display "Missing Dlls" - (which is nothing useful missing actually, just some higher Max dependencies left in those files).

I've found script to "remove missing dlls" and I've found this batch lower version save-as. How to combine them together for a batch processing which remove-missing-dlls message and save-as to lower version? Or how to execute other *.ms file in the time this batch perform action?

Saving time for anyone would combine these 2 function, the remove missing plugin script is the one by M. Breidt ([email protected])was largely published in web. Code below.

(
 
	-- get list of missing plugin classes
	str = stringStream ""
	apropos "*missing*" to:str
	seek str 0
	cls = #()
	while not (eof str) do (
		ln = readLine str
		tk = filterString ln " "
		if tk.count == 4 then (
			clsName = tk[1]
			try (
				val = (execute clsName)
				sc = superClassOf val
				-- Alternative: check for .classID == #(-1,0)
				if sc==MAXWrapper or sc==node or sc==material or sc==MAXWrapperNonRefTarg then (
					append cls val
					format "%: %\n" c val
				) else (
					format "Skipping % (%)\n" val sc
				)
			) catch (
				format "Cannot use % for searching missing plugins.\n" clsName
			)
		) else (
			format "Incorrect string found in missing plugin name list: %\n" tk
		)
	)
	-- now search for instances of those missing plugins
	c = 0
	foundMissing = #()
	for j = 1 to cls.count do (
		cc = cls[j]
		ci = getClassInstances cc
		if ci.count > 0 then (
			format "%: Found % instances of %: %\n" j ci.count cc ci
			for i = 1 to ci.count do (
				-- get current class
				myClass = classOf cc
				append foundMissing myClass
				-- get list of all subclasses
				allClasses = myClass.classes
				for k = 1 to allClasses.count do (
					-- search for useful replacement
					if allClasses[k].creatable then (
						-- create new instance of default (first) class
						newInst = createInstance allClasses[k]
						try (
							-- replace all instances (requires 3ds Max 2008+ or AVG extensions)
							q = replaceInstances ci[i] newInst
							c += 1
							-- and exit for k loop
							exit
						) catch (
							format "Error replacing %\n" ci[i]
							format "Exception: %\n" (getCurrentException())
						)
					)
				) -- end: for k
				-- todo: what happens if NO useful replacement was found?
			) -- end: for i
		) -- end: if
	) -- end: for j
	if c > 0 then (
		-- produce summary message for user
		str = "Replaced "
		append str (c as string)
		append str " missing plugin(s) with default objects:\n"
		for i in foundMissing do (
			append str "\t"
			append str (i as string)
			append str "\n"
		)
		append str "\nUSE RESULT WITH CAUTION!\nSAVE TO A DIFFERENT FILE NAME!"
		messageBox str title:"removeMissingPlugins v0.1" beep:true
		print foundMissing
	) else (
		messageBox "No missing plugins found" title:"removeMissingPlugins v0.1"
	)
)

Thanks miauu & lightcube for given script.

miauu's picture

.

I can't test it, so you have to do it.

--******************************************************************************************************
-- Created: 		14-06-2014
-- Last Updated:	05-12-2015
-- Version:			1.10
--
-- Author :  Kostadin Kotev / [email protected] / http://miauumaxscript.blogspot.com/
-- Version:  3ds max 2009 (10) (should work in older versions too!)
--
-- Version 1.10 (functions added by Shawn Olson / http://www.shawnolson.net )
-- Added drop down to choose Max versions that the current Max can save to
-- Added checkbox to make the copying of files optional. Copy is off, overwrites original files.
--
-- Discription: Batch save selected MAX files to previous versions and optionally make copy
-- Usage: RUN IT
--
-- Wishlist:
--
--******************************************************************************************************
-- MODIFY THIS AT YOUR OWN RISK
 
-- macroscript miauuBatchSaveAsPrevious
-- category:"miauu"
-- tooltip:"Batch SaveAsPrevious"
-- buttonText:"Batch SaveAsPrevious"
(
	global rol_miauuBatchLoadXRefScenes
    try(destroyDialog rol_miauuBatchLoadXRefScenes)catch()
    rollout rol_miauuBatchLoadXRefScenes "miauu's Batch Save As Previous" width:405 height:291
    (
		local ConvertClass = dotnetclass "system.convert"
		local ImageClass = dotnetclass "system.drawing.image"
		local logoIcon = "iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAAIGNIUk0AAHolAACAgwAA+f8AAIDpAAB1MAAA6mAAADqYAAAXb5JfxUYAAAAJcEhZcwAACxIAAAsSAdLdfvwAAALcSURBVDhPbZJLSFRhGIa/1C6IMmmQFNownplzv8y5zIzOqGPimE5hFxfeZxQzu0AXDbtsXHWBwNpWaIt2lQWBFSS0qCholbsW7QwiiKBNRDlv//xTWtjiO9+B77zP+37/+QkA7QxXULu7mZLmVmq1K2lvtIzSjm/A0Wt/NjdEl0d62w+eGe2gyUyCTvXHaawnSRNDTVy7AuhwfdTt+Kg1XBFIWNVLmqZj/ryGc90yVN1CZ3vjx9PDLWpS3UJH+pI0nv0L0MaEaa+cYnr1M0OVIKkWNN0AXsQxe0KCIkvwCxI818bgvsTL8eFWmhpLrgLq9Korri4si4oJVTNg6Covy5RhGQrrOusqQqIEQVSQqI/mjvY1T68AhJCc0wwLuqbwmuwKAfdcDkl4MvAmjr1NEgNpMA0NghCEFXZzKwBRFHP54WhawudbNpbuePg+5+DVBR3vZlxgIYrFqwY+zNjoSckcbNvhVYAkhnIWI4/36czZRiNzzX/07kYYl7MSd812qsC8h96UxFOy81gLOLSHxX3ooi4scsBb5jrVL3PAGJt9u2uju7Wwpuc6awEne1mChRganALgy/0oprMiB5wdsXiCgV1yAeD8B3B8P0vwOIJUfWGFL7ct3DymcsDxLgV45GEo/SfBXyvIssQPcWKQ/XsGaP8NeP+gHtdGFA6YHLOBJxFkdv1nhUBtMOc4Nhflh/lusuKdifPp8j1fYWaksJtpOLFVgFNbOltd44fCLpFpsdiHJbZvhAPa6tj763pkUiJ000JIjzATGW12xfMVQIuygbZv2bhJ2uFbDAYFXDrh4dP1MAMoSCU14GkMnc0Wu+Immqyqz/2xdXXDsYKWPxqkUvJvKyM3UEJ6TUlc8ld+9QsqNNNmrg4ExUHEqPlxwF1/6nAD0WgjUU+0+F9ATVU5WYFSigY3kreDKOIvuaiGqpdNNYTdbtncSJzoYIIoGy+mTLyIAYqYFvQLPey9qVeXvysAAAAASUVORK5CYII="
		local curMaxVersion = ((maxVersion())[1] / 1000)
		local openFileRoll = dotNetObject "System.Windows.Forms.OpenFileDialog"	
        local disableForeColor = (dotNetClass "System.Drawing.Color").white
        local maxFiles = #()      
		function versionNums = (
			local longVersion = ((curMaxVersion - 2) + 2000) 
			for i = 1 to 3 collect (longVersion - (1 * i))
		)
		local versions = versionNums() -- array of versions the current version of Max can save to.
    	dotNetControl lv_Batch "system.windows.forms.listView" pos:[10,10] width:273 height:200
 
    	button btn_getDir "Get Directory" pos:[290,10] width:108 height:21 toolTip:"Select all .max files in the given folder and/or its sub-folders"
    	button btn_getFile "Get file(s)" pos:[290,35] width:108 height:21 toolTip:"Select one or multiple files in given folder"
    	button btn_Clear "Clear" pos:[290,60] width:108 height:21
    	dropdownList ddl_version "Save to Version" pos:[295,223] width:96 height:40 items:(for v in versions collect v as string)
    	checkbox chkBox_showFullPath "Show Full Path" pos:[10,215] width:95 height:15
    	label lbl_select "Select:" pos:[120,215] width:33 height:13
    	button btn_all "All" pos:[157,214] width:40 height:18
    	button btn_none "None" pos:[200,214] width:40 height:18
    	button btn_invert "Invert" pos:[243,214] width:40 height:18
    	button bnt_saveAsPrevious "Save as previous" pos:[9,235] width:276 height:30
    	HyperLink http_miauu "miauu's MaxScripts" pos:[300,270] width:90 height:15 address:"http://miauumaxscript.blogspot.com/" color:(color 7 231 251)
    	progressBar pb_xRefprogress "" pos:[10,270] width:275 height:14 value:0 color:(color 0 255 0)
    	checkbox chk_Copy "Make Copy" pos:[300,204] width:90 height:16 checked:true tooltip:"When off, overwrites the original file."
 
		--	Credits to Peter Addington - http://lonerobot.net/?p=314
		function String2Bmp string =
		(
			local clipboardClass = dotNetClass "System.Windows.Forms.Clipboard"
			local ConvertClass = dotnetclass "system.convert"
			local imageclass = dotNetclass "System.Drawing.image"
			local bytearr = convertclass.FromBase64String string
			local memstream = dotnetobject "System.IO.MemoryStream" bytearr
			local DecodedImg = ImageClass.fromstream memstream
			memstream.close()
			DecodedImg
		)
		--	credits to Denis Trofimiv - http://forums.cgsociety.org/showpost.php?p=7708817&postcount=21
		function LoadMyLogoAsTitlebarIcon =
		(
			d = (windows.getChildHWND 0 rol_miauuBatchLoadXRefScenes.title)[1]
			WM_SETICON = 0x0080
			ICON_SMALL = 0
			bm = dotnetobject "System.Drawing.Bitmap" (String2Bmp logoIcon)			
			ptr = bm.GetHicon()
			icon = (dotnetclass "System.Drawing.Icon").FromHandle (dotnetobject "IntPtr" ptr)			
			windows.SendMessage d WM_SETICON ICON_SMALL icon.handle
		)
 
        function AddColumns theLv columnsAr=
        (
            if chkBox_showFullPath.state == false then
                w=(theLv.width)-6
            else
                w=(theLv.width)+400
            for x in columnsAr do
            (
                theLv.columns.add x w
            )
        )
        function PopulateListView theLv=
        (
            rows=#()
            for x=1 to maxFiles.count do
            (
                if chkBox_showFullPath.state == false then
                    mapName = (getFilenameFile maxFiles[x])
                else
                    mapName = maxFiles[x]
 
                li = dotNetObject "System.Windows.Forms.ListViewItem" mapName
                append rows li
            )
            theLv.items.addRange rows
        )
        function InitListView theLv=
        (            
            theLv.clear()
			theLv.headerStyle = theLv.headerStyle.none
            theLv.view = (dotNetClass "system.windows.forms.view").details
            theLv.FullRowSelect = true    
            theLv.MultiSelect = true    
            theLv.checkBoxes = true                
            theLv.backcolor = (dotNetClass "System.Drawing.Color").DimGray
            theLv.forecolor = (dotNetClass "System.Drawing.Color").lightGray
        )
        function BatchListViewReIinit =
        (
            InitListView lv_Batch
            AddColumns lv_Batch #("")    
            PopulateListView lv_Batch
        )
        function TurnBatchLVchkBoxOn =
        (
            for i = 0 to lv_Batch.Items.count-1 do
                lv_Batch.Items.Item[i].checked = true
            lv_Batch.forecolor = disableForeColor
        )    
        function OpenFolders folderToOpen =
        (
            local checkFolderName = substring folderToOpen 1 (folderToOpen.count-1)
            if (symbolicPaths.isPathName checkFolderName) then
            (
                folderToOpen = symbolicPaths.getPathValue checkFolderName
            )                
            shellLaunch "explorer.exe" folderToOpen
        )        
 
        function GetFilesRecursive root pattern =
        (        
            dir_array = GetDirectories (root+"\*")
            for d in dir_array do
                join dir_array (GetDirectories (d+"*"))    
 
            my_files = #()                
            for f in dir_array do
                join my_files (getFiles (f + pattern))
 
            my_files
        )
 
		function RemoveMissingDLLs =
		(		 
			-- get list of missing plugin classes
			str = stringStream ""
			apropos "*missing*" to:str
			seek str 0
			cls = #()
			while not (eof str) do 
			(
				ln = readLine str
				tk = filterString ln " "
				if tk.count == 4 then 
				(
					clsName = tk[1]
					try 
					(
						val = (execute clsName)
						sc = superClassOf val
						-- Alternative: check for .classID == #(-1,0)
						if sc==MAXWrapper or sc==node or sc==material or sc==MAXWrapperNonRefTarg then 
						(
							append cls val
							format "%: %\n" c val
						) 
						else 
						(
							format "Skipping % (%)\n" val sc
						)
					) 
					catch 
					(
						format "Cannot use % for searching missing plugins.\n" clsName
					)
				) 
				else 
				(
					format "Incorrect string found in missing plugin name list: %\n" tk
				)
			)
			-- now search for instances of those missing plugins
			c = 0
			foundMissing = #()
			for j = 1 to cls.count do 
			(
				cc = cls[j]
				ci = getClassInstances cc
				if ci.count > 0 then 
				(
					format "%: Found % instances of %: %\n" j ci.count cc ci
					for i = 1 to ci.count do 
					(
						-- get current class
						myClass = classOf cc
						append foundMissing myClass
						-- get list of all subclasses
						allClasses = myClass.classes
						for k = 1 to allClasses.count do 
						(
							-- search for useful replacement
							if allClasses[k].creatable then 
							(
								-- create new instance of default (first) class
								newInst = createInstance allClasses[k]
								try 
								(
									-- replace all instances (requires 3ds Max 2008+ or AVG extensions)
									q = replaceInstances ci[i] newInst
									c += 1
									-- and exit for k loop
									exit
								) 
								catch 
								(
									format "Error replacing %\n" ci[i]
									format "Exception: %\n" (getCurrentException())
								)
							)
						) -- end: for k
						-- todo: what happens if NO useful replacement was found?
					) -- end: for i
				) -- end: if
			) -- end: for j
			if c > 0 then 
			(
				-- produce summary message for user
				str = "Replaced "
				append str (c as string)
				append str " missing plugin(s) with default objects:\n"
				for i in foundMissing do 
				(
					append str "\t"
					append str (i as string)
					append str "\n"
				)
				append str "\nUSE RESULT WITH CAUTION!\nSAVE TO A DIFFERENT FILE NAME!"
				print "------------ removeMissingPlugins v0.1 ------------ "
				print str
				print foundMissing
			) 
			else 
			(
				messageBox "No missing plugins found" title:"removeMissingPlugins v0.1"
			)
		)
 
 
    	on rol_miauuBatchLoadXRefScenes open do
    	( 
    		try(LoadMyLogoAsTitlebarIcon())catch()
 
    		openFileRoll.title = "Select Files"
    		openFileRoll.Multiselect = true
    		openFileRoll.Filter = "MAX (*.max)|*.max"
    		openFileRoll.FilterIndex = 1
    		openFileRoll.RestoreDirectory = true	
 
    	    InitListView lv_Batch
    	    AddColumns lv_Batch #("Files")
    	)
    	on lv_Batch mouseDown arg do
    	(
    	    --    delete selected max file from the listview
    	    if arg.button==arg.button.middle then
    	    (                
    	        if (hitNode = lv_Batch.GetItemAt arg.x arg.y) != undefined do
    	        (
    	            deleteItem maxFiles (hitNode.index+1)
    	            BatchListViewReIinit()
    	        )                
    	    )
    	    --    open folder of selected max file
    	    if arg.button==arg.button.right then
    	    (                
    	        if (hitNode = lv_Batch.GetItemAt arg.x arg.y) != undefined do
    	        (
    	            f = (hitNode.index+1)
    	            folderToOpen = (getFilenamePath maxFiles[f])
    	            OpenFolders folderToOpen
    	        )                
    	    )
    	)
    	on btn_getDir pressed do
    	(
    	    dir = getSavePath caption:"Select the directory" initialDir:"$scenes"
    	    if dir != undefined do
    	    (
    	        maxFiles = #()
    	        --    get all max files
    	        maxFiles = getFiles (dir+"\*.max")
    	        --    check for subfolders
    	        subFiles = GetFilesRecursive dir "*.max"
    	        if subFiles.count != 0 then
    	        (
    	            msg = "The selected folder have subfolders!\n"
    	            msg += "Do you want to include the files from the subfolders too?"
    	            if queryBox  msg title:"Sub-folders found" do
    	                join maxFiles subFiles
    	        )
    			makeUniqueArray maxFiles
    	        PopulateListView lv_Batch
    	        TurnBatchLVchkBoxOn()
    	    )
    	)
    	on btn_getFile pressed do
    	(
    		result = openFileRoll.showDialog()
    		result.ToString() 
    		if (result.Equals result.OK) do 
    		(
    			filePath = (openFileRoll.fileNames)
    			join maxFiles filePath
    			makeUniqueArray maxFiles
    	        BatchListViewReIinit()
    	        TurnBatchLVchkBoxOn()
    		)
    	)
    	on btn_Clear pressed do
    	(
    	    maxFiles = #()
    	    BatchListViewReIinit()
    	)
    	on chkBox_showFullPath changed state do
    	(
    		cbState = for i = 0 to lv_Batch.Items.count-1 collect lv_Batch.Items.Item[i].checked
    	    BatchListViewReIinit()
    	    for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = cbState[i + 1]
    	)
    	on btn_all pressed do
    	(
    		for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = true
    	)
    	on btn_none pressed do
    	(
    		for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = false
    	)
    	on btn_invert pressed do
    	(
    		for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = not lv_Batch.Items.Item[i].checked
    	)
    	on bnt_saveAsPrevious pressed do
    	(	
    		local xRefCnt = (lv_Batch.Items.count - 1)
    		setWaitCursor()
    		suspendEditing()
    		resetMaxFile #noPrompt
    		for i = 0 to xRefCnt where (lv_Batch.Items.Item[i].checked == true) do with redraw off
    		(
 
    			if (loadMaxFile maxFiles[i+1] useFileUnits:true quiet:true) do
    			(
 
					RemoveMissingDLLs()
 
    				filePath = getFilenamePath maxFiles[i+1]
					fileName = (getFilenameFile maxFiles[i+1])
					local ver = ddl_version.selected
					if chk_Copy.checked then (
						fileName = (getFilenameFile maxFiles[i+1]) += "_" + ver
					)
    				newName = filePath + "\\" + fileName + ".max"
    				saveMaxFile newName saveAsVersion:(ver as integer) useNewFile:true quiet:true 
    			)
    			resetMaxFile #noPrompt
    			pb_xRefprogress.value = 100.0 * i / xRefCnt
    			if curMaxVersion > 12 do
    				windows.processPostedMessages()
    		)
    		completeRedraw()
    		resumeEditing()
    		setArrowCursor()
    	)
    )
    createdialog rol_miauuBatchLoadXRefScenes width:405 
)

This is the Shawns's version. IF you want to use mine, then you have to edit the script.

nnq2603's picture

Error on running script

Both 2012 and 2014 get the same error:
---------------------------
MAXScript Rollout Handler Exception
---------------------------
-- No ""="" function for (Global:getFilenameFile (RolloutLocal:maxFiles in rollout:rol_miauuBatchLoadXRefScenes[(%"+"() Local:i 1)]))
---------------------------
OK
---------------------------
It stop right there " fileName..."

if chk_Copy.checked then (
 fileName = (getFilenameFile maxFiles[i+1]) += "_" + ver
)
miauu's picture

.

Fixed. Try it:

--******************************************************************************************************
-- Created: 		14-06-2014
-- Last Updated:	05-12-2015
-- Version:			1.10
--
-- Author :  Kostadin Kotev / [email protected] / http://miauumaxscript.blogspot.com/
-- Version:  3ds max 2009 (10) (should work in older versions too!)
--
-- Version 1.10 (functions added by Shawn Olson / http://www.shawnolson.net )
-- Added drop down to choose Max versions that the current Max can save to
-- Added checkbox to make the copying of files optional. Copy is off, overwrites original files.
--
-- Discription: Batch save selected MAX files to previous versions and optionally make copy
-- Usage: RUN IT
--
-- Wishlist:
--
--******************************************************************************************************
-- MODIFY THIS AT YOUR OWN RISK
 
-- macroscript miauuBatchSaveAsPrevious
-- category:"miauu"
-- tooltip:"Batch SaveAsPrevious"
-- buttonText:"Batch SaveAsPrevious"
(
	global rol_miauuBatchLoadXRefScenes
    try(destroyDialog rol_miauuBatchLoadXRefScenes)catch()
    rollout rol_miauuBatchLoadXRefScenes "miauu's Batch Save As Previous" width:405 height:291
    (
		local ConvertClass = dotnetclass "system.convert"
		local ImageClass = dotnetclass "system.drawing.image"
		local logoIcon = "iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAAIGNIUk0AAHolAACAgwAA+f8AAIDpAAB1MAAA6mAAADqYAAAXb5JfxUYAAAAJcEhZcwAACxIAAAsSAdLdfvwAAALcSURBVDhPbZJLSFRhGIa/1C6IMmmQFNownplzv8y5zIzOqGPimE5hFxfeZxQzu0AXDbtsXHWBwNpWaIt2lQWBFSS0qCholbsW7QwiiKBNRDlv//xTWtjiO9+B77zP+37/+QkA7QxXULu7mZLmVmq1K2lvtIzSjm/A0Wt/NjdEl0d62w+eGe2gyUyCTvXHaawnSRNDTVy7AuhwfdTt+Kg1XBFIWNVLmqZj/ryGc90yVN1CZ3vjx9PDLWpS3UJH+pI0nv0L0MaEaa+cYnr1M0OVIKkWNN0AXsQxe0KCIkvwCxI818bgvsTL8eFWmhpLrgLq9Korri4si4oJVTNg6Covy5RhGQrrOusqQqIEQVSQqI/mjvY1T68AhJCc0wwLuqbwmuwKAfdcDkl4MvAmjr1NEgNpMA0NghCEFXZzKwBRFHP54WhawudbNpbuePg+5+DVBR3vZlxgIYrFqwY+zNjoSckcbNvhVYAkhnIWI4/36czZRiNzzX/07kYYl7MSd812qsC8h96UxFOy81gLOLSHxX3ooi4scsBb5jrVL3PAGJt9u2uju7Wwpuc6awEne1mChRganALgy/0oprMiB5wdsXiCgV1yAeD8B3B8P0vwOIJUfWGFL7ct3DymcsDxLgV45GEo/SfBXyvIssQPcWKQ/XsGaP8NeP+gHtdGFA6YHLOBJxFkdv1nhUBtMOc4Nhflh/lusuKdifPp8j1fYWaksJtpOLFVgFNbOltd44fCLpFpsdiHJbZvhAPa6tj763pkUiJ000JIjzATGW12xfMVQIuygbZv2bhJ2uFbDAYFXDrh4dP1MAMoSCU14GkMnc0Wu+Immqyqz/2xdXXDsYKWPxqkUvJvKyM3UEJ6TUlc8ld+9QsqNNNmrg4ExUHEqPlxwF1/6nAD0WgjUU+0+F9ATVU5WYFSigY3kreDKOIvuaiGqpdNNYTdbtncSJzoYIIoGy+mTLyIAYqYFvQLPey9qVeXvysAAAAASUVORK5CYII="
		local curMaxVersion = ((maxVersion())[1] / 1000)
		local openFileRoll = dotNetObject "System.Windows.Forms.OpenFileDialog"	
        local disableForeColor = (dotNetClass "System.Drawing.Color").white
        local maxFiles = #()      
		function versionNums = (
			local longVersion = ((curMaxVersion - 2) + 2000) 
			for i = 1 to 3 collect (longVersion - (1 * i))
		)
		local versions = versionNums() -- array of versions the current version of Max can save to.
    	dotNetControl lv_Batch "system.windows.forms.listView" pos:[10,10] width:273 height:200
 
    	button btn_getDir "Get Directory" pos:[290,10] width:108 height:21 toolTip:"Select all .max files in the given folder and/or its sub-folders"
    	button btn_getFile "Get file(s)" pos:[290,35] width:108 height:21 toolTip:"Select one or multiple files in given folder"
    	button btn_Clear "Clear" pos:[290,60] width:108 height:21
    	dropdownList ddl_version "Save to Version" pos:[295,223] width:96 height:40 items:(for v in versions collect v as string)
    	checkbox chkBox_showFullPath "Show Full Path" pos:[10,215] width:95 height:15
    	label lbl_select "Select:" pos:[120,215] width:33 height:13
    	button btn_all "All" pos:[157,214] width:40 height:18
    	button btn_none "None" pos:[200,214] width:40 height:18
    	button btn_invert "Invert" pos:[243,214] width:40 height:18
    	button bnt_saveAsPrevious "Save as previous" pos:[9,235] width:276 height:30
    	HyperLink http_miauu "miauu's MaxScripts" pos:[300,270] width:90 height:15 address:"http://miauumaxscript.blogspot.com/" color:(color 7 231 251)
    	progressBar pb_xRefprogress "" pos:[10,270] width:275 height:14 value:0 color:(color 0 255 0)
    	checkbox chk_Copy "Make Copy" pos:[300,204] width:90 height:16 checked:true tooltip:"When off, overwrites the original file."
 
		--	Credits to Peter Addington - http://lonerobot.net/?p=314
		function String2Bmp string =
		(
			local clipboardClass = dotNetClass "System.Windows.Forms.Clipboard"
			local ConvertClass = dotnetclass "system.convert"
			local imageclass = dotNetclass "System.Drawing.image"
			local bytearr = convertclass.FromBase64String string
			local memstream = dotnetobject "System.IO.MemoryStream" bytearr
			local DecodedImg = ImageClass.fromstream memstream
			memstream.close()
			DecodedImg
		)
		--	credits to Denis Trofimiv - http://forums.cgsociety.org/showpost.php?p=7708817&postcount=21
		function LoadMyLogoAsTitlebarIcon =
		(
			d = (windows.getChildHWND 0 rol_miauuBatchLoadXRefScenes.title)[1]
			WM_SETICON = 0x0080
			ICON_SMALL = 0
			bm = dotnetobject "System.Drawing.Bitmap" (String2Bmp logoIcon)			
			ptr = bm.GetHicon()
			icon = (dotnetclass "System.Drawing.Icon").FromHandle (dotnetobject "IntPtr" ptr)			
			windows.SendMessage d WM_SETICON ICON_SMALL icon.handle
		)
 
        function AddColumns theLv columnsAr=
        (
            if chkBox_showFullPath.state == false then
                w=(theLv.width)-6
            else
                w=(theLv.width)+400
            for x in columnsAr do
            (
                theLv.columns.add x w
            )
        )
        function PopulateListView theLv=
        (
            rows=#()
            for x=1 to maxFiles.count do
            (
                if chkBox_showFullPath.state == false then
                    mapName = (getFilenameFile maxFiles[x])
                else
                    mapName = maxFiles[x]
 
                li = dotNetObject "System.Windows.Forms.ListViewItem" mapName
                append rows li
            )
            theLv.items.addRange rows
        )
        function InitListView theLv=
        (            
            theLv.clear()
			theLv.headerStyle = theLv.headerStyle.none
            theLv.view = (dotNetClass "system.windows.forms.view").details
            theLv.FullRowSelect = true    
            theLv.MultiSelect = true    
            theLv.checkBoxes = true                
            theLv.backcolor = (dotNetClass "System.Drawing.Color").DimGray
            theLv.forecolor = (dotNetClass "System.Drawing.Color").lightGray
        )
        function BatchListViewReIinit =
        (
            InitListView lv_Batch
            AddColumns lv_Batch #("")    
            PopulateListView lv_Batch
        )
        function TurnBatchLVchkBoxOn =
        (
            for i = 0 to lv_Batch.Items.count-1 do
                lv_Batch.Items.Item[i].checked = true
            lv_Batch.forecolor = disableForeColor
        )    
        function OpenFolders folderToOpen =
        (
            local checkFolderName = substring folderToOpen 1 (folderToOpen.count-1)
            if (symbolicPaths.isPathName checkFolderName) then
            (
                folderToOpen = symbolicPaths.getPathValue checkFolderName
            )                
            shellLaunch "explorer.exe" folderToOpen
        )        
 
        function GetFilesRecursive root pattern =
        (        
            dir_array = GetDirectories (root+"\*")
            for d in dir_array do
                join dir_array (GetDirectories (d+"*"))    
 
            my_files = #()                
            for f in dir_array do
                join my_files (getFiles (f + pattern))
 
            my_files
        )
 
		function RemoveMissingDLLs =
		(		 
			-- get list of missing plugin classes
			str = stringStream ""
			apropos "*missing*" to:str
			seek str 0
			cls = #()
			while not (eof str) do 
			(
				ln = readLine str
				tk = filterString ln " "
				if tk.count == 4 then 
				(
					clsName = tk[1]
					try 
					(
						val = (execute clsName)
						sc = superClassOf val
						-- Alternative: check for .classID == #(-1,0)
						if sc==MAXWrapper or sc==node or sc==material or sc==MAXWrapperNonRefTarg then 
						(
							append cls val
							format "%: %\n" c val
						) 
						else 
						(
							format "Skipping % (%)\n" val sc
						)
					) 
					catch 
					(
						format "Cannot use % for searching missing plugins.\n" clsName
					)
				) 
				else 
				(
					format "Incorrect string found in missing plugin name list: %\n" tk
				)
			)
			-- now search for instances of those missing plugins
			c = 0
			foundMissing = #()
			for j = 1 to cls.count do 
			(
				cc = cls[j]
				ci = getClassInstances cc
				if ci.count > 0 then 
				(
					format "%: Found % instances of %: %\n" j ci.count cc ci
					for i = 1 to ci.count do 
					(
						-- get current class
						myClass = classOf cc
						append foundMissing myClass
						-- get list of all subclasses
						allClasses = myClass.classes
						for k = 1 to allClasses.count do 
						(
							-- search for useful replacement
							if allClasses[k].creatable then 
							(
								-- create new instance of default (first) class
								newInst = createInstance allClasses[k]
								try 
								(
									-- replace all instances (requires 3ds Max 2008+ or AVG extensions)
									q = replaceInstances ci[i] newInst
									c += 1
									-- and exit for k loop
									exit
								) 
								catch 
								(
									format "Error replacing %\n" ci[i]
									format "Exception: %\n" (getCurrentException())
								)
							)
						) -- end: for k
						-- todo: what happens if NO useful replacement was found?
					) -- end: for i
				) -- end: if
			) -- end: for j
			if c > 0 then 
			(
				-- produce summary message for user
				str = "Replaced "
				append str (c as string)
				append str " missing plugin(s) with default objects:\n"
				for i in foundMissing do 
				(
					append str "\t"
					append str (i as string)
					append str "\n"
				)
				append str "\nUSE RESULT WITH CAUTION!\nSAVE TO A DIFFERENT FILE NAME!"
				print "------------ removeMissingPlugins v0.1 ------------ "
				print str
				print foundMissing
			) 
			else 
			(
				print "No missing plugins found"
			)
		)
 
 
    	on rol_miauuBatchLoadXRefScenes open do
    	( 
    		try(LoadMyLogoAsTitlebarIcon())catch()
 
    		openFileRoll.title = "Select Files"
    		openFileRoll.Multiselect = true
    		openFileRoll.Filter = "MAX (*.max)|*.max"
    		openFileRoll.FilterIndex = 1
    		openFileRoll.RestoreDirectory = true	
 
    	    InitListView lv_Batch
    	    AddColumns lv_Batch #("Files")
    	)
    	on lv_Batch mouseDown arg do
    	(
    	    --    delete selected max file from the listview
    	    if arg.button==arg.button.middle then
    	    (                
    	        if (hitNode = lv_Batch.GetItemAt arg.x arg.y) != undefined do
    	        (
    	            deleteItem maxFiles (hitNode.index+1)
    	            BatchListViewReIinit()
    	        )                
    	    )
    	    --    open folder of selected max file
    	    if arg.button==arg.button.right then
    	    (                
    	        if (hitNode = lv_Batch.GetItemAt arg.x arg.y) != undefined do
    	        (
    	            f = (hitNode.index+1)
    	            folderToOpen = (getFilenamePath maxFiles[f])
    	            OpenFolders folderToOpen
    	        )                
    	    )
    	)
    	on btn_getDir pressed do
    	(
    	    dir = getSavePath caption:"Select the directory" initialDir:"$scenes"
    	    if dir != undefined do
    	    (
    	        maxFiles = #()
    	        --    get all max files
    	        maxFiles = getFiles (dir+"\*.max")
    	        --    check for subfolders
    	        subFiles = GetFilesRecursive dir "*.max"
    	        if subFiles.count != 0 then
    	        (
    	            msg = "The selected folder have subfolders!\n"
    	            msg += "Do you want to include the files from the subfolders too?"
    	            if queryBox  msg title:"Sub-folders found" do
    	                join maxFiles subFiles
    	        )
    			makeUniqueArray maxFiles
    	        PopulateListView lv_Batch
    	        TurnBatchLVchkBoxOn()
    	    )
    	)
    	on btn_getFile pressed do
    	(
    		result = openFileRoll.showDialog()
    		result.ToString() 
    		if (result.Equals result.OK) do 
    		(
    			filePath = (openFileRoll.fileNames)
    			join maxFiles filePath
    			makeUniqueArray maxFiles
    	        BatchListViewReIinit()
    	        TurnBatchLVchkBoxOn()
    		)
    	)
    	on btn_Clear pressed do
    	(
    	    maxFiles = #()
    	    BatchListViewReIinit()
    	)
    	on chkBox_showFullPath changed state do
    	(
    		cbState = for i = 0 to lv_Batch.Items.count-1 collect lv_Batch.Items.Item[i].checked
    	    BatchListViewReIinit()
    	    for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = cbState[i + 1]
    	)
    	on btn_all pressed do
    	(
    		for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = true
    	)
    	on btn_none pressed do
    	(
    		for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = false
    	)
    	on btn_invert pressed do
    	(
    		for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = not lv_Batch.Items.Item[i].checked
    	)
    	on bnt_saveAsPrevious pressed do
    	(	
    		local xRefCnt = (lv_Batch.Items.count - 1)
    		setWaitCursor()
    		suspendEditing()
    		resetMaxFile #noPrompt
    		for i = 0 to xRefCnt where (lv_Batch.Items.Item[i].checked == true) do with redraw off
    		(
 
    			if (loadMaxFile maxFiles[i+1] useFileUnits:true quiet:true) do
    			(
 
					RemoveMissingDLLs()
 
    				filePath = getFilenamePath maxFiles[i+1]
					fileName = (getFilenameFile maxFiles[i+1])
					local ver = ddl_version.selected
					if chk_Copy.checked then (
						fileName = (getFilenameFile maxFiles[i+1]) + "_" + ver
					)
    				newName = filePath + "\\" + fileName + ".max"
    				saveMaxFile newName saveAsVersion:(ver as integer) useNewFile:true quiet:true 
    			)
    			resetMaxFile #noPrompt
    			pb_xRefprogress.value = 100.0 * i / xRefCnt
    			if curMaxVersion > 12 do
    				windows.processPostedMessages()
    		)
    		completeRedraw()
    		resumeEditing()
    		setArrowCursor()
    	)
    )
    createdialog rol_miauuBatchLoadXRefScenes width:405 
)
nnq2603's picture

Work like a charm.

Work like a charm and no dialogue display in processing. Output *.max files are all good. Thanks man.

miauu's picture

Hi, Shawn! I have almost the

Hi, Shawn!

I have almost the same version as yours, but instead of ddl I use radiobuttons. :)

I hope the people will find your version useful and will use it.

:)

lightcube's picture

I was going to write a

I was going to write a function like this and luckily searched Google. Thanks Kostadin. Here is a modified version I made that creates a menu for the user to choose the version they need to save to and that the current version of Max is able to save to. Also, I added a checkbox so that the user can choose to overwrite the files instead of make copies (which is something I needed).

--******************************************************************************************************
-- Created: 		14-06-2014
-- Last Updated:	05-12-2015
-- Version:			1.10
--
-- Author :  Kostadin Kotev / mi[email protected] / http://miauumaxscript.blogspot.com/
-- Version:  3ds max 2009 (10) (should work in older versions too!)
--
-- Version 1.10 (functions added by Shawn Olson / http://www.shawnolson.net )
-- Added drop down to choose Max versions that the current Max can save to
-- Added checkbox to make the copying of files optional. Copy is off, overwrites original files.
--
-- Discription: Batch save selected MAX files to previous versions and optionally make copy
-- Usage: RUN IT
--
-- Wishlist:
--
--******************************************************************************************************
-- MODIFY THIS AT YOUR OWN RISK
 
macroscript miauuBatchSaveAsPrevious
category:"miauu"
tooltip:"Batch SaveAsPrevious"
buttonText:"Batch SaveAsPrevious"
(
	global rol_miauuBatchLoadXRefScenes
    try(destroyDialog rol_miauuBatchLoadXRefScenes)catch()
    rollout rol_miauuBatchLoadXRefScenes "miauu's Batch Save As Previous" width:405 height:291
    (
		local ConvertClass = dotnetclass "system.convert"
		local ImageClass = dotnetclass "system.drawing.image"
		local logoIcon = "iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAAIGNIUk0AAHolAACAgwAA+f8AAIDpAAB1MAAA6mAAADqYAAAXb5JfxUYAAAAJcEhZcwAACxIAAAsSAdLdfvwAAALcSURBVDhPbZJLSFRhGIa/1C6IMmmQFNownplzv8y5zIzOqGPimE5hFxfeZxQzu0AXDbtsXHWBwNpWaIt2lQWBFSS0qCholbsW7QwiiKBNRDlv//xTWtjiO9+B77zP+37/+QkA7QxXULu7mZLmVmq1K2lvtIzSjm/A0Wt/NjdEl0d62w+eGe2gyUyCTvXHaawnSRNDTVy7AuhwfdTt+Kg1XBFIWNVLmqZj/ryGc90yVN1CZ3vjx9PDLWpS3UJH+pI0nv0L0MaEaa+cYnr1M0OVIKkWNN0AXsQxe0KCIkvwCxI818bgvsTL8eFWmhpLrgLq9Korri4si4oJVTNg6Covy5RhGQrrOusqQqIEQVSQqI/mjvY1T68AhJCc0wwLuqbwmuwKAfdcDkl4MvAmjr1NEgNpMA0NghCEFXZzKwBRFHP54WhawudbNpbuePg+5+DVBR3vZlxgIYrFqwY+zNjoSckcbNvhVYAkhnIWI4/36czZRiNzzX/07kYYl7MSd812qsC8h96UxFOy81gLOLSHxX3ooi4scsBb5jrVL3PAGJt9u2uju7Wwpuc6awEne1mChRganALgy/0oprMiB5wdsXiCgV1yAeD8B3B8P0vwOIJUfWGFL7ct3DymcsDxLgV45GEo/SfBXyvIssQPcWKQ/XsGaP8NeP+gHtdGFA6YHLOBJxFkdv1nhUBtMOc4Nhflh/lusuKdifPp8j1fYWaksJtpOLFVgFNbOltd44fCLpFpsdiHJbZvhAPa6tj763pkUiJ000JIjzATGW12xfMVQIuygbZv2bhJ2uFbDAYFXDrh4dP1MAMoSCU14GkMnc0Wu+Immqyqz/2xdXXDsYKWPxqkUvJvKyM3UEJ6TUlc8ld+9QsqNNNmrg4ExUHEqPlxwF1/6nAD0WgjUU+0+F9ATVU5WYFSigY3kreDKOIvuaiGqpdNNYTdbtncSJzoYIIoGy+mTLyIAYqYFvQLPey9qVeXvysAAAAASUVORK5CYII="
		local curMaxVersion = ((maxVersion())[1] / 1000)
		local openFileRoll = dotNetObject "System.Windows.Forms.OpenFileDialog"	
        local disableForeColor = (dotNetClass "System.Drawing.Color").white
        local maxFiles = #()      
		function versionNums = (
			local longVersion = ((curMaxVersion - 2) + 2000) 
			for i = 1 to 3 collect (longVersion - (1 * i))
		)
		local versions = versionNums() -- array of versions the current version of Max can save to.
    	dotNetControl lv_Batch "system.windows.forms.listView" pos:[10,10] width:273 height:200
 
    	button btn_getDir "Get Directory" pos:[290,10] width:108 height:21 toolTip:"Select all .max files in the given folder and/or its sub-folders"
    	button btn_getFile "Get file(s)" pos:[290,35] width:108 height:21 toolTip:"Select one or multiple files in given folder"
    	button btn_Clear "Clear" pos:[290,60] width:108 height:21
    	dropdownList ddl_version "Save to Version" pos:[295,223] width:96 height:40 items:(for v in versions collect v as string)
    	checkbox chkBox_showFullPath "Show Full Path" pos:[10,215] width:95 height:15
    	label lbl_select "Select:" pos:[120,215] width:33 height:13
    	button btn_all "All" pos:[157,214] width:40 height:18
    	button btn_none "None" pos:[200,214] width:40 height:18
    	button btn_invert "Invert" pos:[243,214] width:40 height:18
    	button bnt_saveAsPrevious "Save as previous" pos:[9,235] width:276 height:30
    	HyperLink http_miauu "miauu's MaxScripts" pos:[300,270] width:90 height:15 address:"http://miauumaxscript.blogspot.com/" color:(color 7 231 251)
    	progressBar pb_xRefprogress "" pos:[10,270] width:275 height:14 value:0 color:(color 0 255 0)
    	checkbox chk_Copy "Make Copy" pos:[300,204] width:90 height:16 checked:true tooltip:"When off, overwrites the original file."
 
		--	Credits to Peter Addington - http://lonerobot.net/?p=314
		function String2Bmp string =
		(
			local clipboardClass = dotNetClass "System.Windows.Forms.Clipboard"
			local ConvertClass = dotnetclass "system.convert"
			local imageclass = dotNetclass "System.Drawing.image"
			local bytearr = convertclass.FromBase64String string
			local memstream = dotnetobject "System.IO.MemoryStream" bytearr
			local DecodedImg = ImageClass.fromstream memstream
			memstream.close()
			DecodedImg
		)
		--	credits to Denis Trofimiv - http://forums.cgsociety.org/showpost.php?p=7708817&postcount=21
		function LoadMyLogoAsTitlebarIcon =
		(
			d = (windows.getChildHWND 0 rol_miauuBatchLoadXRefScenes.title)[1]
			WM_SETICON = 0x0080
			ICON_SMALL = 0
			bm = dotnetobject "System.Drawing.Bitmap" (String2Bmp logoIcon)			
			ptr = bm.GetHicon()
			icon = (dotnetclass "System.Drawing.Icon").FromHandle (dotnetobject "IntPtr" ptr)			
			windows.SendMessage d WM_SETICON ICON_SMALL icon.handle
		)
 
        function AddColumns theLv columnsAr=
        (
            if chkBox_showFullPath.state == false then
                w=(theLv.width)-6
            else
                w=(theLv.width)+400
            for x in columnsAr do
            (
                theLv.columns.add x w
            )
        )
        function PopulateListView theLv=
        (
            rows=#()
            for x=1 to maxFiles.count do
            (
                if chkBox_showFullPath.state == false then
                    mapName = (getFilenameFile maxFiles[x])
                else
                    mapName = maxFiles[x]
 
                li = dotNetObject "System.Windows.Forms.ListViewItem" mapName
                append rows li
            )
            theLv.items.addRange rows
        )
        function InitListView theLv=
        (            
            theLv.clear()
			theLv.headerStyle = theLv.headerStyle.none
            theLv.view = (dotNetClass "system.windows.forms.view").details
            theLv.FullRowSelect = true    
            theLv.MultiSelect = true    
            theLv.checkBoxes = true                
            theLv.backcolor = (dotNetClass "System.Drawing.Color").DimGray
            theLv.forecolor = (dotNetClass "System.Drawing.Color").lightGray
        )
        function BatchListViewReIinit =
        (
            InitListView lv_Batch
            AddColumns lv_Batch #("")    
            PopulateListView lv_Batch
        )
        function TurnBatchLVchkBoxOn =
        (
            for i = 0 to lv_Batch.Items.count-1 do
                lv_Batch.Items.Item[i].checked = true
            lv_Batch.forecolor = disableForeColor
        )    
        function OpenFolders folderToOpen =
        (
            local checkFolderName = substring folderToOpen 1 (folderToOpen.count-1)
            if (symbolicPaths.isPathName checkFolderName) then
            (
                folderToOpen = symbolicPaths.getPathValue checkFolderName
            )                
            shellLaunch "explorer.exe" folderToOpen
        )        
 
        function GetFilesRecursive root pattern =
        (        
            dir_array = GetDirectories (root+"\*")
            for d in dir_array do
                join dir_array (GetDirectories (d+"*"))    
 
            my_files = #()                
            for f in dir_array do
                join my_files (getFiles (f + pattern))
 
            my_files
        )
 
 
    	on rol_miauuBatchLoadXRefScenes open do
    	( 
    		try(LoadMyLogoAsTitlebarIcon())catch()
 
    		openFileRoll.title = "Select Files"
    		openFileRoll.Multiselect = true
    		openFileRoll.Filter = "MAX (*.max)|*.max"
    		openFileRoll.FilterIndex = 1
    		openFileRoll.RestoreDirectory = true	
 
    	    InitListView lv_Batch
    	    AddColumns lv_Batch #("Files")
    	)
    	on lv_Batch mouseDown arg do
    	(
    	    --    delete selected max file from the listview
    	    if arg.button==arg.button.middle then
    	    (                
    	        if (hitNode = lv_Batch.GetItemAt arg.x arg.y) != undefined do
    	        (
    	            deleteItem maxFiles (hitNode.index+1)
    	            BatchListViewReIinit()
    	        )                
    	    )
    	    --    open folder of selected max file
    	    if arg.button==arg.button.right then
    	    (                
    	        if (hitNode = lv_Batch.GetItemAt arg.x arg.y) != undefined do
    	        (
    	            f = (hitNode.index+1)
    	            folderToOpen = (getFilenamePath maxFiles[f])
    	            OpenFolders folderToOpen
    	        )                
    	    )
    	)
    	on btn_getDir pressed do
    	(
    	    dir = getSavePath caption:"Select the directory" initialDir:"$scenes"
    	    if dir != undefined do
    	    (
    	        maxFiles = #()
    	        --    get all max files
    	        maxFiles = getFiles (dir+"\*.max")
    	        --    check for subfolders
    	        subFiles = GetFilesRecursive dir "*.max"
    	        if subFiles.count != 0 then
    	        (
    	            msg = "The selected folder have subfolders!\n"
    	            msg += "Do you want to include the files from the subfolders too?"
    	            if queryBox  msg title:"Sub-folders found" do
    	                join maxFiles subFiles
    	        )
    			makeUniqueArray maxFiles
    	        PopulateListView lv_Batch
    	        TurnBatchLVchkBoxOn()
    	    )
    	)
    	on btn_getFile pressed do
    	(
    		result = openFileRoll.showDialog()
    		result.ToString() 
    		if (result.Equals result.OK) do 
    		(
    			filePath = (openFileRoll.fileNames)
    			join maxFiles filePath
    			makeUniqueArray maxFiles
    	        BatchListViewReIinit()
    	        TurnBatchLVchkBoxOn()
    		)
    	)
    	on btn_Clear pressed do
    	(
    	    maxFiles = #()
    	    BatchListViewReIinit()
    	)
    	on chkBox_showFullPath changed state do
    	(
    		cbState = for i = 0 to lv_Batch.Items.count-1 collect lv_Batch.Items.Item[i].checked
    	    BatchListViewReIinit()
    	    for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = cbState[i + 1]
    	)
    	on btn_all pressed do
    	(
    		for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = true
    	)
    	on btn_none pressed do
    	(
    		for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = false
    	)
    	on btn_invert pressed do
    	(
    		for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = not lv_Batch.Items.Item[i].checked
    	)
    	on bnt_saveAsPrevious pressed do
    	(	
    		local xRefCnt = (lv_Batch.Items.count - 1)
    		setWaitCursor()
    		suspendEditing()
    		resetMaxFile #noPrompt
    		for i = 0 to xRefCnt where (lv_Batch.Items.Item[i].checked == true) do with redraw off
    		(
 
    			if (loadMaxFile maxFiles[i+1] useFileUnits:true quiet:true) do
    			(
    				filePath = getFilenamePath maxFiles[i+1]
					fileName = (getFilenameFile maxFiles[i+1])
					local ver = ddl_version.selected
					if chk_Copy.checked then (
						fileName = (getFilenameFile maxFiles[i+1]) += "_" + ver
					)
    				newName = filePath + "\\" + fileName + ".max"
    				saveMaxFile newName saveAsVersion:(ver as integer) useNewFile:true quiet:true 
    			)
    			resetMaxFile #noPrompt
    			pb_xRefprogress.value = 100.0 * i / xRefCnt
    			if curMaxVersion > 12 do
    				windows.processPostedMessages()
    		)
    		completeRedraw()
    		resumeEditing()
    		setArrowCursor()
    	)
    )
    createdialog rol_miauuBatchLoadXRefScenes width:405 
)

_______________________

Shawn Olson

Developer of Wall Worm

miauu's picture

.

I don't have time to modify the UI.
Load the files that you want and press the Save As Previous button. All files will be saved in folder where the original files are with prefix _2013.

--******************************************************************************************************
-- Created: 		14-06-2014
-- Last Updated:	14-06-2014
-- Version:			1.00
--
-- Author :  Kostadin Kotev / [email protected] / http://miauumaxscript.blogspot.com/
-- Version:  3ds max 2009 (10) (should work in older versions too!)
--
-- Discription: Batch save selected MAX files as copies for Max 2013
-- Usage: RUN IT
--
-- Wishlist:
--
--******************************************************************************************************
-- MODIFY THIS AT YOUR OWN RISK
 
 
macroscript miauuBatchSaveAsPrevious
category:"miauu"
tooltip:"Batch SaveAsPrevious"
buttonText:"Batch SaveAsPrevious"
(
	global rol_miauuBatchLoadXRefScenes
    try(destroyDialog rol_miauuBatchLoadXRefScenes)catch()
    rollout rol_miauuBatchLoadXRefScenes "miauu's Batch Save As Previous"
    (
		local ConvertClass = dotnetclass "system.convert"
		local ImageClass = dotnetclass "system.drawing.image"
		local logoIcon = "iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAAIGNIUk0AAHolAACAgwAA+f8AAIDpAAB1MAAA6mAAADqYAAAXb5JfxUYAAAAJcEhZcwAACxIAAAsSAdLdfvwAAALcSURBVDhPbZJLSFRhGIa/1C6IMmmQFNownplzv8y5zIzOqGPimE5hFxfeZxQzu0AXDbtsXHWBwNpWaIt2lQWBFSS0qCholbsW7QwiiKBNRDlv//xTWtjiO9+B77zP+37/+QkA7QxXULu7mZLmVmq1K2lvtIzSjm/A0Wt/NjdEl0d62w+eGe2gyUyCTvXHaawnSRNDTVy7AuhwfdTt+Kg1XBFIWNVLmqZj/ryGc90yVN1CZ3vjx9PDLWpS3UJH+pI0nv0L0MaEaa+cYnr1M0OVIKkWNN0AXsQxe0KCIkvwCxI818bgvsTL8eFWmhpLrgLq9Korri4si4oJVTNg6Covy5RhGQrrOusqQqIEQVSQqI/mjvY1T68AhJCc0wwLuqbwmuwKAfdcDkl4MvAmjr1NEgNpMA0NghCEFXZzKwBRFHP54WhawudbNpbuePg+5+DVBR3vZlxgIYrFqwY+zNjoSckcbNvhVYAkhnIWI4/36czZRiNzzX/07kYYl7MSd812qsC8h96UxFOy81gLOLSHxX3ooi4scsBb5jrVL3PAGJt9u2uju7Wwpuc6awEne1mChRganALgy/0oprMiB5wdsXiCgV1yAeD8B3B8P0vwOIJUfWGFL7ct3DymcsDxLgV45GEo/SfBXyvIssQPcWKQ/XsGaP8NeP+gHtdGFA6YHLOBJxFkdv1nhUBtMOc4Nhflh/lusuKdifPp8j1fYWaksJtpOLFVgFNbOltd44fCLpFpsdiHJbZvhAPa6tj763pkUiJ000JIjzATGW12xfMVQIuygbZv2bhJ2uFbDAYFXDrh4dP1MAMoSCU14GkMnc0Wu+Immqyqz/2xdXXDsYKWPxqkUvJvKyM3UEJ6TUlc8ld+9QsqNNNmrg4ExUHEqPlxwF1/6nAD0WgjUU+0+F9ATVU5WYFSigY3kreDKOIvuaiGqpdNNYTdbtncSJzoYIIoGy+mTLyIAYqYFvQLPey9qVeXvysAAAAASUVORK5CYII="
		local curMaxVersion = ((maxVersion())[1] / 1000)
		local openFileRoll = dotNetObject "System.Windows.Forms.OpenFileDialog"	
        local disableForeColor = (dotNetClass "System.Drawing.Color").white
        local maxFiles = #()         
 
        dotNetControl lv_Batch "system.windows.forms.listView" height:200 width:273 pos:[10,10]
 
		button btn_getDir "Get Directory" width:108 pos:[290,10] tooltip:"Select all .max files in the given folder and/or its sub-folders"
        button btn_getFile "Get file(s)" width:108 pos:[290,35] tooltip:"Select one or multiple files in given folder"
        button btn_Clear "Clear" width:108 pos:[290,60]  
 
		checkbox chkBox_showFullPath "Show Full Path" pos:[10,215]
		label lbl_select "Select:" pos:[120,215]
		button btn_all "All" pos:[157,214] width:40 height:18
		button btn_none "None" pos:[200,214] width:40 height:18
        button btn_invert "Invert"	 pos:[243,214]	width:40 height:18
		button bnt_saveAsPrevious "Save as previous" width:275 height:30 pos:[10,235]
		hyperLink http_miauu "miauu's MaxScripts" address:"http://miauumaxscript.blogspot.com/" pos:[300,270] color:(color 7 231 251)
		progressBar pb_xRefprogress value:0 color:green width:275 pos:[10,270]
 
		--	Credist to Peter Addington - http://lonerobot.net/?p=314
		function String2Bmp string =
		(
			local clipboardClass = dotNetClass "System.Windows.Forms.Clipboard"
			local ConvertClass = dotnetclass "system.convert"
			local imageclass = dotNetclass "System.Drawing.image"
			local bytearr = convertclass.FromBase64String string
			local memstream = dotnetobject "System.IO.MemoryStream" bytearr
			local DecodedImg = ImageClass.fromstream memstream
			memstream.close()
			DecodedImg
		)
		--	credits to Denis Trofimiv - http://forums.cgsociety.org/showpost.php?p=7708817&postcount=21
		function LoadMyLogoAsTitlebarIcon =
		(
			d = (windows.getChildHWND 0 rol_miauuBatchLoadXRefScenes.title)[1]
			WM_SETICON = 0x0080
			ICON_SMALL = 0
			bm = dotnetobject "System.Drawing.Bitmap" (String2Bmp logoIcon)			
			ptr = bm.GetHicon()
			icon = (dotnetclass "System.Drawing.Icon").FromHandle (dotnetobject "IntPtr" ptr)			
			windows.SendMessage d WM_SETICON ICON_SMALL icon.handle
		)
 
        function AddColumns theLv columnsAr=
        (
            if chkBox_showFullPath.state == false then
                w=(theLv.width)-6
            else
                w=(theLv.width)+400
            for x in columnsAr do
            (
                theLv.columns.add x w
            )
        )
        function PopulateListView theLv=
        (
            rows=#()
            for x=1 to maxFiles.count do
            (
                if chkBox_showFullPath.state == false then
                    mapName = (getFilenameFile maxFiles[x])
                else
                    mapName = maxFiles[x]
 
                li = dotNetObject "System.Windows.Forms.ListViewItem" mapName
                append rows li
            )
            theLv.items.addRange rows
        )
        function InitListView theLv=
        (            
            theLv.clear()
			theLv.headerStyle = theLv.headerStyle.none
            theLv.view = (dotNetClass "system.windows.forms.view").details
            theLv.FullRowSelect = true    
            theLv.MultiSelect = true    
            theLv.checkBoxes = true                
            theLv.backcolor = (dotNetClass "System.Drawing.Color").DimGray
            theLv.forecolor = (dotNetClass "System.Drawing.Color").lightGray
        )
        function BatchListViewReIinit =
        (
            InitListView lv_Batch
            AddColumns lv_Batch #("")    
            PopulateListView lv_Batch
        )
        function TurnBatchLVchkBoxOn =
        (
            for i = 0 to lv_Batch.Items.count-1 do
                lv_Batch.Items.Item[i].checked = true
            lv_Batch.forecolor = disableForeColor
        )    
        function OpenFolders folderToOpen =
        (
            local checkFolderName = substring folderToOpen 1 (folderToOpen.count-1)
            if (symbolicPaths.isPathName checkFolderName) then
            (
                folderToOpen = symbolicPaths.getPathValue checkFolderName
            )                
            shellLaunch "explorer.exe" folderToOpen
        )        
 
        function GetFilesRecursive root pattern =
        (        
            dir_array = GetDirectories (root+"\*")
            for d in dir_array do
                join dir_array (GetDirectories (d+"*"))    
 
            my_files = #()                
            for f in dir_array do
                join my_files (getFiles (f + pattern))
 
            my_files
        )
 
        on btn_getDir pressed do
        (
            dir = getSavePath caption:"Select the directory" initialDir:"$scenes"
            if dir != undefined do
            (
                maxFiles = #()
                --    get all max files
                maxFiles = getFiles (dir+"\*.max")
                --    check for subfolders
                subFiles = GetFilesRecursive dir "*.max"
                if subFiles.count != 0 then
                (
                    msg = "The selected folder have subfolders!\n"
                    msg += "Do you want to include the files from the subfolders too?"
                    if queryBox  msg title:"Sub-folders found" do
                        join maxFiles subFiles
                )
				makeUniqueArray maxFiles
                PopulateListView lv_Batch
                TurnBatchLVchkBoxOn()
            )
        )
 
        on btn_getFile pressed do
        (
			result = openFileRoll.showDialog()
			result.ToString() 
			if (result.Equals result.OK) do 
			(
				filePath = (openFileRoll.fileNames)
				join maxFiles filePath
				makeUniqueArray maxFiles
                BatchListViewReIinit()
                TurnBatchLVchkBoxOn()
			)
        )
 
		on btn_all pressed do
		(
			for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = true
		)
 
		on btn_none pressed do
		(
			for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = false
		)
 
		on btn_invert pressed do
		(
			for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = not lv_Batch.Items.Item[i].checked
		)
 
        on btn_Clear pressed do
        (
            maxFiles = #()
            BatchListViewReIinit()
        )
 
        on lv_Batch MouseDown arg do
        (
            --    delete selected max file from the listview
            if arg.button==arg.button.middle then
            (                
                if (hitNode = lv_Batch.GetItemAt arg.x arg.y) != undefined do
                (
                    deleteItem maxFiles (hitNode.index+1)
                    BatchListViewReIinit()
                )                
            )
            --    open folder of selected max file
            if arg.button==arg.button.right then
            (                
                if (hitNode = lv_Batch.GetItemAt arg.x arg.y) != undefined do
                (
                    f = (hitNode.index+1)
                    folderToOpen = (getFilenamePath maxFiles[f])
                    OpenFolders folderToOpen
                )                
            )
        )
 
        on chkBox_showFullPath changed state do
        (
			cbState = for i = 0 to lv_Batch.Items.count-1 collect lv_Batch.Items.Item[i].checked
            BatchListViewReIinit()
            for i = 0 to lv_Batch.Items.count-1 do lv_Batch.Items.Item[i].checked = cbState[i + 1]
        )    
 
		on bnt_saveAsPrevious pressed do
		(	
			local xRefCnt = (lv_Batch.Items.count - 1)
			setWaitCursor()
			suspendEditing()
			resetMaxFile #noPrompt
			for i = 0 to xRefCnt where (lv_Batch.Items.Item[i].checked == true) do with redraw off
			(
 
				if (loadMaxFile maxFiles[i+1] useFileUnits:true quiet:true) do
				(
					filePath = getFilenamePath maxFiles[i+1]
					fileName = (getFilenameFile maxFiles[i+1]) + "_2013"
					newName = filePath + "\\" + fileName + ".max"
					saveMaxFile newName saveAsVersion:2013 useNewFile:true quiet:true 
				)
				resetMaxFile #noPrompt
				pb_xRefprogress.value = 100.0 * i / xRefCnt
				if curMaxVersion > 12 do
					windows.processPostedMessages()
			)
			completeRedraw()
			resumeEditing()
			setArrowCursor()
		)
 
        on rol_miauuBatchLoadXRefScenes open do
        ( 
			try(LoadMyLogoAsTitlebarIcon())catch()
 
			openFileRoll.title = "Select Files"
			openFileRoll.Multiselect = true
			openFileRoll.Filter = "MAX (*.max)|*.max"
			openFileRoll.FilterIndex = 1
			openFileRoll.RestoreDirectory = true	
 
            InitListView lv_Batch
            AddColumns lv_Batch #("Files")
        )
    )
    createdialog rol_miauuBatchLoadXRefScenes width:405 
)

Comment viewing options

Select your preferred way to display the comments and click "Save settings" to activate your changes.