Замедление прокрутки Tkinter Canvas в Python - PullRequest
0 голосов
/ 24 марта 2011

В основном у меня работает следующий код, но я не могу найти способ замедлить перетаскивание моего холста, так как на данный момент он работает слишком быстро, чтобы быть функциональным для моего приложения.Это лишь небольшой пример, который показывает, что я пытаюсь устранить:

from Tkinter import * 
import Image, ImageTk

class GUI:
    def __init__(self,root):
        frame = Frame(root, bd=2, relief=SUNKEN)

        frame.grid_rowconfigure(0, weight=1)
        frame.grid_columnconfigure(0, weight=1)
        xscrollbar = Scrollbar(frame, orient=HORIZONTAL)
        xscrollbar.grid(row=1, column=0, sticky=E+W)
        yscrollbar = Scrollbar(frame)
        yscrollbar.grid(row=0, column=1, sticky=N+S)
        self.canvas = Canvas(frame, bd=0, xscrollcommand=xscrollbar.set, yscrollcommand=yscrollbar.set)
        self.canvas.grid(row=0, column=0, sticky=N+S+E+W)

        File = "JPG FILENAME HERE"

        self.img = ImageTk.PhotoImage(Image.open(File))
        self.canvas.create_image(0,0,image=self.img, anchor="nw")
        self.canvas.config(scrollregion=self.canvas.bbox(ALL))
        xscrollbar.config(command=self.canvas.xview)
        yscrollbar.config(command=self.canvas.yview)

        frame.pack()

        self.canvas.bind("<Button 3>",self.grab)
        self.canvas.bind("<B3-Motion>",self.drag)

    def grab(self,event):
        self._y = event.y
        self._x = event.x

    def drag(self,event):
        if (self._y-event.y < 0): self.canvas.yview("scroll",-1,"units")
        elif (self._y-event.y > 0): self.canvas.yview("scroll",1,"units")
        if (self._x-event.x < 0): self.canvas.xview("scroll",-1,"units")
        elif (self._x-event.x > 0): self.canvas.xview("scroll",1,"units")
        self._x = event.x
        self._y = event.y

root = Tk()   
GUI(root)
root.mainloop()

ОТВЕТ:

Ответ Брайана Оукли помог мне, которую я только что изменил:

self.canvas = Canvas(frame, bd=0, xscrollcommand=xscrollbar.set, yscrollcommand=yscrollbar.set)

до:

self.canvas = Canvas(frame, bd=0, xscrollcommand=xscrollbar.set, yscrollcommand=yscrollbar.set,xscrollincrement=10,yscrollincrement=10)

, и это сработало как заклинание.

Ответы [ 3 ]

2 голосов
/ 25 марта 2011

Попробуйте установить значение атрибутов xscrollincrement и yscrollincrement холста на большее, чем ноль. Эти настройки соответствуют units, используемому при вызове xview и yview с аргументом «единицы измерения» (например: self.canvas.xview("scroll",-1,"units").

Согласно официальной документации Tk, если эти значения равны нулю (по умолчанию), xview и yview изменяют "... в единицах параметра [x, y] ScrollIncrement, если оно больше нуля, или в десятых долях окна [ширина, высота] в противном случае "

2 голосов
/ 25 марта 2011

Я действительно не знаю, что я здесь делаю, но, по крайней мере, это движется более управляемо.Сначала явно задайте размер холста:

self.canvas = Canvas(frame, bd=0, height=600, width=800,
                     xscrollcommand=self.xscrollbar.set,
                     yscrollcommand=self.yscrollbar.set)

Затем в __init__() добавьте пару переменных экземпляра для отслеживания текущей позиции:

self.pos_x = self.pos_y = 0.0

Затем заменитеdrag метод с этим:

def drag(self, event):
# Note canvas dimensions are used here
    self.pos_x += float(self._x-event.x) / 800.0
    self.pos_y += float(self._y-event.y) / 600.0

    if self.pos_x < 0.0: self.pos_x = 0.0
    elif self.pos_x > 1.0: self.pos_x = 1.0
    if self.pos_y < 0.0: self.pos_y = 0.0
    elif self.pos_y > 1.0: self.pos_y = 1.0

    self.canvas.xview("moveto", self.pos_x)
    self.canvas.yview("moveto", self.pos_y)

    self._x = event.x
    self._y = event.y

Я не знаю, почему вы должны бросать эти числа, чтобы плавать, но это не работает, если вы этого не сделаете.Это хрупкое;если вы умножаете движение мыши на что угодно, даже на 0,99 или 1,01, движение становится действительно шатким;Я подозреваю, что между движением мыши и движением холста происходит какая-то обратная связь.С полосами прокрутки тоже не очень хорошо;Я полагаю, что мы должны обновить pos_x и pos_y, когда они будут перемещены.Как я уже сказал, на самом деле не знаю, что я делаю;Я не много занимался программированием GUI.В любом случае, надеюсь, это поможет.

0 голосов
/ 09 января 2012

Попробуйте, измените перетаскивание, чтобы использовать только вычисленное значение:

    self.canvas.yview("scroll",self._y-event.y,"units")
    self.canvas.xview("scroll",self._x-event.x,"units")

И измените значения прокрутки на 1.

Теперь ваше изображение должно щелкать и синхронизироваться с мышьюкурсор, похожий на популярные средства просмотра карт и документов.

...