как перетащить все содержимое в прямоугольник, используя tkinter python? - PullRequest
1 голос
/ 08 марта 2020

На экране вывода будет прямоугольник, заключенный в прямоугольник, если я перетаскиваю, внешний прямоугольник внутри прямоугольника также должен быть перетащен, но перетаскивается только внешний. Как перетащить все содержимое внешнего прямоугольника? В любой форме, если форма перетаскивается, ее содержимое также следует перетаскивать, но содержимое не перетаскивают, перетаскивают только внешнюю форму.

Вот мой код.

import tkinter as tk     # python 3
# import Tkinter as tk   # python 2

class Example(tk.Frame):
    """Illustrate how to drag items on a Tkinter canvas"""

    def __init__(self, parent):
        tk.Frame.__init__(self, parent)

        # create a canvas
        self.canvas = tk.Canvas(width=400, height=400, background="bisque")
        self.canvas.pack(fill="both", expand=True)

        # this data is used to keep track of an
        # item being dragged
        self._drag_data = {"x": 0, "y": 0, "item": None}

        # create a couple of movable objects
        #self.create_token(50, 100, "white")
        self.create_token(200, 100, "black")
        self.create_token1(200,100,"white")
        # add bindings for clicking, dragging and releasing over
        # any object with the "token" tag
        self.canvas.tag_bind("token", "<ButtonPress-1>", self.drag_start)
        self.canvas.tag_bind("token", "<ButtonRelease-1>", self.drag_stop)
        self.canvas.tag_bind("token", "<B1-Motion>", self.drag)

    def create_token(self, x, y, color):
        """Create a token at the given coordinate in the given color"""
        self.canvas.create_rectangle(
            x - 25,
            y - 25,
            x + 25,
            y + 25,
            outline=color,
            fill=color,
            tags=("token",),
        )

    def create_token1(self,x,y,color):

        self.canvas.create_rectangle(
            x - 25,
            y - 10,
            x + 25,
            y + 10,
            outline=color,
            fill=color,
            tags=("token",),
        )

    def drag_start(self, event):
        """Begining drag of an object"""
        # record the item and its location
        self._drag_data["item"] = self.canvas.find_closest(event.x, event.y)[0]
        self._drag_data["x"] = event.x
        self._drag_data["y"] = event.y

    def drag_stop(self, event):
        """End drag of an object"""
        # reset the drag information
        self._drag_data["item"] = None
        self._drag_data["x"] = 0
        self._drag_data["y"] = 0

    def drag(self, event):
        """Handle dragging of an object"""
        # compute how much the mouse has moved
        delta_x = event.x - self._drag_data["x"]
        delta_y = event.y - self._drag_data["y"]
        # move the object the appropriate amount
        self.canvas.move(self._drag_data["item"], delta_x, delta_y)
        # record the new position
        self._drag_data["x"] = event.x
        self._drag_data["y"] = event.y

if __name__ == "__main__":
    root = tk.Tk()
    Example(root).pack(fill="both", expand=True)
    root.mainloop()

1 Ответ

1 голос
/ 08 марта 2020

В drag_start() Я использую внешний прямоугольник, чтобы получить его область и добавляю тег «перетаскивать» ко всем элементам, которые полностью находятся внутри этой области

rect = self.canvas.bbox(self._drag_data["item"])

self.canvas.addtag_enclosed("drag", *rect)

В dra() Я перемещаю все элементы с тегом "drag"

self.canvas.move("drag", delta_x, delta_y)

В drag_stop() Я удаляю тег "drag" из всех элементов, имеющих тег "drag"

self.canvas.dtag("drag", "drag")

Таким образом, внешний прямоугольник может перемещаться также и внутренний прямоугольник. Но если вы перемещаете внутренний прямоугольник, то внутренний прямоугольник не двигается. Если вам нужен внешний прямоугольник при перемещении внутреннего прямоугольника, то, возможно, вам следует использовать тег "token"

self.canvas.move("token", delta_x, delta_y)

import tkinter as tk     # python 3
# import Tkinter as tk   # python 2

class Example(tk.Frame):
    """Illustrate how to drag items on a Tkinter canvas"""

    def __init__(self, parent):
        tk.Frame.__init__(self, parent)

        # create a canvas
        self.canvas = tk.Canvas(width=400, height=400, background="bisque")
        self.canvas.pack(fill="both", expand=True)

        # this data is used to keep track of an
        # item being dragged
        self._drag_data = {"x": 0, "y": 0, "item": None}

        # create a couple of movable objects
        #self.create_token(50, 100, "white")
        self.create_token(200, 100, "black")
        self.create_token1(200,100,"white")
        # add bindings for clicking, dragging and releasing over
        # any object with the "token" tag
        self.canvas.tag_bind("token", "<ButtonPress-1>", self.drag_start)
        self.canvas.tag_bind("token", "<ButtonRelease-1>", self.drag_stop)
        self.canvas.tag_bind("token", "<B1-Motion>", self.drag)

    def create_token(self, x, y, color):
        """Create a token at the given coordinate in the given color"""
        self.canvas.create_rectangle(
            x - 25,
            y - 25,
            x + 25,
            y + 25,
            outline=color,
            fill=color,
            tags=("token",),
        )

    def create_token1(self,x,y,color):

        self.canvas.create_rectangle(
            x - 25,
            y - 10,
            x + 25,
            y + 10,
            outline=color,
            fill=color,
            tags=("token",),
        )

    def drag_start(self, event):
        """Begining drag of an object"""
        # record the item and its location
        self._drag_data["item"] = self.canvas.find_closest(event.x, event.y)[0]

        rect = self.canvas.bbox(self._drag_data["item"])
        self.canvas.addtag_enclosed("drag", *rect)
        print(rect)

        self._drag_data["x"] = event.x
        self._drag_data["y"] = event.y

    def drag_stop(self, event):
        """End drag of an object"""
        # reset the drag information
        self._drag_data["item"] = None
        self._drag_data["x"] = 0
        self._drag_data["y"] = 0
        self.canvas.dtag("drag", "drag")

    def drag(self, event):
        """Handle dragging of an object"""
        # compute how much the mouse has moved
        delta_x = event.x - self._drag_data["x"]
        delta_y = event.y - self._drag_data["y"]

        # move the object the appropriate amount
        #self.canvas.move(self._drag_data["item"], delta_x, delta_y)
        self.canvas.move("drag", delta_x, delta_y)

        # record the new position
        self._drag_data["x"] = event.x
        self._drag_data["y"] = event.y

if __name__ == "__main__":
    root = tk.Tk()
    Example(root).pack(fill="both", expand=True)
    root.mainloop()
...