ScriptSpot

Forum topic · Scripts Wanted

Toggle modifier On/Off for certain frames

By joonior1985 · 2023-11-26

Description

Hi,

I've figured out how to toggle modifier for an object so far, i.e.

$Box001.TurboSmooth.enabled = false/true

yaay! But here's a thing - I need to switch this modifier only for frame 3, 4, 5
I'm a complete noob with the maxcript so I'm asking for help. I tried to dig myself but with no result.
Any ideas?

Comments (2)

Using render and viewport callbacks

wobi · 2024-01-04


-- create a global struct to hold all modifiers
-- and the frames on which these should be active
struct ModsOnOff
(
	public modifierObjects,
	public activeFrames,
	
	on create do
	(
		this.modifierObjects = #()
		this.activeFrames = #()
	)
)
global ModsOnOff = ModsOnOff()

-- create a callback that switches the modifiers
-- from the global struct on or off based on the frame number
-- beeing rendered or viewed in the viewport
fn modsOnOffCB =
(
	if not isStruct ModsOnOff then return()
	
	local cbParam = callbacks.notificationParam()
	local currentFrame = if cbParam == undefined then currentTime.frame else cbParam.frame

	for id = 1 to ::ModsOnOff.modifierObjects.count do
	(
		local modEnabled = findItem ::ModsOnOff.activeFrames (currentFrame as integer) != 0
		try ::ModsOnOff.modifierObjects[id].enabled = modEnabled catch continue
	)
)
-- add the callback for the renderer
callbacks.addScript #preRenderEval modsOnOffCB id:#modsOnOff
-- adding the callback to the viewports
registerTimeCallback modsOnOffCB


-- set the modifiers and frames...
-- after setting the values the state of the modifiers
-- will be correct when the time changes again
ModsOnOff.modifierObjects = #($Teapot001.modifiers[1], $Teapot002.modifiers[1])
ModsOnOff.activeFrames = #(2, 3, 6)

-- to remove the callbacks, run the follwoing two lines:
-- callbacks.removeScripts id:#modsOnOff
-- unRegisterTimeCallback modsOnOffCB

Hope this helps...

SimonBourgeois · 2023-12-20

Hi Krzysztof,

I might be wrong but i think that you can't animate modifiers state,
you can animate the iteration value instead, i would do something like that:
(
for obj in selection do
(
obj.modifiers[#TurboSmooth].iterations = 0
obj.modifiers[#TurboSmooth].useRenderIterations = on

with animate on
(
at time 0 obj.modifiers[#TurboSmooth].renderIterations = 0
at time 2 obj.modifiers[#TurboSmooth].renderIterations = 0
at time 3 obj.modifiers[#TurboSmooth].renderIterations = 2
at time 5 obj.modifiers[#TurboSmooth].renderIterations = 2
at time 6 obj.modifiers[#TurboSmooth].renderIterations = 0
)
)
)

----------------------------------------------------------------------------------------
Sadly the viewport Iteration doesn't animate well with turbosmooth, though it works well with meshsmooth:
(
for obj in selection do

with animate on
(
at time 0 obj.modifiers[#meshsmooth].Iterations = 0
at time 2 obj.modifiers[#meshsmooth].Iterations = 0
at time 3 obj.modifiers[#meshsmooth].Iterations = 2
at time 5 obj.modifiers[#meshsmooth].Iterations = 2
at time 6 obj.modifiers[#meshsmooth].Iterations = 0
)
)
---------------------------------------------------------------------------
there might be better ways, i am also a noob at maxscript...