[Closed] Changing Link Constrained Inheritance
After I create a link constraint for an object, I can no longer change it’s inheritance flags using maxscript. However, I can stiill manually check them on/off through the hierarchy menu. Anyone know why or a way around this?
why? no idea – they still seem to take effect; odd.
looks like getInheritanceFlags returns an empty bitArray as well.
How to get around it? I was hoping to spot something in the link constraint itself… e.g. internally-governed link info bits… but alas, nothing in properties/interfaces.
So… time for more scarycode… at least I finally abstracted that darn checkbox checking/unchecking code…
-- toggle an UI checkbox's checked state via UI messages/notifications
-- usage:
-- hwnd -- HWND of the control
-- state -- checked state. 1 = check, 0 = uncheck
-- result:
-- value: OK
-- effect: should check/uncheck the checkbox and have its change effected
fn setUICheckboxState hwnd state = (
local BN_CLICKED = 0 -- clicky message ID
local BM_SETCHECK = 241 -- checkbutton toggle message ID
local WM_COMMAND = 273 -- windows command message
local parent = UIAccessor.getParentWindow hwnd
local id = UIAccessor.getWindowResourceID hwnd
windows.sendMessage hwnd BM_SETCHECK state 0
windows.sendMessage parent WM_COMMAND ((bit.shift BN_CLICKED 16) + id) hwnd
OK
)
-- change to the Link Info panels in Hierarchy mode
-- usage:
-- openLinkInfoUI
-- result:
-- value: OK
-- effect: will change to the Link Info panels in Hierarchy Mode
fn openLinkInfoUI = (
-- toggle to hierarchy mode
max hierarchy mode
-- get all the UI elements currently presented in max
local maxHWND = windows.getMaxHWND()
local maxChildren = windows.getChildrenHWND maxHWND
-- loop over them
for child in maxChildren do (
-- if we find the Link Info button
if (child[5] == "Link Info") then (
-- press it
UIAccessor.pressButton child[1]
-- and bail early
exit
)
)
OK
)
-- get the Hierarchy>Link Info panel>Inherit rollout's checkboxes
-- usage:
-- getInheritCheckboxes()
-- result:
-- value: array of hwnds
-- effect: will change to the Link Info panels in Hierarchy Mode
-- depends on:
-- openLinkInfoUI
fn getInheritCheckboxes = (
-- open the Link Info UI
openLinkInfoUI()
-- get all the UI elements currently presented in max
local maxHWND = windows.getMaxHWND()
local maxChildren = windows.getChildrenHWND maxHWND
-- some variables to help keep track of where we are in perusing the max UI
local foundTab = false
local foundPanel = false
-- an array to hold the actual checkboxes
local checkboxes = #()
-- loop over the UI elements
for child in maxChildren do (
-- find the Hierarchy Task command panel first
if (child[4] == "HierarchyTask") then (
foundTab = true
)
-- if we've found the Hiearchy Task command panel...
if (foundTab) then (
-- then get its children (the rollouts and all the elements therein)
if (child[4] == "RollupPanelTitle") then (
-- look for the Inherit rollout
if (child[5] == "Inherit") then (
foundPanel = true
)
)
) -- foundTab
-- if we've found the Inherit rollout..
if (foundPanel) then (
-- check if the current UI element is the "Move:" groupbox label
-- if it is, we can bail early
-- (it is listed -after- all 9 checkboxes(!))
if (child[5] == "Move:") then ( exit )
-- otherwise, see if we're dealing with a button
-- ( checkboxes are buttons - don't ask :) )
else if (child[4] == "Button") then (
-- and if we are, added the UI element's HWND
-- (all we need for further processing)
-- to our little checkboxes array
append checkboxes child[1]
)
) -- foundPanel
)
-- return the result, which should be our 9 checkboxes
checkboxes
) -- getInheritCheckboxes
-- set inheritance flags via UI messages.
-- usage:
-- setInheritanceFlagsUI <node> <flags> [error:&errorVar]
-- <node> = any valid node
-- <flags> = bitArray #{MoveX,MoveY,MoveZ,RotX,RotY,RotZ,ScaleX,ScaleY,ScaleZ}
-- [error:&errorVar] = optional by-parameter variable to store error message
-- result:
-- value: false = an error occurred, check the errorVar if supplied
-- value: OK = Inheritance flags set via UI
-- effect: appropriate Link Info>Inherit checkboxes checked/unchecked
-- depends on:
-- getInheritCheckboxes
-- openLinkInfoUI
-- setUICheckboxState
fn setInheritanceFlagsUI obj flags &error: = (
-- validate the node first, if it doesn't check out..
if (not (isValidNode obj)) then (
-- set the error message and return false
error = "supplied object is not a valid node"
false
)
-- if the node is valid..
else (
-- ..make sure it's selected
select obj
-- grab the checkboxes from the Inherit rollout
local inheritCheckboxes = getInheritCheckboxes()
-- validate the result, if not quite right..
if (inheritCheckboxes.count != 9) then (
-- then set the error message and return false
error = "could not retrieve Inherit checkboxes"
false
)
-- if the checkboxes are all good..
else (
-- ..then proceed
-- trap for #all and #none by simply creating our own flags bitArray
if (flags == #all) then ( flags = #{1..9} )
else if (flags == #none) then ( flags = #{} )
-- loop over all checkboxes
for i = 1 to 9 do (
-- get their intended state from the flags bitArray
local state = if (flags[i]) then ( 1 ) else ( 0 )
-- and set their state
setUICheckboxState inheritCheckboxes[i] state
)
-- return OK
OK
) -- inheritCheckBoxes.count == 9
) -- isValidNode obj == true
) -- setInheritanceFlagsUI
[size=2]Note that there’s no keepPos: parameter as there is for the standard setInheritanceFlags. I’m not entirely sure what that does in case you use it, but if it does what I suspect it does from the Max Help file, you can easily store the object’s current position in world space, change the link info, and then restore that position.
Other than that, usage of [/size][size=2]setInheritanceFlagsUI [/size][size=2]is the same as for [/size][size=2]setInheritanceFlags, except that your UI will show what’s going on, etc.
I commented pretty much everything in the code – you can remove the comment lines if you just need the functionality.
Edit: just some more comments, for the function headers
[/size]
Thanks too, from the POV of a lurker :)… this stuff isn’t covered very well!