Modding, Mission Design, and Coding > The Modding Workshop

Useful scripts for 3ds Max

<< < (5/6) > >>

zookeeper:

--- Quote from: Scooby_Doo on March 14, 2011, 02:35:04 am ---How about this:
--- End quote ---
Right. Kinda obvious now that I think of it. :banghead:

zookeeper:
Added two more little scripts which might be of use, and also (finally) put them all into [ code ] blocks instead of attachments so they don't get lost.

Scooby_Doo:
Here's a few useful ones:


Used to create properties for subobjects (if it's a turret with uvec, fvec it'll copy the values to the destroyed version)

--- Code: ---macroScript GiveThemProperties category:"Freespace"
(
changeCount = 0

uVecValue = ""
fVecValue = ""

isThisATurret = false
turretDestroyedLocation = -1

-- Go through all the selected objects
for i = 1 to selection.count do
(
test = ""
dummyCount = 0

-- Let's see what we're actually got
if (findString selection[i].name "helper" != undefined) then
continue -- helper object
else if (findString selection[i].name "thruster" != undefined) then
continue -- thruster dummy points
else if (findString selection[i].name "bank" != undefined) then
continue -- missile, gun and glow banks
else if (findString selection[i].name "eye" != undefined) then
continue -- eyepoint
else if (findString selection[i].name "destroyed" != undefined) then
(
-- Possibly a destroyed turret (could be another subsystem)
turretDestroyedLocation = i
continue ;
)
else if (findString selection[i].name "-" != undefined) then
continue -- turret arms, destroyed subsystems
else if (findString selection[i].name "firepoint" != undefined) then
continue -- firepoints
else if (findString selection[i].name "turret" != undefined) then
(
isThisATurret = true
)

-- Retrieve the existing properties, we need to save the uvec,fvec
objectProperties = getUserPropBuffer selection[i]
listofProp = filterString objectProperties "\n\r"

foundUVec = false

-- Save the uvec if theres any
for j = 1 to listofProp.count do
(
if (findstring listofProp[j] "$uvec" != undefined) then
(
foundUVec = true
uVecValue = listofProp[j]
break
)
)

-- Save the fvec if there's any (there should be)
for j = 1 to listofProp.count do
(
if (findstring listofProp[j] "$fvec" != undefined) then
(
fVecValue = listofProp[j]
break
)
)

-- Paste the new data back to the object's property
test = "$special=subsystem\r\n$fov=180\r\n$name=" + selection[i].name

if (foundUVec) then
(
test = test + "\r\n" + uVecValue + "\r\n" + fVecValue
)
changeCount = changeCount + 1

setUserPropBuffer selection[i] test
)

--If this was a turret and had a destroyed version we need to copy the uvec and fvec if they exist
if (isThisATurret) then
(
if (turretDestroyedLocation != -1) then
(
test = uVecValue + "\r\n" + fVecValue
setUserPropBuffer selection[turretDestroyedLocation] test
)
)

if (changeCount == 0) then
(
MessageBox "Nothing useable was selected"
)
)

--- End code ---


Remove ALL properties from anything

--- Code: ---macroScript RemoveProperties category:"Freespace"
(

for i = 1 to selection.count do
(
setUserPropBuffer selection[i] ""
)
)

--- End code ---


Numbering turrets (this also renames the turret0X-arm).  Just group select the turet, arm (if any), firepoints, firepoint, helper and destroyed (if exists) click the Renumber Turret and repeat for each additional turret, it'll convert their names to a numbered "turret0X" correctly.  It does not create uvecs or fvecs, use the other scripts for that. 

