Notifications
Clear all

[Closed] skin.always_deform

Changing the always_deform property on a skin modifier does not work. I have my object selected and am looking right at it, and toggling $.modifiers[#Skin].always_deform = true/false, I see the checkbox changing, but it doesn’t ‘stick’ what I do. If I check the checkbox by hand, it works fine. I’ve tried with the animate button on and off.

I’ll submit this to Autodesk, but is there a workaround anyone has found?

11 Replies

( sounds like the developer put the code handling that checkbox’s toggling in the UI, rather than the parameters? )

did you try the “classOf <node>” thing to get max to re-evaluate it?
Edit – source: http://forums.cgsociety.org/showthread.php?t=665524&highlight=classof

If all else fails, windows.sendmessage should sort you out – but I’m sure there’s simpler methods.

1 Reply
(@robgalanakis)
Joined: 11 months ago

Posts: 0

Yeah, I’ve tried selecting, deselecting, classof, forcecompleteredraw, etc. But I’m doing the script interactively/line-by-line, so none of that really makes a difference (literally going back and forth between false, shift-enter, true, shift-enter, etc., watching the checkbox update). I guess I can use UI Accessor or whatever but I wanted to avoid it.

 S-S

Rob:

    Hi there. I'm not sure if this is any help, but here it goes. 
    
    Which version of max are you using? I tried this in 2008 and 2009, seems to be working OK. 
   
You already mentioned that you were seeing if UI checkbox state changes, so the following is not the case i guess - I take it that you know for sure that always deform off only affects reference frame of skin, so deformation will only be off in that frame? 

This is what i have used:


        theMod = $selection[1].modifiers[#skin]
     
        theMod.always_deform = true
     
        theMod.always_deform = false
        
        
  ...will toggle selected object's skin's "always deform" on and off, and when i deselect the object, check box will still show correct result, and bones will deform or not the mesh accordingly.

        $.modifiers[#Skin].always_deform
         
    And this will show the state of checkbox. Seems to be working here. Or did i miss something here? I checked my old script and it seems to be working... I've written some biped / skin modifier scripts for myself to remove repetitive tasks and i don't remember having any problems with "always deform" in earlier max versions either.
 JHN

Isn’t it one of those horrible Ops things, where you got to have the object selected, the modifier panel open etc…?

Just a thought, not in front of max right now.

-Johan

 S-S

I don’t think that will cause it. You can have no object selected and be in other tab than modify for this to work. I just tested it.

Clicking the checkbox and setting it true/false via script definitely behave differently. Using Max 2008, and others seem to have an issue with it as well according to a forum search.

Try the following:
Create an object and some other objects as bones, apply a Skin modifier to the first object. Now, at the reference frame (frame 0 by default), move the bones- the mesh should deform. But, I want that new bone pose to be the skin pose/reference pose. So, I need to turn ‘always deform’ off and back on, at least that is exactly what I would do when using the checkbox. So, uncheck the box (through the UI)- the mesh snaps back to its unskinned pose (like if you disabled the modifier). Now, check the box- the mesh shouldn’t move. That is correct behaviour.

Now, move a bone at the reference frame, and toggle it (via script) true-false-true-false-true or however many times you want. When you set always_deform true, the mesh snaps back to where it was, just like if you enabled the modifier. This is not the correct behaviour of always deform, assuming the UI’s course of events are the correct one. Perhaps they work in the capacity your scripts needed them to or you didn’t notice it wasn’t working properly, but it is definitely not working (this post was written on my home computer and the first ones were written at work, so it doesn’t seem to my install or scripts either, and I’ve been able to repro it every time).

Edit: Alright I think I’ve found the issue. The script and UI ways DO indeed work differently. However, the scripted version works if you set always deform to false, THEN manipulate the bones, THEN turn it back to true. This order of operations is not needed when you are using the UI but apparently required when using the scripted way.

 S-S

Rob:

“Perhaps they work in the capacity your scripts needed them to or you didn’t notice it wasn’t working properly”

That’s what happened. I haven’t noticed this!

“The script and UI ways DO indeed work differently. However, the scripted version works if you set always deform to false, THEN manipulate the bones, THEN turn it back to true.”

This is the way i worked. I understand the problem now.

“Create an object and some other objects as bones, apply a Skin modifier to the first object. Now, at the reference frame (frame 0 by default), move the bones- the mesh should deform. But, I want that new bone pose to be the skin pose/reference pose”

This is of course not possible with what i suggested… without the workflow you mentioned. Here’s a hack i have used in other case.

I tested it again, and it seems to be working:


  myMod = $teapot01.modifiers[#Skin]
  
  -- off
  myMod.alwaysdeform = false
  
  -- select first bone object... or whatever object in skin...
  max modify mode
  modPanel.setCurrentObject myMod
  
  myBone = getNodeByName (skinOps.GetBoneName myMod  1 1)
  
  
  -- do something in transform which results into nothing
  tmp = myBone.position
  myBone.position.z = 0.0
  myBone.position = tmp
  
  -- on
  myMod.alwaysdeform = true
  

So i just nudge first bone in skin, this way you should be able to first re-pose bones, then run code similar to this and your mesh should pop to it’s “neutral” shape… It might be that moving or rotating bones is not optimal solution if there is some complicated rig or such but this was enough for me, and it worked – i didn’t look for other solutions.

Let me know if it works for you or not!

1 Reply
(@robgalanakis)
Joined: 11 months ago

Posts: 0

It doesn’t… does it work for you? I will try again at home, but it isn’t working at work.

So I found something else totally awesome.

The off-move-on workflow described above, only works when the script is evaluated interactively/in a global scope. If I put it inside of parenthesis, it stops working correctly.

I like the Skin modifier- I really do- but its scripting exposure and methodology is disgraceful. And now I can also say it is buggy.

I’ll probably have to work on a UI Accessor workaround for this crap.

 S-S

Having a lunch break…
That seems to be the case. I’ve come across something similar earlier, but don’t remember how i fixed it then – but here’s one solution.

Tried it as macroscript and inside function, not in global scope.

Adding undo context seems to help! Seems like it works here every time. Without undo it doesn’t.

Notice the pick object thing in the beginning, if you try this.


  Macroscript always_deform_toggle
  	 Category:" tools"
  	 Tooltip:"always deform toggle"
  	 icon:#("Maxscript", 1)
  
  (
  	pickedSkin = pickobject message:"pick an object with skin"
  	
  	myMod = pickedSkin.modifiers[#Skin]
  
  	fn always_deform_toggle =
  	(
  		-- off
  		myMod.alwaysdeform = false
  
  		-- select first bone object... or whatever object in skin...
  		max modify mode
  		modPanel.setCurrentObject myMod
  
  		myBone = getNodeByName (skinOps.GetBoneName myMod  1 1)
  
  
  		-- do something in transform which results into nothing
  		tmp = myBone.position
  		myBone.position.z = 0.0
  		myBone.position = tmp
  
  		-- on
  		myMod.alwaysdeform = true
  	)
  	
  	undo on
  	(
  		always_deform_toggle ()
  	)
  )
  

So,

I created the ‘toggle’ macro that works on the selected object.

I then ran this macro over all the geometry I needed (yikes, running a macro via script…). This didn’t work. However, executing the macro myself, it worked.

So, I copied the code that loops over the geometry, selects it, and runs the macro, and pasted it, so it runs that code twice, and it works.

So, this didn’t work:

for i = 1 to geoArr.count do
(
	select geoArr[i]
	macros.run "test" "always_deform_toggle"
)

But this did:

for i = 1 to geoArr.count do
(
	select geoArr[i]
	macros.run "test" "always_deform_toggle"
)
for i = 1 to geoArr.count do
(
	select geoArr[i]
	macros.run "test" "always_deform_toggle"
)
 S-S

Rob:

Nice to see you figured out how to do it and it works for you! It would be a lot less trouble if always_deform just worked the way one would expect