Pythonモジュール「Tix」にバグかも
今日はTkinterとTixでいろいろやっていたのですが、どうやらTixモジュールのほうにバグがあるようです。。。
症状としては、
・Tix.NoteBookにタブが1つだけの状態でpages()という関数を使用すると、トレースバックが表示される。
というものです。
再現させるためのスクリプトは次の通りです。
かなり単純です。
NoteBookを配置して、そのNoteBookに2つのページ(タブ)を追加しておきます。
次に、ページを1つ削除した状態で、NoteBook.pages()を使用し、NoteBook中のタブオブジェクトのリストを
取得します。NoteBookにはまだ1つページが残っているはずなので、そのオブジェクトを要素とする
リストが取得できるはずなのですが。。。。
# -*- coding: utf-8 -*- import Tix root = Tix.Tk() nb = Tix.NoteBook(root) nb.pack() nb.add('t1', label='tab1') nb.add('t2', label='tab2') print '===== get pages() =====' for p in nb.pages(): print p print 'delete 1st tab.' nb.delete('t1') print '===== get pages() =====' for p in nb.pages(): print p root.mainloop()
以下が実行結果です。
小さくてわかりにくいですが、以下のエラー中「t」の文字を赤文字にしてみました。
本来は「tab2」のはずなのですが、先頭の"t"の文字だけが表示されているようです。。。
kani[tk]$ python nb_test.py ===== get pages() ===== .3083496492L.nbframe.t1 .3083496492L.nbframe.t2 delete 1st tab. ===== get pages() ===== Traceback (most recent call last): File "nb_test.py", line 21, infor p in nb.pages(): File "/usr/lib/python2.5/lib-tk/Tix.py", line 1163, in pages ret.append(self.subwidget(x)) File "/usr/lib/python2.5/lib-tk/Tix.py", line 337, in subwidget raise TclError, "Subwidget " + name + " not child of " + self._name _tkinter.TclError: Subwidget t not child of 3083496492L
さて、Tix.pyの中身を見てみました。
問題の関数は以下のようになっています。
def pages(self): # Can't call subwidgets_all directly because we don't want .nbframe names = self.tk.split(self.tk.call(self._w, 'pages')) ret = [] for x in names: ret.append(self.subwidget(x)) return ret
デバッグしてみると、上記のnamesという変数、タブが2つ以上の場合にはNoteBook中のタブ名(文字列)のリストになっていますが、
タブが1つの場合には、namesは文字列になっています。
ということは、その下のループの処理は、NoteBook中のタブが1つだけの場合、タブ名(文字列)を1文字づつとりだしてサブウィジェットを取得しようとします。たまたま存在することもあるかもしれませんが、今回の場合には存在しないので、エラーとなるわけです。。。。
本来はどうなるのが正しいのかな。。
(1) タブが1つの時でも、上記のnamesはリストになっている。
(2) 取得したnamesのタイプが文字列だったら、その文字列を要素とするリストを作成する。
どっちもありな気がしています。
ところで、上記の内容とは別に、GTKに慣れてしまった私にとって、TKはなにかと不便に感じます。
GTKに比べると、コードの量は減る傾向にあるんですが、どうもかゆいところに手が届きにくくて。。
もう少し慣れれば「Tkinterすごいじゃん!」と思えるのかもしれません。