--- Code: ---macroScript TurretNumber category:"Freespace"
(
turretNumber = 1

rollout rename_rollout "Turret Renumbering"
(
button ResetCount "Reset Turret Count"
button RenameBase "Renumber Turret"

on ResetCount pressed do
(
turretNumber = 1
)

on RenameBase pressed do
(
print "hello"

changeCount = 0

if (turretNumber < 10) then
newName = "turret0" + turretNumber as String
else
newName = "turret" + turretNumber as String

for loop = 1 to selection.Count do
(
oldname = selection[loop].name
if (findString oldName "turret" != undefined) then
(
if (findString oldName "-arm" != undefined) then
(
selection[loop].Name = newName + "-arm"
changeCount = changeCount + 1
)
else if (findString oldName "-destroyed" != undefined) then
(
selection[loop].Name = newName + "-destroyed"
changeCount = ChangeCount + 1
)
else
(
selection[loop].Name = newName
changeCount = changeCount + 1
)
)
)

if (changeCount == 0) then
(
MessageBox "Nothing useable was selected"
)
else
(
turretNumber = turretNumber + 1
)
)

)--end rollout

createDialog rename_rollout

)

--- End code ---


Used to renumber engine thrusters objects (thruster01, thruster02, thruster03.....)  Note this does not create the properties (use the first script above)

--- Code: ---macroScript EngineNumber category:"Freespace"
(
engineNumber = 1

rollout rename_rollout "Engine Renumbering"
(
button ResetCount "Reset Engine Count"
button RenameBase "Renumber Engine"

on ResetCount pressed do
(
engineNumber = 1
)

on RenameBase pressed do
(
changeCount = 0

if (engineNumber < 10) then
newName = "engine0" + engineNumber as String
else
newName = "engine" + engineNumber as String

for loop = 1 to selection.Count do
(
oldname = selection[loop].name
if (findString oldName "engine" != undefined) then
(
if (findString oldName "-destroyed" == undefined) then
(
selection[loop].Name = newName
changeCount = changeCount + 1
)
else
(
selection[loop].Name = newName + "-destroyed"
changeCount = changeCount + 1
)
)
)

if (changeCount == 0) then
(
MessageBox "Nothing useable was selected"
)
else
(
engineNumber = engineNumber + 1
)
)

)--end rollout

createDialog rename_rollout

)

--- End code ---


Same as thrusters but for intakes (if you do have them)

--- Code: ---macroScript IntakeNumber category:"Freespace"
(
intakeNumber = 1

rollout rename_rollout "Intake Renumbering"
(
button ResetCount "Reset Intake Count"
button RenameBase "Renumber Intake"

on ResetCount pressed do
(
intakeNumber = 1
)

on RenameBase pressed do
(
changeCount = 0

if (intakeNumber < 10) then
newName = "intake0" + intakeNumber as String
else
newName = "intake" + intakeNumber as String

for loop = 1 to selection.Count do
(
oldname = selection[loop].name
if (findString oldName "intake" != undefined) then
(
if (findString oldName "-destroyed" == undefined) then
(
selection[loop].Name = newName
changeCount = changeCount + 1
)
else
(
selection[loop].Name = newName + "-destroyed"
changeCount = changeCount + 1
)
)
)

if (changeCount == 0) then
(
MessageBox "Nothing useable was selected"
)
else
(
intakeNumber = intakeNumber + 1
)
)

)--end rollout

createDialog rename_rollout

)

--- End code ---

Scooby_Doo:
4 years later!!  :eek2:

Oh you've added a box, modified it and then copied it many times (be it copy or instances doesn't matter).  Then you realize you probably should have named them better, whoops!  Well this script asks for a name then applies it plus padded number to it... AKA Box becomes Grip01, Grip02, Grip03.... Grip10, Grip11...etc
Rename script:

