2016-11-27 19 views
0

私は、pythonでtkinterを使ってjsonエディタを作成しています。キャンバスでスクロールバーが動作しない

Canvasを作成し、Frameを内部に入れてスクロールバーを追加しました。

次に、Scrollbarコマンドをcanvas.yviewに設定しました。

Theresは2つのことがうんざりしていて、私は理由を知らない。

私はスクロールボタン(上下矢印)を押すとキャンバスは、私はいつでも私ので、代わりにフレームの今のウィンドウ(ルート)上にスクロールバーを梱包しています

  • をスクロールされていない

    1. それをフレームにパックすると、tkinterアプリケーションは開かず、コンピュータファンが起動します...誰でも何が起こっているのか知っていますか? (したがって、あなたがコードを実行しようとした場合、スクロールバーはごくわずかです)

    ここに私のコードです:

    EDIT>コードは、それは少し長いです

    import Tkinter as tk 
    import webbrowser 
    import os 
    import bjson as bj 
    
    class App: 
        def __init__(self, master): 
         self.window = master 
         self.window.geometry("800x450") 
         self.canvas = tk.Canvas(self.window, width=800, height=400) 
         self.master = tk.Frame(self.canvas, width=800, height=400) 
         self.canvas.pack() 
         self.master.place(x=0, y=0) 
         scrollbar = tk.Scrollbar(self.window) 
         scrollbar.pack(side=tk.RIGHT, fill=tk.Y) 
         scrollbar.config(command=self.canvas.yview) 
    
        def init(self): 
         master = self.master 
         self.frames = { 
          "Home": HomeFrame(master) 
         } 
         self.openFrame = None 
         self.loadFrame("Home") 
    
        def loadFrame(self, frame): 
         self.openFrame = self.frames[frame] 
         self.openFrame.display() 
    
        def setTitle(self, t): 
         self.window.title(t) 
    
    class Frame: 
        def __init__(self, master): 
         self.master = master 
         self.frame = tk.Frame(master) 
         self.frame.grid(row=0, column=0, sticky='news') 
         self.init() 
         self.frame_create() 
    
        def display(self): 
         self.frame.tkraise() #raises frame to top 
         self.frame_load()  #initializes the frame 
    
        def clear(self): 
         for widget in self.frame.winfo_children(): 
          widget.destroy() 
    
        def init(self): pass 
        def frame_load(self): pass 
        def frame_create(self): pass 
    
    class HomeFrame(Frame): 
        def frame_create(self): 
         p = self.frame 
         for i in range(20): 
          tk.Label(p, text="This is content... " + str(i)).pack() 
          for j in range(2): 
           LineBreak(p) 
    
    def LineBreak(p): 
        tk.Label(p, text="").pack() 
    
    root = tk.Tk() 
    glob = {} 
    app = App(root) 
    app.init() 
    root.mainloop() 
    

    を短縮し、ちょっと混乱しますが、私はどのようにスクロールバーを追加しているのでしょうか__init__App

    誰もが何が起こっているのか分かりませんそれを修正する方法は?

    ありがとうございます!

  • +0

    可能な限りすべてのコードを削除して、悪い動作を示す例を提供してください。 [最小限の、完全で検証可能な例を作成する方法](http://www.stackoverflow.com/help/mcve) –

    +0

    コードを同じ問題を解決した短縮バージョンに更新しました。ご協力いただきありがとうございます。 –

    答えて

    0

    コードには多くの問題があります。しかし、スクロールバーが正しく動作しない問題は、あなたが無視している2つのことと関係があります。

    まず、スクロールバーとウィジェットは双方向通信が必要です。キャンバスにはスクロールバーについての情報が必要です。スクロールバーにはキャンバスについての情報が必要です。あなたが1ではなく、他のをやっています

    self.canvas.configure(yscrollcommand=scrollbar.set) 
    scrollbar.configure(command=self.canvas.yview) 
    

    第二に、あなたはキャンバスのscrollregion属性を設定する必要があります。これは、tkinterに大きな仮想キャンバスのどの部分を表示したいかを指示します。通常、これはキャンバスのメソッドのバインディングで行われます。通常、キャンバス内のすべてのバウンディングボックスに設定する必要があります。後者の場合は、あなたがbboxメソッドに文字列"all"を渡すことができます:あなたは、スクロール可能になりたい地域の正確なサイズを知っている場合

    self.canvas.configure(scrollregion=self.canvas.bbox("all")) 
    

    が、あなたは、単にその値を設定することができます(例:scrollregion=(0,0,1000,1000)をスクロールします1000×1000ピクセルの領域内で)。

    ポイント2の理由は、同じ親を共有するウィジェットに対してpackgridの両方を使用できないためです。あなたがすると、あなたが描いている行動を得るでしょう。これは、gridがすべてのウィジェットをレイアウトしようとするためです。これにより、一部のウィジェットのサイズが変わることがあります。 packは、1つ以上のウィジェットのサイズの変化に気付き、すべてのウィジェットを再レイアウトしようとします。これにより、一部のウィジェットのサイズが変わることがあります。gridは、1つ以上のウィジェットのサイズの変化に気付き、すべてのウィジェットを再レイアウトしようとします。等々。

    関連する問題