Reputation: 127
I want to create yet another clone of Pong with Python and Turtle. My goal is to let my pupils (that begin to code in Python) to practise a bit further.
I'd like to create a Turtle whose shape is an horizontal filled rectangle, like a stylized paddle. But when I create a shape I suppose to be convenient, I get a rotated (vertical) paddle instead of the horizontal one I hoped for.
Here is a code that demonstrates this odd behaviour.
from turtle import *
begin_poly()
fd(200)
left(90)
fd(40)
left(90)
fd(200)
left(90)
fd(40)
left(90)
end_poly()
shape = get_poly()
register_shape("drawn", shape)
polyNotOk = ( (0,0), (100, 0), (100, 20), (0, 20) )
register_shape("polyNotOk", polyNotOk)
polyOk = ( (0,0), (0, 100), (20, 100), (20, 0) )
register_shape("polyOk", polyOk)
t1 = Turtle(shape="drawn")
t2 = Turtle(shape="polyNotOk")
t3 = Turtle(shape="polyOk")
t1.color("black")
t2.color("red")
t3.color("blue")
t1.stamp()
t2.stamp()
t3.stamp()
t1.goto(100,200)
t2.goto(100,-50)
t3.goto(100,-150)
t1.forward(100)
t2.forward(100)
t3.forward(100)
mainloop()
So, as you can see if you run the code, the first drawing is OK, with an horizontal shape. But when I stamp the Turtle t1
, the shape is vertical.
Same problem with the 2nd shape, defined through polyNotOk
(with values for x and y coords which allow to get a horizontal paddle). I need to create a "vertical" poly to get a horizontal paddle.
So I'm able to find a workaround. Yet I'm still not satisfied with this solution, so I'm asking for brilliant explanations ;-) Thanks in advance.
Upvotes: 0
Views: 277
Reputation: 41872
I hope to illuminate this odd behavior, not defend it. First thing to remember about drawn cursors is that where ever (0, 0)
falls in your cursor drawing, that's the center point about which your cursor rotates and the pixel in your cursor that lands on any point you goto()
.
Some insight might be found in the shapesize()
method documentation:
shapesize(stretch_wid=None, stretch_len=None, outline=None)
stretch_wid is stretchfactor perpendicular to orientation
stretch_len is stretchfactor in direction of turtles orientation.
That is, if the cursor is in the default (East) orientation, this reverses the sense of X and Y. I believe that's what you're seeing in your drawing. The X plane is perpendicular to orientation (vertical) and the Y plane is in the direction of orientation (horizontal). The opposite of what we normally expect.
This doesn't appear to be the fault of the Shape()
class, but buried in the cursor logic. It may be a historical artifact--if we change to mode("logo")
and run your code, we get:
More what we might expect, given that "logo" mode's default orientation is North, and more consistent than before.
Regardless, I would make my paddles a different way. Instead of a custom cursor, I'd use turtle's square cursor and reshape it as needed using shapesize()
:
from turtle import Screen, Turtle
CURSOR_SIZE = 20
screen = Screen()
t0 = Turtle("square")
t0.shapesize(20 / CURSOR_SIZE, 100 / CURSOR_SIZE)
t0.color("green")
screen.exitonclick()
Still rotated logic (not graphic) from what you might expect, but at least the documentation told us that. But, what I really tend to do is make the paddle in the wrong orientation, and use settiltangle()
, but not as a workaround as you did, but to make my paddle face in one direction, but move in the other:
from turtle import Screen, Turtle
CURSOR_SIZE = 20
screen = Screen()
t0 = Turtle("triangle")
t0.shapesize(100 / CURSOR_SIZE, 20 / CURSOR_SIZE)
t0.settiltangle(90)
t0.penup()
t0.color("green")
t0.speed("slowest") # for demonstration purposes
t0.forward(300)
t0.backward(600)
t0.forward(300)
screen.exitonclick()
Notice that I can use forward(10)
and backward(10)
to move my paddle and not have to do awful things like t0.setx(t0.xcor() + 10)
. Works great for Space Invader type games where the player faces upwards but moves sideways.
Upvotes: 1