我正在为PyMOL(http://pmw.sourceforge.net)编写一个Pmw(http://sourceforge.net/projects/pymol/)插件,但我无法使用对Pmw.ComboBox
所做的更改来更新Pmw.RadioSelect
的值控制。
我不断得到的错误是:
File "/Users/x/.pymol/plugins/mymixer.py", line 82, in sdqRadioChanged
self.scheme_listing._list.setlist(scList)
<type 'exceptions.AttributeError'>: MyMixer instance has no attribute 'scheme_listing'
这似乎是范围错误,但我不知道如何重新构建整个插件以便能够访问scheme_listing
实例的MyMixer
属性。在Web上,python / Pmw / tkinter的类似示例似乎工作正常(或者我对python GUI编程的理解有限)。
下面附有一个MWE,它在PyMOL中运行(并失败)(显示在Plugins&gt; MyMixer下的菜单中)。注意:如果在OSX上运行此命令,请确保运行PyMOLX11Hybrid.app
# -*- coding: utf-8 -*-
# ==========================
# IMPORTS
# ==========================
import Pmw
# ==========================
# MAIN CLASS
# ==========================
class MyMixer():
colbrew = {'color':{'red': ['apple', 'strawberry', 'carrot'],
'blue': ['blueberry', 'smurfberry', 'icee'],
'green': ['spinach', 'chilli', 'lettuce']},
'shape':{'round': ['baseball', 'basketball', 'golfball'],
'oblong': ['football', 'shoes', 'eggs'],
'square': ['box', 'laptop', 'yourhead']}}
def __init__(self, app):
parent = app.root
self.parent = parent
self.dialog = Pmw.Dialog(parent, buttons=('Exit', ),
title='MyMixer Plugin',
command=self.button_pressed)
self.dialog.geometry('650x780')
self.dialog.bind('<Return>', self.button_pressed)
# -- Initialize main notebook
self.notebook = Pmw.NoteBook(self.dialog.interior())
self.notebook.pack(fill='both', expand=1, padx=3, pady=3)
self.sdq_radio = Pmw.RadioSelect(self.dialog.interior(),
selectmode='single',
buttontype='radiobutton',
labelpos='nw',
label_text='Colbrew Style:',
label_font='inconsolata 16',
orient='horizontal',
frame_relief='ridge',
command=self.sdqRadioChanged)
self.sdq_radio.pack(padx=0, anchor='n')
schemeStyleTypes = self.colbrew.keys()
for item in schemeStyleTypes:
self.sdq_radio.add(item, font='inconsolata 16')
self.sdq_radio.invoke(0)
scListItems = self.colbrew.get(self.sdq_radio.getvalue())
self.scheme_listing = Pmw.ComboBox(self.dialog.interior(),
scrolledlist_items=scListItems,
labelpos='nw',
label_text='Scheme Name:',
label_font='inconsolata 16',
listbox_height=10,
entry_width=3,
selectioncommand=self.schemeListCommand,
dropdown=True)
self.scheme_listing.pack(padx=20, pady=2, anchor='e')
# -- Reflow notebook
self.notebook.setnaturalsize()
# -- Show the main dialog
self.dialog.show()
def schemeListCommand(self, value):
print value
def sdqRadioChanged(self, value):
scList = self.colbrew.get(value)
self.scheme_listing._list.setlist(scList) # THIS IS THE POINT OF FAILURE !!!
print value
# -- Utility function for button controls
def button_pressed(self, result):
if result == 'Exit' or result is None:
self.dialog.withdraw()
# ==========================
# PLUGIN INITIALIZATION
# ==========================
def __init__(self, *args):
self.menuBar.addmenuitem('Plugin', 'command', 'Start MyMixer',
label='MyMixer',
command=lambda s=self: MyMixer(s))
答案 0 :(得分:0)
您在定义self.sdq_radio.invoke(0)
的语句之前调用self.scheme_listing
。当您调用invoke
方法时,它会在设置之前尝试访问该变量。您应该在调用invoke方法之前设置变量。