Matt,
 
A key PyMOL concept for Tkinter developer to grasp is that Tkinter runs in a
separate thread from PyMOL.  Thus, direct calls to Tkinter from a PyMOL
thread will fail erratically, as observed below. 
 
Fortunately, PyMOL is built so that it can receive API calls asychronously
from any thread.  Therefore, you can develop using Tkinter from the its own
thread, and then message PyMOL from there.  The only hard part is launching
your GUI, which is something you cannot do from a PyMOL script or program
directly.  Instead, you add a new item in the Plugin menu or a whole new
menu for your GUI as part of your initialization.
 
The plugin approach is the safe way to add new functionality using Tkinter.
See modules/pmg_tk/startup/__init__.py for example code to get you started.

 
Cheers,
Warren
 
--
DeLano Scientific LLC
Subscriber Support Services
mailto:del...@delsci.info
 


  _____  

From: pymol-users-boun...@lists.sourceforge.net
[mailto:pymol-users-boun...@lists.sourceforge.net] On Behalf Of Matthew
O'Meara
Sent: Friday, April 25, 2008 12:46 PM
To: PyMOL-users@lists.sourceforge.net
Subject: [PyMOL] access to tkinter root for new Toplevel?


Hi All,

I would like to write a Wizard that spawns a separate window.  Right now I'm
just calling Tkinter.Toplevel() with no arguments but it dies with
non-deterministic tkinter errors.  I think the issue is I need to pass the
Tkinter.Tk() instance into the Toplevel command.  

1) Is there a way I can get access to the main Tkinter.Tk() instance from
within my Wizard?


I've made a simple version of what I would like that shows the behavior I'm
seeing.  To run, copy this into a file called testWizard.py and place into
the wizard directory.  Since I installed from Distutils on linux, my wizard
directory is /usr/local/lib/python2.5/site-packages/pymol/wizard/.  Then
fire up pymol and type into the command line 'wizard testWizard'.  If you
version is <1.0 try deleting '_self=cmd' and '_self'.   For me it crashes
about every third or so time, usually with different errors. 


from pymol.wizard import Wizard
from pymol import cmd
import pymol
import Tkinter


class TestWizard(Wizard):

    def __init__(self,_self=cmd):
        Wizard.__init__(self, _self)

        self.res_table = Tkinter.Tk()  # <- pass app.root in here????

        for i in range( 1000 ): Tkinter.Button(self.res_table,
text=str(i)).pack()


Thanks in advance!
Matt




Reply via email to