--- Code: ---macroScript RenameObjects category:"Fast Utils"
(
rollout renameObjs_rollout "Renaming Objects" width:162 height:72
(
label lbl_Name "New Name"
edittext edit_NewName ""
button btnStart "Start"

on btnStart pressed  do
(
if (edit_NewName.text == "") then
(
MessageBox "You need to give it a name first"
return 0
)

if (selection.Count == 0) then
(
MessageBox "You need to select at least one entry first"
return 0
)

for loop = 1 to selection.Count do
(
-- This keeps the number formatting nice and neat
prefex = ""

upper = ceil ((selection.Count as float)/ (10 as float)) * 10
lower = ceil ((loop as float)/ (10 as float)) * 10

while (lower < upper) do
(
prefex = prefex + "0"
lower = lower * 10
)

selection[loop].Name = edit_NewName.Text + prefex + loop as String
)

destroydialog renameObjs_rollout
)
)

createDialog renameObjs_rollout

)

--- End code ---

Next script, let's say you have all those boxes now named properly, but let's say you want to change something on them, thats when you realize you made a copy and not a reference/instance, oh  :mad:. Well this fixes that (with some caveats).  Simply select the parent object, then select all of the children and it will replace each of the children with a copy/instance/reference of the parent.  The selected object is then deleted. It will also orientate and scale them correctly, HOWEVER, if you have rotated and/or scaled the object to be replaced then did a xreset, the scale/angle info was lost and it'll simply put a new object in the (0,0,0) orientation and 100% scale.

--- Code: ---macroScript ReplaceWithClones category:"Fast Utils"
(
rollout ReplaceObjs_rollout "Replace objects with clones" width:162 height:227
(
 
button btnSelectParent "Select as Parent" pos:[34,7] width:93 height:21
 
button btnProcessInstances "Replace Selected" pos:[49,191] width:56 height:21
edittext edtParentName "" pos:[4,36] width:149 height:25 enabled:false
radiobuttons rdo1 "Replace By..." pos:[10,69] width:73 height:62 labels:#("Copy", "Instance", "Reference") default:2
checkbox chk1 "Delete original" pos:[10,150] width:96 height:20 checked:true


on btnSelectParent pressed do
(
if (selection.count != 1) then
(
MessageBox "Missing object for parent"
return 0
)

parent = selection[1]
edtParentName.text = selection[1].Name
)
on btnProcessInstances pressed do
(
if (edtParentName.Text == "") then
(
MessageBox "First need to select a parent object to copy"
return 0
)

for loop = 1 to selection.Count do
(
case rdo1.state of
(
1:
child = copy parent
2:
child = instance parent
3:
child = reference parent
)

child.pos = selection[loop].pos
child.rotation = selection[loop].rotation
child.scale = selection[loop].scale

)

if (chk1.Checked) then
(
for loop = 1 to selection.Count do
(
delete selection[1]
)
)
)
)
createDialog ReplaceObjs_rollout

)

--- End code ---

