pythonpython-3.xtkintertkinter-canvasalgorithm-animation

How to swap two objects' positions on a tkinter canvas


I am working on a sorting visualization program with tkinter using the height of different rectangles. I was able to randomize the height of each rectangle, but now I am stuck trying to figure out how to switch the position of two rectangles with each other. I need to figure out how to do this before I can start trying to implement a sort.

Here is what I have so far:

import tkinter as tk
import random

window = tk.Tk()
window.title('Sorting')
window.geometry('600x400')

xstart = 5
xend = 15
canvas = tk.Canvas(window, width='600', height='400')
canvas.pack()
barList = []
lengthList = []

for x in range(1,60):
    randomY = random.randint(1,390)
    bar = canvas.create_rectangle(xstart,randomY,xend,395, fill='red')
    barList.append(bar)
    xstart += 10
    xend +=10

for bar in barList:
    x = canvas.coords(bar)
    length = x[3]-x[1]
    lengthList.append(length)



window.mainloop()

Solution

  • Here is a small example to get you started: It swaps rectangle at position 10 and rectangle at position 20 upon clicking on the swap button.

    import tkinter as tk
    import random
    
    
    def swap_two_pos(pos_0, pos_1):
        """This does the graphical swapping of the rectangles on the canvas
        by moving one rectangle to the location of the other, and vice versa
        """    
        x_00, _, x_01, _ = canvas.coords(pos_0)
        x_10, _, x_11, _ = canvas.coords(pos_1)
        # moves each rectangle to the x position of the other; y remains unchanged
        canvas.move(pos_0, x_10-x_00, 0)
        canvas.move(pos_1, x_01-x_11, 0)
    
    
    def random_sort():
        """Not a sort yet, but you have the bare bones operations
        so the swap is executed
        """
        pos_0 = barList[10]
        pos_1 = barList[20]
        swap_two_pos(pos_0, pos_1)
        # it is necessary to swap the values in the list too
        barList[10], barList[20] = barList[20], barList[10]
    
    
    window = tk.Tk()
    window.title('Sorting')
    window.geometry('600x400')
    
    # button to command the swap
    tk.Button(window, text='swap', command=random_sort).pack()
    
    xstart = 5
    xend = 15
    canvas = tk.Canvas(window, width='600', height='400')
    canvas.pack()
    barList = []
    lengthList = []
    
    for x in range(1,60):
        randomY = random.randint(1,390)
        bar = canvas.create_rectangle(xstart, randomY, xend, 395, fill='red')
        barList.append(bar)
        xstart += 10
        xend +=10
    
    for bar in barList:
        x = canvas.coords(bar)
        length = x[3]-x[1]
        lengthList.append(length)
    
    # hardcoded colors so the swap is more visual
    canvas.itemconfig(barList[10], fill='blue')
    canvas.itemconfig(barList[20], fill='yellow')
    
    window.mainloop()