ウィンドウのクローズも短縮キーで
やはり File メニューに Close アイテムを
ここまでのまとめ
前回、ウィンドウ左上のクローズボックスをクリックするとウィンドウが閉じ、アプリケーションも自動的に終了するようにしました。
どうせならウィンドウを閉じるのもマウスによるクリックでなく、コマンドキー+ W のように短縮キーを使いたいです。それには....
ここまでお読み下さっていれば、これは予想がつきますよね。
speakwin.py 変更後:3- ---------------------------------------------- class Win(W.Window): #メインウィンドウのクラス def __init__(self, arg): self.parent = arg #ウィンドウを表示 ・ ・ ・ self.setdefaultbutton(self.speakbutton) self.bind("<close>", self.parent._quit) self.bind("cmdw", self.close) # <----ここ ・ ・ ・ ----------------------------------------------
self.bind("cmdw", self.close)
はい、これです。コマンドキー+w で self.close が実行され、ウィンドウが閉じ、ウィンドウの <close> 動作によって self.parent._quit が実行されるので、結局、アプリケーションが終了します。
どうせ終了するなら
self.bind("cmdw", self.parent._quit)
でもいいような気もしますが、『コマンドキー+ W は閉じるだけ』に変更するかもしれないし、『コマンドキー+ W はクローズである』という Mac 文化に従いました。
self.close メソッドは self.open メソッドと同じく、W.Window クラスなど全ての Wウィジェットの総元締であるベースクラス Widget で定義されています。
『コマンドキー+ W はウィンドウを閉じる』ってみんなよく知っていますよね。だって、File メニューにありますもん。
あれ、ということは...そうでした。第4回で MyApp.py のメニューアイテムをコメントアウトした時に、Close アイテムも「#」でコメントアウトしちゃいました。
それでは、File メニューのClose アイテムはどう働いてウィンドウを閉じているんでしょう?
Close アイテムを復活させて、どうなるか見てみます。
MyApp.py 変更前:112-118 ---------------------------------------------- #newitem = FrameWork.MenuItem(m, "New", "N", 'new') #openitem = FrameWork.MenuItem(m, "Openノ", "O", 'open') #FrameWork.Separator(m) #closeitem = FrameWork.MenuItem(m, "Close", "W", 'close') #saveitem = FrameWork.MenuItem(m, "Save", "S", 'save') #saveasitem = FrameWork.MenuItem(m, "Save asノ", None, 'save_as') #FrameWork.Separator(m) quititem = FrameWork.MenuItem(m, "Quit", "Q", 'quit') ---------------------------------------------- 変更後:112-118 ---------------------------------------------- #newitem = FrameWork.MenuItem(m, "New", "N", 'new') #openitem = FrameWork.MenuItem(m, "Openノ", "O", 'open') #FrameWork.Separator(m) closeitem = FrameWork.MenuItem(m, "Close", "W", 'close') # <--ここ #saveitem = FrameWork.MenuItem(m, "Save", "S", 'save') #saveasitem = FrameWork.MenuItem(m, "Save asノ", None, 'save_as') #FrameWork.Separator(m) quititem = FrameWork.MenuItem(m, "Quit", "Q", 'quit') ----------------------------------------------
closeitem だけ「#」を消しました。
こうして MyApp.py を実行すると、File メニューに Close アイテム『Close W』が現れます。コマンドキー+ W でウィンドウが閉じられ、アプリケーションが終了します。
でも、これだと speakwin.py の方の self.bind("cmdw", self.close) で動いてるのかもしれないので、これを消してみましょう。
speakwin.py 変更前:17-18 ---------------------------------------------- self.bind("<close>", self.parent._quit) self.bind("cmdw", self.close) ---------------------------------------------- 変更後:17-18 ---------------------------------------------- self.bind("<close>", self.parent._quit) #self.bind("cmdw", self.close) ----------------------------------------------
これで MyApp.py を実行すると、やはりコマンドキー+ W でウィンドウが閉じ、アプリケーションが終了しました。
第4回で、メニューアイテムを enable(選択実行可能)、disable(選択実行不可能)にする self._menustocheck からも、closeitem などのアイテムを削除しました。こちらでも closeitem を復活させましょう。
MyApp.py 変更前:137-139 ---------------------------------------------- self._menustocheck = [ undoitem, cutitem, copyitem, pasteitem, clearitem, selallitem] ---------------------------------------------- 変更後:137-139 ---------------------------------------------- self._menustocheck = [closeitem, # <--ここ undoitem, cutitem, copyitem, pasteitem, clearitem, selallitem] ----------------------------------------------
self._menustocheck に加えたことで、enable、disable の機能が働いて、ウィンドウが開いている時に Close アイテムが選択できて、閉じている時にClose アイテムが選択できないのか確認してみたくなりました。
確認するためには、ウィンドウを閉じてもアプリケーションを終了させてはいけません。
speakwin.py 変更前:17-18 ---------------------------------------------- self.bind("<close>", self.parent._quit) #self.bind("cmdw", self.close) ---------------------------------------------- 変更後:17-18 ---------------------------------------------- #self.bind("<close>", self.parent._quit) #self.bind("cmdw", self.close) ----------------------------------------------
というわけで、結局、コメントアウトしました。
これで MyApp.py を実行してみました。ウィンドウがある時の Close アイテムは enable になっています。
コマンドキー+ W やクローズボックスのクリックでウィンドウを閉じた時の Close アイテムは disable になっています。
メニューアイテムの enable/disable については、Wリファレンスの Menubar とMenu クラスの最後にこう書かれています。
メニューアイテムは、呼び出し可能なcallbackに渡されるか、アプリケーション、 最前面のウィンドウあるいは現在のウィンドウの選択されたウィジェットのどちらかで(「どれかで」の訳の誤りか?訳者は...私だ(^^;。)'domenu_callback'メソッドを持つもの、これらのうちのどれかに渡されなければなりません;そうでないならメニューは暗くなります。
Quit アイテムは、callback が 'quit' に設定されています。domenu_quit を MyApp が持っているので、MyApp の domenu_quit が実行されます。
Close アイテムは、callback が 'close' に設定されています。domenu_close ってどこにも出て来ませんでしたが、最前面のウィンドウである Win、そのスーパークラス W.Window(Python:Mac:Tools:IDE:Wwindows.py にあります)が持っています。
したがって、Close アイテムが選択されると Win に対して domenu_close が渡され実行されます。
Win が閉じられると、callback の受け手がいなくなるのでメニューは暗くなります。
ということかなぁ。
ここまでの MyApp.py と speakwin.py、そして MyApp.rsrc を一つのフォルダに入れた speak2.sit.bin(約 30k)を作りました。
また元に戻ってしまった感じがしますが、Close アイテムを使えるようにしたのでお許し下さい。ひとつ大事なことを忘れていたので次回はそれを。