[Tkinter-discuss] Canvas -> move object and remove previous location
John McMonagle
jmcmonagle at velseis.com.au
Tue May 8 01:48:37 CEST 2007
# move the image by the difference between the last point
Teresa Stanton wrote:
> Hi all:
>
> I am working on a program that will take a .gif and move it from origin,
> along a path where the mouse clicks. I understand that the move is
> simply changing the coordinates. I can place several .gif's on the
> canvas, but I would like to make the previous image go away (delete or
> be removed) and thus far been unable to do that. The example program I
> wrote simply takes the image and moves it. I should mention that I've
> tried 'move() and coord()' to get the object to move, but I am not
> getting the effect I want. When I use move in successive steps it just
> appears at the last move coordinates. And when I try to use delete,
> well, it doesn't work, I get an error message. I should mention that
> I'm using python25.
>
>
Ok. You need to understand some of the Canvas methods better.
Firstly the canvasx and canvasy methods translate screen coordinates
from your event to the Canvas coordinates. So when you generate a
Button-1 event, the event.x and event.y attributes need to be converted
to your Canvas x and y coordinates.
x2 = canvas1.canvasx(event.x)
y2 = canvas1.canvasy(event.y)
Second, you need to know what the coordinates are of your canvas image
object. This is where the coords method of the Canvas widget will help
you. But before you get the coordinates you need to know the object tag
or id. The easiest way to do this is to use the tags option when first
creating the tag.
canvas1.create_image(x,y, image=photo, tags='myPhoto')
Now, you can get the coordinates of this tag:
x1, y1 = canvas1.coords('myPhoto')
Thirdly, the move method of the Canvas widget moves the tag or id dx, dy
canvas units - it is a differential move. You could simply move the
image to the new coordinates by computing the difference between the
original x,y and the new x,y (as clicked):
canvas1.move('myPhoto', x2-x1, y2-y1)
However, you want to move the image to the clicked point in slow steps.
So, this will require you computing a stepped difference between the
two points, loop over the steps, moving the image, sleeping, then updating.
Fourthly, the delete method of the Canvas widget deletes an item or tag
(but you don't need it here).
canvas1.delete('myPhoto')
The following code is pretty rough, but should illustrate some of the
concepts needed. It also doesn't handle the zero increment case.
from Tkinter import *
import time
root = Tk()
root.title("Click me!")
def next_image(event):
# Convert the screen coordinates of the event to canvas coordinates
x2 = canvas1.canvasx(event.x)
y2 = canvas1.canvasy(event.y)
x2 = int(x2)
y2 = int(y2)
# get the phot object coordinates
x1, y1 = canvas1.coords('myPhoto')
x1 = int(x1)
y1 = int(y1)
# create two lists of stepped x and y
xinc = (x2 - x1)/100
yinc = (y2 - y1)/100
print xinc, yinc
xlist = []
for x in xrange(x1, x2+xinc, xinc):
print x
xlist.append(x)
ylist = []
for y in xrange(y1, y2+yinc, yinc):
print y
ylist.append(y)
# move the image by the difference between the last point, sleep
# for half a millisecond, update the display
for i, x in enumerate(xlist):
if i == 0:
canvas1.move('myPhoto', x-x1, ylist[i]-y1)
else:
canvas1.move('myPhoto', x-xlist[i-1], ylist[i]-ylist[i-1])
time.sleep(0.05)
root.update()
image = "DustY1.GIF" # use any gif, this is a cartoon of my dog
photo = PhotoImage(file=image)
# make canvas the size of image1/photo1
width1 = photo.width()
height1 = photo.height()
canvas1 = Canvas(width=width1, height=height1)
canvas1.pack()
# display photo, x, y is center
x = (width1)/2.0
y = (height1)/2.0
# this is the first image
canvas1.create_image(x, y, image=photo, tags='myPhoto') # added tags option
canvas1.bind('<Button-1>', next_image) # bind left mouse click
root.mainloop()
Regards,
John
More information about the Tkinter-discuss
mailing list