How To Make It Better?

new.gif MAXScript Frequently Asked Questions


Avoid using persistent global variables

new.gif A good idea gone bad.

Initially added to support scripted controllers and xrefs.




Using scripted CAs for persistent data storage

new.gif Scripted Custom Attributes can be used instead of persistent global variables to store data with the scene file, avoiding the problems mentioned above.

A scripted CA can be placed on the scene root:

sceneDataCADef = attributes sceneDataCADef version:1 attribID:#(0x61e9ff5f, 0x63784819)


parameters main rollout:params

( note type:#string ui:et_note default:"" )

rollout params "Scene Data Parameters"

( edittext et_note "Note: " )



thescene = (refs.dependents rootnode)[1]

rootNodeDataCA = undefined

if (custattributes.add rootnode sceneDataCADef) do

 rootNodeDataCA = rootnode.custAttributes[rootnode.custAttributes.count]

sceneDataCA = undefined

if (custattributes.add thescene sceneDataCADef) do

 sceneDataCA = thescene.custAttributes[thescene.custAttributes.count]



rootNodeDataCA.note = "rootnode"

sceneDataCA.note = "thescene"


If the file is saved and reloaded, you can access the CAs:

rootNodeDataCA = undefined

if (rootnode.custAttributes.count != 0) do

 rootNodeDataCA = rootnode.custAttributes[rootnode.custAttributes.count]

sceneDataCA = undefined

if (thescene.custAttributes.count != 0) do

 sceneDataCA = thescene.custAttributes[thescene.custAttributes.count]


If the file is brought in as an XRef scene, you can still access the CAs:

xr = xrefs.getXRefFile 1

xr_root = xr.tree

xr_rootNodeDataCA = undefined

if (xr_root.custAttributes.count != 0) do

 xr_rootNodeDataCA = xr_root.custAttributes[xr_root.custAttributes.count]


Building UI on Script/Expression Controller

new.gif By placing a scripted Custom Attributes definition on a script or expression controller, you can provide a custom UI for the controller.


floatDataCADef = attributes floatDataCADef version:1


parameters main rollout:params

( prop1 type:#float ui:s_prop1 )

rollout params "Parameters"

( spinner s_prop1 "Prop1: " )

fn getRollout = params



sc = float_Script()

custattributes.add sc floatDataCADef

floatCA = sc.custattributes[1]

sc.addTarget "prop1" floatCA[#prop1]


displayControlDialog sc ""


mscas = for ca in sc.custattributes where isMSCustAttrib ca collect ca

rollouts = for ca in mscas where isproperty ca #getrollout collect ca.getrollout()

if rollouts.count == 1 then

 createdialog rollouts[1]

else if rollouts.count > 1 do


 width = rollouts[1].width

 for ro in rollouts do

  width = amax width ro.width

 rof = newrolloutfloater "" (width+13) 0 0 0

 for ro in rollouts do addrollout ro rof

 height = 6

 for ro in rollouts do

  height += ro.height + 24

 rof.size = [rof.size.x,height]



See also

How To Make It Faster?

Frequently Asked Questions