2016-03-28 8 views
2

私はテキストベースのゲームのための本当に基本的なレイアウトに苦労しています。最初の列のテキストが文字列の終わりより前に停止するのはなぜですか、なぜそのウィンドウが高すぎるのでしょうか?以下のコードは、どんなヘルプにも感謝します。Tkinterテキストの基本レイアウト

from Tkinter import * 
import tkFont 

class TreasureHunt: 

    def __init__(self, master): 
     app = Frame(master) 
     app.grid() 

     self.mono_font = tkFont.Font(family="monospace",size=24,weight="bold") 
     self.instructions = "Find the hidden treasure!\n\nUse the arrow keys to select where to look, then press Enter to check. \ 
     There is a 50/50 chance you will be told the distance from the treasure. Keep hunting until you find it. Good luck!" 

     self.info = Text(app, wrap=WORD, padx=10, pady=10, bd=0,width=10) 
     self.info.insert(1.0,self.instructions) 
     self.info.grid(row=0,column=0,sticky=N) 

     self.island = Text(app, bg="cyan",bd=0, padx=20, pady=20, font=self.mono_font,width=20) 
     self.island.insert(1.0, "ready") 
     self.island.grid(row=0,column=1) 

     self.display_grid() 

    def display_grid(self): 
     self.matrix = [["# " for col in range(8)] for row in range(8)] 
     for row in range(len(self.matrix)): 
      row_str = "".join(self.matrix[row]) +"\n" 
      self.island.insert(1.0,row_str) 


root = Tk() 
game = TreasureHunt(root) 
root.mainloop() 
+0

"最初の列のテキストが文字列の最後より前に停止するのはなぜですか? 。それは私に "止まる"ようではない - それは次の行にラップする。それはあなたが意味することですか? –

+0

コードをそのまま使用すると、テキストは「宝のもと」に止まります。 "あなたがそれを見つけるまで狩りを続ける。幸運を!"不足している。私は最初の列の縦のスペースが完全であると推測していますが、右の列の垂直の高さのために表示されています。 – Robin

答えて

1

なぜなら、ウィンドウが高すぎる理由は、何かに明確な高さを与えないからです.Tkinterはそのデフォルトに依存しなければなりません。デフォルトでは、テキストウィジェットは24行の高さになります。

右側のウィジェットは最も高いフォントを使用しているため、ウィジェットはウィンドウ内で最も高いウィジェットになります。ウィンドウはすべてにフィットしようとします。そのテキストウィジェットを小さくするとウィンドウ全体が小さくなります。

self.island = Text(app, ..., height=9) 

"最初の列の文字列が文字列の最後より前にある"という文字ではわかりません。私はそれが止まって見ることはありません、私はあなたがそれを指示したように、私が期待していたようにラッピングを見ます。あなたは10文字の幅を設定し、ワード境界で折り返すように言いました。

また、gridを使用する場合、経験則として少なくとも1つの行と1つの列に重みを与える必要があります。重みは、余分なスペースをどのように割り当てるかをTkinterが知っている方法です。ウィンドウのサイズを変更すると、内部のウィジェットが拡大または縮小しないことに注意してください。これは、行と列のデフォルトの重みが0(ゼロ)であるためです。

これを変更するには、row_configurecolumn_configureを使用してください。あなたが青の領域は、すべての余分なスペースを取るために展開したい場合たとえば、それは行と列の1(1)の重量です与える:

app.grid_rowconfigure(0, weight=1) 
app.grid_columnconfigure(1, weight=1) 

あなたが見つけることを行うと....何も変わらないTkinterは実際に行0と列1に余分なスペースを与えます。しかし、もっと多くのことが必要です。 gridを呼び出す際に、sticky属性を使用する必要があります。この属性は、与えられたスペースの端にウィジェットがスティックすることを要求します。

self.info.grid(row=0,column=0,sticky=N+S+E+W) 
... 
self.island.grid(row=0,column=1,sticky=N+S+E+W) 

これを行うと、何も変わりません。これは、appがフレームであり、そのフレームがルートウィンドウの内側にあるためです。しかし、appが入っている行と列の重みを指定しておらず、stickyという値も指定していませんでした。

ただし、ルートウィンドウにちょうど1つのウィジェットしかない場合、グリッドではなくpackを使用する方が少し簡単です。私がこれを言う理由は、行と列の重みを設定することを心配する必要がないということです。

この行を変更してみてください:

app.grid() 

...これに:それと

app.pack(fill="both", expand=True) 

、あなたは今のウィジェットは、ウィンドウを埋めることがわかりますし、ウィンドウのサイズを変更する場合それに応じてすべてがサイズ変更されます。

興味深い練習として、アプリの重さを設定する場所にこの行を追加してみてください。そこに他の行を残して、両方の列に重みを与えたいとします。それを試して、手動でウィンドウのサイズを変更したときに何が起こるかを確認してください。

app.grid_columnconfigure(0, weight=1) 

内部ウィジェットが両方とも拡張されていることに注意してください。列の重さは同じなので、等しく展開されます。左の2倍の大きさに拡大するには、その重さを2に設定します。

+0

ありがとうございます。私はこの種の根本的な概念の深い説明に本当に感謝しています。私は不思議です - グリッドとパックを混在させることはいいえでしたが、ここではアプリは詰まっていますが、grid_columnconfigは基になるグリッドを参照しているようです。状況は、「単純にするために、アプリケーションフレームをルートウィンドウにパックしていますが、そのフレームの他のウィジェットがグリッドを使用している場合は、これらのウェイトを割り当てますか? – Robin

+0

@Robin:同じ親を持つウィジェットで両方を使用する場合は、グリッドとパックの混合を避けなければなりません。それは問題ではなく、さらに好ましいことです! - アプリケーション全体で両方を使用する。 –

関連する問題