And last....
This isn't really useful for POF as exporting to DAE and PCS can handle it well, but it seems to clear up problems exporting to Unreal 4.  What this script does is save your selected objects first, make copies of those objects, collapse just those, stuff those into a layer "ExportLayer", select all those and let's you export however necessary.  Finally there is a cleanup Finish, which deletes those objects, removes the layer and then reselects the objects you had originally selected, as if nothing had happened.  It's not foolproof and might be buggy, thats why I had the collapsed meshes put into a unique layer, so if things go bad you can simply delete everything from that layer.  Oh and ya don't have a "ExportLayer" in your project.  It can take sometime to actually process, depending on how complicated your model is.  It takes about a half minute to export a 300K model with some 130+ objects.  Couple other notes: if you see a bug in your model after prepping, don't fix it there, it'll just get deleted, nuke that export (hit "finish") fix the problem and try again.  Two: Groups seem to cause some problems, they will appear as big boxes that are empty, just delete them for now, the actual meshes will still be there (they're no longer part of the group upon resetting).

--- Code: ---macroScript PrepForExport category:"Fast Utils"
(
mySavedArray = #()
rollout ExportPrep_rollout "Prep for Export" width:162 height:68
(
 
button btnSelect "Select object(s)" pos:[34,7] width:93 height:21
 
button btnFinish "Finished exporting" pos:[34,40] width:93 height:21

on btnSelect pressed do
(
if (selection.Count == 0) then
(
MessageBox "You need to select at least one entry first"
return 0
)


myNewArray = #()

layer = LayerManager.newLayer ()
layer.setName "ExportLayer"

for loop = 1 to selection.count do
(
entry = copy selection[loop]
print entry.Name

collapseStack entry
ResetXForm entry
collapseStack entry
layer.addnode entry

append myNewArray entry

windows.processpostedmessages ()

)

for obj in selection do
(
append mySavedArray obj
windows.processpostedmessages ()
)
max select none
select myNewArray

result = IsolateSelection.EnterIsolateSelectionMode()

MessageBox "You may now export your model"
)
on btnFinish pressed do
(
max select none

layer = LayerManager.GetLayerFromName "ExportLayer"

if (layer == undefined) then
(
return 0
)

layer.nodes &temp

select temp
delete selection

LayerManager.DeleteLayerByName "ExportLayer"

result = IsolateSelection.ExitIsolateSelectionMode ()
select mySavedArray
)
)
createDialog ExportPrep_rollout

)

--- End code ---

Whew!

Scooby_Doo:
Two years latter I've got some more for you...

If you have more than one object you want to replace with something else this script makes it easy.  Let's say you have a bunch of the same object but decide you want to replace or modify it. You realize you forget to make references or instances of it. Opps...

First select the parent object, hit "select as parent" then select all the objects you want replaced, then hit "Replace Selected".  You can choose to copy, instance or replace and you can choose to ignore the scale and/or rotation.  And finally you don't have to actually delete the original one.  Couple of caveats: The new objects are stuck in whichever layer is currently active, it may not be the one that the original object is located in (that should be fixable), and if the object(s) to be replaced have been xform resetted, you probably won't get the correct results.

--- Code: ---macroScript ReplaceWithClones category:"Fast Utils"
(
rollout ReplaceObjs_rollout "Replace objects with clones" width:162 height:227
(
 
button btnSelectParent "Select as Parent" pos:[34,7] width:93 height:21
 
 
button btnProcessInstances "Replace Selected" pos:[3,191] width:145 height:21
edittext edtParentName "" pos:[4,36] width:149 height:25 enabled:false
radiobuttons rdoReplaceBy "Replace By..." pos:[10,69] width:73 height:62 labels:#("Copy", "Instance", "Reference") default:2
checkbox chkDeleteOrg "Delete original" pos:[10,166] width:96 height:20 checked:true
checkbox chkIgnScale "Ignore scale" pos:[10,150] width:103 height:17
checkbox chkIgnRot "Ignore rotation" pos:[9,132] width:103 height:15

global parent

on btnSelectParent pressed do
(
if (selection.count != 1) then
(
MessageBox "Misisng object for parent"
return 0
)

if (selection.Count == 0) then
(
MessageBox "You need to select at least one entry first"
return 0
)

parent = selection[1]
edtParentName.text = selection[1].Name
)
on btnProcessInstances pressed do
(
if (edtParentName.Text == "") then
(
MessageBox "First need to select a parent object to copy"
return 0
)

props = getUserpropBuffer parent

for loop = 1 to selection.Count do
(
case rdoReplaceBy.state of
(
1:
child = copy parent
2:
child = instance parent
3:
child = reference parent
)

if (chkIgnScale.checked == false) then
(
child.scale = selection[loop].scale
)


if (chkIgnRot.checked == false) then
(
child.rotation = selection[loop].rotation
)


child.pos = selection[loop].pos
setuserPropBuffer child props

)

if (chkDeleteOrg.Checked) then
(
for loop = 1 to selection.Count do
(
delete selection[1]
)
)
)
)
createDialog ReplaceObjs_rollout

)

--- End code ---

Navigation

[0] Message Index

[#] Next page

[*] Previous page

Go to full version