ZBrushCentral

aargh my brain! (trying to make a little things to recentre subtools)

So this script language is somehow crazy for me to understand. I got something dong something though, which was exciting. I’m hoping someone with deeper knowledge can help me get this working properly. :slight_smile:

The goal is to move all subtools by an x-offset derived from the selected subtool when the script is triggered. Suonds prettysimple, but I’m getting strange issues when setting the position with this line:

[ISet, Tool:Geometry:X Position, #Newpos]

Sometimes is seems to applya different value from the UI - odd indeed.

Anyone who has a moment and wants to see if they can help me would get virtual cookies.

Script is just this:

[IButton,“Zplugin:cwtools:recentre”,“recentre subtools x”,

[If, [IGet, Transform:Edit],

//get current subtool position as centre

[VarDef, NewCentreOffset, 0]
[VarDef, ThisCentre, 0]
[VarDef, SetPosition, 0]
[VarDef, Thispos, 0]
[VarDef, Newpos, 0]

[VarSet, NewCentreOffset, [IGet,Tool:Geometry:X Position]*-1]

[note, [StrMerge,"offset for current subtool: ",NewCentreOffset, " subtoolpos: ",[IGet,Tool:Subtool:X Position]]]

[Loop,[SubToolGetCount], [If,[Val,n]==0,[SubToolSelect,1],[SubToolSelect,0]] [SubToolSelect,[Val,n]] [VarSet, Thispos, [IGet,Tool:Geometry:X Position]] [VarSet, Newpos, Thispos+NewCentreOffset] [ISet, Tool:Geometry:X Position, #Newpos]

,n]
[SubToolSelect,0]
] // Not a 3D object

]

cheers!

Not sure what your end intent is, are you trying to animate it? marcus_civis wrote a script that will process all subtools. I sent you a PM.

cheers,

Goal is to take the selected subtool’s centre and move all subtools by the same amount so that the everything is centred around the new centre in the relative correct positions. It works ok if you do it by hand. :confused:

Why not use TransposeMaster?

transpose mater didn’t seem to have the precision I would like, I will look again at it though, maybe I missed something.

Well, this doesn’t actually work in the way it should. I don’t mean there’s anything wrong with your code, just that ZBrush doesn’t behave as you’d expect.

You can set the positions of the subtools to the reference one just by using that value - you don’t need to subtract or add it:

[VarSet,currentSubTool,[SubToolGetActiveIndex]]

[VarSet, NewCentreOffset, [IGet,Tool:Geometry:X Position]] [Loop,[SubToolGetCount], [SubToolSelect,[Val,n]] [If,([Val,n] != currentSubTool), [ISet, Tool:Geometry:X Position,#NewCentreOffset] ] ,n] [SubToolSelect,currentSubTool]

This is presumably to do with how ZBrush handles the visual feedback. However, the zscript exposes a weakness in that ZBrush will crash soon after using the zscript more than once. There may be a solution - I’ll let you know if I find it.

EDIT: The crash seems to only occur if the zscript is run immediately after adjusting a slider by hand. (It seems that the screen & slider can sometimes not update properly, causing some instability.) If you rotate the mesh a little before pressing the zscript button all is well.

Hey marcus! thanks, I will give this a try.

Primarily this was to help somebody at work who was new to zbrush and mistakenly brought an off centre component as the first mesh into a scene and was stuck with the floor being located in the middle of that rather than 0,0,0 in worldspace.

I’ll give this a try. Fingers crossed!

Ah. I’ve read your reply more properly now and that’s not the aim, though I see what you mean.

The goal is not to move all subtools to subtool n’s x position, but to move subtool n back to zero in x, and apply the same offset to all the others to keep relative distance identical.

The sliders/ui update does seem to be the thing flipping out though. Something fishy going on for sure. It kind of works, except the non main subtools seem to move exactly double the amount I would expect. Sometimes in the wrong direction!

Thanks for the tips though. I will post some pics so the idea is clearer.

It’s OK, did you try it? It should work OK the way you want.

Using my code has the effect you were after. ZBrush adds the value to the slider’s current value instead of setting the slider to the value.

See the pics for an example. (the last pic is on the left!)

Attachments

01-Before.jpg

02-Centred.jpg

03-After.jpg

ok so here is the aim:

zscript_centre_x.png

Hopefully the goal is clearer. One can work around it by starting a fresh tool with a symmetrical world space centred object as the first subtool and then re-appending all the other subtools to it. Just a ballache. It just caught my eye as ‘one of those zbrush things’ which I wondered if I could figure out.

If this clears the issue up and anyone still has ideas I am all ears.

cheers!

I always understood what you were after. Did you try my code?

This could help. http://www.zbrushcentral.com/showthread.php?167639-My-Zbrush-Plugin!&p=1074277&viewfull=1#post1074277

I sure did chap, didn’t get the same effect.

marcus_help1.png

The bit about Zbrush adding to slider value automatically is interesting. It might explain some of what I’m getting.

Attachments

marcus_help1.png

I have a mysterious offset of 2 and some floating point error looking stuff, but this is as close as I have got.

strange.jpg
Thanks for the help guys - I looked through nicks scripts already (it does help with the workaround of appending tools for sure)

Can you post the exact code you’re using?

Sure thing.

[IButton,“Zplugin:cwtools:recentre”,“recentre subtools x”,

[VarSet, NewCentreOffset, 0]
[VarSet, mainSubTool,[SubToolGetActiveIndex]]

//move main subtool
[SubToolSelect,mainSubTool]
[VarSet, NewCentreOffset, Tool:Geometry:X Position*-1]
[ISet, Tool:Geometry:X Position,0]
[note, [StrMerge,"offset for current subtool: ",NewCentreOffset]]

//move other subtools
[Loop,[SubToolGetCount],
[SubToolSelect,[Val,n]]
[VarSet, Newpos, NewCentreOffset]
[If,([Val,n] != mainSubTool),
[ISet, Tool:Geometry:X Position,#Newpos]
]
,n]
[SubToolSelect,0]
]

Well, you didn’t copy my code, which goes some way to explaining the different result. Note how NewCentreOffset is simply set to the position of the selected subtool:

[IButton,“Zplugin:cwtools:recentre”,“recentre subtools x”,
[If, [IGet, Transform:Edit],
//get current subtool position as centre
[VarSet,currentSubTool,[SubToolGetActiveIndex]]
[VarSet, NewCentreOffset, [IGet,Tool:Geometry:X Position]]
[Loop,[SubToolGetCount],
[SubToolSelect,[Val,n]]
[If,([Val,n] != currentSubTool),
[ISet, Tool:Geometry:X Position,#NewCentreOffset]
]
,n]
[SubToolSelect,currentSubTool]
] // Not a 3D object
]

But there are other things that affect this.

You need to set the select subtool to 0 by hand; setting it in the script doesn’t work.

But after further testing I find that the results are inconsistent and I’ve not yet found out why. For example, the DemoSoldier, and the anatomy model (all 89 subtools) work perfectly but if I try to set up a test using primitives it will fail.

There’s obviously something going on under the hood which is beyond the reach of zscript.

Thanks for your help,

The pics on post #12 are using your (kindly done) code (although I put it in the button - that’s the only difference.)

When I run your code on the anatomy model (after offsetting one part to act as the new centre) the result is that all the other subtools move across and line up nicely with the offset subtool.

This is not what I’m trying for (although still useful). What I want is for the selected subtool to be centred on the ‘floor’ plane by moving over to position 0, and the same offset be applied to other subtools to move them as well by the same amount and keep everything relatively the same.

So running on anatomy model with a part offset, I woud want the end result to look exactly the same, except now the floor plane would be centred on the offset part.

Maybe I am just explaining what you aready know, so I apologise if I am parping on. :slight_smile: I’m not 100% sure I am making sense. :slight_smile:

Thanks again for your help, it’s much appreciated.

I’m going to grab this as it’s useful and might be fun to play with. :wink:

I wasn’t sure which code you were using for what result, so thanks for the clarification!

What you describe with the anatomy model is expected behaviour because the model is already centred (the top subtool is at X position = 0) when you load the file. The only way to test is to offset it away from the centre first and press the button to move the subtools. But if after doing that you reset the top subtool’s position to 0 and press the button again then everything is moved back to where it should be.

But as I said, there are situations where this code will fail. It’s something to do with how ZBrush stores the relative positions of the subtools. I may look into this at some time but I don’t have time right now.

In the meantime, a different approach is probably best. This uses the Tool>Deformation sub-palette to offset the subtools. There’s no need to hand set the top subtool to 0 before pressing the button. (In fact doing so will screw things up!)

[IButton,“Zplugin:cwtools:recentreB”,“recentre subtools x”,
[VarSet,isNeg,0]
[If, [IGet, Transform:Edit],
//select top subtool
[SubToolSelect,0]
//get offset
[VarSet, NewCentreOffset,[IGet,Tool:Geometry:X Position]]
//find if negative
[If,NewCentreOffset < 0,[VarSet,isNeg,1]]
//get Absolute value
[VarSet, NewCentreOffset,ABS(NewCentreOffset)]
//get integer
[VarSet,newV,INT(NewCentreOffset)]
//set axis for Deformation>Offset
[VarSet,tmpMod,[IModGet,Tool:Deformation:Offset]]
[IModSet,Tool:Deformation:Offset,1]
//set value to adjust slider to full extent
[If,isNeg,[VarSet,shift,100],[VarSet,shift,-100]]
//repeat as necessary
[Loop,newV,
[ISet,Tool:Deformation:Offset,shift]
[IPress,Tool:Deformation:Repeat To Other]
]
//set remaining value from fraction
[VarSet,newV,FRAC(NewCentreOffset)]
[VarMul,newV,100]
[If,isNeg,[VarSet,newV,NEG(newV)]]
[ISet,Tool:Deformation:Offset,newV]
[IPress,Tool:Deformation:Repeat To Other]
//reset axis
[IModSet,Tool:Deformation:Offset,tmpMod]
] // Not a 3D object
]

Hey marcus!

I was ogling the deformation palette when I began to look at this, but it seemed less straightforward (who knew!) :slight_smile:

Your example is excellent and almost perfect for me.

I’ve made a small change where instead of assuming top subtool is the new centre the index is stored for the one you have selected. It now does precisely what I was after.

Thanks so much for your assistance folks!

here’s my tiny change should you want to try it out:

[IButton,“Zplugin:cwtools:recentreB”,“recentre subtools x”,
[VarSet,isNeg,0]
[VarSet, mainSubTool,[SubToolGetActiveIndex]]
[If, [IGet, Transform:Edit],
//select top subtool
[SubToolSelect,mainSubTool]
//get offset
[VarSet, NewCentreOffset,[IGet,Tool:Geometry:X Position]]
//find if negative
[If,NewCentreOffset < 0,[VarSet,isNeg,1]]
//get Absolute value
[VarSet, NewCentreOffset,ABS(NewCentreOffset)]
//get integer
[VarSet,newV,INT(NewCentreOffset)]
//set axis for Deformation>Offset
[VarSet,tmpMod,[IModGet,Tool:Deformation:Offset]]
[IModSet,Tool:Deformation:Offset,1]
//set value to adjust slider to full extent
[If,isNeg,[VarSet,shift,100],[VarSet,shift,-100]]
//repeat as necessary
[Loop,newV,
[ISet,Tool:Deformation:Offset,shift]
[IPress,Tool:Deformation:Repeat To Other]
]
//set remaining value from fraction
[VarSet,newV,FRAC(NewCentreOffset)]
[VarMul,newV,100]
[If,isNeg,[VarSet,newV,NEG(newV)]]
[ISet,Tool:Deformation:Offset,newV]
[IPress,Tool:Deformation:Repeat To Other]
//reset axis
[IModSet,Tool:Deformation:Offset,tmpMod]
] // Not a 3D object
]