[Closed] Is it possible to select arbitrary FFD control points?
I have a box with applied FFD 3x3x3.
Run a script. Control points 1,3,5,7 are selected, so, I can use the Gizmo to move it(without selecting them one by one in the viewport).
Is it possible?
no! i couldn’t find any way to select (or get selection of FFD gizmo points) via mxs, therefore i wrote a c++/SDK script extension.
I found the code below(I modified it a little) in this forum, which shows the indexes of the selected FFD control points.
So, the solution is to abandon the idea.
(
-- usage:
-- <array>getSelectedCPs <ffdModifier>
-- output array contains selected control points as <int>index for each CP
function GetSelectedFFDCPs _FFDmod =
(
-- defines
WM_SETFOCUS = 0x007
-- back up some stuff we'll be changing
oldCommandMode = toolmode.commandmode
cmdPanelMode = getCommandPanelTaskMode()
modPanelObj = modpanel.getCurrentObject()
oldSubObjectLevel = subObjectLevel
oldModEnabledInViews = _FFDmod.enabledInViews
-- disable the modifier in viewports to speed up some calculations
_FFDmod.enabledInViews = false
-- let's collect all the control points' current positions
theMaster = _FFDmod[#master]
theCount = theMaster.numsubs
animateAll _FFDmod
curPositions = for i = 1 to theCount where theMaster[i].value != undefiend collect theMaster[i].value
-- go into modify mode
setCommandPanelTaskMode #modify
-- select the modifier
modpanel.setCurrentObject _FFDmod
-- go to the control point sub-object level
subObjectLevel = 1
-- change to move mode
toolmode.commandmode = #move
-- open the transform type-in dialog
max tti
-- find the tti dialog
local desktopHWND = windows.getDesktopHWND()
local desktopChildren = windows.getChildrenHWND desktopHWND
local tti
for child in desktopChildren do
(
if (child[5] == "Move Transform Type-In") do
(
tti = child
exit
)
)
if (tti == undefined) do ( return false )
-- get the tti's handle
local ttiHWND = tti[1]
-- get its children
local ttiChildren = windows.getChildrenHWND ttiHWND
-- set focus to the X Offset custedit control
UIAccessor.sendMessage ttiChildren[10][1] WM_SETFOCUS 0 0
-- change its value via the proper edit control - let's just offset by 1.0 unit
UIAccessor.setWindowText ttiChildren[12][1] "1.0"
-- now set focus to the Y offset custedit control
UIAccessor.sendMessage ttiChildren[13][1] WM_SETFOCUS 0 0
-- now, let's collect the new positions.
newPositions = for i = 1 to theCount where theMaster[i].value != undefiend collect theMaster[i].value
-- set focus to the X Offset custedit control
UIAccessor.sendMessage ttiChildren[10][1] WM_SETFOCUS 0 0
-- change its value via the proper edit control - move the control points back 1.0 unit
UIAccessor.setWindowText ttiChildren[12][1] "-1.0"
-- now set focus to the Y offset custedit control
UIAccessor.sendMessage ttiChildren[13][1] WM_SETFOCUS 0 0
-- close that tti dialog
UIAccessor.CloseDialog ttiHWND
-- now let's figure out what the difference between the two arrays is
selectedCPs = for i = 1 to curPositions.count where (curPositions[i] != newPositions[i]) collect i
-- restore stuff
_FFDmod.enabledInViews = oldModEnabledInViews
setCommandPanelTaskMode cmdPanelMode
if (modPanelObj != undefined) do
(
modpanel.setCurrentObject modPanelObj
)
if (oldSubObjectLevel != undefined) do
(
subObjectLevel = oldSubObjectLevel
)
toolmode.commandmode = oldCommandMode
--
selectedCPs
)
selCP = GetSelectedFFDCPs selection[1].modifiers[1]
format "selCP: %
" selCP
)
If you are using a ffd modifier over top the box click the animate all button and this will enable all the control points tracks. Then you can grab each point with this code.
$.ffd2x2x2.controlpoint1
You’ll have to manually set a key on all points to enable the tracks for the ffd gizmos.
Cheers!
Nick
I know this, but the goal is to select some of the control points via script, not by hand.