Max Script
Max Script
www.discreet.com 4
MAXSCRIPT REFERENCE
January 2001
Copyright © 2001 Autodesk, Inc.
All Rights Reserved
This publication, or parts thereof, may not be reproduced in any form, by any method, for any purpose.
AUTODESK, INC. MAKES NO WARRANTY, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY IMPLIED
WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE, REGARDING THESE MATERIALS AND MAKES
SUCH MATERIALS AVAILABLE SOLELY ON AN "AS-IS" BASIS.
IN NO EVENT SHALL AUTODESK, INC. BE LIABLE TO ANYONE FOR SPECIAL, COLLATERAL, INCIDENTAL, OR CONSEQUENTIAL
DAMAGES IN CONNECTION WITH OR ARISING OUT OF PURCHASE OR USE OF THESE MATERIALS. THE SOLE AND EXCLUSIVE
LIABILITY TO AUTODESK, INC., REGARDLESS OF THE FORM OF ACTION, SHALL NOT EXCEED THE PURCHASE PRICE OF THE
MATERIALS DESCRIBED HEREIN.
Autodesk, Inc. reserves the right to revise and improve its products as it sees fit. This publication describes the state of this product at
the time of its publication, and may not reflect the product at all times in the future.
Autodesk Trademarks
The following are registered trademarks of Autodesk, Inc., in the USA and/or other countries: 3D Plan, 3D Props, 3D Studio, 3D Studio
MAX, 3D Studio VIZ, 3DSurfer, ActiveShapes, ActiveShapes (logo), Actrix, ADE, ADI, Advanced Modeling Extension, AEC Authority
(logo), AEC-X, AME, Animator Pro, Animator Studio, ATC, AUGI, AutoCAD, AutoCAD Data Extension, AutoCAD Development System,
AutoCAD LT, AutoCAD Map, Autodesk, Autodesk Animator, Autodesk (logo), Autodesk MapGuide, Autodesk University, Autodesk View,
Autodesk WalkThrough, Autodesk World, AutoLISP, AutoShade, AutoSketch, AutoSurf, AutoVision, Biped, bringing information down
to earth, CAD Overlay, Character Studio, Design Companion, Drafix, Education by Design, Generic, Generic 3D Drafting, Generic
CADD, Generic Software, Geodyssey, Heidi, HOOPS, Hyperwire, Inside Track, Kinetix, MaterialSpec, Mechanical Desktop, Multimedia
Explorer, NAAUG, ObjectARX, Office Series, Opus, PeopleTracker, Physique, Planix, Powered with Autodesk Technology, Powered with
Autodesk Technology (logo), RadioRay, Rastation, Softdesk, Softdesk (logo), Solution 3000, Tech Talk, Texture Universe, The AEC
Authority, The Auto Architect, TinkerTech, VISION*, WHIP!, WHIP! (logo), Woodbourne, WorkCenter, and World-Creating Toolkit.
The following are trademarks of Autodesk, Inc., in the USA and/or other countries: 3D on the PC, 3ds max, ACAD, Advanced User
Interface, AEC Office, AME Link, Animation Partner, Animation Player, Animation Pro Player, A Studio in Every Computer, ATLAST, Auto-
Architect, AutoCAD Architectural Desktop, AutoCAD Architectural Desktop Learning Assistance, AutoCAD Learning Assistance, AutoCAD
LT Learning Assistance, AutoCAD Simulator, AutoCAD SQL Extension, AutoCAD SQL Interface, Autodesk Animator Clips, Autodesk
Animator Theatre, Autodesk Device Interface, Autodesk Inventor, Autodesk PhotoEDIT, Autodesk Point A (logo), Autodesk Software
Developer's Kit, Autodesk View DwgX, AutoFlix, AutoPAD, AutoSnap, AutoTrack, Built with ObjectARX (logo), ClearScale, Colour
Warper, Combustion, Concept Studio, Content Explorer, cornerStone Toolkit, Dancing Baby (image), Design 2000 (logo),
DesignCenter, Design Doctor, Designer's Toolkit, DesignProf, DesignServer, Design Your World, Design Your World (logo), Discreet,
DWG Linking, DWG Unplugged, DXF, Extending the Design Team, FLI, FLIC, GDX Driver, Generic 3D, Heads-up Design, Home Series,
i-drop, Jobnet, Kinetix (logo), Lightscape, ObjectDBX, onscreen onair online, Ooga-Chaka, Photo Landscape, Photoscape, Plugs and
Sockets, PolarSnap, Pro Landscape, QuickCAD, Real-Time Roto, Render Queue, SchoolBox, Simply Smarter Diagramming, SketchTools,
Sparks, Suddenly Everything Clicks, Supportdesk, The Dancing Baby, Transform Ideas Into Reality, Visual LISP, Visual Syllabus, VIZable,
Volo, Where Design Connects, and Whereware.
Third-Party Trademarks
All other brand names, product names, or trademarks belong to their respective holders.
Use, duplication, or disclosure by the U.S. Government is subject to restrictions as set forth in FAR 12.212 (Commercial Computer
Software-Restricted Rights) and DFAR 227.7202 (Rights in Technical Data and Computer Software), as applicable.
Contents
Introduction........................................................................................................xxxi
3ds max 4 MAXScript Online Reference ................................................................................. xxxi
MAXScript Overview .............................................................................................................. xxxii
Using the MAXScript Documentation .................................................................................. xxxiii
The MAXScript Utility Panel ...................................................................................................... xxxiv
The MAXScript Listener Window ......................................................................................... xxxvi
Using the MAXScript Listener .............................................................................................. xxxvii
Listener Commands ............................................................................................................ xxxviii
Using the ‘?’ Symbol................................................................................................................... xli
Turning On the Listener Log...................................................................................................... xli
Controlling the Listener Contents and the Insertion Point ..................................................... xlii
The MAXScript Editor Windows .............................................................................................. xliv
MAXScript Editor Commands.................................................................................................. xlvi
Running Scripts ........................................................................................................................ xlix
Accessing Scripted Utilities............................................................................................................ l
The Macro Recorder....................................................................................................................... l
General MAXScript Topics...............................................................................................................lii
Error Messages ............................................................................................................................ liii
Aborting Execution with the ESC Key ........................................................................................ lv
MAXScript Desktop State ........................................................................................................... lvi
Startup Scripts............................................................................................................................. lvi
Running Scripts from the Command Line................................................................................ lvii
Source Code Layout and Continuation Lines ........................................................................... lvii
Including Scripts Within Scripts ................................................................................................ lix
Encrypting Script Files ................................................................................................................. lx
Syntax Definitions in This Document ..............................................................................................lx
Objects and Classes in Object-Oriented Programming ................................................................lxii
Inheritance and Polymorphism ............................................................................................... lxiii
Properties, Methods, Operators, and Literals ........................................................................... lxiv
iv Contents
Mesher ........................................................................................................................................... 82
Network Render Interface ............................................................................................................. 82
Node Handles................................................................................................................................. 83
Node vertexColorType................................................................................................................... 83
OLE Automation............................................................................................................................. 84
MAXScript.reg - Registery file..................................................................................................... 84
Parameter Wiring........................................................................................................................... 85
Plug-In Manager ............................................................................................................................ 86
Portable Licence Manager ............................................................................................................. 87
maxOps....................................................................................................................................... 87
Quad Menu .................................................................................................................................... 90
Reactors.......................................................................................................................................... 91
Reactor controller ....................................................................................................................... 91
Render Element Manager .............................................................................................................. 92
Scripted Plug-Ins ............................................................................................................................ 93
type:#integer parameters in scripted plug-in parameter blocks ................................................ 93
Scripted Plug-in Events............................................................................................................... 93
Scripted Cameras ........................................................................................................................... 94
Scripted Controllers ....................................................................................................................... 95
dependsOn For Scripted Controllers .......................................................................................... 95
Matrix3 Scripted Controller ....................................................................................................... 96
Scripted Manipulators ................................................................................................................... 97
Scripted Objects........................................................................................................................... 106
on detachedFromNode For Object Scripted Plug-ins ............................................................... 106
Scripted RenderEffects................................................................................................................. 107
RenderEffects Progress Callback Mechanism .......................................................................... 107
Scripted Rollouts .......................................................................................................................... 108
Multi-line editText UI items in Scripted Rollouts .................................................................... 108
Skin............................................................................................................................................... 109
Joint Angle Morph ....................................................................................................................... 109
Spring Controller ......................................................................................................................... 109
SubObject Mode .......................................................................................................................... 112
System Tools ................................................................................................................................ 112
Trackbar Interface ........................................................................................................................ 113
Trackviews.................................................................................................................................... 114
Visual MAXScript ......................................................................................................................... 117
Xref Objects ................................................................................................................................. 120
Zip-file Script Packages ................................................................................................................ 122
version 4 MAXScript Language Improvements .......................................................................... 127
Additional Keyword Parameter On pickObject() forceListenerFocus: ..................................... 127
Affect Region Function............................................................................................................. 127
“Apropos” and “ShowProperties” and now “Help” and “Show” ............................................ 128
BinStream for Binary Reading and Writing ............................................................................. 128
By Reference Parameter Passing ............................................................................................... 129
C++-style bracketing comments ............................................................................................... 131
Coercion of bitArray to array and integer arrays to bitArrays ................................................. 132
Command line -U MAXScript startup scripts .......................................................................... 133
vi Contents
See also
MAXScript Overview (p. xxxii)
Using the MAXScript Documentation (p. xxxiii)
The MAXScript Utility Panel (p. xxxiv)
General MAXScript Topics (p. lii)
Learning MAXScript (p. 577)
Syntax Definitions in This Document (p. lx)
Objects and Classes in Object-Oriented Programming (p. lxii)
What’s New in MAXScript (p. 1)
3ds max 4 MAXScript Online Reference (p. xxxi)
MAXScript Overview
The MAXScript language is specifically designed to complement 3ds max. It has many special
features and constructs such as coordinate system contexts, object primitives and materials that
mirror high-level concepts in the 3ds max user-interface. It has an animation mode with automatic
keyframing and access to scene objects using hierarchical path names that match the 3ds max object
hierarchy.
The language syntax is simple enough for non-programmers, as it includes minimal punctuation
and formatting rules. Coupled with the use of the command-line Listener window, the ability to
install scripts as toolbar buttons, and the recording of user actions as MAXScript commands,
MAXScript can be employed casually by the user while working in the 3ds max point-and-click user
interface.
MAXScript is also rich enough to enable sophisticated programming tasks, with capabilities such as
3D vector, matrix, and quaternion algebra. MAXScript is well suited to working with large
collections of objects; for example, making complex procedural selections, constructing random star
fields, or placing objects in numerically precise patterns.
MAXScript allows scripts to be packaged as Utility panel rollouts, as modeless windows, and as
3ds max toolbar buttons. MAXScript can also be used to extend or replace the user interface for
objects, modifiers, materials, textures, render effects, and atmospheric effects; or to create custom
mesh objects, modifiers, and render effects. This allows job-specific tools to be scripted by the
technical department and made available to artists and animators through standard 3ds max
point-and-click user interfaces.
MAXScript supports formatted text I/O, so it is possible to produce asset reports directly from
3ds max scene files and read files containing scene layout, naming, texture details, and so on,
exported from other project management software.
MAXScript can also be used as a high-level scene import utility. By outputting MAXScript scripts
containing object creation commands, it is possible for other programs and packages to export
directly using any of the high-level 3ds max constructs.
Using the MAXScript Documentation xxxiii
Open Listener
Opens the MAXScript Listener window, or restores and brings it to the front if it is minimized or is
behind other 3ds max windows. The Listener window can also be opened by right-clicking in the
Mini Listener in the 3ds max status bar and choosing Open Listener Window, by choosing
MAXScript > MAXScript Listener in the 3ds max menu bar, or by pressing F11.
For Listener window features and commands, see The MAXScript Listener Window (p. xxxvi) topic.
New Script
Opens a new MAXScript Editor window used for writing a new script. A new Editor window is also
opened by choosing MAXScript > New Script in the 3ds max menu bar, or File > New Script in the
Listener window menu bar.
For Editor window features and commands, see The MAXScript Editor Windows (p. xliv) topic.
Open Script
Opens a common File Open dialog for choosing an existing script. A new MAXScript Editor window
then displays the selected script. A script file can also be opened by choosing MAXScript > Open
Script in the 3ds max menu bar, or File > Open Script in the Listener window menu bar.
For Editor window features and commands, see The MAXScript Editor Windows (p. xliv) topic.
Run Script
Opens a common File Open dialog for choosing an existing script. MAXScript then reads and
executes the selected script. Any output is printed to the Listener window. A script file can also be
run by choosing MAXScript > Run Script in the 3ds max menu bar, or File > Run Script in the Listener
window menu bar.
For more information, see the Running Scripts (p. xlix) topic.
Utilities
Displays a list of available scripted utilities. A MAXScript defining a scripted utility must be executed
before the scripted utility name appears in the Utilities list.
For more information, see the Accessing Scripted Utilities (p. l) topic.
Close
Closes the MAXScript Utility rollout. Any scripted Utilities panel rollouts are also closed.
xxxvi Chapter | Introduction
You can open only one instance of the MAXScript Listener window at a time. To open Listener,
choose the MAXScript utility on the Utilities panel and click Open Listener. Other methods for
opening Listener are described in The MAXScript Utility Panel (p. xxxiv) topic.
The Listener window is a resizable, modeless window. You can switch between it and 3ds max as you
work. If you close the Listener window and then reopen it, the text in the window before it was
Using the MAXScript Listener xxxvii
closed reappears. If Auto Open Listener on Output is checked in Customize > Preferences >
MAXScript, the Listener window opens automatically when a script outputs to it.
Listener is divided into two panes. The top (pink) pane is the Macro Recorder pane, and the bottom
(white) pane is the output pane. When the Macro Recorder is enabled, everything recorded is
displayed in the Macro Recorder pane. The output of results from scripts are displayed in the output
pane. The output of code executed in the Macro Recorder pane is always directed to the output pane
so as not to clutter the recordings. Both panes allow you to cut-and-paste, drag-and-drop, edit, select,
and execute code. You can resize the panes by dragging on the split bar between them.
The left-end of the 3ds max status panel contains a resizable Mini Listener. If the Mini Listener is not
visible, drag on the vertical split bar at the left edge of the status panel to reveal the Mini Listener.
The Mini Listener panes act as single-line sliding windows for the current line in the corresponding
Listener panes. The Mini Listener panes always show what you are typing or where the edit cursor
is placed in the Listener panes. Conversely, anything you type into a Mini Listener pane is entered
into the corresponding Listener pane at the current edit cursor position.
You can install Listener into a 3ds max viewport by right-clicking the viewport label, choosing
Extended, and then MAXScript Listener.
See also
Using the MAXScript Listener (p. xxxvii)
• Color-coding for distinguishing between input text, output text, and error message text. Three
MAXScript system global variables control these colors, and you can assign them new colors to
customize your Listener.
For commands within the Listener window, see the Listener Commands (p. xxxviii) topic.
See also
Using the ‘?’ Symbol (p. xli)
Turning on the Listener Log (p. xli)
Controlling the Listener Contents and the Insertion Point (p. xlii)
Including Scripts Within Scripts (p. lix)
Aborting Execution with the ESC Key (p. lv)
Listener Commands
Menu Bar Commands and Keyboard Shortcuts
The following menu bar commands and keyboard shortcuts are available in Listener. The edit
commands listed are also available in the Listener right-click menu. The menu bar commands for
Macro Recorder are described in The Macro Recorder (p. l) topic.
CTRL+B
Selects the text in the current bracket. Bracket balancer lets you check bracket balancing in long
pieces of code. The balancer works with any of the following: (), [], and {}. To use it, place the cursor
anywhere in the script text and press CTRL+B. If the cursor is next to a bracket, the code bracketed
by it and its matching bracket will be selected and highlighted. If the cursor is not next to a bracket,
the closest bracketed code containing the cursor will be selected. If you press CTRL+B again, the next
outer bracketed fragment is selected, and so on. You can keep pressing CTRL+B to move out through
bracket nestings. If at any point there is a bracket mismatch, the balancer will beep and not select
any text.
End-Of-Text Commands
The simplest way to use the MAXScript Listener is to enter commands at the end of the existing text
and press ENTER. This is called the end-of-text compilation. After each command is executed and any
results are printed to the output pane, you can enter another command and press ENTER, and so on.
When you write new commands at the end of the text in Listener, pressing ENTER executes the last
line and inserts a new line.
See also
Using the MAXScript Listener (p. xxxvii)
or:
logfile=”my_log.txt”
openLog logfile
xlii Chapter | Introduction
The default mode (mode:”w”) creates a new file or overwrites an existing file. To append
the log results to an existing file; specify mode:”a”. If the specified file does not exist, an
error message will be generated. Both input and output are logged by default; specify
outputOnly:true to log only MAXScript output. For example:
openLog “my_log.txt” mode:”a” outputOnly:true
would append only the MAXScript output to file my_log.txt.
If a log file is already open, the openlog() method will close that log file.
MAXScript echoes Listener activity as it occurs to the log file until you stop logging. The log file data
is not continuously written to the file, rather the log data is written to a buffer in memory, and when
the buffer is full the data in the buffer is written to the file. You can use the flushLog() method to
ensure the log’s buffer is flushed so that all output is written to the file:
flushLog()
You can stop logging, flush the log’s buffer, and close the log file using the closeLog() method:
closeLog()
No error message is generated if the flushLog() or closeLog() methods are called and no log file
is open.
while the following would select all of the text in the Listener output pane text:
setListenerSel #(0,-1)
selections set using the setListenerSel() method are recognized by this method. If no
selection has been set using the setListenerSel() method, the start and end values
returned are the offset to the end of the Listener output pane text.
getListenerSelText()
Returns the currently selected text, or an empty string if no text is selected and only the
insertion point is showing. Only the selections set using the setListenerSel() method
are recognized by this method. If no selection has been set using the setListenerSel()
method, an empty string is returned. For example, the following lines would capture the
entire contents of the Listener output pane to variable ListenerText:
( global ListenerText -- declare variable so its scope is higher
-- than inside just the following block
-- expression
( setListenerSel #(0,-1) -- select all the text
ListenerText=getListenerSelText() -- get selected text
setListenerSel #(-1,-1) -- set insertion point at
-- end of output pane
)
)
setListenerSelText <replacement_string>
Replaces the currently selected text with the replacement string. If no text is selected and
only the insertion point is showing, setListenerSelText() inserts the replacement
string at the insertion point. Only the selections set using the setListenerSel()
method are recognized by this method. If no selection has been set using the
setListenerSel() method, the insertion point is the end of the Listener output pane
text. <replacement_string> is a string literal or an expression that evaluates to a string.
include <filename_string>
Inserts the specified file’s content into the Listener output pane. The inserted text is not
evaluated. You can use this method to load a script and then step through it, executing
any selected text with SHIFT+ENTER. <filename_string> is a string literal or an
expression that evaluates to a string, and specifies the name of the file to insert. Example
uses are:
include “my_script.ms”
or:
scriptfile=”c:\\my_scripts\\my_script.ms”
include scriptfile
If you don’t explicitly specify a directory in the file name, the file will be searched for in
the following directories, in the order listed:
xliv Chapter | Introduction
To create a fresh script, press New Script on the MAXScript rollout, File > New Script in the Listener
menu bar, or MAXScript > New Script in the 3ds max menu bar to open a new, empty MAXScript
Editor window. You can write and edit text, including drag-and-drop editing, in the MAXScript
Editor as you would in other editors like WordPad. The menus are similar to those in many standard
Windows text editors. You may have any number of MAXScript Editor windows open at the
same time.
The MAXScript Editor Windows xlv
MAXScript Editor is suited to developing longer scripts or code fragments you want to keep. You can
edit and test parts of them until they are complete, then save your code in a script file for later use.
This is a common method for developing large scripts, utilities, and function libraries.
You can select one or more text lines and drag them to a 3ds max toolbar to create a Macro Script
containing the selected lines. For more information, see the Defining Macro Scripts (p. 1521) topic.
You can open a MAXScript Editor window from within the Listener or from other running scripts
by calling the edit() method. The syntax for the edit() method is:
edit <filename_string>
where <filename_string> is a string literal or an expression that evaluates to a string,
and specifies the name of the file whose contents are to be loaded into the new MAXScript
Editor window. Example uses are:
edit “my_script.ms”
or:
scriptfile=”my_script.ms”
edit scriptfile
The file will be searched for in the following directories, in the order listed:
• The current MAXScsript directory
• The 3ds max executable main directory
• The Windows NT 32-bit system directory (system32)
• The Windows 16-bit system directory (system)
• The Windows directory
• The directories that are listed in the PATH environment variable
You can create an empty MAXScript Editor window from within the Listener or from other running
scripts by calling the newScript() method. The syntax for the newScript() method is:
newScript()
Opens an empty MAXScript Editor window and returns a WindowStream value that may
be used as the target for print and format operations. This is useful for directing output to
a separate window for ease of inspection or editing, or later saving to a file. Output to a
WindowStream is inserted at the current cursor position in that window. For example:
debug = newScript()
...
print $foo to:debug
...
format “name is %\n” obj.name to:debug
If you need to locate the source of a scripted function, you can use the showSource() method. It
displays a MAXScript Editor window containing the source file in which the function was defined,
positioned at the function’s definition. The form is:
showSource <fn>
xlvi Chapter | Introduction
TAB, CTRL+I
Indents selected lines of text by one tab width.
SHIFT+TAB, SHIFT+CTRL+I
Unindents selected lines of text by one tab width.
xlviii Chapter | Introduction
SHIFT+ENTER
A MAXScript Editor can send code selections to Listener for evaluation. Select some text in
MAXScript Editor and press SHIFT+ENTER to send the selected text to Listener. Listener compiles
and evaluates it and prints out the result at the end of the current text in Listener. If you press
SHIFT+ENTER with no text selected, the line containing the cursor is sent to Listener for evaluation.
This behavior is similar to using SHIFT+ENTER in Listener, except that the results of the evaluations
are printed in the Listener, not inserted into the MAXScript Editor text.
If you have a number pad on your keyboard, the Number-Pad ENTER key is an alternative to
SHIFT+ENTER and can be used to execute commands. You may find the Number-Pad ENTER key
faster and easier to use.
CTRL+Right-Click
Displays a pop-up menu of all the utility, structure, user-interface item, function, handler, plug-in,
tool, Macro Script, and rcmenu definitions that exist in the current script. Select one of the items in
the pop-up menu to position that definition at the top of the MAXScript Editor window. This
simplifies large script navigation.
Running Scripts xlix
CTRL+B
Selects the text in the current bracket. Bracket balancer lets you check bracket balancing in long bits
of code. The balancer works with any of the following: (), [], and {}. To use it, place the cursor
anywhere in the script text and press CTRL+B. If the cursor is next to a bracket, the code bracketed
by it and its matching bracket will be selected and highlighted. If the cursor is not next to a bracket,
the closest bracketed code containing the cursor will be selected. If you press CTRL+B again, the next
outer bracketed fragment is selected, and so on. You can keep pressing CTRL+B to move out through
bracket nestings. If at any point there is a bracket mismatch, the balancer will beep and not select
any text.
CTRL+D
Performs a simple syntax coloring scheme in the MAXScript Editor. Each time you press CTRL+D, the
window is redrawn with comments in green, MAXScript reserved words in blue, and string literals
in light red. This often helps in reading large, complex programs. New text is always colored black
and you have to press CTRL+D at some point to recolor the script. Syntax coloring is a programming
aid and does not effect script execution.
CTRL+R
Places the cursor at the location where it was previously placed with a mouse click or a find
operation. Consecutive uses of CTRL+R cycle through the last eight cursor positions. This feature is
useful if you edit at one location, move the cursor elsewhere with find or scroll operations, and then
want to return to the edit location. This feature allows you to quickly review the code pieces you
recently worked on.
Running Scripts
To run an existing script file, press Run Script on the MAXScript rollout, File > Run Script in the
Listener menu bar, or MAXScript > Run Script in the 3ds max menu bar. This opens a common File
Open dialog for choosing the script. MAXScript then reads and executes the selected script. Any
output is printed to the Listener output pane.
You can also run a script from Listener or from within other scripts using the fileIn() method:
fileIn <filename_string> [ quiet:<boolean> ]
where <filename_string> is a string literal or an expression that evaluates to a string,
and specifies the name of the script file whose content is executed. The script file content
is executed one expression at a time, and halts processing if an error is encountered at any
point. By default, the file is not listed as it is loaded; use quiet:false to get a running
listing to the Listener. Example uses are:
fileIn “my_script.ms”
or:
scriptfile=”my_script.ms”
fileIn scriptfile
l Chapter | Introduction
The script file content is compiled in a global scope context, as opposed to the scope in effect when
the filein() method is executed. For more information, see the Scope of Variables (p. 646) topic.
make a button that does the sequence of events just recorded. For more information, see the Defining
Macro Scripts (p. 1521) topic.
The following Macro Recorder menu commands are available in Listener:
Enable
When Enable is selected the Macro Recorder will generate MAXScript commands.
If Selection-Relative Scene Object Names is enabled, a typical generated command would be:
move $ [0,-47.8044,0]
By using Selection-Relative Scene Object Names, you can apply the recorded script to a different
selection, thereby making it somewhat general. Use Explicit Scene Object Names if you want the
script to always work on the same objects regardless of the current scene selection.
When the Absolute Transform Assignments option is selected, absolute transform assignments are
output only if a single object is transformed. If multiple objects are selected, relative transform
operations are output.
By using Selection-Relative Sub-object Sets, you can apply the recorded script to a different selection,
thereby making it somewhat general. Use Explicit Sub-object Sets if you want the script to always
work on the same sub-objects regardless of the current sub-object selection.
Tool Selections
When Tool Selections is selected, the Macro Recorder will generate MAXScript commands for the
selection of tools in the 3ds max toolbar. In most cases, recording the selection of tools is superfluous
as most scripts are not dependent on the tool selection to work.
Error Messages
When MAXScript detects a runtime error in your script, it displays an error message and prints
diagnostic information to the Listener output pane. If the error occurs in a controller script or rollout
panel script, the error message is displayed in an Alert Box window, otherwise it is printed in the
Listener output pane.
The diagnostic information is in the form of a call stack trace-back which can help determine the
cause and location of the error in your code. The call stack trace-back shows the nesting of called
MAXScript functions at the point of error, deepest ones first to outermost ones last. The call stack
trace-back also displays the values in all the local variables and function parameters at the levels they
are declared or first used. Note that for loops produce separate entries in the call stack trace-back
and include a variable dump for the loop variable and any locals in the loop body.
As a further aid in locating the error, MAXScript shows the line in which the error occurred in an
MAXScript Editor window if the running code was compiled from a source file (any code not entered
directly in the Listener). If the source file is not currently open in a window, MAXScript opens the
file in a new MAXScript Editor window. The line containing the code in which the error occurred is
highlighted and scrolled into view. The error message is either displayed in a Alert Box window or
the Listener window. In both cases, the Alert Box or Listener window is brought to the front and the
MAXScript Editor window containing the code causing the error is immediately behind.
All compile and runtime error messages reported in the Listener output pane are preceded by the
comment symbol “--”, so you can reselect and evaluate code in Listener that might have embedded
error messages and not have them cause syntax errors.
In the following figure, an Editor and a Listener window are shown where an error was detected
while running the script. The error occurred in the highlighted line in the Editor window. Looking
at the call stack trace-back, we see the error occurred when the for loop variable i is equal to 6. In
the line in error, the position of the object specified by the sixth element of array b is being set. After
further investigation, it was found the array b only had five elements defined. Thus element b[i]
contained the value undefined, which resulted in the error as there is no position property
associated with undefined.
liv Chapter | Introduction
In the following figure, an error dialog and script controller dialog are shown. An error was detected
while running the script assigned to a script controller. This error was caused by the deletion of
object box02, whose position was used in the script.
Aborting Execution with the ESC Key lv
Startup Scripts
When the 3ds max is first started, MAXScript searches for any startup script files that it then
automatically loads and runs. This feature is useful if you have function libraries you always use and
want preloaded, or if you want to establish custom UI settings, define scripted plug-ins, or load
scripted utility rollouts.
The automatic loading of startup script files can be deactivated by turning off the Auto Start
MAXScript option in the MAXScript page of the 3ds max Preferences dialog, as described in the
MAXScript Preferences Settings topic in the 3ds max online help.
MAXScript first searches for a file named startup.ms in the following directories, in the order listed:
• The Scripts directory (defined in the 3ds max Configure Paths dialog)
• The Startup Scripts directory (defined in the 3ds max Configure Paths dialog)
• The 3DS executable main directory
• The Windows NT 32-bit system directory (system32)
• The Windows 16-bit system directory (system)
• The Windows directory
• The directories that are listed in the PATH environment variable
MAXScript stops searching when it finds the first occurrence of startup.ms.
MAXScript then recursively scans the 3ds max plug-ins and Startup Scripts directories (both defined
in the 3ds max Configure Paths dialog) and directories nested within them for .ms and .mse script
files and loads them. In this pass, any script files with the name startup.ms are ignored. This allows
you to place your scripted plug-in scripts in the 3ds max plug-in folders for automatic loading. They
can be managed like DLL plug-ins, and used to organize your startup scripts into groups in their own
directories for easier management. You can prevent a nested directory from being scanned by
placing its name in parentheses, for example “(old-versions)”, allowing you to enable and disable
scripts in handy directory-based groupings.
Running Scripts from the Command Line lvii
This example command line would launch the 3ds max executable in c:\3dsmax, start MAXScript,
and then have it run the launch script rendercams.ms.
The following example launch script loads two scenes, renders frames from each of the cameras in
them, and then quits 3ds max:
loadMaxFile “foo.max”
for c in cameras do render camera:c outputfile:(”foo_”+c.name+”.bmp”)
loadMaxFile “baz.max”
for c in cameras do render camera:c outputfile:(”baz_”+c.name+”.bmp”)
quitMax #noPrompt
This example makes use of the quitMax() method to exit 3ds max (see Exiting and Resetting
3ds max (p. 1669) ) when the script is finished. Launch scripts need not be batch scripts as in this
example, but may be used to condition 3ds max for interactive use, for example by loading a scene
file and setting some user-interface options.
The normal startup scripts, startup.ms and those in the Startup Scripts directory, are run before the
launch script.
It is also possible to install scripts into individual scene files that run automatically when that scene
is open or closed or at certain other events (see General Event Callback Mechanism (p. 29)).
This line can be broken after any of the operators. MAXScript continues to read the next line,
because an operator needs another argument. For example:
a + b * c / d - e +
f * g / h
You cannot break the example line as shown next and get the same result, because the expression
on the first line is a complete expression. MAXScript considers the two lines as separate expressions,
and the second line is now syntactically wrong, because it starts with an operator.
a + b * c / d - e
+ f * g / h
This scheme allows you to write the following forms of the same statement without using periods
or semicolons, as you might in other freeform languages. For example, a if/then/else construct could
be written as:
if a < b then print c else print d
or,
if a < b then print c
else print d
or,
if
a < b
then
print c
else
print d
If you do want to break a line at the end of a sub-expression, you can use the backslash line
continuation character: ‘\’. The previous example above of an invalid break can be made valid using
the line continuation character after the ‘e’:
a + b * c / d - e \
+ f * g / h
Whenever MAXScript encounters a ‘\’ as the last character on a line, except for spaces, tabs, or
comments, it continues to read the next line as though the line break were not present.
Line continuations are often used to break up function calls with many arguments, as shown in
many of the Expressions (p. 667) topics.
MAXScript also lets you combine multiple statements and expressions in a single line. The
statements or expressions are separated with a ‘;’.
Including Scripts Within Scripts lix
Examples:
print “End of input data reached” to:f ; close f ; f = undefined
if a < 0 do (print “value out of range”;a=0)
Comments in MAXScript begin with a double-hyphen (‘--’) and extend to the end of the current
line. Many code examples in this help file use comments in this style.
Example:
-- special cases...
if first do
subanims[6]=undefined -- subanims[6] is #Image_Motion_Blur_Multiplier
The include <file> construct is effectively replaced in the source code at that point with the
contents of the named file.
You can nest included files as deeply as needed; included files can include other files, and so on.
Because include is a compile-time construct, the current MAXScript scope is maintained within the
included file. This is opposed to the fileIn() method described in the Running Scripts (p. xlix) topic,
whose script file content is compiled in a global scope context. For more information, see the Scope
of Variables (p. 646) topic.
lx Chapter | Introduction
The include <file> can appear at any point a new token is expected, such as a name, literal, or
punctuation. This means that you could complete a partial expression with an included file. For
example:
include “op1.ms” + include “op2.ms”
if include “test2.ms” then print a else print b
You cannot place an include <file> within a token. For example, the following is not valid:
timeval = 2:include “framenum.ms”.0
or:
scriptfile=”my_script.ms”
encryptScript scriptfile
The encrypted script file from the previous examples would be named my_script.mse.
The Run Script button in the MAXScript rollout and the fileIn() method described in the Running
Scripts (p. xlix) topic automatically support .mse encrypted scripts.
You can couple this script source code encryption with the hardwareLockID variable and the
encrypted file I/O functions to provide authorization-based protection for your scripts.
Syntax Definition
[-]{<digit>} an optional minus sign (the sign), followed by 0 or more digits (the integer part),
followed by
[.{<digit>}] an optional sequence (the fraction part) comprised of:
a period character, followed by 0 or more digits, followed by
[(e | E)[+ | -]{<digit>}+] an optional sequence (the exponent part) comprised of:
either an ‘e’ or ‘E’, followed by an optional plus or minus sign, followed by one or
more digits.
The syntax definitions in the MAXScript Grammar (p. 1681) topic are in the form of named rule
definitions. For example:
number ::= [-]{<digit>}[.{<digit>}](e | E)[+ | -]{<digit>}+]
allowing the rule to be referred to by name in other rules in the grammar. An example of such a
rule is:
mod <number1> <number2>
modulo arithmetic, the remainder when <number1> is divided by <number2>
Some definitions throughout this document also use the convention of showing alternative
definitions for a rule on consecutive lines instead of separating them with the ‘|’ symbol.
lxii Chapter | Introduction
See also
Inheritance and Polymorphism (p. lxiii)
Properties, Methods, Operators, and Literals (p. lxiv)
Inheritance and Polymorphism lxiii
Various characteristics are defined for a class, and each lower class inherits those characteristics. For
example, the classOf() method is defined for class Value, and class Box inherits this method
through its hierarchy. Thus you can specify a Box object as a parameter to the classOf() method.
In the MAXScript Class Hierarchy (p. 1688) topic, all the built-in classes in MAXScript are laid out in
their place in the hierarchy so you can see for each class the classes it inherits characteristics from.
Some of the hierarchy comes from within 3ds max itself which is internally object-oriented. All of
its objects, modifiers, controllers, and so on are arranged in a well-defined inheritance hierarchy.
Once the objects have been grouped into classes, the symbology for the operations that can be
performed on objects of each class can be simplified. The classic example of this comes from
mathematics. The symbolic operators ‘+’, ‘-’, ‘*’, and ‘/’ are shared among many types of values
(integers, reals, complex, vectors, matrices, and so on), and perform the correct action on the types
they are applied to. This capability for a single-named operation to work on different types is called
polymorphism. Object-oriented languages let you use the same name for different methods or
operators across different classes, and the correct method to apply is automatically determined based
on the class of the value it is used with.
lxiv Chapter | Introduction
In MAXScript, all math operators and methods are polymorphic in this sense and reflect the
standard mathematical conventions. An interesting example for 3ds max use is the random()
method. It takes two arguments and generates a random value between them. So, if you give it floats
it gives you a float back; if you give it 3D points, it gives you a random point in the box they define
the corners of; if you give it quaternions, it gives you back a random rotation between them, and
so on.
Further, all the methods that work on 3ds max objects are polymorphic within their hierarchies. So
move, hide, and select work on all types of scene objects; time scaling and insertion work on all the
types of controllers, and so on.
Note:
ParamBlock2s make it possible for plug-ins to host all of their user visible parameters in one or more
parameter blocks, including complex parameters such as ReferenceTargets, Sub-Anims, dynamic
parameter tables (Tabs<>), and class parameters. The parameter blocks handle old-version loading
and reference management automatic. They augment the Parameter Map mechanism to provide
automatic UI for the new parameter types including common MAX controls such as node pickers,
texmap selectors, etc. as well as listboxes for tabular parameters and, further, to automate the
construction of ParamMaps and ParamDlgs in common situations. Additionally, ParamBlock2’s
provide a system that describes all the parameter blocks and parameters of a plug-in along with a
metadata ‘reflection’ API so that systems like the MAXScript, the Macro Recorder, Schematic View,
and custom exporters can access plug-in data automatically. This metadata includes version and
position-independent parameter IDs and both localized and fixed machine-parsable names for all
classes and parameters. This helps to address version compatibility and scripter/exporter
localization issues.
For design details see the 3ds max sdk help file topic “Parameter Blocks and Maps in Release 3”.
Note:
The MAXScript SDK is a set of Visual C++ headers and import libraries that C++ programmers can
use to extend MAXScript. These extensions can be in the form of new built-in functions, new system
globals or descriptors for new MAX plug-in class properties. This is useful for 3rd-party plug-in
developers to write custom scripting interfaces for their plug-ins, and for programmers to do custom
C++ performance code and drive it with scripts for hybrid tools.
2 Chapter 1 | What’s New in 3ds max 4 MAXScript
The scripter SDK allows extensions to be added either incrementally through a MAXScript-specific
DLL file type that is loaded by MAXScript or by runtime calls directly to MAXScript from within an
existing plug-in.
For design details see the 3ds max sdk help file topic “MAXScript SDK”.
Note:
The areas in this documentation exposed by Function Publishing will document the interface
information provided by the “showInterfaces” function (p. 159), in three sections: Properties,
Methods, and Actions. In the Properties section, each property exposed by the interface is
listed along with its data type or enumeration values and whether the property can be read and
written to. In the Methods section, each method is listed along with its return type and its argument
list. The value type for each argument is shown. If the return type is shown as <void>, the method
returns a value of ‘ok’. Methods that are used by Actions are commented as such. These methods
typically require that the object be selected and active in the appropriate command panel. In the
Actions section, each Action is listed along with its category and action description as shown in
the Customize User Interface dialog, and the shortcut keys, if any, assigned to the Action.
The following topics are new to MAXScript:
• Learning MAXScript (p. 577): Walkthrough tutorial for beginning MAXScript users.
Additional Note:
The name of the atmosphere in releases prior to 3ds max 4 known as the “Combustion effect” is now
called “Fire Effect”.
The following are new MAXScript features in 3ds max 4:
Action Manager:
Action Manager (p. 9)
ActiveX Controls in MAXScript Rollouts:
ActiveX Controls in MAXScript Rollouts (p. 10)
Asset Browser:
Asset Browser enhancements (p. 22)
Bones:
Access to the new node bone properties and methods (p. 23)
Bone Creation (p. 25)
Cache Modifiers:
Point Cache Modifier (p. 26)
CallBack Notification Codes:
RenderEffect Progress Callback Mechanism (p. 28): You can control the main RenderEffects
dialog progress bar using several callbacks.
Notify Callbacks for Animate button on and off Transitions (p. 27)
Color Manager:
Color Manager (p. 35)
What’s New in 3ds max 4 MAXScript 3
Combustion:
Combustion (p. 38)
Constraints:
Path Constraint (p. 39)
LookAt Constraint (p. 40)
Orientation Constraint Controller (p. 40)
Position Constraint (p. 41)
Link Controller for Constraints (p. 42)
Controller Functions for use with Constraint Assignments (p. 42)
Context Filters:
Context Filters (p. 43)
Custom Attributes:
Scripted Custom Attributes (p. 45)
Depth of Field:
Depth of Field (p. 54)
Edit Mesh:
ApplyOperation function (p. 54)
Editable Patch:
Patches (p. 55)
Filters:
class id filter (p. 59)
Selection Filter (p. 61)
iDrop - drag and drop:
iDrop - drag and drop (p. 62)
Interfaces:
Interfaces (p. 67)
Core Interfaces (p. 70)
Other Interfaces (p. 71)
Inverse Kinematics:
HD IK controller chains can be assigned to existing hierarchies (p. 73)
IKLimb Solver (p. 74)
Materials:
Multi/Sub Material (p. 75)
Menu Manager:
Menu Manager (p. 75)
Mesher:
Mesher (p. 82)
Network Render Interface:
Network Render Interface (p. 82)
4 Chapter 1 | What’s New in 3ds max 4 MAXScript
Node Handles:
Node Handles (p. 83)
Node vertexColorType:
Node vertexColorType (p. 83)
OLE Automation:
MAXScript.reg - Registery file (p. 84)
Parameter Wiring:
Parameter Wiring (p. 85)
Plug-In Manager:
Plug-In Manager (p. 86)
Portable Licence Manager:
maxOps (p. 87)
Quad Menu:
Quad Menu (p. 90)
Reactors:
Reactor controller (p. 91)
Render Elements Manager:
Render Element Manager (p. 92)
Scripted Plug-In:
type:#integer parameters in scripted plug-in parameter blocks (p. 93)
Scripted Plug-in Events (p. 93)
Scripted Cameras:
Scripted Cameras (p. 94)
Scripted Controllers:
dependsOn For Scripted Controllers (p. 95)
Matrix3 Scripted Controller (p. 96)
Scripted Manipulators:
Scripted Manipulators (p. 97)
Scripted Objects:
on detachedFromNode For Object Scripted Plug-ins (p. 106)
Scripted RenderEffects:
RenderEffect Progress Callback Mechanism (p. 28)
Scripted Rollouts:
Multi-line editText UI items in Scripted Rollouts (p. 108)
Spring Controller:
Spring Controller (p. 109)
System Tools:
System Tools (p. 112)
TrackBar:
Trackbar Interface (p. 113)
What’s New in 3ds max 4 MAXScript 5
Trackviews:
Trackviews (p. 114)
Visual MAXScript:
Visual MAXScript (p. 117)
Xref Objects:
Xref Objects (p. 120)
Zip-file Script Packages:
Zip-file Script Packages (p. 122)
MAXScript Language Improvements in 3ds max 4:
The following are new MAXScript methods for 3ds max 4:
IsValidNode (p. 136)
getTextExtent (p. 175)
isActive <atmos> (p. 1338)
isActive <renderEffect> (p. 1348)
affectRegionVal (p. 1104)
getMAXSaveFileName & getMAXOpenFileName (p. 1640)
Language Improvements:
Affect Region Function (p. 127)
BinStream for Binary Reading and Writing (p. 128)
By Reference Parameter Passing (p. 129)
C++-style bracketing comments (p. 131)
Coercion of bitArray to array and integer arrays to bitArrays (p. 132)
Detecting Deleted Nodes (p. 133)
Dereferencing Operator (p. 133)
forceUpdate Function added to UVWUnwrap (p. 134)
hasProperty() function (p. 135)
Improved the Performance of Iterating and Indexing the ‘selection’ and ‘$’ Object Sets (p. 135)
isValidNode (p. 136)
Readable/Writable Checks (p. 135)
RubberBanding in pickObject() Function (p. 136)
SetDir (p. 136)
Shortcut system replaced (p. 137)
startObjectCreation() (p. 138)
Subanim Indexing Operator, [], on MAX Objects Now Takes Subanim Names (p. 139)
superclasses read-only global variable (p. 139)
Symbolic Pathnames (p. 140)
System Information (p. 141)
validModifier() function (p. 142)
Visible Class For ‘&’ Reference Values (p. 142)
6 Chapter 1 | What’s New in 3ds max 4 MAXScript
Controllers:
List Controller (p. 143)
mapKeys() method (p. 144)
moveKeys function (p. 145)
Keys:
Bezier Keys inTangentLength and outTangentLength (p. 158)
Object Inspector Functions:
Class and Object Inspector Functions Enhanced (p. 159)
Renderer:
render() Function Re-entrant (p. 160)
SuperClasses:
Bitmap Manager - Function Published BMM control (p. 161)
Utilities, Global Utilities and Render Element plug-ins (p. 161)
Renderer (p. 162)
2 New Scripted Pug-in Superclasses (p. 162)
Globals and Locals:
Definition Constructs Can Include Global Variable Declarations At Top Level (p. 162)
Changes to Undeclared Implicit Global Variables (p. 163)
Material Editor, Material and Textures:
Accessing The Material Editor Active Slot (p. 163)
BitmapTex Reload and viewImage (p. 164)
BMP, PNG, JPEG and TGA I/O Interfaces (p. 164)
Material Editor Access (p. 165)
Material Level Show-in-viewport State (p. 166)
Maxops:
maxOps (p. 87)
User Interface:
Angle UI element (p. 168)
CreateDialog (p. 169)
Curve Control (p. 170)
isActive (p. 176)
keyboard.escPressed (p. 176)
MAX Open & Save Dialogs (p. 177)
Menu and CUI Loading (p. 178)
mtlBrowser (p. 180)
SetBackground Method (p. 180)
mouseTrack() Function (p. 180)
snapMode (p. 182)
Spinner UI Item setKeyBrackets (p. 182)
Timer UI element (p. 183)
TimeSlider on/off toggle (p. 183)
What’s New in 3ds max 4 MAXScript 7
The MAXScript Interface: actionMan (p. 353) has a function called “executeAction”. It takes as
parameters the ID of the action table and the “persistent id” of the action. A comment string
that includes the category and tooltip for the action follows it. Some action items have custom code
emitters that emit better looking code.
This interface is currently intended only for running macro recorded actions.
Note:
There is no way currently to query the action manager for all the available action items.
actionMan.loadKeyboardFile “KbdFile.kbd”
This loads the named keyboard file from the current UI directory.
actionMan.saveKeyboardFile “KbdFile.kbd”
Saves the current keyboard configuration into the given file name in the UI directory.
actionMan.getKeyboardFile()
Returns the full path to the current keyboard file.
See Also
Interface: actionMan (p. 353)
The Macro Recorder (p. l)
Defining Macro Scripts (p. 1521)
The MAXScript Listener Window (p. xxxvi)
Turning On the Listener Log (p. xli)
Listener Commands (p. xxxviii)
10 Chapter 1 | What’s New in 3ds max 4 MAXScript
Compound controls
Microsoft Excel,
Microsoft Internet Explorer
Adobe Acrobat
…
This provides numerous possibilities in MAXScript which include:
• Embed a web browser into a rollout and then navigate the user to a web site.
• Embed an Excel spreadsheet into a rollout, extract the user entered values from cells and then
create animation in Max.
• Create an ActiveMovie player through MAXScript, load an Avi file and then synchronize the
animation between the rendered Avi in ActiveMovie player to animation in Max.
The technology behind this feature is a MAXScript extension plug-in (MxsActiveX.dlx) making it
MAXScript capable. It does not use ParamBlock2.
The plug-in adds a new type of rollout control. The syntax is:
activeXControl <name> [ <control_type> ] [ prop1:<value> ] [ prop2:<value> ] …
Parameters:
<control_type>
A string to create the control. The string must be formatted in one of the following ways:
• A Program ID such as “MSCAL.Calendar.7”
• A Class ID such as “{8E27C92B-1264-101C-8A2F-040224009C02}”
• A URL such as “http://www.microsoft.com”
• A reference to an Active document such as “file://\\Documents\MyDoc.doc”
• A fragment of HTML such as “MSHTML:<HTML><BODY>This is a line of text</BODY></
HTML>”
What’s New in 3ds max 4 MAXScript 11
Note:
“MSHTML:” must precede the HTML fragment so that it is designated as being a
MSHTML stream.
prop1:<value>
prop2:<value>
…
These are control specific keyword arguments. You can get a list of properties and their
types by calling showProperties on the control.
Examples:
activeXControl ax “{05589FA1-C356-11CE-BF01-00AA0055595A}” height:200 \
width:300 align:#left
Examples:
----------------------------------------------------------------------
-- Creates a Windows media player in a rollout.
-- Load an avi file by clicking the “Pick Avi” button and choosing an Avi file.
-- When the play button is hit the “on timer...” is called
-- This synchronizes the time slider with the active frame in the media player
-- Clicking show properties to get all the properties listed in the listbox
-- You can also set a property by picking a property from the listbox and entering
the new value in the text below
--------------------------------------------------------------------
rollout rActiveX “Creates a Windows media player in a rollout”
(
local val
activeXControl ax “{05589FA1-C356-11CE-BF01-00AA0055595A}” height:200 width:300
align:#left
on btnPick pressed do
(
local f = getOpenFileName caption:”Pick Any Avi File” types:”*.avi”
if f != undefined then
ax.FileName = f
)
on btnProps pressed do
(
showProperties ax
lbProps.items = getPropNames ax
)
on lbProps selected sel do
(
if lbProps.items.count > 0 then
(
try ( val = getProperty ax lbProps.items[sel] )
12 Chapter 1 | What’s New in 3ds max 4 MAXScript
format “----Application----”
showProperties rExcel.ax.application
format “----Parent----”
showProperties rExcel.ax.parent
format “----Container----”
showProperties rExcel.ax.container
-- In case of MS Excel .document points to the msexcel.workbook
workbook = rExcel.ax.document
format “----Document----”
showProperties workbook showHidden:true
showMethods workbook showHidden:false
props = getPropNames workbook
sort props
for prop in props do
(
try
(
format “\t%=%\n” (prop as string) (getProperty workbook prop)
) catch ()
)
14 Chapter 1 | What’s New in 3ds max 4 MAXScript
Properties
There are 2 common properties for ActiveX controls, .pos and .size. Other ActiveX properties are
control specific and vary from one control to another.
Properties can be set like:
ax.filename = true
where ax is the control name.
Additionally, there is support for color properties. The internal representation of colors for ActiveX
controls is COLORREF(unsigned integer) so you’ll always get them in integers but you can set them
as follows:
ax.forecolor = red -- if a .forecolor property exists
Methods
All methods of ActiveX controls are control specific and vary from one control to another. Methods
can be called like:
ax.AboutBox()
ax.loadURL “www.discreet.com”
Events
Events are notifications sent by the ActiveX controls to the rollout, whenever an action is performed
on the control, e.g.: clicking a button, browsing to a webpage. If supporting event handler is
implemented for the event, in the rollout context, the handler is called with supporting arguments.
Supporting Functions
showAllActiveXControls [ to:<stream> ]
Prints a list of ActiveX controls with their progID and classID, registered on your system.
showMethods <axControl> [ to:<stream> ] [showHidden:<false>]
Prints a list of methods and their arguments that can be invoked on the control
showEvents <axControl> [ to:<stream> ]
Prints a list of events and their arguments that are sent by the control
showProperties <axControl> [ to:<stream> ] [showHidden:<false>]
Prints a list of the properties and their types, supported by the control. Some properties are
marked read-only
getPropNames <axControl> [showHidden:<false>]
Returns an array of the properties supported by the control
What’s New in 3ds max 4 MAXScript 15
Common Parameters
to:<stream>
is the output stringstream.
showHidden:<boolean>
controls whether hidden properties/methods should be included in the enumeration. The
default value is false.
All supported COM datatypes are converted to an appropriate MAXScript wrapper when passed to
and from a COM object. Here are the supported types and their mapping
undefined - VT_EMPTY
boolean - VT_BOOL
integer - VT_UI1
integer - VT_UI2
integer - VT_UI4
integer - VT_UI8
integer - VT_I1
integer - VT_I2
integer - VT_I4
integer - VT_I8
float - VT_R4
float - VT_R8
string - VT_BSTR
float - VT_CY
date - VT_DATE
error - VT_ERROR
color - VT_COLOR
MSDispatch - VT_DISPATCH
font - VT_FONT
undefined - VT_UNKNOWN
ComArray - VT_SAFEARRAY
ComArray - VT_CARRAY
ComArray - VT_ARRAY
Valid string handling for property sets and method call arguments, you can safely do
ax.Navigate “beta.discreet.com”
where: ax is the Microsoft Web Browser Control
16 Chapter 1 | What’s New in 3ds max 4 MAXScript
Note:
Restricted functions like QueryInterface, AddRef, Release are displayed by showMethods() function.
Examples:
---------------------------------------------------------
-- creates a IE browser control in a rollout as registers it an extended
-- viewport. Pick “Web Page” from the Extended Views
-- menu to display the rollout in the webpage. Also click various hypertext links
-- to see the text change in the viewports
---------------------------------------------------------
rollout rWebpage “Web page”
(
local txtObj
local vpsz = getViewSize()
activeXControl ax “www.yahoo.com” height:(vpsz.y-50) width:(vpsz.x-50)
align:#center
fn checkTextObject =
(
if $text01 == undefined then
(
txtObj = text text:”“ name:”text01”
addModifier txtObj (extrude amount:10)
txtObj.wirecolor = red
)
else ( txtObj = $text01 )
)
on rWebpage open do ( checkTextObject() )
on ax TitleChange txt do
(
checkTextObject()
if not (matchPattern txt pattern:”http:”) then
(
if txtObj.text != text then
(
print txt
txtObj.text = txt
max tool zoomextents all
)
)
)
)
fWebPage = newRolloutFloater “Web page” rWebpage.vpsz.x rWebpage.vpsz.y
addRollout rWebPage fWebPage
registerViewWindow fWebPage
showProperties rWebpage.ax
What’s New in 3ds max 4 MAXScript 17
(
accelState.text = if (enableAccelerators) then “Enabled” else “Disabled”
accelState.checked = enableAccelerators
)
on accelState changed state do
(
enableAccelerators = state
accelState.text = if (enableAccelerators) then “Enabled” else “Disabled”
)
)
nf = newRolloutFloater ““ 100 100
addRollout rAccelState nf
)
on rFlash open do
(
axFlash.movie = “e:\\Movie1.swf”
axFlash.movie = “e:\\Movie1.swf” -- need to load 2nd time sometimes
checkTextObject();
)
)
flashFloater = newRolloutFloater “Shockwave Flash Object” 350 300 10 10
addRollout rFlash flashFloater
or:
ax.listItems[1].text = “foo”
.description property
on any activeX control returns a description string of the format
<TypeLib name> (TypeLib info) ? <Help file name if any> - <help context id>
MAXScript sample
rollout controlR92 “Microsoft ListView Control, version 6.0”
(
activeXControl ax “{BDD1F04B-858B-11D1-B16A-00C0F0283628}” height:200 width:300
align:#left
--on ax Click do format “handler: Click\n”
--on ax DblClick do format “handler: DblClick\n”
on controlR92 open do
(
showProperties ax
ax.MousePointer = #ccArrow
ax.GridLines = true
ax.AllowColumnReorder = true
ax.BorderStyle = #ccFixedSingle
ax.view = #lvwReport
chs = ax.columnHeaders
--showProperties chs
--showMethods chs
hTargets = chs.Add()
What’s New in 3ds max 4 MAXScript 21
hWeights = chs.Add()
hTargets.text = “Node”
hWeights.text = “Weights”
lis = ax.listItems
for i=0 to 10 do
(
local li
li = lis.Add()
li.text = “Item “ + i as string
)
for li in ax.listItems do li.bold = true
li = ax.HitTest 100 1500
if li != undefined do
(
showProperties li
li.text = “Just Hit Tested”
showEvents controlR92.ax
showMethods controlR92.ax
)
)
)
nr92 = newRolloutFloater “Microsoft ListView Control, version 6.0” 350 300 10 10
addRollout ControlR92 nr92
See Also
i-drop - drag and drop (p. 62)
Visual MAXScript (p. 117)
MAXScript Dialogs and Rollout Floaters as Extended viewports (p. 186)
22 Chapter 1 | What’s New in 3ds max 4 MAXScript
Asset Browser
Asset Browser enhancements
Topic: version 4 MAXScript New Features/Asset Browser
The Asset Browser provides access from your desktop to design content on the World Wide Web.
From within the program you can browse the Internet for texture samples and product models. This
includes bitmap textures (BMP, JPG, GIF, TIF, and TGA), or geometry files (MAX, DWG, and so on).
You can drag these samples and models into your scene for immediate visualization and
presentation. You can use the CTRL key to drag geometry into predefined locations. You can also use
the Asset Browser to browse thumbnail displays of bitmap textures and geometry files on your hard
disk or shared network drives. Then you can either view them or drag them into your sceneor into
valid map buttons or slots.
• Several special new icons are now used in Thumbnail view to represent script files (.ms, .mcr,
.mse), dropScripts (.ds), and script zip packages (.mzp).
• Now viewing or double-clicking script source files (.ms, .mcr, .ds) will open them in a MAXScript
editor window, ready for editing and evaluation. You can also double-click .mzp script zip
package files to open them in WinZip or some other zip utility if the type .mzp has been
associated with that utility.
• Executable script files (.ms, .mcr, .mse, .mzp) now have a Run... menu item available in the
right-click menu on their thumbnail icons in the thumbnail view, allowing you to launch them
directly from within the asset browser.
• The home page for web views is now <max-directory>\web\maxindex.html.
Properties:
assetBrowser.open ()
Return Value:
Opens the asset browser if it is not already open.
Properties:
assetBrowser.gotoURL <URL_string>
Parameters:
<URL_string>
Opens the given URL in the asset browser.
Remarks:
This can be a web URL or a local or network disc directory path name.
See Also
Interface: browserMgr (p. 355)
i-drop - drag and drop (p. 62)
Zip-file Script Packages (p. 122)
Access to the node bone properties and methods 23
Bones
Note:
Changing the state of this check box will not have an immediate visual effect on the skeleton. It
only affects future behavior when bones are moved. This option is only available if Bone is off.
<node>.boneFreezeLength
boolean
When turned on, the bone maintains its length. When turned off, the bone’s length is based on
the translation of its child bone. This option is available only if Auto-Align is on.
<node>.boneScaleType
one of #scale, #squash, or #none
None: No stretch takes place.
Scale: Lets the bone scale. The stretch happens along one axis.
Squash: Lets the bone squash. The bone gets fatter as it gets shorter, and thinner as it gets
longer.
<node>.stretchTM
matrix3, read-only
The new methods are:
Prototype:
<node>.setBoneEnable <onOff_boolean> <initial-time_time>
Remarks:
Sets the Bone enable on or off.
24 Chapter 1 | What’s New in 3ds max 4 MAXScript
Parameters:
<onOff boolean>
When turned on, the bone or object behaves as a bone. Turning this option off causes
the node to stop behaving like a bone. There is no auto alignment or stretching. Note
that turning this option on will not cause the object to immediately align or stretch.
However future translations of children may cause rotation and stretching.
Default=on for bone objects, off for other kinds of objects.
<initial-time time>
Specifies the time at which to calculate and store initial child position. This is usually
user with the current time slider position. The time associated with the time slider can
be queried and set using the sliderTime global variable. Time Control (p. 1580)
Note:
A very good macroscript example to review, which uses .setBoneEnable, can be found at
..\ui\macroscripts\Macro_Bones.mcr.
Prototype:
<node>.realignBoneToChild ()
Remarks:
When turned on, the bone or object behaves as a bone. Turning this option off causes the node to
stop behaving like a bone. There is no auto alignment or stretching. Note that turning this option
on will not cause the object to immediately align or stretch. However future translations of children
may cause rotation and stretching. Default=on for bone objects, off for other kinds of objects.
Prototype:
<node>.resetBoneStretch ()
Remarks:
Resets the initial child position used to compute the stretch factor to the current child position. This
will cause the stretch factor to become equal to one. If it was previously not equal to one then the
object would snap to its original unstretched state.
See Also
Node Common Properties, Operators, and Methods (p. 820)
Bone Creation (p. 25)
Bone : Helper (p. 978)
Skin : Modifier (p. 1157)
Bones : System (p. 991)
Interface: BoneSys (p. 354)
Bone Creation 25
Bone Creation
Topic: version 4 MAXScript New Features/Bones
Interface: BoneSys (p. 354)
There is a function published interface to create bone links.
Prototype:
BoneSys.createBone <startPosition> <endPosition> <zAxis>
Parameters:
<startPosition>
The location of the new bone as point3
<endPosition>
The direction (X axis) of the bone and the bone length as point3
<zAxis>
The direction of the Z axis for the new bone node as point3
Return Value:
It returns the new bone node that was created.
Note:
If the Z axis is not perpendicular to the X axis, the Z axis will be made perpendicular. To create a
bone chain, call createBone repeatedly with the startPosition set to the value of the previous
endPosition. Note that newly created bones are not linked to any parent. So to create a bone chain,
the script would also need to link each newly created bone segment to the previous.
See Also
Bones : System (p. 991)
Core Interfaces (p. 70)
Node Common Properties, Operators, and Methods (p. 820)
Bone Creation (p. 25)
Bone : Helper (p. 978)
Skin : Modifier (p. 1157)
Access to the new node bone properties and methods (p. 23) Bones_System
26 Chapter 1 | What’s New in 3ds max 4 MAXScript
Cache Modifiers
Point Cache Modifier
Topic: version 4 MAXScript New Features/Cache Modifiers/Point Cache Modifier
Point Cache - superclass: modifier (p. 314)
This is a simple point caching system. It lets you store modifier animation to a disk file that records
only changes in vertex positions, and then play back the animation using the information in the
disk file instead of the modifier keyframes. It caches the points of an object across time and then
reads them from the disk on play back. It is useful when you have large intricate stacks that you want
to speed up or modifiers such as flex that you want to bake.
This modifier sacrifices memory for speed, it stores three caches of the points to allow for fast reading
from the disk. You can instance this modifier but the instances must have the same number of
points, otherwise the results will be inconsistent. This also only record point position it does not
store mapping, topology changes etc. It also cannot deal with animated topology changes.
Four MAXScript interface methods have been exposed to allow pressing the Record, Set Cache,
EnableMods, and DisableMods buttons.
Methods
Prototype:
<void>record()
Remarks:
Stores the vertex animation to a disk file. Call Record to activate the Save Points dialog, which lets
you specify a path and file name for the cache file. Click OK to record the file, and then load it into
the Point Cache modifier, ready for playback.
Prototype:
<void>setCache()
Remarks:
Loads a vertex animation from a cache file on disk into the Point Cache modifier. If number of
vertices in the cache file does not match the number of vertices in the object, a warning appears, but
no error occurs.
Prototype:
<void>enableMods()
Remarks:
Turns on all stack modifiers below the Point Cache modifier. Use this when you want to change
modifier settings.
Notify Callbacks for Animate button on and off Transitions 27
Prototype:
<void>disableMods()
Remarks:
Turns off all the object’s stack modifiers below Point Cache so that only the cached vertex animation
appears when you play back the animation.
Note:
The WSM is identical to the local space version except it records points in World Space and exist
higher in the stack.
See Also
PointCache interfaces: (p. 486)
PointCache - superclass: modifier (p. 316)
See Also
General Event Callback Mechanism (p. 29)
28 Chapter 1 | What’s New in 3ds max 4 MAXScript
The first argument is the bitmap value to be modified by the effect, and progressCB is a progress
callback interface object. This interface has several methods you can call during the course of
processing the bitmap that control the progress bar and check for user cancellation.
Methods
progressCB.setTitle <string>
Sets the title on the progress bar.
progressCB.progress <done> <total>
Indicates the progress of the rendering. Both arguments are integers; done indicates how
much of the rendering has been completed, and total indicates how much there is
to do.
When this is called, the main render effects progress bar is updated to reflect this progress.
This function also returns a boolean, which if true indicates that the user has hit the
escape key to cancel the effect rendering.
progressCB.check()
Indicates whether the user has hit the escape key to cancel the effect rendering. This
function returns a boolean; false if processing should continue, and true if the user has
cancelled the rendering.
Example:
on apply bm progressCB: do
(
…
progressCB.setTitle “My Effect Pass1”
…
escapeEnable = false -- turn on scripter escape processing
for i in …
(
<the effect rendering loop>
…
if progressCB.progress completed total then exit
)
…
escapeEnable = true
…
)
The progress bar update is done inside the main processing loop and the check for user cancel is
done on the same call, causing the loop to exit prematurely in this example.
General Event Callback Mechanism 29
See Also
RenderEffect : MAXWrapper (p. 1347)
Scripted RenderEffect Plug-ins (p. 1566)
Render Effects Common Properties, Operators, and Methods (p. 1347)
For example:
callbacks.addScript #preRender “setUpRenderGeom()” \
id:#jbwRender
registers a new callback script that will be called just before a render is performed. The
script invokes a function (that has presumably already been set up). An unique ID has
been assigned to the script for later selective removal.
callbacks.removeScripts [ <callback_type_name> ] [ id:<name> ]
This method is used to unregister and remove one or more callback scripts. Specifying
just a callback event type name removes all the callback scripts for that event.
Specifying just an id:<name> removes all callback scripts in all events with that ID.
Specifying both limits the ID-based removal to the specified event type.
callbacks.show ()
This method lists out the current callback scripts in the Listener window.
callbacks.broadcastCallback <callback_type_name>
This method provides a way for you to simulate one of the events and have all the
callback scripts for it executed. Within 3ds max, the #preRenderFrame and
#preRenderFrame callbacks can only be called by the renderer. These callbacks can
not be called by using this method.
The following is a list of valid callback event type names:
#unitsChange
Sent if the user changes the unit setting.
#timeunitsChange
Sent if the user changes the time format setting.
#viewportChange
Sent if the user changes the viewport layout.
#spacemodeChange
Sent if the user changes the reference coordinate system.
#modPanelSelChanged
Sent whenever the Modify panel opens on a new selection, either because the Modify
panel was just selected or because a new selection is made in the scene. The notify occurs
at a point just prior to panel redraw but after the selection has been established, so that
callback functions can modify the panel state without it being overwritten.
System Notifications
#systemPreReset
Sent before 3ds max is reset.
#systemPostReset
Sent after 3ds max is reset.
#postSystemStartup
Sent when the software goes live.
#pluginLoa\ded
Sent whenever a plug-in is loaded.
General Event Callback Mechanism 31
#systemPreNew
Sent just before 3ds max is reset.
#systemPostNew
Sent just after 3ds max is reset.
#preSystemShutdown
Sent just before the software enters the shutdown process.
#postSystemShutdown
Sent just before the software finishes the shutdown process.
#colorChanged
Sent when the system is updating it’s custom colors.
File Notifications
#filePreOpen
Sent before a new file is opened.
#filePostOpen
Sent after a new file is opened successfully.
#filePreMerge
Sent before a file is merged.
#filePostMerge
Sent after a file is merged successfully.
#filePreSave
Sent before a file is saved.
#filePostSave
Sent after a file is saved.
Renderer Notifications
#preRender
Sent before rendering is started. This notification is sent out before the renderer creates the
render instance objects, which means that you can create nodes and other objects as a
response to this event. When rendering multiple frames, this event is sent only once at the
beginning of the rendering phase, and not on a per-frame basis. In the #preRender
callback, you can’t change any of the render parameters (height, width, aliasing, etc) and
effect the current render sessions. Those parameters have already been set up internally in
3ds max, and so changes to them won’t occur until the next render session occurs.
#postRender
Sent after rendering has finished. This notification is sent out after the renderer destroys
the render instance objects, which means that you can create nodes and other objects as a
response to this event. When rendering multiple frames, this event is sent only once at the
end of the rendering phase, and not on a per-frame basis.
#preRenderEval
Sent just before the renderer starts evaluating objects.
32 Chapter 1 | What’s New in 3ds max 4 MAXScript
#preRenderFrame
Sent just before each frame is rendered by the renderer. This notification is sent out after
the renderer has taken a snapshot of the scene geometry. At the time of this call the scene
cannot be modified. The renderer has already called GetRenderMesh() on all the object
instances, and the materials and lights are already updated. If you don’t modify anything
that is rendered, then it is okay to use this callback. The current frame being rendered is set
into the MAXScript currentTime context and system global, so any references to other
scene object properties will automatically be resolved at the currently rendering frame’s
time. This notification is not sent out when the renderer is called to update the Material
Editor sample spheres, only during output rendering.
#postRenderFrame
Sent just after each frame is rendered by the renderer. The current frame being rendered is
set into the MAXScript currentTime context and system global, so any references to other
scene object properties will automatically be resolved at the currently rendering frame’s
time. This notification is not sent out when the renderer is called to update the Material
Editor sample spheres, only during output rendering.
#renderParamsChanged
Sent whenever the common renderer parameters have changed.
Import/Export Notifications
#preImport
Sent before a file is imported.
#postImport
Sent after a file is imported successfully.
#importFailed
Sent if import fails.
#preExport
Sent before a file is exported.
#postExport
Sent after a file is exported successfully.
#exportFailed
Sent if export fails.
#nodeFreeze
Sent when a node is frozen.
#nodeUnfreeze
Sent when a node is unfrozen.
#nodeLinked
Sent when a new parent-child link is made.
#nodeUnlinked
Sent when a parent-child link is broken.
#nodePreMaterial
Sent just before a node gets a new material
#nodePostMaterial
Sent just after a node gets a new material
#sceneNodeAdded
Sent just after a node is added to the scene.
#selNodesPreDelete
Sent just before selected nodes are deleted.
#selNodesPostDelete
Sent just after selected nodes are deleted.
#nodeMaterialChanged
Sent after the material is changed for the selected nodes.
#nodeWSCacheUpdated
Sent whenever the modifier stack display is reevaluated.
VIZ-Only Notifications
#heightMenuChanged
Sent when a user operated the height menu.
#fileLinkPreBind
Sent just before a file link bind.
#fileLinkPostBind
Sent just after a file link bind.
#fileLinkPreDetach
Sent just before a file link detach.
#fileLinkPostDetach
Sent just after a file link detach.
#fileLinkPreReload
Sent just before a file link reload.
#fileLinkPostReload
Sent just after a file link reload.
#fileLinkPreAttach
Sent just before a file link attach.
#fileLinkPostAttach
Sent just after a file link attach.
Other Notifications
#wmEnable
Sent when main window gets an wm_enable (BOOL enabled).
#selectionSetChanged
Sent after the selection set has changed.
#bitmapChanged
Sent after a bitmap is reloaded.
General Event Callback Mechanism 35
Color Manager
Topic: version 4 MAXScript New Features/Color Manager
There is a Function Published interface in MAXScript called “colorMan (p. 356)” that exports the
color manager interface.
All colors are represented as Point3 values of the form [red, green,blue], where each value runs from
0.0 to 1.0.
colorMan.useStandardWindowsColors()
Returns true if the standard windows colors are used and false if custom colors are used.
colorMan.setUseStandardWindowsColors onOff
Sets the value of “useStandardWindowsColors”. Passing in “true” tells the system to use
the standard windows colors, and false tells the system to use the custom colors.
colorMan.registerColor color name category defaultColor
This registers a new color with the system. This adds a color to the color manager database
that is then accessible from the color customization UI.
Example:
colorMan.registerColor #myNewColor “My Own Color” “Ugly Colors” [1,0,0]
This registers a new color, with the name #myNewColor, with a default value of red.
The category in the customization UI will be “Ugly Colors” and the name will be “My
Own Color”.
In other scripts you can access this color using:
colorMan.getColor #myNewColor
Note:
colorMan.registerColor should be called from a script in the “.\stdplugs\stdscripts” folder. These
scripts are run when MAX starts, so the color will be available in the customization UI immediately.
If the user customizes this color, its value will be saved in the MaxColors.clr file.
colorMan.loadColorFile()
This method will load the specified color file from the current UI directory.
colorMan.saveColorFile()
This brings up the file save dialog and lets the user save a new color file.
colorMan.setColor color colorValue
This sets the value of the given color to the given value. Besides the colors that you register
using registerColor, there is a set of built-in colors that you can set and get:
#background -- The background for all controls and buttons
#text -- The text for all controls and buttons
#activeCommand -- The color command mode buttons turn when pressed
#hilight -- The hilight color for 3d controls
#shadow -- The shadow color for 3d controls
#window -- The background color for edit boxes, list boxes and other
windows
#activeCaption --
#appWorkspace --
36 Chapter 1 | What’s New in 3ds max 4 MAXScript
These two are currently unused, but would be used if a 3rd party developer uses the
Windows colors in C++ code:
GetCustSysColor(COLOR_APPWORKSPACE)
or:
GetCustSysColor(COLOR_ACTIVECAPTION)
These were put in for completeness with the windows API.
#toolTipBackground -- The background for viewport tool tips
#toolTipText -- The text color for viewport tool tips
#hilightText -- The hilight color in the stack view drop-down list
#windowText -- The color used in edit boxes, list boxes and other windows
#itemHilight -- Used as the highlight color on the stack-view drop down list
of modifiers.
#subObjectColor -- The color used to hilight sub-object levels in StackView
#3dDarkShadow -- the dark shadow color on 3d controls
#3dLight -- the light color on 3d controls
#trackbarBg -- trackbar background
#trackbarBgSel -- trackbar background for selected keys
#trackbarText -- trackbar text
#trackbarTicks -- trackbar ticks
#trackbarKeys -- trackbar keys
#trackbarSelKeys -- track bar selected keys
#trackbarCursor -- track bar cursor
#pressedButton -- background color for pressed buttons, like the transform
constraints
#timeSliderBg -- The background for the time slider bar.
#viewportBorder -- The viewport border color
#activeViewportBorder -- The active viewport border color
#rollupTitleFace -- Rollout title background
#rollupTitleText -- rollout title text
#rollupTitleHilight-- rollout title 3d highlight
#rollupTitleShadow -- rollout title 3d shadow
#selectionRubberBand -- the selection marquee color
#stackViewSelection -- the color of a selected item in stack view
colorMan.getColor color
Gets the value of the given color.
colorMan.getName color
Gets the name of the given color.
colorMan.getCategory color
Gets the category of the given color.
colorMan.getIconColorScale type which
Gets the value of the icon image processing value.
type enums: {#disabledIcon|#enabledIcon}
which enums: {#saturationScale|#valueScale|#alphaScale}
Returns a floating point value (in the range 0.0f to 1.0f) that is one of the scale factors
applied to the specified icon type. These scale values used to do image processing on the
icons at start-up time.
General Event Callback Mechanism 37
Here is a macroScript that turns the time slider and trackbar backgrounds blue:
Example:
macroScript BlueBar
category: “Color”
tooltip: “Blue Bar”
(
on execute do
(
colorMan.setColor #timeSliderBg [0, 0, .6]
colorMan.repaintUI #repaintTimeBar
colorMan.setColor #trackbarBg [0, 0, .6]
colorMan.repaintUI #repaintTrackBar
)
)
MAXScript calls that let you load, save and query color files.
colorMan.loadColorFile “MyColors.clr”
Loads the given color file from the current UI directory.
Returns true if it succeeds, and false otherwise.
colorMan.saveColorFIle “MyColors.clr”
Saves the current color scheme into the named file in the current UI directory.
Returns true if it succeeds, and false otherwise.
colorMan.getColorFile()
Returns the full path to the current color file.
38 Chapter 1 | What’s New in 3ds max 4 MAXScript
Example:
To set the selected object color to red, you would use:
SetUIColor 0 red
colorMan.repaintUI #repaintall
See Also
Interface: colorMan (p. 356)
3ds max User Interface Colors (p. 1604)
Combustion
Topic: version 4 MAXScript New Features/Combustion
With the Combustion map, you can create maps interactively using the Discreet combustion
product and 3ds max at the same time. You use combustion software to paint on a bitmap, and the
material updates automatically in the 3ds max Material Editor and in shaded viewports.
Important: The combustion map works only if Discreet combustion is installed on your system.
You can use combustion as a material map in 3ds max. With a Combustion map, you can create a
material from a Paint or composite operator, and in turn apply that material to objects in a 3ds max
scene. The Combustion map can include combustion effects, and it can be animated.
In addition, with combustion you can import 3ds max scenes that have been rendered to a rich pixel
file (RPF or RLA file). The imported rich pixel rendering becomes an element of your composite. You
can adjust its 3D position relative to video elements of the composite, and you can apply
combustion 3D Post effects to objects within it. See the combustion User’s Guide for more information.
Note: Because 3ds max runs only on Windows, you cannot use combustion to create material maps
on a Macintosh.
Note: The environmental atmospheric effect known as “Combustion” in versions prior to 3ds max 4
is now known as the Fire effect.
A Combustion map is a 2D map (p. 274). It is a combustion project used by the 3ds max Material
Editor, so like any combustion project, it is vector-based, animatable, and fully editable. From within
the Material Editor, you can have combustion create a new project from scratch, or use an existing
composite or Paint branch. You can synchronize the combustion Timeline with the 3ds max time
slider so animated materials synchronize with your 3D scene.
A macroScript has been added that gets called by the render management system to output render
element info to the combustion(tm) .cws file format.
../UI/MacroScripts/Macro_CombustionOutput.mcr
Associated files include:
RenderElements-fns.ms
CombustionExport-fns.ms
CombustionExport.ini
Path Constraint 39
Example:
C = combustion()
See Also
Combustion.coordinates - superclass: MAXObject (p. 274)
Render Element Manager (p. 92)
Material Common Properties, Operators, and Methods (p. 1203)
Constraints
Path Constraint
Topic: version 4 MAXScript New Features/Constraints
Path Constraint - superclass: PositionController (p. 307)
Path Constraint interfaces: (p. 468)
A path constraint restricts an objects movement along a spline or at an averaged distance between
multiple splines.
See Also
path interfaces: (p. 462)
LookAt Constraint (p. 40)
Orientation Constraint Controller (p. 40)
Link Controller for Constraints (p. 42)
Controller Functions for use with Constraint Assignments (p. 42)
40 Chapter 1 | What’s New in 3ds max 4 MAXScript
LookAt Constraint
Topic: version 4 MAXScript New Features/Constraints
LookAt Constraint - superclass: RotationController (p. 297)
LookAt Constraint interfaces: (p. 455)
Look-At Constraint constrains an object’s orientation so that it’s always looking at another object.
Note:
The old Look At Controller, which is a full transform controller, will be invisible to the user unless
an old file is loaded. The new LookAt Constraint Controller is a rotation controller and NOT a TM
controller which the old LookAt was. The old LookAt will be phased out.
At this time, old LookAt.IsPublic returns zero, so that the users won’t see the old LookAt. However,
the old MAX files will still load the old LookAt and the camera and the light will continue to use the
old LookAt.
See Also
Path Constraint (p. 39)
Position Constraint (p. 41)
Orientation Constraint Controller (p. 40)
Link Controller for Constraints (p. 42)
Controller Functions for use with Constraint Assignments (p. 42)
See Also
Path Constraint (p. 39)
Position Constraint (p. 41)
LookAt Constraint (p. 40)
Link Controller for Constraints (p. 42)
Controller Functions for use with Constraint Assignments (p. 42)
Position Constraint
Topic: version 4 MAXScript New Features/Constraints
Position Constraint - superclass: PositionController (p. 320)
Position Constraint interfaces: (p. 488)
A position constraint causes an object to follow the position of an object or the averaged position
of several objects.
In order to activate, a position constraint requires an object and a target object. Once assigned the
object becomes constrained to the target objects position. Animating the target’s position causes the
constrained object to follow
Each target has a weight value defining its influence. A value of 0 is equal to off. Any value greater
than 0 will cause the target to influence the constrained object. Weight values may be animated to
create effects such a ball being picked up from a table.
Multiple targets can be used to influence a constrained object. When using multiple targets, each
target’s weight value defines how much it influences the constrained object. For example if a sphere
is Position constrained between 2 targets and each target’s weight value is 100. Then the sphere will
maintain an equal distance between both targets even when they are in motion. If one of the weight
values is 0 and the other is 50, then the Sphere is only influenced by the target with the higher value.
Example:
posCtrl = Position_Constraint()
posConstraintInterface = posCtrl.constraints
appendNode <node>
Adds a node to the node list with a default weight of 50
appendWeightedNode <node> <weight>
Adds a node to the node list with the specified weight
getNode <index>
Returns the node specified by the index. Index is a 1 based array
setNode <node> <index>
Replaces the node with the given index with a new node
getWeight <index> <time>
Returns the weight at the time for the node specified by the index.
setWeight <weight> <index> <time>
Sets the weight for the node specified by the index at the given time.
42 Chapter 1 | What’s New in 3ds max 4 MAXScript
Use:
posConstraintInterface.appendNode $box01
posConstraintInterface.appendWeightedNode $box02 200
node1 = posConstraintInterface.getNode 1
posConstraintInterface.setNode $box03 2
weight = posConstraintInterface.getWeight 1 50
posConstraintInterface.setWeight 250 1 0
See Also
Path Constraint (p. 39)
LookAt Constraint (p. 40)
Orientation Constraint Controller (p. 40)
Link Controller for Constraints (p. 42) Controller Functions for use with Constraint Assignments (p. 42)
See Also
Path Constraint (p. 39)
LookAt Constraint (p. 40)
Position Constraint (p. 41)
Orientation Constraint Controller (p. 40)
Link Controller for Constraints (p. 42)
Controller Functions for use with Constraint Assignments (p. 42)
Prototype:
AddListController OBJ Trans ListType
Remarks:
Checks to see if a list controller is assigned. If not, it will assign to the designated Trans using the
ListType, This way it can be used for all list controllers.
Controller Functions for use with Constraint Assignments 43
Example:
Foo = Selection as array
AddListController “Foo[1]” “Pos” “Position_List”
Prototype:
AddConstraint OBJ Trans Constraint List
Prototype:
SetActiveController OBJ Trans Controller
Prototype:
AddConstraintTargets OBJ Trans Array Target
See Also
Path Constraint (p. 39)
LookAt Constraint (p. 40)
Position Constraint (p. 41)
Orientation Constraint Controller (p. 40)
Context Filters
Topic: version 4 MAXScript New Features/Context Filters
Filter functions for context sensitive menus:
Use this for .IsEnabled or .IsVisible handlers in macrocripts. isEnabled and isChecked handlers have
been added to many of the existingmacroScripts. All of the modifier, creation and polygon toolbox
macroScripts have these two handlers.
These handlers allow object creation CUI buttons to turn green while creating objects, and modifier
buttons are only enabled if they apply to the current selection. The polygon toolbox buttons also
only enable when applicable, and the selection level buttons stay pressed while in the sub-object
level.
This structure is defined in .\stdplugs\stdscripts\FilterFunctions.ms.
An example use of the filter functions can be found in the Selection and Display Callbacks Script
File, .\stdplugs\stdscripts\Selection_Display_Filters.ms
#Struct:Filters(
Is_EditMesh:<fn>,
Is_NURBS:<fn>,
Is_EditPoly:<fn>,
Is_EditPatch:<fn>,
Is_EditSpline:<fn>,
Is_MeshSelect:<fn>,
Is_PolySelect:<fn>,
Is_SplineSelect:<fn>,
Is_PatchSelect:<fn>,
Is_PosXYZ:<fn>,
Is_RotationXYZ:<fn>,
44 Chapter 1 | What’s New in 3ds max 4 MAXScript
Is_ScaleXYZ:<fn>,
is_Child:<fn>,
This is used for the new IK assignments.
is_Parent:<fn>,
This is used for the new IK assignments.
CanSwitchTo_XXXX for SubObject levels
CanSwitchTo_Vertex:<fn>,
CanSwitchTo_Edge:<fn>,
CanSwitchTo_Face:<fn>,
CanSwitchTo_Polygon:<fn>,
CanSwitchTo_Element:<fn>,
CanSwitchTo_Border:<fn>,
CanSwitchTo_Patch:<fn>,
CanSwitchTo_Segment:<fn>,
CanSwitchTo_Spline:<fn>,
Return Value:
They return true if the selected object’s function name condition is met.
See Also
Macro Scripts (p. 1624)
Defining Macro Scripts (p. 1521)
macros const StructDef (p. 239)
Scripted Custom Attributes 45
Custom Attributes
Note:
You cannot use Custom Attributes for per-face-data. The face-data channels store objects of a user
defined type and the scripter cannot create objects of types other than those known by MAXScript.
The new syntax has the following form:
attributes <varname>
[version:n]
[silentErrors:t/f]
[initialRollupState:0xnnnnn]
(
<locals>
<globals>
<parameters>
<rollouts>
<handlers>
)
Remarks:
The name is now simply a descriptive name for the definition and can be either a <name> or a
<string>.
Example:
attributes “Game Data”
(
...
)
or
attributes gameData
(
...
)
46 Chapter 1 | What’s New in 3ds max 4 MAXScript
The attribute header keyword parameters and main clauses are basically identical to the same
keyword parameters and clauses in Scripted Plug-ins (p. 1538). The ‘custom attributes’ are effectively
the parameters defined in any parameter clauses in the body of the attributes definition. The UI for
them is defined by the rollout clauses, which will be automatically displayed in the Command Panel
and Material Editor when an object containing custom attributes is selected.
Example:
attributes weaponData
(
parameters main rollout:params
(
hitPoints type:#float ui:hits default:10
cost type:#float ui:cost default:100
sound type:#string
)
Remarks:
This defines three new attributes, say for weapon objects in a game level editor set up. The attributes,
hitPoints, cost and sound, are defined as parameters and the UI for them in a rollout.
Note:
The auto-UI connection between the parameters and rollout items via the ui and keyword is the
same as the support in Scripted Plug-ins (p. 1538). You can treat attribute scripting as basically
identical to scripting plug-ins, in terms of parameter, rollout setup and handler programming.
Remarks:
Adds a set of attributes to an object or a collection. You can only add one custom attribute set of a
particular attributes definition to an object, but you can have as many different attribute sets from
different definitions as needed.
Parameters:
#unique
Scripted Custom Attributes 47
When adding custom attributes to an object using the custAttributes.add() function, you
can now supply an optional #unique keyword as the third argument. If you do this, each
object being added to will have custom attributes added that have their own private copy
of the definition and do *not* share the original definition. Any later redefinitions of the
original attributes definition will not update these custom attributes. To update the
individual object’s attributes, you would get the unique definition from the object using
custAttributes.getDef, and redefine it in one of the two ways described.
Note:
If you extract the uniquely-added definition, and use it directly in another non-unique
custAttributes.add() on some other object, a definition sharing will be set up. Using #unique
when adding a global definition will make the added custom attributes non-global, they will
have their own private definition which starts out being identical to the original global
definition.
Example:
custAttributes.add $weapon01 weaponData
Opening $weapon01 in the Modify panel will now display the “Weapon Parameters”
rollout and allow them to be edited as can normal object parameters. You can use
attribute definitions to add their defined sets of attributes to any object at any time.
Any appropriate type of parameter can be animated, also, exactly as with scripted
plug-ins.
The custAttributes.add() function can be applied to an object collection to add sets of attributes to
a group of objects in one go.
Example:
custAttributes.add $weapon* weaponData
Adds a separate set of these custom attributes to all objects whose names begin
“weapon” in the scene.
Note:
Further, an object can have any number of separate sets of custom attributes added from different
attribute definitions.
As with Scripted plug-ins (p. 1538), an attributes definition can have any number of sets of parameter
and rollout clauses, to allow you to organize added attributes into multiple rollouts as needed.
Scripted custom attributes added to an object or modifier can be accessed in MAXScript. They turn
up directly as properties on the objects they are added to. If the names of any of the custom
attributes are the same as existing properties on the host object, the custom attributes are
effectively hidden when accessed directly. As an alternative, you can access each added block
of custom attributes by their attributes definition name and then access individual
attributes as properties within that block.
48 Chapter 1 | What’s New in 3ds max 4 MAXScript
• scripted custom attributes are properly saved to and loaded from scene files.
• you can assign a fixed, global definition ID to an attributes definition.
This acts in a similar way to class IDs in scripted plug-ins. Such definitions are global across
any number of scenes that custom attributes may be present in and all instances of custom
attributes of a global definition will have the same shape. The ID is specified with a new
header parameter, ‘attribID:’
attributes <name>
attribID:#(<number>, <number>)
(
...
)
Remarks:
The ID number pair is chosen to be unique, perhaps generated with the genClassID (p. 141) ()
function in MAXScript. Attribute definitions without attribID’s are private to the current MAX
session.
genClassID()
This method generates a random class ID similar to #(0x9b7ea231, 0xb6db86ef), and prints it
to Listener. You can just cut and paste this class ID into your script to use the generated ID.
Scripted Custom Attributes 49
This example adds a separate set of the defined custom attributes to box01 and box02. The
definition is shared between the two boxes. Now this is a private definition, it has no attribID:, so if
you evaluated the ‘def = attributes (...)’ again, it would *not* automatically update box01’s and
box02’s attributes, as used to happen in prior builds, but create a new definition. In order to redefine
a specific attribute definition so that all objects will be updated that had attributes added using it,
you use one of two schemes that operate on the actual definition value (as it sits in the ‘def’ variable
in the above, for example). First, you can use the new ‘redefine:’ attributes definition parameter.
Example:
attributes “Game Data”
redefine:def
(
parameters ...
rollout ...
)
This expects an existing attributes definition as the value given in the redefine: parameter and will
update it to the definition that follows, and update any custom attributes made from that particular
definition value. In the example, this would update $box01 and $box02.
Alternatively, you can use the new custAttributes.redefine method:
custAttributes.redefine <def> <definition_string>
50 Chapter 1 | What’s New in 3ds max 4 MAXScript
Example:
local new_def = “attributes \“Game Data\“ ( ... )”
custAttributes.redefine def new_def
This is particularly useful in situations where you are generating the attributes definition
automatically as a string. You can use this function to compile and apply the redefinition to a
particular definition object in one go, without having to construct a name for the object, as you
would if you used the redefine: parameter scheme.
To redefine the attributes on some object, say based on the defData in that object’s custom attributes,
you might use this sequence:
old_def = custAttributes.getDef $box03 1 -- get existing def
old_def_data = custAttributes.getDefData old_def -- get my defData from it
new_def_string = generate_new_def old_def_data ... -- make new def string
custAttributes.redefine old_def new_def_string -- redefine it
These redefinition techniques can be used with global definitions (with explicit attribID:), but are
strictly unnecessary since the particular definition value is specified uniquely by the attribID:
parameter. In any situation that you evaluate a global definition, all custom attributes in the current
scene made from that definition will be updated.
Note:
The custom attribute set values, returned by the custAttributes. are effectively holder
values for the object’s custom parameters in that attribute set. You can get at these
parameter values as simple properties on the attribute set value.
Example:
gp = custAttributes.get $ gameParams
gp.hitPoints = 50
this is equivalent to accessing the custom attribute parameters directly on the object:
$.gameParams.hitPoints = 50
Return Values:
Returns an array containing a runtime readable encoding of all of the parameter block
definitions in the custAttributes definition. in the following form:
#(<paramblock>, <paramblock2>, ...)
52 Chapter 1 | What’s New in 3ds max 4 MAXScript
Parameters:
<paramblock>
An array of details for one parameter block in this form:
#(<name>, <id>, <refno>, <keyword_params>, <parameter1>, <parameter2>,
<parameter3>, ....)
<id>
The parameter block’s internal ID number
<refno>
The reference number of the parameter block in the owning plug-in instance
<keyword_params>
An array of the keyword parameters given on the parameter block definition in
the form:
#(<keyword>, <value>, <keyword2_name>, <value2>, ...)
<Parameter1 to ParameterN
Definition details for each parameter in the block in the following form:
#(<param_name> <keyword_params>)
<keyword_params>
An array containing all of the keyword parameters specified on that parameter’s
definition in the cust attrib definition, in the same form as the
<keyword_params> above.
Example:
Here is a function that will extract pBlock data from a custom attribute.
mapped fn custAttribute_showPBlockDefs obj =
(
format “%\n” obj.name
for objDef in (custAttributes.getDefs obj) do
(
format “\t%\n” objDef
format “\tname: %\n” objDef.name
format “\tattribute id: %\n” objDef.attribID
format “\tParameter Blocks:”
pbArray = custAttributes.getPBlockDefs objdef
for a = 1 to pbArray.count do
(
itms = pbArray[a]
format “\n\t\tname = %\n” itms[1]
format “\t\tid = %\n” itms[2]
format “\t\towners reference number = %\n” itms[3]
keywordParams = itms[4]
format “\t\tparameter block keywords:\n”
for x = 1 to keywordParams.Count/2 do
(
format “\t\t\t% = %\n” keywordParams[x] keywordParams[x+1]
x = x+1
)
format “\t\tparameters:”
Scripted Custom Attributes 53
for y = 5 to itms.Count do
(
format “\n\t\t\t#name = %\n” itms[y][1]
for z = 1 to itms[y][2].Count by 2 do
(
format “\t\t\t% = %\n” itms[y][2][z] itms[y][2][z+1]
)
)
)
)
)
custAttributes.getSceneDefs ()
Returns an array of all the attribute definitions in the current scene.
custAttributes.deleteDef <attrib_def>
Deletes the given attribute definiton from the current scene and the current running MAX
session. There must be no objects in the scene containing custom attributes added using this
definition.
Note:
Its name can be gotten via the .name property.
Note:
Typing CAT_Debug = True in the MAXScript listener window will expose the code in the listener
when you add a custom attribute through the User Interface.
See Also
custAttributes const StructDef (p. 234)
54 Chapter 1 | What’s New in 3ds max 4 MAXScript
Depth of Field
Topic: version 4 MAXScript New Features/
Depth of field is available for any renderer plug-in via a published function publishing interface. No
ui has been added. Functionality can be tested by enabling various parameters via MAXScript, and
performing a normal render.
The settable dof parameters can be seen by typing ‘apropos “dof”’ in the MAXScript listener window
or here (p. 234).
To create a DOF display in a camera viewport, simply call
maxops.DisplayActiveCameraViewWithMultiPassEffect
Note that if the active view is not a camera view, or if DOF is not turned on in the camera’s
properties, then this call does nothing. Additionally, note that this method works with general
multi-pass effects and not just DOF.
See Also
DOF const StructDef (p. 234)
Depth of Field : RenderEffect (p. 1354)
Interface: maxOps (p. 368)
Edit Mesh
ApplyOperation function
Topic: version 4 MAXScript New Features/Edit Mesh
The ApplyOperation function is used by the Quad menu for activating object functions.
fn ApplyOperation ctype oper =
(
If (Modpanel.getcurrentObject () == $.baseobject) then oper $
If Classof (Modpanel.getcurrentObject ()) == ctype then
(oper $.modifiers[modPanel.getModifierIndex $
Modpanel.getcurrentObject))])
)
Example:
ApplyOperation Edit_Mesh meshops.StartExtrude
Remarks:
Starts the extrude function on EditMesh if it is either the currently selected modifier or baseobject.
Patches 55
See Also
Quad Menu (p. 90)
MAXScriptFunction List (p. 190)
Editable Patch
Patches
Topic: version 4 MAXScript New Features/Editable Patch
There is a patch function package containing a large number of functions for creating, modifying
and accessing patch objects. The sub-object selection system in MAXScript has also been extended
to cover patch objects.
• The Editable Patch object in MAX was called ‘Patch’ in MAXScript. It has been renamed to
‘Editable_Patch’ to be consistent with Editable_Mesh and Editable_Poly, and to allow the new
patch function package to be named ‘patch’.
• The MAXScript sub-object selection system has been extended to work with Editable Patch
objects. This means that all the MAXScript VertexSelection, FaceSelection, and EdgeSelection
properties and operations now work with patch objects. The ‘face’ sub-object selections in this
system correspond to the ‘patch’ sub-object level when applied to patches.
• The Patch functions. All the functions in this package take either a scene node containing an
Editable Patch object or an Editable Patch base object as the first argument. QuadPatch and
TriPatch objects need to be converted to Editable Patches for the Patch functions to be
applicable. For example, when using the convertTo $foo Editable_Patch.
• To create a patch object from scratch, create an Editable_Patch scene object to create an empty
patch object and use the geometry & topology creations functions below to fill the patch out,
then use the patch.update() function to complete construction.
Note:
Any set of changes to a patch object using the following functions do not fully take effect until the
patch.update() function is called on it. This makes construction substantially more efficient, but can
leave a patch in an unstable state if the script that contains the changing code finishes before calling
patch.update on it, which may result in a MAX crash.
Functions:
The following functions are used to get and set the overall geometry of the patch. Supply keep:true
to the setNumXXX functions for them to retain existing vertex/vector/patch/edge data, defaults to
false, which cleans out the geometry.
The functions are largely direct calls to the methods of the same name on the MAX SDK class
PatchMesh. See the SDK Help file Advanced Topic “Working with Patches,” and the documentation
for the main Patch system classes for more detailed info.
56 Chapter 1 | What’s New in 3ds max 4 MAXScript
The following functions get and set individual vertex and vector handle locations.
The vertex and vector coordinates are interpreted in MAXScript’s current working coordinate
context.
Consistent with the rest of MAXScript, all vertex/patch/vector/edge indexes start numbering at 1.
<point3> patch.getVert <obj> <index>
patch.setVert <obj> <index> <point3>
<point3> patch.getVec <obj> <index>
patch.setVec <obj> <index> <point3>
The following two functions are the main mechanism for creating individual patches in the
patch mesh.
patch.makeQuadPatch <obj> <index> <va> <vab> <vba> <vb> <vbc> <vcb> <vc> <vcd>
<vdc> <vd> <vda> <vad> <i1> <i2> <i3> <i4> <sm>
where:
index = The index of the patch to create (0> = index < numPatches).
va = The first vertex.
vab = Vector ab.
vba = Vector ba.
vb = The second vertex.
vbc = Vector bc.
vcb = Vector cb.
vc = The third vertex.
vcd = Vector cd.
vdc = Vector dc.
vd = The fourth vertex.
vda = Vector da.
vad = Vector ad.
i1 = Interior 1.
i2 = Interior 2.
i3 = Interior 3.
i4 = Interior 4.
sm = The smoothing group mask
patch.makeTriPatch <obj> <index> <va> <vab> <vba> <vb> <vbc> <vcb> <vc> <vca> <vac>
<i1> <i2> <i3> <sm>
Patches 57
where:
index = The index of the patch to create (0> = index < numPatches).
va = The first vertex.
vab = Vector ab.
vba = Vector ba.
vb = The second vertex.
vbc = Vector bc.
vcb = Vector cb.
vc = The third vertex.
vca = Vector ca.
vac = Vector ac.
i1 = Interior 1.
i2 = Interior 2.
i3 = Interior 3.
sm = The smoothing group mask
The following function forces all the geometry and topology caches to be rebuilt, change
notifications to be sent and a screen redraw request to be flagged.
You must call this function after making any changes to a path object before exiting the script
making the changes otherwise and invalid patch may bepassed to MAX possibly causing a crash. The
patch.update() function is similar in function and purpose to the update() function in mesh object
scripting.
patch.update <obj>
The following functions give access to the topology of an existing patch object. They return either
indexes or arrays of indexes of the sub-objects requested.
Example:
getVertVecs() returns an array of the vectors coming out of the specified vertex.
<integer_array> patch.getVertVecs <obj> <index>
<integer_array> patch.getVertPatches <obj> <index>
<integer_array> patch.getVertEdges <obj> <index>
<integer> patch.getVecVert <obj> <index>
<integer_array> patch.getVecPatches <obj> <index>
<integer> patch.getEdgeVert1 <obj> <index>
<integer> patch.getEdgeVert2 <obj> <index>
<integer> patch.getEdgeVec12 <obj> <index>
<integer> patch.getEdgeVec21 <obj> <index>
The following functions access and manipulate the texture mapping information in the
patch object.
patch.setNumMaps <obj> <num> [keep:<bool>]
<integer> patch.getNumMaps <obj>
patch.setMapSupport <obj> <map_chan> [init:<boolean>]
<boolean> patch.getMapSupport <obj> <map_chan>
patch.maxMapChannels <obj>
patch.setNumMapVerts <obj> <map_chan> <num> [keep:<boolean>]
<integer> patch.getNumMapVerts <obj> <map_index>
58 Chapter 1 | What’s New in 3ds max 4 MAXScript
The following functions get and set the material ID for the patch object as a whole or for individual
patches.
<integer> patch.getMtlID <obj>
patch.setMtlID <obj> <mtl_id>
<integer> patch.getPatchMtlID <obj> <index>
patch.setPatchMtlID <obj> <patch_index> <mtl_id>
The following functions access and control viewport and renderer tessellation and visibility.
patch.setMeshSteps <obj> <steps>
patch.getMeshSteps <obj>
patch.setMeshStepsRender <obj> <steps>
patch.getMeshStepsRender <obj>
patch.setShowInterior <obj> <bool>
patch.getShowInterior <obj>
patch.setAdaptive <obj> <bool>
patch.getAdaptive <obj>
The following functions access topology info for the specified sub-object.
<integer_array> patch.getEdges <obj> <v1> [<v2>]
<integer_array> patch.getPatches <obj> <v1> [<v2>]
<integer_array> patch.getVectors <obj> <vert>
The following function transforms all the vertices and vectors in the patch object by the given
matrix. This transform happens in object local space.
patch.transform <obj> <matrix3>
The following functions get and manipulate surface normal information. Again, normal vectors are
given in MAXScript’s current working coordinate context.
patch.patchNormal <obj> <patch>
patch.edgeNormal <obj> <edge>
patch.updatePatchNormals <obj>
class id filter 59
The following functions access and change the vertex and interior vertex types:
patch.changeVertType <obj> <vert> #corner|#coplanar
patch.getVertType <obj> <vert> -> #corner or #coplanar
patch.changePatchInteriorType <obj> <patch> #automatic|#manual
patch.getPatchInteriorType <obj> <patch> -> #automatic or #manual
The following function returns the current mesh tessellation for the patch object:
<mesh value> patch.getMesh <obj>
The following functions are used to interpolate individual patch surfaces. A tri-patch interpolation
takes u,v,w barycentric coordinates. A quad-patch takes u and c parameters. In both cases, the point
returns is given in the current MAXScript working coordinate context.
<point3> patch.interpTriPatch <obj> <patch> <u> <v> <w>
<point3> patch.interpQuadPatch <obj> <patch> <u> <v>
See Also
patch const StructDef (p. 245)
patchOps const StructDef (p. 247)
Patch Select - superclass: modifier (p. 307)
Patch : GeometryClass (p. 1088)
Filters
class id filter
Topic: version 4 MAXScript New Features/Filters
In the Selection filters/combos filter you can, in addition to registering super classid filters, add
class id filters. The bottom left list box displays a list of all helper and geom class ids. To add a
filter select one and hit the add button below the list box. It will then appear in the lower right list
box. This list displays all of the current class id filters. Once OK is pressed then the select filter drop
down contains those class ids that were added.
You can also register filters through a callback in MAXScript.
fn selectfilter_cb node =
(
print currentTime
true
)
registerSelectFilterCallback selectfilter_cb “MAXScript”
60 Chapter 1 | What’s New in 3ds max 4 MAXScript
The above example filter prints out the current time and filters nothing. The selectfilter_cb will
return TRUE if the node is to be selectable else false.
Prototype:
registerSelectFilterCallback <filterFunction> <name>
Parameters:
<filterFunction>
The filter function
<name>
The string which appears in the filter drop down list
Remarks:
The registerSelectFilterCallback takes 2 parameters. The filter function expects one parameter, which
is the node to be checked.
Prototype:
unregisterSelectFilterCallback <filterFunction>
Parameters:
<filterFunction>
The filter function
Remarks:
There is also an unregisterSelectFilterCallback which removes the callback.
Example:
unregisterSelectFilterCallback selectfilter_cb
See Also
Selection Filter (p. 61)
Main Toolbar (p. 1574)
toolMode const StructDef (p. 257)
Selection Filter 61
Selection Filter
Topic: version 4 MAXScript Language Improvements/User Interface
The Selection Filter list lets you restrict to specific types and combinations of objects that can be
selected by the selection tools. For example, if Cameras is selected, you can select only cameras with
the selection tools. Other objects do not respond.
Prototype:
<int>GetSelectFilter
Return Value:
Returns your current selected select filter in the toolbar.
Prototype:
<void >SetSelectFilter <int_index>
<int_index>
The index of the display filter that you want to check.
Return Value:
Sets your current select filter in the toolbar.
Prototype:
<int >GetNumberSelectFilters
Return Value:
Returns the number select filters in the drop down.
Prototype:
<BOOL>GetDisplayFilter <int_index>
Parameters:
<int_index>
The index of the display filter that you want to check.
Return Value:
Returns whether a display filter is on or not in the display panel.
Prototype:
<void>SetDisplayFilter <int_index> <bool_on>
Parameters:
<int_index>
The index of the display filter that you want to check.
<bool_on>
The state that you want to set the display filter to.
62 Chapter 1 | What’s New in 3ds max 4 MAXScript
Remarks:
Sets the state of a display filter.
Prototype:
<int>GetNumberDisplayFilters
Return Value:
Returns the number of display filters in the display panel.
Prototype:
<string>GetSelectFilterName <int_index>
Parameters:
<int_index>
The index of the display filter that you want to check.
Return Value:
These just return the name that appears in the interface for the appropriate filter.
Prototype:
<string>GetDisplayFilterName <int_index>
Parameters:
<int_index>
The index of the display filter that you want to check.
Return Value:
These just return the name that appears in the interface for the appropriate filter.
See Also
class id filter (p. 59)
Main Toolbar (p. 1574)
toolMode const StructDef (p. 257)
HTML:
<!doctype html public “-//w3c//dtd html 4.0 transitional//en”>
<html>
<head>
<meta http-equiv=”Content-Type” content=”text/html; charset=iso-8859-1”>
<meta name=”Author” content=”Your Name”>
<meta name=”GENERATOR” content=”Mozilla/4.7 [en] (WinNT; U) [Netscape]”>
<title>example</title>
</head>
<body>
Here is an i-drop activeX control ....
<p>
<object name=”idrop” width=”64” height=”80” classid=”clsid:AF2880B4-B183-11D2-
ADE7-00A0245D8F3F”>
<param name=”package” value=”file:///G:/iDrop/example.xml”>
</object>
</body>
</html>
The XML package file:
<?xml version=”1.0”?>
<package xmlns=”x-schema:http://vizdevel/idrop/idrop-schema.xml”>
<proxy defaultsrc=”file:///G:/iDrop/blob.gif”>
<caption>i-Drop it!</caption>
<img src=”file:///G:/iDrop/blob.gif”/>
</proxy>
<dataset>
<datasrc clipformat=”CF_IDROP.MAX”>
<datafile src=”file:///G:/iDrop/foo.max”/>
</datasrc>
</dataset>
</package>
Drag-and-Drop Manager
Interface: dragAndDrop (p. 362)
A new type of datasrc file in an i-drop XML file can be specified that contains a macroScript with
drag-and-drop handlers that will be run when you drag and drop the i-drop control onto a MAX
viewport. These new kinds of files are called ‘drop scripts’ and have the suffix .ds. Such files
should contain a single macroScript definition with handlers for one or more of the special
dropscript events. If there is more than just a single macroScript in the .ds file, all other text is
ignored.
Here is a sample XML specifying a dropScript file called “foo.ds”:
<?xml version=”1.0”?>
<package xmlns=”x-schema:http://vizdevel/idrop/idrop-schema.xml”>
<proxy defaultsrc=”file:///G:/iDrop/blob.gif”>
<caption>i-Drop Script!</caption>
<img src=”file:///G:/iDrop/blob.gif”/>
</proxy>
64 Chapter 1 | What’s New in 3ds max 4 MAXScript
<dataset>
<datasrc clipformat=”CF_IDROP.MAX”>
<datafile src=”file:///G:/iDrop/foo.ds”/>
</datasrc>
</dataset>
</package>
dropScript Events
The current dropScript events are delivered as a mixture of positional and keyword parameters. The
first parameter is positional and is always the code name for the window on which the drop is
currently occurring. Subsequent parameters are keyword parameters that vary in name and number
depending on the window being currently dragged over or dropped on.
on droppable <window> node: point: do ...
on drop <window> node: point: do ...
Parameters:
<window>
a window identifier
node:
any item (scene node) currently under the mouse pointer
point:
Remarks:
If supplied, the ‘droppable‘ handler is called continuously while the i-drop control is dragged over
the MAX viewport, and should return true or false depending on whether the item is droppable at
that position. If the mouse is not over a scene node, the <item> argument value is undefined. You
implement the ‘droppable’ filter if the dropScript wants to limit droppability in any way.
The ‘drop’ handler is called when the user finally drops the i-drop control over a viewport and is
given the same parameters as ‘droppable’.
For example, currently for viewport windows, the full signatures are:
on droppable window node: point: do ...
on drop window node: point: do ...
but since keyword arguments are optional, you can choose any subset of the keyword arguments you
need, such as:
on drop window node: do ...
or:
on drop window do ...
Remarks:
Passing by keyword like this allows different context windows to supply a variable and large range
of context info without requiring an unwieldy and fixed set of positional args.
Selection Filter 65
Example:
Here is a sample ‘foo.ds’ file.
macroScript foo
(
on droppable window item return
window == #viewport and
item != undefined and
classOf item == sphere
Example Remarks:
The droppable handle only allows dropping when the mouse is over a sphere scene node. When
dropped, that sphere will be scaled up by 1.2 and be assigned the material currently in slot 1 in the
material editor.
Note:
Dropping .max scene file anywhere onto the MAX UI outside viewport will automatically perform
a scene open.
Remarks:
Note the use of the newly-added ‘showInViewport’ property on materials.
From an i-drop, the .mzp file is first downloaded to the <max>\downloads directory, along with any
other files specified in the i-drop XML file, overwriting any files currently there. If the .mzp file is
the first file in the i-drop file set, it is the prime dropped file and the following .mzp processing
continues. The .mzp file is then extracted to a new temp directory, in the system’s main TEMP
directory, and the mzp.run control file is run. If there is no mzp.run file in the package, the first
file in the .mzp package is dropped, causing whatever drop protocol is appropriate for that file type.
If supplied, a typical mzp.run control file will contain extract to, move and copy commands
to control the disposition of the files extracted from the package, say placing any texture files in
$maps & scene files in $scenes, etc.
During this execution of the mzp.run file after initial load, all copies and moves are performed, and
a ‘drop’ command is looked for. The file specified on the drop command is remembered for later
drop processing. Any ‘run’ commands are ignored.
At this point, the drop file is known, either because it was supplied on a ‘drop’ command in the
mzp.run file or because it is the first file in the .mzp package if there was no mzp.run file or drop
command. If the drop file is anything other than .ds dropScript file, the drop protocol
appropriate to that file is engaged. If it is a .ds dropScript, and the drop is from an i-drop, any
‘on droppable’ handler in the dropscript is repeatedly run as the mouse is moved off MAX’s
windows, and the cursor changes to show valid drop targets. If the drag-and-drop is from a file
directory, the arrow+ cursor shows, but the ‘on droppable’ handler is NOT called. This is a
consequence of the limitations of simple file drag-and-drop in Windows. When the mouse-click is
released, the ‘on droppable’ handler is called on the target window and object and if it returns
OK or is not supplied, the ‘on drop’ handler is called. This protocol is identical to dropping .ds
dropScript files directly, as if they were not inside a .mzp package.
Note:
You can specify a file type other than a dropScript on the ‘drop’ command, such as an image or scene
file. This allows the .mzp drag-and-drop to be used for dropping any kind of package, not just scripts.
See Also
Interface: dragAndDrop (p. 362)
Zip-file Script Packages (p. 122)
Interfaces
Topic: version 4 MAXScript New Features/Interfaces
The Function Publishing System, new to 3ds max version 4, is a system that allows plug-ins to
publish their major functions and operations in such a way that code outside the plug-in can
discover and make inquiries about these functions and is thus able to call them though a common
calling mechanism. The whole system is very similar to Window’s COM and OLE Automation
systems and share many similar concepts in the architecture. However, the Function Publishing
System is not based on COM and OLE but instead is a custom architecture more suited and
optimized for MAX. The Function Publishing API serves a number of purposes, which allow 3rd
68 Chapter 1 | What’s New in 3ds max 4 MAXScript
party developers to open up important portions of their plug-ins for use by external sources,
allowing for users to extend and control these directly.
Note:
For complete details on the Function Publishing System, please see the 3ds max sdk help file topic
“Function Publishing System”.
Interfaces
Core Interfaces (p. 70)
Other Interfaces (p. 71)
Functions are published in one or more Interfaces by a plug-in. Action functions must be published
in their own set of interfaces. Each interface is represented by an instance of a class derived from the
base class FPInterface. An external system can find out about the interfaces published by calling
various query methods on ClassDesc that access these interface definition objects. As well as these
enquiry or ‘reflection’ methods, an FPInterface also has the calling methods for actually invoking a
particular function in the interface, so that if something has hold of one of your interfaces, it can
call any of its published functions.
Action Interfaces
Action Manager (p. 9)
A special kind of interface is the Action Interface. These interfaces only contain UI Action Functions
that provide a programmatic way of “pressing” buttons and keys in the UI for a plug-in.
This is true for all the types of FP interfaces that turn up in MAXScript, static, mixin and core. As a
further optimization, MAXScript now effectively promotes all interface methods and properties to
the level of the interface, so if individual methods and properties have unique names within all the
interfaces of an object or class, you can elide the interface name. The above examples could now be
written
Example:
r = $cyl01.getRadius()
$cyl01.setRadius 23
Selection Filter 69
and:
r = $cyl01.radius
$cyl01.radius = 23
If there is a naming conflict, you can always include the interface name level to resolve this.
Associated Method:
getCoreInterfaces()
Returns an array of core interface values.
See Also
Core Interfaces (p. 70)
Other Interfaces (p. 71)
By Reference Parameter Passing (p. 129)
Dereferencing Operator (p. 133)
Visible Class For ‘&’ Reference Values (p. 142)
Action Manager (p. 9)
Class and Object Inspector Functions Enhanced (p. 159)
Class and Object Inspector Functions (p. 799)
70 Chapter 1 | What’s New in 3ds max 4 MAXScript
Core Interfaces
Topic: version 4 MAXScript New Features/Interfaces
Interfaces (p. 67)
actionMan (p. 353)
BoneSys (p. 354)
browserMgr (p. 355)
cmdPanel (p. 356)
colorMan (p. 356)
dragAndDrop (p. 362)
HDIKSys (p. 365)
IKSys (p. 365)
manip (p. 366)
maxOps (p. 368)
medit (p. 371)
menuMan (p. 372)
msZip (p. 378)
netrender (p. 379)
NullInterface (p. 409)
objXRefs (p. 409)
paramWire (p. 410)
pluginManager (p. 414)
quadMenuSettings (p. 414)
rollup (p. 427)
SceneExposureControl (p. 427)
SceneRadiosity (p. 428)
timeSlider (p. 428)
trackviews (p. 429)
See Also
Other Interfaces (p. 71)
Class and Object Inspector Functions (p. 799)
Class and Object Inspector Functions Enhanced (p. 159)
Other Interfaces 71
Other Interfaces
Topic: version 4 MAXScript New Features/Interfaces
Interfaces (p. 67)
bitmapTex (p. 434)
Block Control (p. 435)
BMP (p. 437)
Flex interfaces: (p. 438)
float list (p. 441)
Float Reactor (p. 443)
Float Wire interfaces: (p. 448)
FloatList (p. 450)
FloatReactor (p. 452)
HSDS Modifier (p. 453)
HSDS Object (p. 453)
IKChainControl (p. 453)
imageMotionBlur (p. 454)
JPEG (p. 454)
Link (p. 455)
Link Constraint (p. 455)
LookAt Constraint (p. 455)
Motion Blur (p. 462)
Orientation Constraint (p. 462)
Path (p. 462)
Path Constraint (p. 468)
Plugin Manager (p. 473)
Portable Network Graphics (p. 473)
Point3 list (p. 475)
Point3 Reactor (p. 477)
Point3 Wire (p. 477)
Point3List (p. 479)
Point3Reactor (p. 481)
Point3Spring (p. 482)
Point Cache (p. 484)
Point CacheSpacewarpModifier (p. 485)
72 Chapter 1 | What’s New in 3ds max 4 MAXScript
See Also
Core Interfaces (p. 70)
Class and Object Inspector Functions (p. 799)
Class and Object Inspector Functions Enhanced (p. 159)
Inverse Kinematics
Prototype:
HDIKSys.ikChain <startJoint> <endJoint> <assignEE>
Parameters
<startJoint>
The first node in the new chain, called the ancestor.
<endJoint>
The last node in the chain, called the decendent.
<assignEE>
A boolean parameter: when TRUE, a position end effector is created at the endJoint.
Example:
If 4 boxes existed in the scene and Box02 was a child of Box01, Box03 was a child of Box02, and
Box04 was a child of Box03:
HDIKSys.ikChain $Box01 $Box04 TRUE
would assign HD IK controllers and create an end effector at Box04.
Note:
Both IKControl and IKChainControl can not be instanced.
See Also
IKChainControl interfaces: (p. 453)
Interface: HDIKSys (p. 365)
Interface: IKSys (p. 365)
IKLimb Solver (p. 74)
IKLimb Solver
Topic: version 4 MAXScript New Features/IK
The IK Limb Solver is specifically meant for animating the limbs of human characters; for example,
the hip to the ankle, or the shoulder to the wrist. It affects only two bones in a chain. It is an
analytical solver that is very fast and accurate in viewports.
Note: To use with the IK Limb solver, a bones system must have three bones in the chain. The goal
is placed at the pivot point of the third bone, and the IK solution is calculated for the first and second
bones.
The IK Limb solver works not only with bone hierarchies, but with any linked hierarchy that has
three elements, and is set up to model a human limb. The additional requirements are:
• The first joint is “spherical.” That is, it has 3 degrees of freedom.
• The second joint is “revolute.” That is, it has 1 degree of freedom.
If you attempt to put an IK Limb solver on an inappropriate chain, a warning message informs you
that your IK Limb solver assignment has no effect.
The IK Limb solver uses the same controls as the HI IK solver, so it follows the model of setting
preference angles for joints, and allows for mixing periods of forward and inverse kinematics in the
same animation period. It does not use the HD IK Solver methods of damping, precedence, and
setting joint limits.
The IK Limb solver is provided as part of the Discreet Open Source initiative, so it can be exported
directly to a game engine.
The joint angles are obtained by computing the transformation (rotation) between the initial
chain plane and the target chain plane. The initial chain plane is defined by three unit vectors:
1. shoulder-to-elbow unit vector (at the initial pose)
2. projection of end-effector-axis on a plane perpendicular to the shoulder-to-elbow unit vector
(at the initial pose)
3. cross product of the above two.
Similarly, the target plane is defined by three analogous vectors at the target pose.
IKLimb Solver 75
See Also
Interface: IKSys (p. 365)
Interface: HDIKSys (p. 365)
HD IK controller chains can be assigned to existing hierarchies (p. 73)
IKChainControl interfaces: (p. 453)
Materials
Multi/Sub Material
Topic: version 4 MAXScript New Features/Material/Multi/Sub Material
Each entry in the Multi/Sub matl interface now has an associated ID. The previous version had the
ID being the same as the number of the sub-material in the list.
This can be seen here: MultiMaterial : Material (p. 1210)
Menu Manager
Topic: version 4 MAXScript New Features/Menu Manager
MAXScript has full access to the menu manager and menu creation system.
Note:
Be very careful when using or testing this API. It makes permanent changes to the menu database,
and it is very easy to mess things up quite badly. For example, if you “unRegister” the main menu
bar, 3ds max won’t start.
Anyone using this API should make a copy of the “..\UI\MaxMenus.mnu” file before running any
of the scripts. If anything messes up, just copy the backup version back on to MaxMenu.mnu.
There are 4 exposed interfaces to MAXScript: the menu manager, menu objects, quad menu objects
and menu items.
• The menu manager is a database of menus and quad menus.
• The main menubar and all sub-menus are menu objects.
• A quad menu object holds 4 menu objects, one for each quad.
• A menu object is a container for menu items.
• A menu item can be a separator, an action that invokes a macroScript or a sub-menu that pops
up a cascading menu.
Menu Manager
menuMan.loadMenuFile “file.mnu”
This loads a new menu file with the given name. It looks in the current “UI” directory for
the file. It return true if successful, and false if not.
menuMan.saveMenuFile “file.mnu”
This saves a new menu file with the given name. It saves it in the current “UI” directory.
76 Chapter 1 | What’s New in 3ds max 4 MAXScript
menuMan.getMenuFile()
Returns the full path to the current menu file.
menuMan.updateMenuBar()
This updates the main menu bar with any changes that have been made. This MUST be
called after changing anything on the main menu bar.
menuMan.registerMenuContext contextId
This call is used to register menu extensions. The “contextId” is a random 32-bit integer. It
can be generated using the “genclassid()” (p. 141). This function registers an extension with
the menu manager that is remembered permanently. It returns true the first time the
extension is registered, and false every time thereafter. This is saved in the MaxMenu.mnu
file, so it is sticky from session to session. This is used so that scripts can add items and
sub-menus MAX’s main menu bar and quad menus. See the sample scripts below for the
proper usage.
menuMan.findMenu “menuName”
This function returns the menu with the given name. It returns “undefined” if no menu
exists in the menu manager with the given name. This requires the full name of the menu,
including and “&” characters that might be in the name.
Example:
helpMenu = menuMan.findMenu “&Help”
Retrieve 3ds max’s help menu.
menuMan.findQuadMenu “qhadMenuName”
This works like “findMenu” but it gets quad menus instead of menus.
menuMan.unRegisterMenu menu
This removes a menu from the menu manager. Use extreme caution with this method! If
you unregister a menu that is used as a sub-menu, or in a quad menu, or the main menu
bar, bad things will result.
menuMan.unRegisterQuadMenu quadMenu
This is like “unregisterMenu” but for quad menus.
menuMan.createMenu “name”
This creates a new, empty menu with the given name.
menuMan.createQuadMenu “name” “quad1Name” “quad2Name” “quad3Name” “quad4Name”
This creates a new, empty quad menu. It contains, 4 empty menus, one for each quad.
menuMan.createSubMenuItem “name” subMenu
This creates a new sub-menu item that can be added to a menu. It uses the given “name”
and it displays the given sub-menu.
menuMan.createSeparatorItem()
This creates a new menu separator that can be added to a menu.
menuMan.createActionItem “macroScriptName” “macroScriptCategory”
This creates a new menu item that can be added to a menu. The item is an action that
executes the macro script with the given name and category. This returns “undefined” if
there is no macroScript with the given name and category.
IKLimb Solver 77
Example:
menuMan.setViewportRightClickMenu #nonePressed “Modeling 2”
That sets the default (no keys pressed) quad menu to “Modeling 2”. The menu name must be a
quad menu that is listed in the “Quads” customization dialog, and the name must match
exactly, including capitalization.
menuMan.SetViewportRightClickMenu returns FALSE if you try to set the viewport right-click
menu to a menu that is not allowed.
menuMan.getViewportRightClickMenu which
Retrieves the quad menu used for right-clicking in the viewport. The “which” parameter
can be one of the following:
#nonePressed
#shiftPressed
#altPressed
#controlPressed
#shiftAndAltPressed
#shiftAndControlPressed
#controlAndAltPressed
#shiftAndAltAndControlPressed
menuMan.getMainMenuBar()
Returns the menu being used as MAX’s main menu bar.
menuMan.setMainMenuBar menu
Sets the menu being used as MAX’s main menu bar. You must call
“menuMan.updateMenuBar()” in order to see the result.
menuMan.getShowAllQuads quadMenu
Gets the “show all quads” setting for the given quad menu.
menuMan.setShowAllQuads quadMenu value
This sets the “show all quads” flag for the given quad menu. “Value” can be true or false.
menuMan.getQuadMenuName quadMenu
This returns the name of the given quad menu.
menuMan.setQuadMenuName quadMenu “name”
This sets the name of the give quad menu.
78 Chapter 1 | What’s New in 3ds max 4 MAXScript
menuMan.numMenus()
Returns the total number of menus in registered with the menu manager.
menuMan.getMenu index
Retrieves the “index” th menu in the menu manager. This is a 1-based index.
menuMan.numQuadMenus()
Returns the total number of quad menus registered with the menu manager.
menuMan.getQuadMenu index
Retrieves the “index” th quad menu in the menu manager. This is a 1-based index.
Menu Objects
Menus are containers for menu items, and have the following functions:
menu.setTitle “title”
Sets the title of the menu to the give string.
menu.getTitle()
Returns the current title of the menu.
menu.numItems()
Returns the number of items the menu holds.
menu.getItem index
Retrieves the menu item at the given index. The index is 0-based.
menu.addItem menuItem position
This inserts an item in the menu at the given position, which is 0-based. If the position is
-1, then the item is appended to the end of the menu.
menu.removeItemByPosition position
This removes the item at the given position.
menu.removeItem menuItem
This removes the given item from the menu, if it is in the menu.
IKLimb Solver 79
Example:
-- This example adds a new entry to MAX’s main “Help” menu.
-- Register a menu context. This returns true the first time it
-- is registered, and we can add things to the menu. If
-- it returns false, then the context is already registered,
-- and the items are already in the menu.
-- The number 0x246c6dbe is random, and can be generated
-- using the genClassID() function (p. 141).
80 Chapter 1 | What’s New in 3ds max 4 MAXScript
Example:
-- This example adds a new command to MAX’s default right-click quad menu
if menuMan.registerMenuContext 0x36690115 then
(
-- Get the default viewport right-click quad menu
local quadMenu = menuMan.getViewportRightClickMenu #nonePressed
-- Get the lower-left menu from the quad
local menu = quadMenu.getMenu 3
-- create a menu item that calls the sample macroScript
local testItem = menuMan.createActionItem “MyTest” “Menu Test”
-- Add the item to the menu
menu.addItem testItem -1
)
Example:
Here are two macroScripts that set and reset two of the right-click menus:
macroScript SetQuads
category:”Custom UI”
tooltip:”Set Quad”
(
on execute do
(
quadmenu = menuMan.findQuadMenu “Modeling 2”
if quadmenu != undefined do menuMan.setViewportRightClickMenu
#nonePressed quadmenu
quadmenu = menuMan.findQuadMenu “Sample 4x1”
menuMan.setViewportRightClickMenu #controlPressed quadmenu
)
)
macroScript ResetQuads
category:”Custom UI”
tooltip:”Reset Quads”
(
on execute do
(
quadmenu = menuMan.findQuadMenu “Default Viewport Quad”
if quadmenu != undefined do menuMan.setViewportRightClickMenu
#nonePressed quadmenu
quadmenu = menuMan.findQuadMenu “Modeling 1 [Cntrl+RMB]”
if quadmenu != undefined do menuMan.setViewportRightClickMenu
#controlPressed quadmenu
)
)
82 Chapter 1 | What’s New in 3ds max 4 MAXScript
The menu name must be a quad menu that is listed in the “Quads” customization dialog,
and the name must match exactly, including capitalization.
See Also
Quad Menu (p. 90)
Menu and CUI Loading (p. 178)
maxOps (p. 87)
Interface: quadMenuSettings (p. 414)
Interface: menuMan (p. 372)
Interface: maxOps (p. 368)
Mesher
Topic: version 4 MAXScript New Features/Mesher
The Mesher compound object converts procedural objects to mesh objects on a per-frame basis so
that you can apply modifiers such as Bend or UVW Map. It can be used with any type of object, but
is designed primarily to work with particle systems. Mesher is also useful for low-overhead
instancing of objects with complex modifier stacks.
See Also
Mesher - superclass: GeometryClass (p. 298)
particleMesher - superclass: GeometryClass (p. 306)
Note:
For additional details regarding network rendering, please see the topic “Network Rendering” in
the 3ds max online reference.
See Also
3D Studio MAX System Globals (p. 630)
IKLimb Solver 83
Node Handles
Topic: version 4 MAXScript New Features/Node Handles
A property has been added to a node’s interface called .handle. This can be used to get the unique
node handle ID from the node.
Usage:
id = $Box01.handle-- returns the unique id associated with the node
A method in the maxOps interface (p. 368) will return a node associated with a given handle.
Usage:
node = maxOps.getNodeByHandle <number>-- returns the node associated with the id passed in.
Note:
It is safer to say $box01.inode.handle than $box01.handle. This is to prevent cases where the
baseobject has property called handle, like a teapot, and you get that object’s handle instead of the
node handle.
See Also
maxOps (p. 87)
Node vertexColorType
Topic: version 4 MAXScript New Features/Node vertexColorType
In the node interface, the vertexColorType property has been changed to take a symbolic enum. This
is the assigned vertex color displayed in viewports.
.vertexColorType : enum : Read|Write
vertexColorType enums: {#color|#illum|#alpha|#color_plus_illum}
Example:
$Sphere01.vertexColorType = #illum
See Also
Node : MAXWrapper (p. 820)
Node Common Properties, Operators, and Methods (p. 820)
Node Handles (p. 83)
Class and Object Inspector Functions Enhanced (p. 159)
Access to the node bone properties and methods (p. 23)
84 Chapter 1 | What’s New in 3ds max 4 MAXScript
OLE Automation
See Also
Setting Up MAXScript OLE Automation (p. 1673)
OLE Automation (p. 1671)
Running the OLE Demo (p. 1674)
Exposing MAXScript Functions (p. 1673)
3ds max Specific Errors (p. 1674)
MAXScript.reg - Registery file 85
Parameter Wiring
Topic: version 4 MAXScript New Features/Parameter Wiring
The Parameter Wire manager is described in the core interface ‘paramWire’.
In the general case, a wire controller can be wired to any number of other wire controllers in
two-way relationships. Each wire has a set of information that defines it, accessible using the
indexed accessor functions.
Example:
The following will demonstrate a way to query a wire controller and determine what parameters
it is referencing.
local wc = $foo.pos.controller -- get pos controller
if classOf wc == WirePosition then
(
-- list out its connections
for i in 1 to wc.numWires do
(
local parent = wc.getWireParent i,
parent_owner = (refs.dependents parent)[1], -- hack!
param_name = getSubAnimName parent wc.getWireSubnum
format “wire %: % in %\n” i param_name parent_owner
)
)
Additionally, you can use the subAnim indexing operator as a way to scan down through an
object for wire controllers:
for i in 1 to $foo.numSubs do
if classOf $foo[i].controller == ...
Also, you might also find the exprForMAXObject() (p. 809) method useful here to get a scripter
expression for the parent or parent owner.
See Also
Interface: paramWire (p. 410)
Float Wire interfaces: (p. 448)
Position Wire interfaces: (p. 492)
Rotation Wire interfaces: (p. 508)
Scale Wire interfaces: (p. 515)
86 Chapter 1 | What’s New in 3ds max 4 MAXScript
Plug-In Manager
Topic: version 4 MAXScript New Features/Plug In Manager
The Plug-in Manager lets you manage plug-ins dynamically without any initialization required. The
Plug-in Manager provides a list of all plug-ins found in the 3ds max plug-in directories, including
the plug-in description, type (object, helper, modifier, and so on), status (loaded or deferred), size,
and path. The Plug-in Manager provides options to load or tag as deferred, any particular plug-in,
regardless where they reside on disk.
When you start the Plug-in Manager, it scans through all the plug-in paths specified in the plug-in.ini
file and lists them in the Plug-in Manager dialog.
Actually there are two different FP interfaces in the plug-in manager, one is a action interface
accessed through Plug-in_manager and the other one is a static interface called plug-inManager.
You can access the static interface like
plug-inManager.show = true
or:
plug-inManager.loadClass Flex
Currently there is no way to integrate these into one so.
Properties:
plug-inManager.visible = true --show
plug-inManager.visible = false –hide
Remarks:
Show and hide the plug-in manager.
maxOps 87
Prototype:
plug-inManager.loadClass <class>
Remarks:
Will ensure that the given class is loaded, in the event that it is a deferred loading class, and so any
MAXScript methods or Function Published interfaces it publishes will be available.
Example:
plug-inManager.loadClass Flex
After this code is executed, all the Flex modifier MAXScript methods are installed and callable.
Note this is only needed in situations where a plug-in loading may be deferred and it does not
have any instances already in the current scene.
See Also
Interface: plug-inManager (p. 414)
Plug-in Manager interfaces: (p. 473)
maxOps
Topic: version 4 MAXScript Language Improvements/maxops
There are many new MAXScript functions exposed in maxops (p. 368):
maxOps.setActiveViewportTransparencyDisplay takes a single integer argument.
0 turns off transparency in the active viewport
1 sets it to screendoor
2 sets it to blended transparency.
maxOps.productVersion
the enum values returned are as follows:
#productVersionDevel- debug build, or licensed in-house
#productVersionTrial - trial license
#productVersionOrdinary - commercial license
#productVersionNFR - not for resale
#productVersionEdu - educational or student license
88 Chapter 1 | What’s New in 3ds max 4 MAXScript
maxOps.licenseBehavior
the enum values returned are as follows:
#licenseBehaviorPermanent - permanent license, or hardware lock
#licenseBehaviorExtendable - term license, can be extended
#licenseBehaviorNonextendable - term license, cannot be extended
maxOps.licenseDaysLeft
Its return value is an integer indicating the number of full days left in the term of the license. A
value of 0 means that today is the last day of validity. For permanent licenses, a fixed value is
returned indicating greater than 10 years are left.
Note:
It should be noted that the all copies of 3ds max return a hardwarelockid (p. 630) of “-1” while under
the grace period and until they have been authorized. You can check for that number and initiate
your own demo mode.
maxOps.getNodeByHandleNode_Handles
Returns the node associated with the id passed in.
maxOps.setSelectionType <auto> <method>
<auto>
True or False
<method>
Valid values or method are #window, #crossing, #leftToRight, #rightToLeft.
#window or #crossing is to be used if the first argument (auto) is false. #leftToRight or
#rightToLeft is to be used when auto is true.
maxOps.trackBar
maxOps.getTrackBarItrackBar()
maxOps.trackBar.visible
maxOps.trackBar.filter
maxOps.trackBar.showFrames
maxOps.trackBar.showAudio
maxOps.trackBar.showSelectionRange
maxOps.trackBar.showSnapToFrames
maxOps.trackBar.keyTransparency
maxOps.trackBar.selKeyTransparency
maxOps.trackBar.cursorTransparency
maxOps.trackBar.redraw()
maxOps.trackBar.getNextKeyTime()
maxOps.trackBar.getPreviousKeyTime()
maxOps.cloneNodes
Prototype:
<boolean>CloneNodes <&node array>nodes <&point3>offset expandHierarchy:<boolean>
cloneType:<enum> actualNodeList:<node array> newNodes:<node array>
maxOps 89
Arguments:
nodes is In parameter
This is the list of nodes that you want to clone.
offset is In parameter
The positional offset that will be applied to the cloned nodes.
Keyword arguments:
expandHierarchy default value: false
Indicates if children will be cloned in hierarchies. Default is false.
cloneType enums: {#copy|#instance|#reference}
default value: #copy
actualNodeList default value: #()
This node array will be filled in with the original nodes to be cloned. The reason for
this is that there can be dependencies between nodes that causes other nodes to be
added to the list. For example light/camera targets, nodes part of systems, part of
groups or expanded hierarchies etc.
newNodes default value: #()
This node array will be filled in with the new cloned nodes. There is a one to one
relationship between the nodes in the resultSource and the resultTraget.
Return Value:
If successful true, otherwise false.
maxOps.CollapseNode node noWarnings
maxOps.CollapseNodeTo node modIndex noWarnings
See Also
Interface: maxOps (p. 368)
ItrackBar (p. 113)
Node Handles (p. 83)
3D Studio MAX System Globals (p. 630)
90 Chapter 1 | What’s New in 3ds max 4 MAXScript
Quad Menu
Topic: version 4 MAXScript New Features/Quad Menu
When you click the right mouse button anywhere in an active viewport, except on the viewport
label, the program displays a Quad menu at the mouse cursor. The quad menu can display up to four
quadrant areas with various commands.
In the MAXScript listener window, type apropos “quadmenusettings” to see the list of functions
available.
The Quad menu is set in the startup scripts directory called QuadOptions_Startup.ms.
The two right quadrants of the default quad menu display generic commands, which are shared
between all objects. The two left quadrants contain context-specific commands, such as mesh tools
and light commands. Each of these menus provides convenient access to functions found in the
command panel.
The quad menu contents depend on what is selected, as well as any customization options you may
have selected in the Quads panel of the Customize UI dialog. The menus are set up to display only
the commands that are available for the current selection, therefore selecting different types of
objects displays different commands in the quadrants. Consequently, if no object is selected, all of
the object-specific commands will be hidden. If all of the commands for one quadrant are hidden,
the quadrant will not be displayed.
Note:
PickObject() does not pick objects when launched from a Quad Menu. It will hang and refuses to
pick any object. Hit ‘escape’ for emergency exit. PickObject works correctly from a shortcut and
toolbar.
See also
Interface: quadMenuSettings (p. 414)
ApplyOperation function (p. 54)
Menu Manager (p. 75)
Interface: menuMan (p. 372)
Menu and CUI Loading (p. 178)
Reactor controller 91
Reactors
Reactor controller
Topic: version 4 MAXScript New Features/Reactors
The Reactor controller is a procedural controller that reacts to changes in any other controller within
the software. Reactor comes in five different forms: Position Reactor, Rotation Reactor, Point3
Reactor, Scale Reactor, and Float Reactor. Any animatable parameter in the software can react to
changes in any other animatable parameter. Reactor is not based on time, but is based on other
variables in your scene.
Example:
-- Setup a scene
ball = sphere name:”ball” pos:[-40,0,50] radius:10
ball.pos.controller = position_XYZ()
-- create some keys
key = addNewKey ball.pos.Zposition.controller 0
key.outTangentType = #slow
key.value = 50
key = addNewKey ball.pos.Xposition.controller 0
key.value = -40
key = addNewKey ball.pos.Zposition.controller 25
key.InTangentType = #fast
key.outTangentType = #fast
key.value = 4
key = addNewKey ball.pos.Xposition.controller 25
key.value = -10
key = addNewKey ball.pos.Zposition.controller 50
key.InTangentType = #slow
key.value = 50
key = addNewKey ball.pos.Xposition.controller 50
key.value = 20
ball.showtrajectory = true
-- assign a reactor controller to the scale of the ball
reactor = Scale_Reactor()
ball.scale.controller = reactor
-- Pick the react to object, and create reactions
reactor.reactions.reactTo ball.pos.ZPosition.controller 0
reactor.reactions.setName 0 “UnSquashed”
reactor.reactions.setVectorState 0 [1,1,1]
reactor.reactions.create “squashed” 25
reactor.reactions.setVectorState 1 [2.5,2.5,.4]
reactor.reactions.setValueAsFloat 0 10
reactor.reactions.setInfluence 0 6
reactor.reactions.setInfluence 1 5.5
reactor.reactions.setStrength 1 1.5
reactor.reactions.setFalloff 0 1.75
ss = StringStream ““
reactor.reactions.getType()
92 Chapter 1 | What’s New in 3ds max 4 MAXScript
ct = reactor.reactions.getCount()
format “Reactor Statistics: \n------------------------------\n \n” to:ss
format “Count : %\n” ct to:ss
format “\n” to:ss
for i = 0 to ct-1 do
(
format “Reaction #: % \n------------------------------------------------
Name : %
State: %
Value: %
Strength: %
Influence : %
Falloff: % \n\n” (i) (reactor.reactions.getName i)
(getReactionState reactor (i+1)) (getReactionValue reactor (i+1))
(reactor.reactions.getStrength i) (reactor.reactions.getInfluence i )
(reactor.reactions.getFalloff i ) to:ss
)
print ss
See Also
Reactor Controllers (p. 1326)
Float Reactor interfaces: (p. 443)
Point3 Reactor interfaces: (p. 477)
Scale Reactor interfaces: (p. 515)
Position Reactor interfaces: (p. 492)
See Also
Interface: maxOps (p. 368)
Combustion (p. 38)
type:#integer parameters in scripted plug-in parameter blocks 93
Scripted Plug-Ins
See Also
Scripted Plug-ins (p. 1538)
Scripted Plug-in Events (p. 93)
Scripted Cameras (p. 94)
See Also
Scripted Plug-ins (p. 1538)
type:#integer parameters in scripted plug-in parameter blocks (p. 93)
Scripted Cameras (p. 94)
Scripted Cameras
Topic: version 4 MAXScript New Features/Scripted Plug-In/Scripted Cameras
Scripted camera plug-ins can now be written in MAXScript. At present, you can write either
extending camera plug-ins that extend existing MAX cameras or temporary camera plug-ins that can
be used to host create tools for a custom camera system.
The plug-in superclass for cameras is ‘camera’.
An event handler is available to scripted cameras that gives access to the
CameraObject::renderApertureChanged callbacks made by the rendering dialog to a camera
when the user adjusts parameters that affect render aperture. The new handler is optional.
on renderApertureChanged val do ....
The ‘val’ parameter contains the new render aperture value. This typically gets called
when you select a new apeture in the Output Size dropdown in the render dialog or adjust
a spinner when in Custom mode.
There are several cases where this handler is called:
• In the Render Scene dialog, if Image Aspect is unlocked and you change Width, Height, or
Pixel Aspect
• In the Render Scene dialog, if you click on one of the output size preset buttons
• In the Render Scene dialog, if Image Aspect is locked and you change Width, Height, or Pixel
Aspect, or if you change Aperture Width, and then click on either Render or Close
The value being passed into handler is the aperture width. You can get the remaining values via:
renderWidth, renderHeight, and RenderPixelAspect global variables. However, what you get for
these values are typically the old value, with the exception of the Aperture Width value. The call to
the handler is coming from a “InvalidateCameras” method, which is called right before setting the
new values. Doesn’t look like any broadcasts are made after the new values are set, and if safe frames
isn’t turned on in any viewport, none of the viewports are redrawn.
We recommend that if a scripted camera uses this handler, it should cache the old Aperture Width
value and test the incoming value against the cached value before proceeding.
dependsOn For Scripted Controllers 95
Example:
plug-in Camera CamTest
name:”CamTest”
classID:#(0x47db14ff, 0x4e9b5f90)
category:”Standard”
( on renderApertureChanged val do format “renderApertureChanged: %\n” val
tool create
( on mousePoint click do #stop
)
)
See Also
Scripted Plug-ins (p. 1538)
Scripted Plug-in Events (p. 93)
type:#integer parameters in scripted plug-in parameter blocks (p. 93)
Scripted Cameras (p. 94)
Scripted Controllers
will always keep $foo centered between $foo1 and $foo2. The objects given to the dependsOn()
function can be any MAX object, controllers, base object, nodes, materials, etc. They must be
individual, explicit objects, not wild-card path names or arrays of objects. The object can be the
exact controller you want to depend on or any containing object. The strict dependency for the
above script would be,
Example:
dependsOn $foo2.pos.controller $foo3.pos.controller
The simpler $foo2 $foo3 will catch *any* kind of changes to those nodes or components in them
like base objects, modifiers, or materials and update the script-controlled object. The dependency is
96 Chapter 1 | What’s New in 3ds max 4 MAXScript
established the first time the controller is evaluated after any script change or recompile. This can
be when editing in a controller property box, or after a scene load.
You can programmatically force a recompile and reset of the dependents by setting the control script
to itself:
$foo.pos.controller.script = $foo.pos.controller.script
See Also
script controllers (p. 162)
See Also
transform_script - superclass: Matrix3Controller (p. 339)
Script Controllers (p. 1329)
Scripted Manipulators
Topic: version 4 MAXScript New Features/Scripted Plug-In/Scripted Manipulators
Manipulators are a new type of helper object. They are designed to support direct manipulation of
parameters in the3D viewports. They can be set up to manipulate parameters on objects, modifiers,
controllers and nodes.
There is a “Manipulate” button on the main toolbar. When pressed, the system will show all the
manipulators for selected objects. As the mouse passes over a manipulator, it turns red, and a tool
tip pops up with the name of the current value of the parameter that is affected by that manipulator.
To manipulate the value, you click down on the gizmo with the left mouse button and drag it. Most
manipulators are designed so that the gizmo will track under the current mouse position, if possible.
Note that “Manipulate” is not a separate mode. It modifies whatever mode you are currently in
(select, move, create, etc.) to show manipulators and allow manipulation. If you are in move mode,
for example, you can still move things around as usual. The only difference is that if you click down
on a manipulator, you will manipulate, instead of move.
There are two flavors of manipulators. The first are manipulators that are automatically created
when you enter “Manipulate” mode. The hotspot manipulator is like that. The second kind is
stand-alone objects, like the slider manipulator. These are usually used in conjunction with
parameter wiring to get make them useful.
To create a stand-alone manipulator, you go to the “Helpers” section of the create panel, and select
“Manipulators” in the drop-down list.
Stand-alone manipulators do not need to be selected in order to be manipulated. However, the
automatically created manipulators, like the hotspot manipulator, are only displayed for selected
objects.
Manipulators support both 3d gizmos and 2d (screen space) gizmos. The hotspot manipulator is an
example of a 3d gizmo, and the slider is an example of a 2d gizmo.
Manipulators can be created either as standard MAX plug-ins in C++, or they can be implemented
in MAXScript. In MAXScript, they are a type of Scripted Plug-in object (p. 1538), so if you want to write
your own manipulator, it would be a good idea to read about Scripted Plug-ins (p. 1538) first. They are
very similar to scripted geometry objects.
Three scripted manipulators that you can use as sample code can be found in the
“..\stdplugs\stdscripts” folder.
• RadiusManip.ms: Generic “radius” manipulator
• SliderManip.ms: A 2d viewport slider. A stand-alone manipulator
• UVWManip.ms: A set of manipulators for the UVW modifier
98 Chapter 1 | What’s New in 3ds max 4 MAXScript
Radius Manipulator
The radius manipulator is fairly simple, so it makes a good example to describe the scripted
manipulator system.
The code for the manipulator is included below, followed by a detailed description of how it works.
--------------------------------------------------------------------
-- Generic radius manipulator
-- Written by Scott Morrison
-- This manipulator sets the radius on any object or modifier with
-- a parameter named “radius”. It creates a circle gizmo of the appropriate
-- radius centered at the origin in the XY plane.
plug-in simpleManipulator radiusManip
name:”RadiusManip”
invisible:true
(
-- Create the green and red colors for the gizmo
local g = [0, 1, 0], r = [1, 0, 0]
-- This manipulator manipulates any node with a “radius” property
on canManipulate target return (findItem (getPropNames target) #radius) != 0
-- Create the manipulator gizmo.
-- This is called initially and whenever the manipulator target changes
on updateGizmos do
(
-- Clear the current gizmo cache
this.clearGizmos()
-- Set the radius of circle gizmo a little bigger than the target radius
giz = manip.makeCircle [0,0,0] (target.radius * 1.01) 28
-- Add the circle to the manipulator
this.addGizmoShape giz 0 g r
-- return the ToolTip string
return node.name + “ radius = “ + target.radius as string
)
-- mouseMove is called on every mouse move when dragging the manip
-- It needs to convert the mouse position ‘m’ into a new value for the
radius
on mouseMove m which do
(
-- Create the XY plane.
-- manip.makePlaneFromNormal takes a normal vector and a point
-- and creates a plane passing through the point with the given normal
local pl = manip.makePlaneFromNormal z_axis [0, 0, 0],
projectedPoint = [0,0,0]
-- Compute the hit-ray in local coordinates
viewRay = this.getLocalViewRay m
-- Intersect the plane with the view ray
res = pl.intersect viewRay &projectedPoint
Matrix3 Scripted Controller 99
The header:
plug-in simpleManipulator radiusManip
name:”RadiusManip”
invisible:true
Indicates to MAXScript that this is a scripted manipulator plug-in called “RadiusManip”. The
“invisible:true” tells the system not to make a creation button for the manipulator in the
create panel.
The body:
A set of handlers for various events.
on canManipulate target return (findItem (getPropNames target) #radius) != 0
“canManipulate” is called on every manipulator, for every node that is selected when the
“Manipulate” button is pressed. The “target” parameter is the object that we might potentially
manipulate. It is called on the base object, all the modifiers on the object, and transform controllers
on the object’s node. Also, if the transform controller is a PRS controller, it calls “canManipulate”
on the position, rotation and scale controllers.
In the case of the radius manipulator, it can manipulate any object that has a property named
“radius”.
If you want to create a manipulator that works on a specific object type, say a sphere, you can say:
on canManipulate target return classOf target == sphere
There is an alternative handler that may be needed in some cases called “canManipulateNode n”.
This is called passing in the each selected node to the handler. This is not normally needed, but
available if your manipulator wants to manipulate property of a node other than the ones that are
passed as the “target” to “canManipulate”.
Note:
A Scripted Plug-in should only implement one of these handlers, not both.
The next handler is called “updateGizmos,” and this is called whenever a manipulator need to build
its gizmos. This happens when the manipulator is created, and whenever the target that it is
manipulating changes.
When MAXScript creates a manipulator, it sets up some variables that are available inside the calls
to its handlers. One of these is called “target” and it is the object, modifier or controller that is
being manipulated. Another is called “this” and it is the manipulator itself. It also sets up some
constant values that can be used as flags on gizmos. These will be described later. There is also a
“node” value available which is the node that owns the target.
100 Chapter 1 | What’s New in 3ds max 4 MAXScript
The first thing every manipulator must to in the “updateGizmos” handler is call
“this.clearGizmos()”. This clears any currently cached gizmos.
Next it creates a set of gizmos that will be displayed in the viewport. In the case of the radius
manipulator, it creates a single circle that represents the radius being manipulated.
giz = manip.makeCircle [0,0,0] (target.radius * 1.01) 28
“manip” is a exported set of utility interface functions that manipulators can use. See the
“Reference” section below for full details. In this case we are creating a circle, centered at the
origin, with radius 1.01 times the radius we are manipulating, and 28 segments. The “1.01” factor
was added so that the gizmo will stick out a little bit from the object it is manipulating. If we used
the radius directly, then it might not be visible in the viewport, because it co-exists with the object
it is manipulating.
Note that 3d gizmos are defined in the local coordinate system of the node that owns the
manipulator target. The system will automatically compensate if the node is moved, rotated or
scaled when displaying or hit-testing the manipulator.
Next, we add the gizmo to the manipulator:
this.addGizmoShape giz 0 g r
This tells the manipulator to add the shape gizmo to the manipulator, with no special flags values
ie. the “0”. All of the the flags will be decribed below. Additionally, the command indicates to use
green (“g”) as the unselected color and red (“r”) as the selected color. The selected color is used when
the mouse passes over it, and the unselected color is used when the mouse isn’t over it.
Finally, this method returns a string value that will be used as the tool tip when the mouse passes
over the gizmo.
In general, gizmos can be made from meshes, shapes (wire frame), text and markers. The details are
covered in the reference section below.
The next handler is called “mouseMove m which”. This is called on every mouse movement when
the target is being manipulated. The “m” parameter holds the screen coordinates of the mouse
location, and the “which” parameter is an index that indicates which gizmo is being dragged. The
gizmos are numbered in the order of their creation in “updateGizmos,” starting at 0.
The mouseMove handler is usually the trickiest part of the manipulator to implement. It needs to
update the value of the parameter being manipulated in such a way that the manipulator gizmo
tracks under themouse, if possible.
For manipulators that exist in 3d space, this is normally done by computing a “hit-ray,” which is
a ray in 3d space that passes through the mouse position, and travels in the direction of the view.
This is computed as follows:
viewRay = this.getLocalViewRay m
This view ray is then intersected with some plane, and the new parameter value is computed using
the intersection point.
Matrix3 Scripted Controller 101
In the case of the radius manipulator, the plane we use is the XY plane, because the radius circle lies
on the XY plane, in local coordinate space.
This plane is computed as follows:
local pl = manip.makePlaneFromNormal z_axis [0, 0, 0],
This create “pl” which is a plane whose normal is the Z axis, and which passes through the origin
([0,0,0]).
To intersect this with the view ray, we use the “intersect” operation on planes:
projectedPoint = [0,0,0]
We set up “projectedPoint” first at the holder of the result of the intersection. The return value
“res” is a boolean value that tells us if the intersection worked or not. If it returns true, the
intersection worked, if it returns false, it failed. It can fail if the plane is parallel to the view ray.
Once we have the intersection point, in “projectedPoint,” then we use that to determine a new
value for the radius. In this case we use the distance from the origin (“length projectedPoint”)
as the new radius. We scale it by dividing by 1.01 to compensate for the fact that we made the gizmo
1.01 time bigger than the actual radius being manipulated.
That’s it! Generally, you will need to use some trigonometry and linear algebra in your
“mouseMove” handler. The idea behind direct manipulation is that the gizmo should track directly
under the mouse.
For a more complicated example of a 3d manipulator, check the code in UVWManip.ms.
Stand-alone Manipulators
Stand-alone manipulators, like the 2d slider, require a bit more work.
The code in SliderManip.ms will be used for this discussion.
The header has a bit more information:
plug-in simpleManipulator sliderManipulator
name:”Slider”
classID:#(0x47db14ef, 0x4e9b5990)
category:”Manipulators”
Since stand-alone manipulators can be saved in the MAX file, it needs a class ID (p. 141). See the
MAXScript reference for more information about that. It also does not include the
“invisible:true” line, which means that the system will create a button for it in the “Create”
panel. It will be placed in the “Manipulators” section of the helper create panel.
We also need to define a parameter block and rollout UI for the object. This is done in the same way
as other scripted plug-ins.
Stand-alone manipulators manipulate themselves, so the “canManipulate” handler looks like this:
on canManipulate target return (classOf target) == sliderManipulator
102 Chapter 1 | What’s New in 3ds max 4 MAXScript
We also need to provide a creation tool that handles mouse interaction when creating the
manipulator. This is handle exactly like other scripted plug-ins.
A stand-alone manipulator also needs some special code in its “updateGizmos” handler. For the
slider this looks like:
-- If this is not a stand-alone manip, get values from the manip target
if (target != undefined) then
(
this.value = target.value
this.minVal = target.minVal
this.maxVal = target.maxVal
this.xPos = target.xPos
this.yPos = target.yPos
this.width = target.width
this.hide = target.hide
this.sldName = target.sldName
this.snapToggle = target.snapToggle
this.snapVal = target.snapVal
unselColor = greenColor
)
else
(
unselColor = yellowColor
)
The test of “target != undefined” is to see if this if this is a manipulator, or stand-alone object.
When the object is stand-alone, the value of “target” is undefined, and it uses the value of the
parameters from its own parameter block. It target is defined, then this means it is manipulating. In
that case, we want to copy the values of the parameters from the target that we are manipulating.
Reference
Scripted manipulators can have the following handlers:
on canManipulate target
This returns a value that says whether this manipulator manipulate the given target.
on canManipulateNode n
This returns a value that says whether this manipulator manipulate the given node.
Note:
A manipulator should only implement one of these handlers.
on updateGizmos
This is called whenever the manipulator needs to build its gizmos. It returns a string value
that is used for the tool tip. If it returns an empty string, no tool tip is displayed.
on mouseMove m which
This is called when the user has grabbed a gizmo and is dragging it.
Matrix3 Scripted Controller 103
The “m” parameter hold the current screen coordinates of the mouse, and the “which”
parameter indicates the 0-based index of the gizmo that is being dragged. This is what
handles that actual manipulation.
Note:
Normally this will set a value of a parameter of the manipulation target based on the mouse location.
on mouseDown m which
Called when the user first clicks the mouse down on the gizmo.
on mouseUp m which
Called when the user releases the mouse after manipulation is done.
Helper Functions
There are some built-in functions that manipulators support, and a couple of helper packages with
utility functions.
The simpleManipulator type itself has these functions available:
this.clearGizmos()
This must be called at the beginning of the “updateGizmos” handler in order to clear the
current gizmo cache.
this.addGizmoMesh mesh flags unselColor selColor
This creates a gizmo from a mesh (or geometry in MAX lingo). The mesh can be any
arbitrary MAX mesh, and created with the tools in MAXScript for creating meshes. One
convenient way to do this is to create an instance of a primitive and get the mesh from it.
The flags can be 0, or one or more of these value. If you want more than one flag to apply,
then you add the values together. Here are all the flags, and whether that can be used with
addGizmoText, addGizmoMarker, addGizmoShape and addGizmoMesh:
gizmoDontDisplay
Tells the system to not display the gizmo. It will be hit-tested, but not displayed,
applies to all.
gizmoDontHitTest
Tells the system to not hit-test the gizmo. It will be displayed, but not hit-tested,
applies to all.
gizmoActiveViewportOnly
Tells the system to only display and hit-test this gizmo in the active viewport, applies
to all.
this.addGizmoShape gizmoShape flags unselColor selColor
This creates a gizmo from a shape object. The gizmoShape can be created using functions
from the “manip” package, described below.
The flags can take on the same value as for “addGizmoMesh,” with two new values
supported:
gizmoUseScreenSpace
104 Chapter 1 | What’s New in 3ds max 4 MAXScript
This tells the system to interpret the coordinates of the shape as device coordinates in
the viewport, not as 3d values. The values are still specified as 3d points, but the “Z”
coordinate is ignored, applies to all but addGizmoMesh.
gizmoUseRelativeScreenSpace
This is like gizmoUseScreenSpace, but the coordinates are specified as values from 0.0
to 1.0, and interpreted in each viewport as a percentage of the width or height of the
viewport, applies to all but addGizmoMesh.
addGizmoMarker markerType position flags unselColor selColor
The creates a gizmo using a marker. The value of the “markerType” parameter can be:
#point
#hollowBox
#plusSign
#asterisk
#xMarker
#bigBox
#circle
#triangle
#diamond
#smallHollowBox
#smallCircle
#smallTriangle
#smallDiamond
#dot
#smallDot
The position is a point in 3d space, or 2d screen space. The flags are the same ones
supported by addGizmoShape.
addGizmoText text position flags unselColor selColor
This creates a gizmo that is text on the screen. Note that text cannot be hit-tested or
grabbed by the mouse. It is used for display purposes only.
getLocalViewRay m
This function takes a mouse position and returns the ray that passes through that mouse
position in the direction of the view. It is returned in the local coordinates of the node that
owns the manipulator target.
Plane objects
The plane objects returned from “manip.makePlaneFromNormal” have the following functions
available:
projectedPoint = [0,0,0]
plane.intersect ray &intersectionPoint
This intersects the given ray with the plane. It returns true if it succeeds, and false if it
doesn’t. If it works, then the intersection point is set in the “intersectionPoint” value,
which must be initialized to a Point3 value in advance.
plane.mostOrthogonal ray otherPlane
This returns the plane that is most orthogonal to the given ray. This means the plane that
is most “square” to the view direction.
Sometimes a manipulator might choose between two different planes on which to project a ray. It
is usually best to project it to the plane which faces the view ray most directly, and this function
determines that. See “UVWManip.ms” for an example of how to use this.
plane.getNormal()
Returns the normal of a plane.
plane.getPoint()
Return the point that the plane passes through.
plane.getPlaneConstant()
Return the value of the plane constant. This is the value of “D” in the equation that
defines the plane:
Ax + By +Cz + D = 0
GizmoShape objects.
A GizmoShape is a shape object that you can use to construct wire-frame gizmos. You can get an
empty GizmoShape as follows:
local giz = manip.makeGizmoShape()
giz.startNewLine()
This begins a new line segment in the shape.
giz.transform matrix
This transforms the gizmo by the given Matrix3 transform.
Note:
See the UVWManip.ms for an example of creating 3d gizmos with GizmoShape.
See Also
Interface: manip (p. 366)
sliderManipulator interfaces: (p. 520)
radiusManip interfaces: (p. 500)
uvwMappingHeightManip interfaces: (p. 551)
uvwMappingLengthManip interfaces: (p. 555)
uvwMappingUTileManip interfaces: (p. 558)
uvwMappingVTileManip interfaces: (p. 562)
uvwMappingWidthManip interfaces: (p. 565)
ConeAngleManip - superclass: helper (p. 277)
PlaneAngleManip - superclass: helper (p. 311)
Scripted Plug-ins (p. 1538)
sliderManipulator - superclass: helper (p. 333)
Scripted Objects
See Also
Scripted Plug-ins (p. 1538)
RenderEffects Progress Callback Mechanism 107
Scripted RenderEffects
The first argument is the bitmap value to be modified by the effect, and progressCB is a progress
callback interface object. This interface has several methods you can call during the course of
processing the bitmap that control the progress bar and check for user cancellation.
Methods
progressCB.setTitle <string>
Sets the title on the progress bar.
progressCB.progress <done> <total>
Indicates the progress of the rendering. Both arguments are integers; done indicates how
much of the rendering has been completed, and total indicates how much there is
to do.
When this is called, the main render effects progress bar is updated to reflect this progress.
This function also returns a boolean, which if true indicates that the user has hit the
escape key to cancel the effect rendering.
progressCB.check()
Indicates whether the user has hit the escape key to cancel the effect rendering. This
function returns a boolean; false if processing should continue, and true if the user has
cancelled the rendering.
Example:
on apply bm progressCB: do
(
…
progressCB.setTitle “My Effect Pass1”
…
escapeEnable = false -- turn on scripter escape processing
for i in …
(
<the effect rendering loop>
…
if progressCB.progress completed total then exit
)
…
escapeEnable = true
…
)
108 Chapter 1 | What’s New in 3ds max 4 MAXScript
The progress bar update is done inside the main processing loop and the check for user cancel is
done on the same call, causing the loop to exit prematurely in this example.
See Also
RenderEffect : MAXWrapper (p. 1347)
Scripted RenderEffect Plug-ins (p. 1566)
Render Effects Common Properties, Operators, and Methods (p. 1347)
Scripted Rollouts
See Also
Edittext (p. 1496)
Rollout Floater Windows (p. 1477)
Multi-line editText UI items in Scripted Rollouts 109
Skin
Joint Angle Morph
Spring Controller
Topic: version 4 MAXScript New Features/Spring Controller
The Spring controller adds secondary dynamics effects to any point or object position. The end
result is secondary mass/spring dynamics similar to Flex. This constraint adds realism to generally
static animations.
When you apply Spring to an animated object, its original motion is preserved and secondary,
velocity-based dynamics are applied. When you first apply the controller, it constructs a virtual
spring between the object’s original position and where it would end up after forces are applied to
it. You can adjust spring tension and dampening. Increasing the tension creates a tighter spring,
while increasing the dampening smoothes out jitters in the motion.
Users have control over the point’s Mass and Drag, the spring’s Tension and Dampening, and other
world space constraints. These include being able to add external forces like Wind and Gravity
(spacewarps), and being able to constrain the spring effects along a given axis. This way you can add
vertical dynamics while controlling the about of effect it has in the horizontal directions.
The solution is calculated using a start time and a step size. Solutions are cached once for the last
tick calculated, and once per frame. Performance should be the same one each frame as you step
forward, and significantly faster after the first pass if nothing changes. Cached values will be used if
going backwards in time.
The biggest slowdown occurs when animating an object that the controller uses as a force way down
the time line since this is a history dependant solver. If a lot of animation is going to occur along a
long timeline you can shut off the spring solver by setting steps to 0. Set this back to the desired
value when you want the solution recalculated.
Methods
Prototype:
<float>getMass()
Return Value:
Returns the mass.
Prototype:
<void>setMass <float>mass
Parameters:
<float>mass
110 Chapter 1 | What’s New in 3ds max 4 MAXScript
Remarks:
Sets the mass. The mass of the object to which the Spring controller is applied. Increasing the mass
causes the “bouncing” spring motion to become more exaggerated.
Prototype:
<float>getDrag()
Return Value:
Returns the drag.
Prototype:
<void>setDrag <float>drag
Parameters:
<float>drag
Remarks:
Sets the drag. Acts as air friction on the spring motion. A low Drag setting results in a greater
“bouncing” effect, while a high Drag results in subdued bouncing. Default=1. Range=0 to 10.
Prototype:
<float>getTension <index>springIndex
Parameters:
<index>springIndex
Return Value:
Gets the tension for the spring corresponding to the index.
Prototype:
<void>setTension <index>springIndex <float>tension
Parameters:
<index>springIndex
<float>tension
Remarks:
Sets the tension for the spring corresponding to the index. The “stiffness” of the virtual spring
between the controlled object and the highlighted spring object(s).
Prototype:
<float>getDampening <index>springIndex
Parameters:
<index>springIndex
Return Value:
Gets the dampening for the spring corresponding to the index.
Multi-line editText UI items in Scripted Rollouts 111
Prototype:
<void>setDampening <index>springIndex <float>dampening
Parameters:
<index>springIndex
<float>dampening
Remarks:
Sets the dampening for the spring corresponding to the index. : Acts as a multiplier of an internal
factor that determines how quickly the object comes to rest. With the Self Influence spring,
changing Dampening has the same effect as changing Drag. With other springs, Dampening affects
only the movement caused by that spring. Internally, the dampening value is proportional to the
tension, so as you increase the tension and make the solution more stiff, the dampening is increased
to maintain system stability.
Prototype:
<boolean>addSpring <node>node
Parameters:
<node>node
Remarks:
Adds the node to the spring list.
Return Value:
Returns true if successful, false otherwise
Prototype:
<integer>getSpringCount()
Return Value:
Returns the number of springs in the spring system.
Prototype:
<void>removeSpringByIndex <index>springIndex
Parameters:
<index>springIndex
Remarks:
Removes the spring corresponding to the index.
Prototype:
<void>removeSpring <node>node
Parameters:
<node>node
Remarks:
Removes the spring if the node is in the spring list.
112 Chapter 1 | What’s New in 3ds max 4 MAXScript
See Also
PositionSpring interfaces: (p. 497)
Point3Spring interfaces: (p. 482)
SpringPoint3Controller interfaces: (p. 523)
SpringPoint3Controller - superclass: Point3Controller (p. 336)
SpringPositionController interfaces: (p. 526)
SpringPositionController - superclass: PositionController (p. 337)
Flex : Modifier (p. 1128)
Flex interfaces: (p. 438)
flexOps const StructDef (p. 235)
SubObject Mode
System Tools
Topic: version 4 MAXScript New Features/System Tools
A new global struct called “systemTools” has been added to MAXScript.
This group of functions lets you gather various pieces of information about the system that you
are using.
systemTools.NumberOfProcessors()
Returns the number of processors
systemTools.GetScreenWidth()
Returns the screen width including multiple monitors.
systemTools.GetScreenHeight()
Returns the screen height including multiple monitors.
systemTools.IsWindows98or2000()
Returns true if the OS is Windows98 or Win2000
systemTools.IsWindows9x()
Returns true if the OS is a Win9x flavor
systemTools.IsDebugging()
Returns true if running in a debugger
See Also
systemTools const StructDef (p. 256)
System Information (p. 141)
sysInfo const StructDef (p. 255)
Multi-line editText UI items in Scripted Rollouts 113
Trackbar Interface
Topic: version 4 MAXScript New Features/TrackBar
An interface has been added to access properties and methods of the trackbar. The trackbar interface
can be retrieved using a function or property in maxOps. (p. 368)
trackBar_Interface = maxOps.trackBar
or:
trackBar_Interface = maxOps.getTrackBar()
The following methods and properties are available for the trackbar.
Properties:
.visible : boolean : Read|Write
Displays or hides the trackbar
.filter : enum : Read|Write
filter enums: {#all|#TMOnly|#currentTM|#cbject|#mat}
Sets and gets the filter that determines which keys are displayed in the trackbar
.showFrames : bool : Read|Write
Sets/gets whether or not frames are displayed in the trackbar
.showAudio : bool : Read|Write
Sets/gets whether or not the audio track is displayed in the trackbar
.showSelectionRange : bool : Read|Write
Sets/gets whether or not selection ranges are displayed in the trackbar
.showSnapToFrames : bool : Read|Write
Sets/gets whether or not keys are snapped to frames when moved
.keyTransparency : integer : Read|Write
Sets/gets the key transparency value. Acceptable values range 0-255
.selKeyTransparency : integer : Read|Write
Sets/gets the selected key transparency value. Acceptable values range 0-255
.cursorTransparency : integer : Read|Write
Sets/gets the cursor transparency value. Acceptable values range 0-255
114 Chapter 1 | What’s New in 3ds max 4 MAXScript
Methods:
<void>redraw forceRedraw:<bool>
forceRedraw default value: false
Indicates if the redraw should be forced
Redraws the trackbar.
<time>getNextKeyTime()
Gets the next key time. The “at time” context can be used to determine the starting point.
<time>getPreviousKeyTime()
Gets the previous key time. The “at time” context can be used to determine the
starting point.
See Also
maxOps (p. 87)
Interface: maxOps (p. 368)
Trackviews
Topic: version 4 MAXScript New Features/Trackviews
The methods and properties are:
trackviews.isOpen <fpvalue>name or index
Returns a boolean value indicating if the specified trackview is open.
trackviews.isCurrent <fpvalue>name or index
Returns a boolean value indicating if the trackview is the last one used or not.
trackviews.setCurrent <fpvalue>name or index
Sets the specified trackview to be the current one. Returns true if successful.
trackviews.currentTrackView
Read only property that returns the interface for the currently used trackview. Returns
undefined if the trackview is closed.
trackviews.lastUsedTrackViewName
Read only property that returns the name of the current trackview.
trackviews.openLastUsedTrackView()
Opens the current trackview if it has been closed.
trackviews.delete <fpvalue>name or index
Deletes the specified trackview.
trackviews.close <fpvalue>name or index
You can now close a trackview based on it’s index or name.
trackviews.open <fpvalue>name or index
You can now open a trackview based on it’s index or name.
trackviews.getTrackView <fpvalue>name or index
This method will get a trackview based on it’s index or name.
Multi-line editText UI items in Scripted Rollouts 115
Example:
showInterface (trackviews.getTrackView 1)
trackviews.getAllTrackViews()
Returns an array of trackviews.
trackviews.numTrackViews()
Returns the number of trackviews.
trackviews.getTrackViewName <index>index
Returns the name of the trackview window based on the index.
<void>setName <string>name
Sets the name of the trackview window
<integer>getNumTracks()
Gets the number of tracks currently displayed in trackview
<integer>numSelTracks()
Gets the number of selected tracks
<boolean>canAssignController()
Tests to see if all selected tracks are of the same type
<void>assignControllerDialog
Invokes the assign controller dialog if canAssignController()
<boolean>assignController <maxObject>controller
Assigns the controller to the selected tracks if canAssignController() is true and the
controller is the appropriate type
<void>showControllerTypes <boolean>state
Sets the ShowControllerType property
<void>expandTracks()
Expands all tracks
<void>zoomSelected()
Zooms to the selected object’s track
<void>zoomOnTrack <maxObject>parent <index>subNum
Zooms to the track defined by the parent and the subNum
<maxObject>getTrack <index>index
Returns the object belonging to the indexed track
<maxObject>getParent <index>index
Gets the parent of the object belonging to the index track. If the object is a position
controller, the parent is the Transform controller
<maxObject>getSelected <index>index
Gets the objects belonging to the selected, indexed track
<maxObject>getParentOfSelected <index>index
Gets the indexed selected tracks parent object
<index>getSelectedSubNum <index>index
Gets the subNum of the selected track
<index>getIndex <maxObject>object
Gets the index for the animatable object
116 Chapter 1 | What’s New in 3ds max 4 MAXScript
trackviews.getAllTrackViews()
Once you have an instance of the trackview interface you can call the following new methods on it.
getEditMode()
Gets the current edit mode as an symbolic enum.
setEditMode <type as symbolic enum>
Sets the current edit mode
editMode
Property to do the same as the above two methods
valid symbolic enum values are:
#editKeys
#editTime
#editFCurves
#editRanges
#positionRanges
See Also
trackView const StructDef (p. 257)
Interface: trackviews (p. 429)
Track View (p. 1609)
Multi-line editText UI items in Scripted Rollouts 117
Visual MAXScript
Topic: version 4 MAXScript New Features/Visual MAXScript
“Visual MAXScript is a direct-manipulation, multithreaded, forms-based editor that you can use to
layout and edit MAXScript rollouts. Rollout scripts can be created from scratch in the forms editor,
or use it to interactively edit and add to an existing rollout definition in a script editor window.”
The layout editor can be accessed in two ways:
• as a stand-alone Utility plug-in named “Visual MAXScript”
When accessed as a Utility through the Utility command panel, the layout editor operates in a
“stand-alone” mode. Any forms created can either be exported as separate script files containing
the rollout definition script or saved in a special .vms binary layout file that can be opened again
by the Visual MAXScript utility. When used in this mode, any script files exported can be
opened in script editor windows for further editing in MAXScript or merging with other
script files.
118 Chapter 1 | What’s New in 3ds max 4 MAXScript
• through 2 new menu items in the Edit menu in script editor windows
When accessed through the new script editor Edit menu items, the layout editor is designed for
application to rollout definition sections in the active script editor. The “New Rollout” menu
item is used to create a rollout definition from scratch. You place the cursor in the edit window
where you want the newly-generated rollout code to be inserted and choose Edit>New Rollout.
This opens the editor on a blank form to which you can add and arrange and edit rollout items.
Choosing File>Save or hitting the Save icon in the layout editor window will cause the script for
the rollout to be inserted at that point in the editor window. Subsequent edits and saves while
the layout editor is still open cause that inserted code to be updated.
The “Edit Rollout” item (hotkey F2), is used to edit an existing rollout definition in the active script
editor. You place the cursor anywhere inside a rollout or utility definition, choose Edit>Edit Rollout
(F2), and the layout editor is opened showing that rollout. You can edit and add to the rollout in the
layout editor and when you choose File>Save or click the Save icon in the layout editor, the original
definition is replaced with new code corresponding to the edited rollout. Subsequent changes and
saves while the layout editor is still open cause that code to be updated each time.
Features:
• You can have more than one layout editor open at a time This allows you to cut and paste
operations between them. Also, note that cutting and pasting in VMS also copies event code.
• When opened from a script editor window, the text in that editor window becomes ‘frozen’
while the layout editor is open. The editor window can be brought to the front and scrolled and
saved, but any other operation will be ignored and a beep will sound. The editor will ‘unfreeze’
as soon as you close the layout editor.
• The Edit>Edit Rollout function can be applied to any existing rollout definition. It attempts to
parse the definition and open an equivalent editable version in the layout editor. This is a
somewhat tricky heuristic and may well fail for certain rollouts until we get the bugs out.
MAXScript preserves all the code in the rollout and updates only those parts that correspond to
the things you can edit in the layout editor, namely, UI items and their handlers.
• Code generated by the layout editor always specifies explicit pos: width: and height:
parameters for UI items, it does not use align:, offset:, or any of the other
auto-layout parameters. This means that any rollout that you edit that uses automatic
layout will be transformed into an explicitly-positioned layout when you do the first File>Save.
It is quite difficult to preserve the auto-layout parameters under arbitrary edits in the editor and
the assumption is that once you start editing a rollout using the layout editor you will continue
to do so.
Note:
An extreme example of this is the group ( ) construct which is used to nest a set of items in a group
box. Nested group ( ) constructs are removed completely by the layout editor and replaced with new
groupBox UI items that define an explicitly-sized box around the original items. You can edit and
add and nest groupBoxes as needed in the editor.
Multi-line editText UI items in Scripted Rollouts 119
• If there is a syntax error in a rollout definition being opened by Edit>Edit Rollout, the syntax
error is reported and highlighted and the layout editor does not open - it can only be opened
on error free source.
• When you first edit or create a rollout in the layout editor, it defaults to the standard width for
Command Panel rollouts. You can adjust this width in the editor by resizing the outer gray
rectangle and the editor emits width: and height: parameters on the generated rollout
header. You can edit these numbers in the script editor and they will be honored by the layout
editor when you next edit that rollout.
For command panel rollouts and other scripted plug-ins, there are now symbolic
constants provided that produce the correct width automatically. These are:
#cmdPanel
#effectsDlg
#mtlEditor
so, to set up the rollout for a scripted material (p. 1565), you’d add a width: parameter to
the rollout header like this:
rollout foo “Frabulation” width:#mtlEditor
(
...
• You add new UI items by clicking its button in the item toolbar at the bottom and then dragging
out a rectangle for it in the main form. You can select an existing item and edit its paramters in
the property list on the right. You can select multiple items by fence-dragging or ctrl-clicking
and perform various alignments operations, see the Layout menu. A selected item can be deleted
by clicking the red X toolbar button. The various panes can be resized or even torn off if you
want to customize the editor layout.
• Axis restriction works by holding the shift down while moving objects. This will restrict
movement to the X or Y axis based on the angle of the mouse from its initial position.
• editText boxes in the editor can now be multi-line, consistent with the mulit-line editText in
MAXScript (p. 108).
• Editing in the Array editor dialog has been rationalized and improved. Clicking on an item in
the list box toggles the selection state of it. When items are selected in the list box, changing
text in the edit field and hitting enter changes all the selected items to what was in the edit box,
this allows for editing of entries in the middle of the list.
• A new custom item type has been added to the item type toolbar at the bottom of the VisualMS
dialog, allowing custom items to be created from scratch in the editor. Its icon appears in the
toolbar as a face in profile. When first created, the item class parameter in the parameter list
shows as ‘???’ and must be edited to contain the desired custom item type.
• An ActiveX control rollout item type is available in MAXScript. The icon for it appears in the UI
item toolbar at the bottom of the VisualMS dialog, as a dot array with the word OLE
superimposed. ActiveX Controls in MAXScript Rollouts (p. 10)
120 Chapter 1 | What’s New in 3ds max 4 MAXScript
• Editing an existing rollout source that contains any unrecognized UI item types, such as those
added from 3rd-party .dlx MAXScript extensions appear in the VisualMS rollout window as new
‘custom’ items, displaying as a rectangle containing the new ‘custom’ type icon. Any definition
parameters on are displayed and editable in the parameter list, and overall position and size of
the bounding rectangle of the custom type can be edited in the rollout pane.
• You can de-select everything by clicking in the white space around the main form.
• The main form always has a black rectangle drawn around it even when deselected. This allows
you to see the form if both the background of the application and the form are the same color.
• Resizing of the main form now snaps to the grid if it is on.
• The paste command now works much better. Pasted objects are offset by [10,10] pixels,
maintain unique names, and then pasting everything is de-selected and the pasted objects get
selected.
• When editing an existing rollout definition that makes use of autmatic layout in VMS for the
first time, it is highly recommended that you add a ‘width:n’ parameter to the rollout header
first so that the editor can position items correctly.If no width: parameter is supplied, it
defaults to Command Panel width which may be too small for floating window rollouts or
scripted materials or effects.
For rollouts that will appear in a rolloutFloater, you should set the rollout width: equal to
the floater window width minus 30.
Example:
rollout foo “Frabulation” width:#270
(
...
)
...
rf = newRolloutFloater “Frabo” 300 220
addRollout foo rf
Xref Objects
Topic: version 4 MAXScript New Features/Xref Objects
An updated function published interface for Xref Objects.
Interface: objXRefs (p. 409)
Explicit References
A file being xref’d that has a script controller whose script has explicit references ($sphere01, etc.)
to objects in the incoming xref file have a potential problem for the script writer. The problem is,
the objects in the xref file are invisible to the scripter, and so a script will fail. This is actually a
general problem with xrefs, you cannot have scripts of any kind in the file (scripts controllers, param
wires, callback scripts, etc.) that depend on explicit scene object references.
Multi-line editText UI items in Scripted Rollouts 121
The persistent global solution is the only one that is viable at this time. There are two general
solutions: 1) associate an owning-scene context with controller scripts, etc., when they come in via
xref and use that to anchor pathname searches and other scene-relative references, and 2) have an
accessible ‘evaluation context’ for controllers sent as part of the GetValue() call, so we can know
what object’s parameter the current GetValue() call is being made for and can therefore get rid of
many of the uses of explicit pathnames in the scripts.
Currently, MAXScript now fully loads any persistent globals in xref’d and merged files, but does NOT
make them persistent in the current scene. As an example of a setup showing how this can be used,
imagine a file with 3 spheres that will be xref’d. You need to establish persistent globals for all the
scene objects to be referrenced in controller scripts, like this:
persistent global s1 = $sphere01, s2 = $sphere02, s3 = $sphere03
this has to be run sometime while the to-be-xrefed scene is the currently open scene. Then
in the controller scripts, you’d say something like:
global s1, s2
dependsOn s1 s2
(s1.pos + s2.pos) / 2
Note this uses ‘global’ not ‘persistent global’, so you don’t go making them persistent
again when they get xref’d into some other scene.
See Also
XRef Files (p. 1643)
XRefScene Values (p. 1038)
XRefObject : Node (p. 1037)
xrefs const StructDef (p. 259)
xrefPaths const StructDef (p. 259)
Interface: objXRefs (p. 409)
122 Chapter 1 | What’s New in 3ds max 4 MAXScript
Example:
name “test package”
version 3
treeCopy flobber to $scripts
copy *.ms to $scripts\flobber\dobber
move foo.max $scenes
drop $scenes\foo.max
The zip package is a text file that contains one or more of the following commands. All are optional.
name “<package_name>“
Names the package.
description “<text>“
Describes the package. Normally, a readme file in the package would give extended
operating instructions, if they are provided.
version <number>
Returns the version number of the package.
extract to “<directory>“
Specifies the location in which to extract the contained files. This can be an absolute path
name (starting with a drive letter or \) or a relative name. Relative names are taken as
being relative to the default temp directory. The special prefix $max can be used to specify
the main MAX executable directory
run “<script_file_name>“
If the package is launched from a MAXScript run menu item or via a fileIn() function, run
the named script file. There can be more than one run command and they are run in
order. These are ignored if the package is launched via a fileIn() call that is supplied with
an explicit script file to run.
drop “<dropScript_file_name>“
If the package is launched by drag-and-drop into MAX, run the named dropScript file.
There can only be one of these per msp.startup file.
copy “<files>“ to “<directory>“
Copies the named file or files (if the <files> string contains wild-cards) to the given
directory. The special $max prefix can be used here.
clear temp
Cause the temporarily-extracted files to be deleted once all the nominated scripts are run
or dropped.
clear temp on MAX exit
Cause the temporarily-extracted files to be deleted when the currently running MAX
session exits.
clear temp on reset
Cause the temporarily-extracted files to be deleted when a file open or reset is performed.
keep temp
Prevents any deletion of the extracted files.
124 Chapter 1 | What’s New in 3ds max 4 MAXScript
File Searches:
The following functions will perform searches for files given as relative file names in the current
package file:
fileIn <filename> (p. xlix)
include <filename> (p. lix)
openBitmap <filename> (p. 755)
editScript <filename>
Note:
Any saves will not go back into the package, but into the temp extracted file.
loadMAXFile <filename>
mergeMAXFile <filename> ...
getMAXFileObjectNames <filename>
importFile <filename> ...
loadMaterialLibrary <filename>
Bitmap Searches:
The following UI items will search for named bitmap .bmp files in the package:
bitmap <name> fileName:<filename>
button <name> images:<image_spec_array>
checkButton <name> images:<image_spec_array>
These cause files from within the package to be copied or moved as specified. The treeCopy &
treeMove variants move whole nested directories of files. By default, any existing files in the
destination location are replaced with the newly extracted ones, add the ‘noReplace’ keyword to
prevent this.
The <to> spec must always be a directory. Any treeCopy/Move replicates the source sub-directories
into the <to> directory, making new directories as needed. The <from> spec for copy & move may
be any relative or fully specified file name or wild-card pattern. Relatively named files are looked for
in that relative position in the package. Fully specified names are looked for in the main file-system.
The <from> spec for treeCopy/Move may be just a directory path, in which case the whole directory
and its subdirectories are copied/moved, or it can be a wild-card path name in which case just the
matching files or directory trees are copied/moved.
Multi-line editText UI items in Scripted Rollouts 125
The file path names you can specify in the various commands (extract to, run, copy, move, etc.) can
have a starting path that is one of several special names beginning with $. These name useful
locations in the currently running MAX installation.
The $ names recognized are:
$max - main MAX executable directory
$maps - first directory in Maps directory config
$scenes - scenes directory
$fonts - fonts directory
$imports - imports directory
$sounds - sounds directory
$matlibs - matlibs directory
$scripts - scripts
$startupScripts - auto-load startup scripts
$plug-ins - first in the Plug-ins directory config
$plugcfg - plugcfg
$images - images
$ui - UI
$macroScripts - macroScripts in UI directory
$web - web directory
$temp - system temp directory
These directories reflect any customization the user has set up in the various preference dialogs.
Example:
If you had set up a package with several scenes, plug-ins & map files in several directories in the
package, you could install them with some move commands in the mzp.run file, something like this:
move “plug-ins\*.*” to “$plug-ins”
move “*.max” to “$scenes”
move “texmaps\*.bmp” to “$maps”
Note:
As an added feature, if the scripts run from within a package define any functions, macroScripts,
plug-ins, rollouts, or any major MAXScript value or construct that might live longer that the
running script, then the package is ‘associated’ with that defined value or construct and will again
become the initial search location whenever the functions or handlers in the rollouts/plug-ins/
macroScripts/etc. are later run.
Winzip:
You can initially create a .mzp with a zip utility such as WinZip. You can then associate that utility
with the .mzp type, so simple double-clicking a .mzp file will open it in that editor. You only need
to set up this association once, and you can do this in the Windows Explorer by selecting a .mzp file,
shift-right-clicking on the selected file and choosing “Open with...” in the popup menu that
appears. Scroll the application list that appears to find you desired zip utility and check the “Always
use this program ...” checkbox at the bottom of the dialog.
msZip Interface:
The MAXScript zip package interface (p. 378) has exposed 2 scripter-callable functions:
msZip.fileInPackage <mzpFilename> &<exractDirVar>
and will return true if success or false if there is a failure, or a missing or invalid .mzp file, and it will
also return the directory that the package file were extracted to in the pass-by-reference
<extractDirVar> argument.
Example:
local extractDir = ““
if msZip.fileInPackage “foo.mzp” &extractDir then
(
-- extractDir contains the extracted-to directory name
...
)
The ‘unloadPackage’ function performs an extract and executes all the file copying and moving
commands in any enclosed mzp.run file, but will not execute any scripts in the package. The
extractTo directory and any ‘drop’ command file found will be returned in the pass-by-reference
arguments.
Example:
local extractDir = ““, dropFile = ““
if msZip.unloadPackage’ “foo.mzp” &extractDir &dropFile then
(
-- extractDir contains the extracted-to directory name
-- dropFile contains any found drop file name (the path to extracted
location )
...
)
See Also
i-drop - drag and drop (p. 62)
Additional Keyword Parameter On pickObject() forceListenerFocus: 127
See Also
Picking Scene Nodes By Hit (p. 1618)
RubberBanding in pickObject() Function (p. 136)
See Also
Affect Region : Modifier (p. 1103)
128 Chapter 1 | What’s New in 3ds max 4 MAXScript
See Also
Class and Object Inspector Functions (p. 799)
Class and Object Inspector Functions Enhanced (p. 159)
See Also
FileStream Values (p. 763)
Example:
function foo x y &z =
(
...
z = x * y
...
return true
)
Declares a function taking three parameters, x, y and z. The &z in the parameter list indicates
the z parameter is to be passed by-reference. To call this function, you provide a reference value
for the z parameter using the new ‘&‘ reference operator.
Example:
local var1, var2
...
var1 = foo 2 3 &var2
Calls the foo function with the arguments 2, 3 and &var2. The &var2 is a reference to
the var2 local variable. When the function is called, the z parameter in the body is a
reference to var2 local in the caller, and the
z = x * y
assignment in the body of foo will cause x * y to be assigned to the var2 local in the
caller. After
var1 = foo 2 3 &var2
var1 will contain true and var2 will contain x * y or 6.
Any number of by-reference parameters can be used and they can be keyword parameters if needed:
fn foo x y &z: = ...
called like this:
var1 = foo 2 3 z:&var2
The ‘&’ reference operator used to supply references in a call can be applied to any
<accessor> construct in MAXScript. These are:
variables (locals, globals, rollout locals, plug-in locals, etc.)
property access
array index
parameter (of a scripted plug-in)
Example:
p = [1, 2, 3]
foo 2 3 &p.x
would cause the x coordinate in the point to be passed by-reference and so after the call,
the value in p would be
[6, 2, 3]
C++-style bracketing comments 131
Example:
a = #(1, 2, 3, 4, 5)
foo 2 3 &a[3]
would cause the 3rd element in the array to be passed by-reference and so after the
call, the value in a would be #(1, 2, 6, 4, 5)
Note:
This mechanism is used by the Function Publishing interface in MAXScript to support BY-REF
interface method parameters and results. Any parameter defined as by-ref (or with a type code
suffix _BR) in the published interface, requires an ‘&’ reference value.
See Also
Dereferencing Operator (p. 133)
Visible Class For ‘&’ Reference Values (p. 142)
You can also use this within a line to comment out a script fragment:
for i in 1 to 10 do ( /* messageBox “in loop”; */ frabulate i )
Note:
The /* and */ have to be adjacent characters. If you leave out the closing */ or make it * /, the rest of
the file will be commented out.
See Also
MAXScript Editor Commands (p. xlvi)
Source Code Layout (p. 580)
Source Code Layout and Continuation Lines (p. lvii)
132 Chapter 1 | What’s New in 3ds max 4 MAXScript
Example:
a=#{1..5,10)
b=a as array
c=b as bitarray
Return Value:
Returns the number of bits set
.isEmpty
Return Value:
Returns true if no bits are set and false if one or more bits are set.
Example:
a=#{1..5,10..20}
a.numberset --> 16
a.isEmpty --> false
a=#{}
a.numberset --> 0
a.isEmpty --> true
The ‘*’ operator has been added to bitArrays which performs an ‘AND’ operation:
<bitarray> * <bitarray> -- intersection (”AND” operation)
See Also
BitArray Values (p. 791)
Value Common Properties, Operators, and Methods (p. 714)
Command line -U MAXScript startup scripts 133
See Also
Running Scripts from the Command Line (p. lvii)
See Also
Node Common Properties, Operators, and Methods (p. 820)
Dereferencing Operator
Topic: version 4 MAXScript Language Improvements/Language Improvements
Visible Class For ‘&’ Reference Values (p. 142)
A Function Published dereferencing prefix operator, *, has been added to MAXScript. This can be
used in conjunction with the new ‘&’ reference operator that was added to support pass-by-reference
arguments to functions and interface methods.
The ‘&’ operator is used to get a ‘reference’ to a variable or property or array element slot in
MAXScript. You can pass this reference in to a function that accepts by-reference arguments,
allowing its code to directly assign values to the referenced variable or property or array element,
thus supporting a kind of multiple-value return.
The new ‘*’ operator allows you to work with ‘&’ reference values anywhere in MAXScript code.
Therefore ‘dereference’ the reference and get the value in the slot or variable it is referring to and to
assign it to the referenced slot.
Examples:
ref = &$foo.pos
this puts a value into ref which is a reference to the .pos property in the scene object $foo.
Elsewhere in the code, you could use the new ‘*’ dereferencing operator to say:
$baz.pos = *ref
the ‘*’ dereferences the reference value in ref, essentially making this equivalent to:
$baz.pos = $foo.pos
you can also use this construct as a destination for an assignment:
134 Chapter 1 | What’s New in 3ds max 4 MAXScript
*ref = [10,0,0]
first dereferences the reference in ‘ref’ to $foo.pos and then assigns to that, effectively
setting $foo’s position.
In order to avoid ambiguity with the ‘*’ multiply operator, the precedence of the ‘*‘ dereferencing
operator is set at just lower than the function call and just higher than the ‘as’ coercion operator.
This means that if you want to send a dereferenced value into a function as an argument, you must
surround the dereferencing with parentheses, as in:
foo (*ref) x y z
Remember that reference values can be generated for variables, properties and array elements, as
Example:
&foo
&$box.position.x
&valArray[23]
The ‘*’ dereferencing operator is a moderately advanced feature in MAXScript that is often used to
allow very general purpose code to be written that uses references instead of actual objects so that it
can be applied to different kinds of objects and properties at different times.
Nested property access allowed in ‘&’ reference values in MAXScript. This allows constructs like:
r = &$foo.pos, and later *r.controller to mean $foo.pos.controller.
See Also
By Reference Parameter Passing (p. 129)
See Also
UVWUnwrap interfaces: (p. 568)
Unwrap UVW interfaces: (p. 530)
hasProperty() function 135
hasProperty() function
Topic: version 4 MAXScript Language Improvements/Language Improvements
Prototype:
hasProperty <obj> <prop_name_or_pattern_string>
Return Value:
Returns true if the object has the given property.
See Also
Properties, Methods, Operators, and Literals (p. lxiv)
See Also
Node Common Properties, Operators, and Methods (p. 820)
Readable/Writable Checks
Topic: version 4 MAXScript Language Improvements/Language Improvements
MAXScript now does readable/writable checks and throws an error if you try to read from a
write-only file and vice versa. Some modes are read/write, such as “a+” “w+” and “r+”.
See Also
FileStream Values (p. 763)
136 Chapter 1 | What’s New in 3ds max 4 MAXScript
isValidNode
Topic: version 4 MAXScript Language Improvements/Language Improvements
isValidNode <var>
Returns true if <var> is a node value, and the node has not been deleted. False otherwise.
See Also
Detecting Deleted Nodes (p. 133)
Node Common Properties, Operators, and Methods (p. 820)
If rubberBand: is supplied on the pickObject() call, it enables rubberbanding, with the given
<point3> as world-space coordinates for the start point of the rubber band. You can use the
rubberBandColor: argument to override the default line color of gray (color 128 128 128).
Example:
obj2 = pickObject rubberBand:obj1.pos rubberBandColor:yellow
See Also
Picking Scene Nodes By Hit (p. 1618)
Additional Keyword Parameter On pickObject() (p. 127)
SetDir
Topic: version 4 MAXScript Language Improvements/Language Improvements
SetDir <filetype_name> <string>
Sets the directory specified in string. Replicated in the Customize > Configure Paths dialog
for the specified file type.
Shortcut system replaced 137
Returns true if successful, false if not. Does not check to see if <string> is a valid path. Any change
made through this function is immediately reflected in the 3dsmax.ini file and so is persistent. Use
with caution.
See Also
3ds max System Directories (p. 1625)
from, and the “persistent id” if the action. Actions exported from core all have persistent
ids that are fixed integers as a string.
Actions are accessible, all that you need to know are the ActionTableId and the persistent ID in order
to invoke the operation.
Note:
Certain actions emit much better code. If an action is exported using a function published action
table, then the code it emits calls that function. For example, if you bring up the “Plug-in Manager”
from the customize menu, the code emitted is:
Plug-in_Manager.Plug-inMgrAction.show ()
If the action comes from a macro script, which many of our actions do, the code looks like:
macros.run “Modifiers” “Bend”
See Also
Action Manager (p. 9)
Interface: actionMan (p. 353)
startObjectCreation()
Topic: version 4 MAXScript Language Improvements/Language Improvements
The startObjectCreation() function has been enhanced.
startObjectCreation <maxobjclass> [returnNewNodes:<flag>] [newNodeCallback:<fn>]
The values that can now be supplied to the optional ‘returnNewNodes:’ keyword argument are true,
false (the default) or #first. If ‘true’ is supplied, all of the nodes created, up until the current create
mode is exited, will be returned in an array. If #first is supplied, only the first node created is
returned, immediately after it is created. The function doesn’t wait for the create mode to be exited
by the user.
The optional ‘newNodeCallback:’ keyword argument can supply a scripted function of one
argument to the create mode that is started, such that the function will be called each time a node
is created with the new node as its argument. This is similar to supplying pickObject() filter
functions, although the return value of the newNodeCallback: function is ignored. Note that the
callback function is invoked immediately upon new node creation, *before* any base object is
installed in it, so *only* node-related properties can be accessed and changed during this callback.
Example:
fn setColor n = n.wireColor = red
startObjectCreation box newNodeCallback:setColor
would cause all new boxes created in the started create mode to have red wire color.
The ‘returnNewNodes:’ and ‘newNodeCallback:’ can both be supplied on the same call; the callback
will be called on each node, and they will be returned in an array as the result of the
startObjectCreation() function.
Subanim Indexing Operator, [], on MAX Objects Now Takes Subanim Names 139
See Also
Create Panel (p. 1572)
Defining Macro Scripts (p. 1521)
Change Handlers and Callbacks (p. 1649)
callbacks const StructDef (p. 233)
The names you can use are those seen in the track view or retrieved with the functions
getSubAnimName() or getSubAnimNames().
See Also
Indexed Access to Animatable Properties in 3D Studio MAX Objects (p. 806)
See Also
Utilities, Global Utilities and Render Element plug-ins (p. 161)
Scripted Plug-ins (p. 1538)
140 Chapter 1 | What’s New in 3ds max 4 MAXScript
Symbolic Pathnames
Topic: version 4 MAXScript Language Improvements/Language Improvements
Support for $<name> symbolic pathnames to all the places that filenames can be supplied for
opening things in MAXScript. Any filename you give to MAXScript in the following situations can
begin with a ‘$’ followed by one of the symbolic directory names below.
Example:
fileIn “$scripts\foo.ms”
will open the file “foo.ms” in the current MAX scripts directory. The situations in which
MAXScript honors ‘$’ symbolic directories are as follows:
Functions:
fileIn()
openBitmap()
createBitmap() in the fileName: parameter
render() in the outputFile: parameter
Compiler directives:
include <filename_string>
Rollouts:
any bitmap image file names for buttons, checkbuttons, bitmap
The following symbolic names are recognized:
$max - main MAX executable directory
$maps - first directory in Maps directory config
$scenes - scenes directory
$fonts - fonts directory
$imports - imports directory
$sounds - sounds directory
$matlibs - matlibs directory
$scripts - scripts
$startupScripts - auto-load startup scripts
$plug-ins - first in the Plug-ins directory config
$plugcfg - plugcfg
$images - images
$ui - UI
$macroScripts - macroScripts in UI directory
$web - web directory
$temp - system temp directory
Please note that these are similar to the 3D Studio MAX System Globals (p. 630) filetype names which
start with a “#”.
See Also
Zip-file Script Packages (p. 122)
3D Studio MAX System Globals (p. 630)
System Information 141
System Information
Topic: version 4 MAXScript Language Improvements/Language Improvements
sysInfo const StructDef (p. 255)
sysInfo.windowsdir
A read only variable to get the Windows directory as a <string> value.
sysInfo.systemdir
A read only variable to get the Windows System directory as a <string> value.
sysInfo.windowsdir
A read only variable to get the Temp directory as a <string> value.
sysInfo.windowsdir
Variable to get/set the current directory as a <string> value.
sysInfo.username
A read only variable to get the user name as a <string> value.
sysInfo.computername
A read only variable to get the computer name as a <string> value.
sysInfo.cpucount
A read only variable to get the number of CPUs as a <integer> value.
See Also
System Tools (p. 112)
This method generates a random class ID similar to #(0x9b7ea231, 0xb6db86ef), and prints it to
Listener. You can just cut and paste this class ID into your script to use the generated ID.
MAX, and each plug-in falls into one of these predefined categories define the Super Class IDs. For
instance, all Texture Map plug-ins share the same Super Class ID of TEXMAP_CLASS_ID. Each
individual texture map plug-in has its own unique Class ID however. Thus, the Super Class ID
defines which kind of object it is, the Class ID uniquely identifies a specific plug-in class.
142 Chapter 1 | What’s New in 3ds max 4 MAXScript
See Also
Scripted Plug-ins (p. 1538)
Scripted Custom Attributes (p. 45)
Menu Manager (p. 75)
validModifier() function
Topic: version 4 MAXScript Language Improvements/Language Improvements
The validModifier() function improved so that it will take a modifier class in place of a modifier to
preclude the need to create a modifier to do the test.
Prototype:
validModifier <node_or_node_collection> <mod_or_mod_class>
It is recommended that classes be used in RCMenus and macroScripts using validModifier() to reduce
resource usage.
Example:
if validModifier $ Edit_Mesh then ...
instead of:
if validModifier $ (Edit_Mesh()) then ...
The MAXScript isValidModifier function will check if it has been passed a modifier that doesn’t exist
at runtime. It returns false in this case. It uses the ClassEntry to determine the InputType() of the
modifier.
See Also
Node Common Properties, Operators, and Methods (p. 820)
Modifier Common Properties, Operators, and Methods (p. 1096)
See Also
By Reference Parameter Passing (p. 129)
Dereferencing Operator (p. 133)
Controllers
List Controller
Topic: version 4 MAXScript Language Improvements/Controllers
The List controller combines multiple controllers into a single effect. It is a compound controller
with tools for managing the order in which its internal controllers are calculated. Controllers are
evaluated in a top to bottom order; the controller at the top of the list is evaluated first.
When you assign a List controller to a parameter, the current controller is moved one level below
the List controller; it becomes the first controller in the list. A second parameter is added below the
List controller and is named Available. This is an empty placeholder for the next controller you add
to the list.
ListCtrl const StructDef (p. 238)
Example:
lst = $.pos.controller -- if this is a list controller
showInterfaces lst -- interface name is “list”
Methods:
lst.getCount()
Returns the count function.
lst.count
Returns count property (read only).
lst.SetActive <index>
Set active function
lst.GetActive()
Get active function
lst.active
Get/set active property.
lst.cut <index>
Cut the indexed sub-controller
lst.paste <index>
Paste clip to index location.
lst.delete <index>
Delete the indexed sub-controller.
lst.setName <index> <string>
Sets the name of the indexed sub-controller.
144 Chapter 1 | What’s New in 3ds max 4 MAXScript
lst.getName <index>
Gets the name of the indexed sub-controller.
Example:
b = Box lengthsegs:1 widthsegs:1 heightsegs:1 length:65.7611 width:32.0211
height:39.8261 pos:[-15.6972,-84.9615,0] isSelected:on
b.pos.controller = position_list ()
b.pos.controller.Available.controller = Position_XYZ ()
b.pos.controller.Available.controller = tcb_position ()
b.pos.controller.Available.controller = bezier_position ()
lst = b.pos.controller -- the list controller
showInterfaces lst-- interface name is “list”
lst.getCount() -- count function
lst.count-- count property (read only)
lst.SetActive 3 -- set active function
lst.GetActive() -- get active function
lst.active-- active property
lst.cut 2-- cut the second sub-controller
lst.paste 1-- paste it to the top of the list
lst.delete lst.count -- delete the second to last sub-controller
lst.setName 2 “My Bezier” -- sets the name of the second sub-controller
lst.getName 2-- gets the name of the sub-controller
See Also
List Controllers (p. 1317)
mapKeys() method
Topic: version 4 MAXScript Language Improvements/Controllers
The mapKeys() method gives access to the SDK function Control::MapKeys().
The form is:
mapKeys <max_object> (<map_struct> | <fn> <arg>) [#allKeys] [#selection] *
[#slide] [#rightToLeft]
This is like other recursive controller key functions (p. 1294) in MAXScript, such as moveKeys,
deleteKeys, etc., which operate on all the keys in nested controllers in the object you supply. The
thing to be mapped is either a scripted function and argument pair or a struct instance. If a function
is supplied, it should take two arguments, the time value to be mapped and the <arg> from the
mapKeys() call, and pass back the mapped time.
Example:
fn bumpTime t delta = t + delta
mapKeys $foo bumpTime 23 #selection
will add 23 to all the selected keys in controllers within $foo.
If a struct is supplied, it should have at least a ‘map’ member function that takes a time to be mapped
and returns the mapped time. The advantage of a struct is that it is a way to set up complex
parameterized mapping by having as many data members as needed to hold the parameters.
moveKeys function 145
Example:
struct mapper
(
scale,
offset,
fn map t = return t * scale * offset
)
mapKeys $foo (mapper scale:0.5 offset:10)
See Also
Time and Key Functions on Object Hierarchies (p. 1299)
Nested Object Controller Functions (p. 814)
Controller Time Functions (p. 1292)
Controller Key Functions (p. 1294)
MAXKeyArray Values (p. 793)
moveKeys function
Topic: version 4 MAXScript Language Improvements/Controllers
moveKeys <key_array> <time> [ #selection ]
Moves all keys by the time given. If #selection is specified, move the current selection otherwise
move all keys.
moveKeys function only works on track properties, .controller and .track. It is not defined on the
keys virtual array.
Example:
moveKeys $box01.pos.controller 5
or:
moveKeys $box01.pos.track 5
See Also
Time and Key Functions on Object Hierarchies (p. 1299)
Nested Object Controller Functions (p. 814)
Controller Time Functions (p. 1292)
Controller Key Functions (p. 1294)
MAXKeyArray Values (p. 793)
146 Chapter 1 | What’s New in 3ds max 4 MAXScript
Properties:
<Hose>.End_Placement_Method Integer default: 1 -- integer
<Hose>.Generate_Mapping_Coordinates Integer default: 0 -- integer
Sets up required coordinates for applying mapped materials to the hose. Default=off.
<Hose>.Hose_Height Float default: 1.0 -- animatable;
float
Use this field/spinner to set the straight-line height or length of the hose when it is not
bound. This is not the actual length of the hose. Available only when Free Hose is chosen.
<Hose>.Segments_Along_Hose Integer default: 45 -- animatable;
integer
The total number of segments in the hose’s length. Increase this setting for a smooth
profile when the hose is curved. Default=16.
<Hose>.Smooth_Spring Integer default: 0 -- integer
Choose one of the following smoothing options:
All: The entire hose is smoothed.
Sides: Smoothing is applied along the length of the hose but not around its circumference.
None: No smoothing is applied.
Segments: Smoothing is applied only on the inner section of the hose.
<Hose>.Renderable_Hose Integer default: 1 -- integer
When on, the hose is rendered using the specified settings. When off, the hose is not
rendered. Default=on.
<Hose>.Hose_Cross_Section_Type Integer default: 0 -- integer
Sets a circular cross-section.
Lets you specify different settings for width and depth.
Similar to Rectangular Hose, but rounds one side for a D-shaped cross-section.
<Hose>.Round_Hose_Diameter Float default: 0.2 -- animatable;
float
The maximum width of the hose at the ends.
Hose - superclass: GeometryClass 147
See Also
GeometryClass Common Properties, Operators, and Methods (p. 852)
Node Common Properties, Operators, and Methods (p. 820)
MAXWrapper Common Properties, Operators, and Methods (p. 809)
Value Common Properties, Operators, and Methods (p. 714)
Drag - superclass: SpacewarpObject 149
Constructor:
Drag ...
Properties:
<Drag>.‘time on’ Integer default: 0 -- integer; Time_On
The frame numbers at which the space warp becomes active and becomes inactive.
<Drag>.‘time off’ Integer default: 16000 -- animatable; integer;
Time_Off
The frame numbers at which the space warp becomes active and becomes inactive.
<Drag>.symmetry Integer default: 0 -- radio button number;
Damping_Symmetry
This group lets you choose Linear Damping, Spherical Damping, or Cylindrical Damping,
plus a set of parameters for each.
<Drag>.dampingx Float default: 5.0 -- animatable; percentage;
X_Damping; Controller Scaling: (1 : 100.0)
Specifies the percentage of particle motion along the local Drag space warp axis that’s
affected by the damping.
<Drag>.rangex Float default: 100.0 -- animatable; float; X_Range
Sets the thickness of the “range plane,” or the infinite plane perpendicular to the specified
axis. Takes effect only when Unlimited Range is turned off.
<Drag>.falloffx Float default: 1000.0 -- animatable; float;
X_Falloff
Specifies the distance beyond the X, Y, or Z Range within which Linear Damping is
applied. Damping is strongest at the Range distance, decreases linearly out to the limit of
the Falloff, and has no effect beyond that. While Falloff is effected only beyond the Range,
it is measured from the center of the icon, and always has a minimum value equal to the
Range value. Takes effect only when Unlimited Range is turned off.
<Drag>.dampingy Float default: 0.0 -- animatable; percentage;
Y_Damping; Controller Scaling: (1 : 100.0)
Specifies the percentage of particle motion along the local Drag space warp axis that’s
affected by the damping.
150 Chapter 1 | What’s New in 3ds max 4 MAXScript
See Also
Modifier and SpacewarpModifier Types (p. 1100)
MultiRes - superclass: modifier 153
Properties:
<MultiRes>.Vtx_Count Integer default: 0 -- animatable;
integer
The total number of vertices in the modified object. Use this control to set the maximum
number of vertices in the output mesh. Adjusting this setting alters the Percent value
as well.
<MultiRes>.Vertex_Percentage Float default: 100.0 --
animatable; float
The modified object’s vertex count as a percentage of the overall number of vertices in the
original mesh. Adjusting this setting alters the Count value as well.
Note: After you type in a specific percentage, such as 30, you might find that the software
changes the value to a slightly lower one, such as 29.971. This is due to the relationship
between the overall number of vertices in the model and the percentage calculation. It is
not a bug, but simply the closest solution to your request.
<MultiRes>.Vertex_Merging BooleanClass default: false -- boolean
When on, lets MultiRes merge vertices between discrete elements in a model.
For example, if you apply MultiRes to a teapot, which comprises four separate elements,
and turn on Vertex Merging, as you adjust the vertex resolution, the separate components
will meld together into one contiguous lower-resolution object.
To control Vertex Merging, you can set a Merge Threshold. This value determines the
3ds max unit distance within which to merge elements.
<MultiRes>.Threshold Float default: 0.0 -- float
This spinner value sets the maximum distance in 3ds max units between vertices in order
for those vertices to be considered for merging. Once this threshold is achieved, then the
vertices between elements will be welded together as the mesh is reduced in complexity.
Note: To eliminate only coincident vertices, set Merge Threshold to 0.0. This is similar to
the Weld Vertex function.
154 Chapter 1 | What’s New in 3ds max 4 MAXScript
general, crease angles approaching 0 yield smoother shading. Crease angles approaching
180 yield more visible corners.
<MultiRes>.Crease_Angle Float default: 75.0 -- float
The value of the crease necessary in order to generate multiple normals. Available only
when Multiple Normals Per Vertex is on.
The optimal crease angle depends on the model; set it interactively and check the viewport
and rendered images for shading effects. While use of multiple normals per vertex enables
more accurate shading, it can require more internal data.
<MultiRes>.Generate BooleanClass default: false -- boolean
Applies the current MultiRes settings to the modified object. When you first apply
MultiRes to an object, it must initialize its mesh-optimizing algorithm; you are prompted
by the modifier to “Generate when ready”.
Note: When working with complex meshes, the initial analysis may take a little while.
During this time, MultiRes displays a special cursor to indicate it is working. Progress is
indicated on this cursor by the movement of the gray area from top to bottom. To cancel
this process, press ESC.
Example:
modPanel.addModToSelection(MultiRes())
$.modifiers[#MultiRes].Vtx_Count = 482
$.modifiers[#MultiRes].Vertex_Percentage = 100
$.modifiers[#MultiRes].Vertex_Percentage = 99
$.modifiers[#MultiRes].Vtx_Count = 476
$.modifiers[#MultiRes].Vertex_Percentage = 98.7552
$.modifiers[#MultiRes].Vertex_Merging = on
$.modifiers[#MultiRes].Threshold = 0.01
$.modifiers[#MultiRes].Merge_Within = on
$.modifiers[#MultiRes].Boundary_Metric = on
$.modifiers[#MultiRes].Maintain_Base_Vertices = on
$.modifiers[#MultiRes].Crease_Angle = 75.75
See also
Modifier Common Properties, Operators, and Methods (p. 1096)
MAXWrapper Common Properties, Operators, and Methods (p. 809)
Value Common Properties, Operators, and Methods (p. 714)
156 Chapter 1 | What’s New in 3ds max 4 MAXScript
Properties:
<Vortex>.‘time on’ Integer default: 0 -- integer; Time_On
The frame numbers at which the space warp becomes active and becomes inactive.
<Vortex>.‘time off’ Integer default: 16000 -- animatable;
integer; Time_Off
The frame numbers at which the space warp becomes active and becomes inactive.
<Vortex>.axialstrength Float default: 0.1 -- animatable; float;
Axial_Drop_Strength
Specifies how quickly particles move in the direction of the drop axis.
<Vortex>.axialrange Float default: 100.0 -- animatable;
float; Axial_Range
The distance from the center of the Vortex icon, in system units, at which Axial Damping
has its full effect. Takes effect only when Unlimited Range is turned off.
<Vortex>.axialfalloff Float default: 1000.0 -- animatable;
float; Axial_Falloff
Specifies the distance beyond the Axial Range within which Axial Damping is applied.
Axial Damping is strongest at the Range distance, decreases linearly out to the limit of the
Axial Falloff, and has no effect beyond that. Takes effect only when Unlimited Range is
turned off.
<Vortex>.axialdamping Float default: 5.0 -- animatable;
percentage; Axial_Damping; Controller Scaling: (1 : 100.0)
Controls the degree to which particle motion parallel to the drop axis is restrained per
frame. Default=5.0. Range=0 to 100.
For subtle effects, use values of less than 10%. For more overt effects, try using higher
values that increase to 100% over the course of a few frames.
<Vortex>.rotationstrength Float default: 0.5 -- animatable; float;
Orbital_Speed_Strength
Specifies how quickly the particles rotate.
Vortex - superclass: SpacewarpObject 157
See Also
Node Common Properties, Operators, and Methods (p. 820)
MAXWrapper Common Properties, Operators, and Methods (p. 809)
Value Common Properties, Operators, and Methods (p. 714)
Keys
Bezier Keys inTangentLength and outTangentLength
Topic: version 4 MAXScript Language Improvements/Keys
There are 2 additional properties in MAXScript for bezier keys .inTangentLength and
.outTangentLength. These are the handles’ magnitude in frames.
There is a new check box to the key property/Master Point control dialog found in the Motion Panel.
It is called Free Handle. When Free Handle is checked, the user can move the horizontal handle
where ever s/he feels. Otherwise, s/he is constrained, to prevent discontinuities.
Correspondingly, there is a new bezier key property called .freeHandle that implements the
functionality described above.
Note:
There are a fair number of classes that don’t implement the showproperties method. MAXKey is one
of them. getPropNames is not implemented for it either.
See Also
MAXKey Values (p. 767)
MAXKeyArray Values (p. 793)
MAXKey Common Properties, Operators, and Methods (p. 768)
Working with MAXKey Values (p. 769)
Class and Object Inspector Functions Enhanced 159
See Also
Core Interfaces (p. 70)
Other Interfaces (p. 71)
Renderer
See Also
Controlling the Renderer (p. 1664)
Interface: NetRender (p. 379)
Bitmap Manager – Function Published BMM control 161
SuperClasses
See Also
BMP, PNG, JPEG and TGA I/O Interfaces (p. 164)
BMP interfaces: (p. 437)
Portable Network Graphics interfaces: (p. 473)
JPEG interfaces: (p. 454)
Targa interfaces: (p. 529)
See Also
Render Element Manager (p. 92)
Plug In Manager (p. 86)
Plug-in Manager interfaces: (p. 473)
Visual MAXScript (p. 117)
162 Chapter 1 | What’s New in 3ds max 4 MAXScript
Renderer
Topic: version 4 MAXScript Language Improvements/SuperClasses
A MAXClass wrapper added for the plug-in renderer superclass so that a renderer instances can be
worked with in MAXScript. The new superclass is named “Renderer”.
See Also
Controlling the Renderer (p. 1664)
Interface: NetRender (p. 379)
See Also
Scripted Cameras (p. 94)
Scripted Manipulators (p. 97)
In prior releases, globals had to be declared inside on-handler bodies. Any initializers present in a
global declaration like this are at compile time, so the initial value expressions must be executable
at the time the script is compiled.
See Also
Scope of Variables (p. 646)
See Also
Definition Constructs Can Include Global Variable Declarations At Top Level (p. 162)
Scope of Variables (p. 646)
See Also
Material Editor (p. 1606)
Material Editor Access (p. 165)
Material Level Show-in-viewport State (p. 166)
164 Chapter 1 | What’s New in 3ds max 4 MAXScript
See Also
bitmapTex interfaces: (p. 434)
BitmapTexture : TextureMap (p. 1243)
BMP, PNG, JPEG and TGA I/O Interfaces (p. 164)
Material Editor Access (p. 165)
Accessing The Material Editor Active Slot (p. 163)
Material Level Show-in-viewport State (p. 166)
showTextureMap() function (p. 167)
Prototype:
<boolean>OkMtlForScene <material>mtl
Parameters:
<material>mtl
The pointer to the material.
Return Value:
This method is available in release 4.0 and later only.
Before assigning material to scene, call this to avoid duplicate names.
Prototype:
<void>UpdateMtlEditorBrackets()
Remarks:
This method is available in release 3.0 and later only.
This method makes sure the Materials Editor slots correctly reflect which materials are used in the
scene, which are used by selected objects, etc. This is used internally for the drag-and-drop of
materials to nodes -- there is no reason why a plug-in developer should need to call it.
See Also
Interface: medit (p. 371)
BitmapTex Reload and viewImage (p. 164)
See Also
Material Common Properties, Operators, and Methods (p. 1203)
i-drop - drag and drop (p. 62)
showTextureMap() function 167
showTextureMap() function
Topic: version 4 MAXScript Language Improvements/Material Editor, Material and Textures
The showTextureMap() function has been updated to allow control over material level texture
showing in the viewport. The full form is now:
showTextureMap <material> [<texmap>] <boolean>
If the optional <texmap> is supplied, it must be a direct subtexture of the supplied material and its
show-in-viewport state will be set on or off according to the <boolean> argument. If only a
<material> is supplied, its show-in-viewport state will be set by the <boolean> argument.
Example:
showTextureMap $foo.material on
showTextureMap $foo.material $foo.material.diffusemap off
Note:
Mapping coordinates aren’t explicitly enabled for the objects at creation time. When a script is
run in the Listener, using ‘showTextureMap’ is indirectly turning mapping coordinates on. This
happens during the scene redraw which happens after each line is executed, if needed. If a script
is run from a script editor, or if you put parenthesis around a script, no scene redraw is
performed until the entire script is run. Since no redraw is performed, no mapping coordinates
exist on the object when the script tries to access them. Solutions: explicitly perform a scene
redraw [redrawViews()] after ‘showTextureMap’, or explicitly turn on mapping coordinates for
the object.
See Also
Material Editor (p. 1606)
TextureMap Common Properties, Operators, and Methods (p. 1235)
Material Level Show-in-viewport State (p. 166)
Accessing The Material Editor Active Slot (p. 163)
Material Editor Access (p. 165)
168 Chapter 1 | What’s New in 3ds max 4 MAXScript
User Interface
Angle UI element
Topic: version 4 MAXScript Language Improvements/User Interface
The Angle UI element:
• Display of caption string
• Handling of align layout parameter
• StartDegrees and startRadians properties - controls the zero degrees position
• Dir property - either #cw or #ccw (default #ccw)
• Range property - point3 specifying min, max, and value in degrees.
• If min and max values are the same sign, click and move in angle UI will give result of correct
sign. If min and max are different signs, shift or ctrl click will give negative result, click will give
positive result.
Example:
rollout test “ Angle Test”
(
Angle ang2 “Angle” diameter:40 align:#center range:[-180,180,45] startdegrees:270
dir:#cw
)
createdialog test 200 100
See Also
Rollout User-Interface Controls (p. 1481)
Rollout User-Interface Controls Types (p. 1484)
Rollout User-Interface Controls Common Layout Parameters (p. 1483)
Rollout User-Interface Controls Common Properties (p. 1481)
CreateDialog 169
CreateDialog
Topic: version 4 MAXScript Language Improvements/User Interface
CreateDialog has been enhanced. The prototype is now:
CreateDialog <Rollout> [<height> <width> <position_x> <position_y>] \
[pos:<Point2>] [width:<integer>] [height:<integer>] \
[bgcolor:<color>] [fgcolor:<color>] \
[bitmap:<bitmap>] {bmpstyle:<bmpstyle> \
[menu:<RCMenu>] [style:<array>] [modal:<boolean>]
Modal dialog support added to MAXScript scripter dialogs, those created with the CreateDialog()
function. A new keyword argument can be supplied to the CreateDialog() function,
modal:<boolean>, to control whether the dialog is modal or not. Defaults to modal:false.
A modal dialog ignores all user interactions except those within the dialog. Call DestroyDialog() to
close it, presumably in a scripted OK button, or the like. The user can also close a modal scripted
dialog by hitting the <escape> key.
Associated Methods:
Prototype:
<Point2> GetDialogPos <Rollout>
Remarks:
Returns the position of the Dialog built from the rollout relative to the upper left corner of the screen
in Point2 format.
Prototype:
SetDialogPos <Rollout> <Point2>
Parameters:
<Rollout>
The rollout used to build the Dialog to set the position of.
<Point2>
Position where to place the Dialog.
Remarks:
Sets the position of the dialog built from the rollout relative to the upper left corner of the screen.
See Also
MAXScript Dialogs and Rollout Floaters as Extended viewports (p. 186)
170 Chapter 1 | What’s New in 3ds max 4 MAXScript
Curve Control
Topic: version 4 MAXScript Language Improvements/User Interface
uiFlags:
Any combination of the following flags:
#drawBG, #drawgrid, #upperToolbar, #showReset, #scrollBars, #constrainY,#xvalue
rcmFlags:
Any combination of the following flags:
#move_xy, #move_x, #move_y, #scale, #corner, #bezier, #delete, #all
Properties:
<curvecontrol>.visible : Boolean
<curvecontrol>.x_range : Point2
Curve Control 171
<curvecontrol>.y_range : Point2
<curvecontrol>.displayModes : BitArray
<curvecontrol>.commandMode : Name
<curvecontrol>.zoomValues : Point2
Note:
The following will automatically do a zoom extents all:
zoom <curvecontrol> #all
<curvecontrol>.scrollValues : Point2
<curvecontrol>.curves : Array, read-only
Returns an array of curves of type MAXCurve
Events:
In the following events <ci> represents the active Curve Index.
on <curvecontrol> selChanged <ci> <val> do <expr>
Sent when a point is selected or deselected. <val> is the number of points, which
are selected.
on <curvecontrol> ptChanged <ci> <val> do <expr>
Sent when a point is changed, <val> is the index of the changed point
on <curvecontrol> tangentChanged <ci> <val> type do <expr>
Sent when a point’s in or out tangent is changed, <val> is the index of the changed point
type is #inTangent or #outTangent, depending on what changed.
on <curvecontrol> deleted <ci> <val> do <expr>
Sent when a point is deleted, val is the index of the deleted point.
on <curvecontrol> reset <ci> do <expr>
Sent when a curve is reset
ccCurve represents a single curve in a curve control
Properties:
<ccCurve>.animatable : Boolean
<ccCurve>.color : Color
<ccCurve>.disabledColor : Color
<ccCurve>.width : Integer
<ccCurve>.disabledWidth: Integer
<ccCurve>.disabledStyle : Name
<ccCurve>.style : Name
these are the drawing styles for the curves, can be any one of the following
#solid, #dash, #dot, #dashDot, #dashDotDot, #null, #insideFrame
<ccCurve>.lookupTableSize: Integer
This method sets the size of the Curve Control lookup table. The lookup table allows users of the
Curve Control to easily speed up their value access. The default value for the lookup table size is
1000. Used when getValue() is called on the curve.
172 Chapter 1 | What’s New in 3ds max 4 MAXScript
<ccCurve>.numPoints: Integer
<ccCurve>.points: Array, read-only
Returns a CurvePointsArray
Methods:
getValue ccCurve <time_value> <float_x> [lookup:<false>]
Returns a Point2
isAnimated ccCurve <index>
Returns a Boolean value
getSelectedPts ccCurve
Returns a BitArray
setSelectedPts <ccCurve> <bitarray> [#select] [#deSelect] [#clear]
setPoint <ccCurve> <index> <ccpoint> [checkConstraints:<true>]
getPoint <ccCurve> <index>
insertPoint <ccCurve> <index> <ccpoint>
deletePoint <ccCurve> <index>
CurvePointsArray represents an array of curve points. CurvePointValue represents a
curve point.
CurvePointValue represents a curve point, you create a curve point like:
ccPoint <pt_point2> <in_point> <out_point2> \
[bezier:<false>] [corner:<false>] [lock_x:<false>] [lock_y:<false>] \
[select:<false>] [end:<false>] [noXConstraint:<false>]
Properties:
<ccpoint>.value: Point2
<ccpoint>.inTangent: Point2
<ccpoint>.outTangent: Point2
<ccpoint>.bezier: Boolean
<ccpoint>.corner: Boolean
<ccpoint>.lock_x: Boolean
<ccpoint>.lock_y: Boolean
<ccpoint>.selected: Boolean
<ccpoint>.end: Boolean
<ccpoint>.noXConstraint: Boolean
Example:
rollout uTestCurveControl “Curve Control”(
-- Curve control Properties
local ccProps = #(
#visible,
#numCurves,
#x_range,
#y_range,
#displayModes,
#zoomValues,
#scrollValues,
#commandMode)
Curve Control 173
-- Curve properties
local curveProps = #(
#name,
#animatable,
#color,
#disabledColor,
#width,
#disabledWidth,
#style,
#disabledStyle,
#numPoints,
#lookupTableSize)
on btn_props pressed do
(
local tab = “\t”
-- print the CC properties
format “Curve Control Properties\n”
for p in ccProps do
format (tab + “% : %\n”) (p as string) (getProperty cc_test p)
for p in curveProps do
format (tab + “\t% : %\n”) (p as string) (getProperty crv p)
See Also
Rollout User-Interface Controls (p. 1481)
Rollout User-Interface Controls Types (p. 1484)
Rollout User-Interface Controls Common Layout Parameters (p. 1483)
Rollout User-Interface Controls Common Properties (p. 1481)
getTextExtent
Topic: version 4 MAXScript Language Improvements/User Interface
getTextExtent <string>
Returns a Point2 value containing the size of the string in pixels if it was displayed in a
command panel.
See Also
String Values (p. 722)
176 Chapter 1 | What’s New in 3ds max 4 MAXScript
isActive
Topic: version 4 MAXScript Language Improvements/User Interface
Prototype:
isActive <atmos>
Return Value:
Returns true if the atmospheric is set to active; false otherwise
See Also
Atmospheric Effects Common Properties, Operators, and Methods
Prototype:
isActive <renderEffect>
Return Value:
Returns true if the render effect is set to active; false otherwise
See Also
Render Effects Common Properties, Operators, and Methods (p. 1347)
keyboard.escPressed
Topic: version 4 MAXScript Language Improvements/User Interface
keyboard const StructDef (p. 237)
A new keyboard key-state system variable, keyboard.escPressed. Read-only variable yields true or
false depending on whether the Esc key is currently pressed.
See Also
Keyboard Entry (p. 1623)
3D Studio MAX System Globals (p. 630)
In order to make the menu and CUI files more easily localized, a keyword argument,
GlobalCategory:, has been added to the macroScript facility.
Previously, when a macroScript is assigned to a CUI button or menu item, it is identified in the CUI
or MNU file using the macroScript name and category, like this (from the menu file):
Item6_Action=647394:Isolate`Tools
The problem is when the macroScript is localized, the category is localized but the macroScript name
“Isolate” should not be localized. When it is localized, then the MNU file entry of “Isolate `Tools”
no longer works.
A non-localized category name is needed that would be used to write the operation to MNU and
CUI files.
In this case the macroScript now looks like:
MacroScript Isolate
Category:”Tools”
GlobalCategory:”Tools” -- This is the new keyword
ToolTip:”Isolate Tool”
Icon:#(”ViewPortNavigationControls”,7)
When this macroScript is localized the Category would be translated, but the GlobalCategory
would not.
See Also
3ds max File Loading and Saving (p. 1639)
178 Chapter 1 | What’s New in 3ds max 4 MAXScript
The function returns true of it succeeds and false if it can’t find the named menu.
You can set the quad right-click menu that MAX uses in the viewports using the following
MAXScript:
menuMan.setViewportRightClickMenu #nonePressed “Modeling 2”
Sets the default (no keys pressed) quad menu to “Modeling 2”. The menu name must be a quad
menu that is listed in the “Quads” customization dialog, and the name must match exactly,
including capitalization.
For the first parameter, you can use one of the following 8 values:
#nonePressed
#shiftPressed
#altPressed
#controlPressed
#shiftAndAltPressed
#shiftAndControlPressed
#controlAndAltPressed
#shiftAndAltAndControlPressed
Here are two macroScripts that set and reset two of the right-click menus:
Example:
macroScript SetQuads
category:”Custom UI”
tooltip:”Set Quad”
(
on execute do
(
menuMan.setViewportRightClickMenu #nonePressed “Modeling 2”
menuMan.setViewportRightClickMenu #controlPressed “Sample 4x1”
)
)
------------------------------
macroScript ResetQuads
category:”Custom UI”
Menu and CUI Loading 179
tooltip:”Reset Quads”
(
on execute do
(
menuMan.setViewportRightClickMenu #nonePressed “Default Viewport
Quad”
menuMan.setViewportRightClickMenu #controlPressed “Modeling 1
[Cntrl+RMB]”
)
)
See Also
cui const StructDef (p. 234)
3D Studio MAX System Globals (p. 630)
180 Chapter 1 | What’s New in 3ds max 4 MAXScript
mtlBrowser
Topic: version 4 MAXScript Language Improvements/User Interface
mtlBrowser const StructDef (p. 244)
Prototype:
mtlBrowser.browseFrom [#mtlLibrary | #mtlEditor | #activeSlot | #selected | #scene |
#new]
Remarks:
Lets you set the Browse From: source for the modeless material browser.
See Also
Miscellaneous Dialogs (p. 1621)
SetBackground Method
Topic: version 4 MAXScript Language Improvements/User Interface
Changed SetBackground to take a color in addition to a point3.
Prototype:
setBackGround [<time>] <color>
Remarks:
If the time value is not specified, the current MAXScript time is used.
Prototype:
getBackGround [<time>]
Remarks:
Gets method that parallels setBackGround method.
See Also
Working with Atmospherics (p. 1345)
mouseTrack() Function
Topic: version 4 MAXScript Language Improvements/User Interface
While the tracking is going on, this function is called whenever a mouse action occurs, such as a
button click or a drag, etc. The function has the form:
mouseTrack [on:<node>] [prompt:”msg”] [snap:#2D|#3D]
[trackCallback:fn|#(fn,arg)]
mouseTrack() Function 181
Parameters:
on:<node>
Optionally specifies a scene object to track on. If you don’t supply an object, the
mouse tracks on the current active grid. Note that the object surface tracker uses
the SDK function IntersectRay() which is not reliably implemented on all object
types. Editable meshes always work OK, so you can convertToMesh() if needed.
prompt:”msg”
Displays the prompt message in the MAX status line
snap:#2D|#3D
Relevant when not tracking on an object surface (no on:<node> specified). If snap
mode is on and #2D is supplied, snaps to snap points on grid, if #3D is specified
snaps to any near snap point in space.
trackCallback:fn|#(fn,arg)
Is where you specify the function to be called as the mouse is dragged over the
active grid or object surface. You can specify it is a single function or a function
and an argument value in a two element array. The latter form is useful if you
have a common callback function for many tasks and want to send in a parameter
to control its operation for a particular use. The function you give must be of the
following form:
fn callback_fn msg ir obj faceNum shift ctrl alt = ...
in other words, a scripted function of 7 arguments. While the tracking is going
on, it is called whenever a mouse action occurs, such as a button click or a
drag, etc.
The ‘msg’ argument is a message code that indicates what kind of action occurred, and can be one of:
#freeMove - means the mouse is moved without a button being pressed
#mousePoint - means the left mouse button has just been pressed
#mouseMove - means the mouse is being dragged with the left button down
#mouseAbout - means the right mouse button was clicked, normally meaning cancel
Parameters:
‘ir’
The grid or surface intersection normal Ray at the current mouse position. The ray
has a .pos property giving the point in space of the normal and a .dir property
giving the normal’s direction vector.
‘obj’
The object being dragged over or undefined if no on:<node> was supplied.
‘faceNum’
The number of the face the mouse is over if the object being tracked is an editable
mesh, undefined otherwise.
182 Chapter 1 | What’s New in 3ds max 4 MAXScript
See Also
Rollout User-Interface Controls (p. 1481)
snapMode
Topic: version 4 MAXScript Language Improvements/User Interface
snapMode const StructDef (p. 254)
Prototype:
snapMode.active
Remarks:
Lets you get and set a Boolean value defining the Snap toggle state - on (true) or off (false).
Prototype:
snapMode.type
Remarks:
Lets you get and set a Name value defining whether 2D (#2D), 2.5D (#2_5D), or 3D (#3D)
is the current snap type.
See Also
3D Studio MAX System Globals (p. 630)
See Also
Spinner (p. 1509)
Rollout User-Interface Controls (p. 1481)
Rollout User-Interface Controls Types (p. 1484)
Rollout User-Interface Controls Common Layout Parameters (p. 1483)
Rollout User-Interface Controls Common Properties (p. 1481)
Timer UI element
Topic: version 4 MAXScript Language Improvements/User Interface
The Timer UI element has been enhanced in the following ways:
• The initial state of timer now respects the timer’s .active parameter.
• A new .ticks read/write property which is incremented by 1 at each ‘tick’ of the timer.
See Also
Timer (p. 1512)
Rollout User-Interface Controls (p. 1481)
Rollout User-Interface Controls Types (p. 1484)
Rollout User-Interface Controls Common Layout Parameters (p. 1483)
Rollout User-Interface Controls Common Properties (p. 1481)
See Also
Interface: timeSlider (p. 428)
184 Chapter 1 | What’s New in 3ds max 4 MAXScript
will generate an undo-block for all the operations in the block-expression following the
prefix, which will display in the undo/redo lists with the given string as its name. The
name must be a literal string and is optional, and will default to “MAXScript”.
See Also
undo (p. 687)
Sticky Contexts (p. 689)
Zoom to Bounds
Topic: version 4 MAXScript Language Improvements/User Interface
ZoomToBounds just zooms the current or selected viewport to a bounding region.
Prototype:
Viewport.ZoomToBounds <A_Point3> <B_Point3> <All_Bool>
Parameters:
A_Point3 and B_Point3 define the bounding region to zoom to.
All_Bool determines whether only the selected or all viewports get zoomed
See Also
viewport const StructDef (p. 258)
Customize The Order of Rollup Pages 185
See Also
Interface: cmdPanel (p. 356)
Rollout Systems ‘category’ Mechanism (p. 188)
Rollout User-Interface Controls (p. 1481)
Rollout User-Interface Controls Types (p. 1484)
Rollout User-Interface Controls Common Layout Parameters (p. 1483)
Rollout User-Interface Controls Common Properties (p. 1481)
Visual MAXScript (p. 117)
186 Chapter 1 | What’s New in 3ds max 4 MAXScript
See Also
ActiveX Controls in MAXScript Rollouts (p. 10)
See Also
Rollout User-Interface Controls (p. 1481)
Rollout User-Interface Controls Types (p. 1484)
Rollout User-Interface Controls Common Properties (p. 1481)
Rollout User-Interface Controls Common Layout Parameters (p. 1483)
See Also
Rollout User-Interface Controls (p. 1481)
Rollout User-Interface Controls Types (p. 1484)
Rollout User-Interface Controls Common Properties