Pressing the shelf button “Symmetrize” will import tool_symmetrize.py, reload tool_symmetrize.py and launch function tool_symmetrize.symmetrizeWindow().
3/ tool_symmetrize.symmetrizeWindow() will launch a tool with cmds.window. Buttons inside this window will launch function from tool_symmetrize.
Exemple: tool_symmetrize.py:
def testA():
print 'test A'
cmds.window(....)
cmd = "testA()"
cmds.button('Launch Test A', command=cmd)
cmds.showWindow(....)
The problem is that from a newly opened maya, after succesfully loading tool_symmetry.symmetrizeWindow() from the shelf, calling functions from tool_symmetry.py with the buttons won’t work:
Error: NameError: file line 1:name ‘tool_symmetrize’ is not defined
So… tool_symmetrize.py doesn’t seems to be loaded, but symmetrizeWindow() which works fine is loaded from this very module. I don’t understand.
I tried changing from step 3/ cmd = “testA()” to cmd = “tool_symmetrize.testA()”, but it does not work either.
Can someone help me? I don’t understand how a module clearly loaded by maya can’t be defined when a function from that module call a function from the module.
First step – don’t use the string form of the command, it often results in this kind of confusion (see this link for a more detailed explanation why). You want to convert
cmd = "testA()"
cmds.button('Launch Test A', command=cmd)
to
import tool_symmetrize
#...
cmds.button('Launch Test A", cmd = tool_symmetrize)
that may still fail – but it should fail at import time (before the button is actually created) ; that’s a canary in the coalmine proving that tool_symmetrize.py is not available on the path. The string for hides that problem until the button is actually pressed , and often it will work for you because you’ve been testing on your own machine and then fail for others. Doing it by passing the functions directly helps you spot path related problems early
Button calllbacks always have to handle a (useless) extra argument that maya passes. Other gui things (menus, I’m not sure about shelf buttons) also have extra arguments. It’s safe to ignore them if you don’t need them,
Bob’s answer is one of the two ways – they other is simply to use an inline function.
def callback(*_):
tool_symmetrize(arg1, arg2, arg3)
cmds.button('label', c = callback)
Depending on style or complexity both work fine (the link in my first answer covers the differences).
The basics won’t actually change much – and Pyside / QT is a much more complex system with lots of opportunities to shoot yourself in the foot. I’d wait and learn it after you already are comfortable with cmds.
I’ll definitly try mGui with my next tool.
PySide2 seems interesting as it’s a cross platform skill to learn, if I understood correctly, but I don’t really have time for “lots of opportunities to shoot yourself in the foot”… I’ll probably try it on a personnal project.