Hi Vern, hi everybody!

I've had a look to turtlenew - which in fact has not very much new stuff ...

I provide a set of sample programs, sort of test, which I use to use as 
test cases with my (X)turtle module - work inprogress .. I've modified 
them, so they work with turtlenew.

Just save them together with turtlenew2.py in a directory and run them 
from within IDLE (or uncomment the mainloop - call). All of them except 
demo.py will also run with turtlenew.py

I've - as a proposition - added one function to turtlenew: 
towards(*args), which returns the angle between the line from the turtle 
     to the arg and the positive x-axis-direction. As a demo it's used 
in demo.py. (The idea is of course taken from Logo, where it is also 
present) This method uses atan2. So it's not elementary and young 
students won't be able to program it on their own. So I consider it 
rather essential. (In fact I incorporated it also into my book-specific 
turtle.py three years ago - which was also a moderate extension of the 
original one.)

I've also changed one line in the speed-method  just for aesthetic 
reasons. (Line 317 intutlenew2.py)

If hope you appreciate these changes, and I'd like to see them 
integrated into turtle.py

Imho there is one serious problem with circle and fill - they don't fit 
together. You can observe this with the yinyang - program and with 
demo.py . They simply do not work as everybody would naturally expect.

I fear this could only be solved by abandoning the use of the arc items 
of the canvas widget.

Regards,
Gregor



-- 
Gregor Lingl
Reisnerstrasse 3/19
A-1030 Wien

Telefon: +43 1 713 33 98
Mobil:   +43 664 140 35 27

Website: python4kids.net


--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups 
"edupython" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at http://groups.google.com/group/edupython
-~----------~----~----~----~------~----~------~--~---
# Xturtle ==> turtle example
# yinyang

# NOTE:  In the first import statement
# replace Xturtle by turtle to see, how
# the original turtle acts here.

from turtlenew2 import *
from Tkinter import mainloop

def yin(radius, farbe1, farbe2):
    width(3)
    color("black")
    fill(1)
    circle(radius/2., 180)
    circle(radius, 180)
    left(180)
    circle(-radius/2., 180)
    color(farbe1)
    fill(1)
    left(90)
    up()
    forward(radius*0.375)
    right(90)
    down()
    circle(radius*0.125)
    left(90)
    color(farbe2)
    fill(1)
    up()
    backward(radius*0.375)
    down()
    left(90)

reset()
yin(100, "white", "black")
yin(100, "black", "white")

#mainloop()
from turtlenew2 import *        
from Tkinter  import mainloop
from time import sleep

def demo1():
    # demo des alten turtle-Moduls
    reset()
    tracer(1)
    up()
    backward(100)
    down()
    # draw 3 squares; the last filled
    width(3)
    for i in range(3):
        if i == 2:
            fill(1)
        for j in range(4):
            forward(20)
            left(90)
        if i == 2:
            color("maroon")
            fill(0)
        up()
        forward(30)
        down()
    width(1)
    color("black")
    # move out of the way
    tracer(0)
    up()
    right(90)
    forward(100)
    right(90)
    forward(100)
    right(180)
    down()
    # some text
    write("startstart", 1)
    write("start", 1)
    color("red")
    # staircase
    for i in range(5):
        forward(20)
        left(90)
        forward(20)
        right(90)
    # filled staircase
    fill(1)
    for i in range(5):
        forward(20)
        left(90)
        forward(20)
        right(90)
    fill(0)
    # more text
    write("wait a moment...")
    tracer(1)

def demo2():
    # einige weitere und einige neue features
    speed(1)
##    st()
    width(3)
    setheading(towards(0,0))
    x,y = position()
    r = (x**2+y**2)**.5/2.0
    right(90)
    pendown = True
    for i in range(18):
        if pendown:
            up()
            pendown = False
        else:
            down()
            pendown = True
        circle(r,10)
    sleep(2)
   
    reset() 
    left(90)

    l = 10
    color("green")
    width(3)
    left(180)
    sp = 1
    for i in range(-2,16):
        if i > 0:
            color(1.0-0.05*i,0,0.05*i)
            fill(1)
            color("green")
        for j in range(3):
            forward(l)
            left(120)
        l += 10
        left(15)
        if sp < 4:
            sp = sp+1
            speed(sp)
    color(0.25,0,0.75)
    fill(0)
    color("green")

    left(120)
    up()
    forward(70)
    right(30)
    down()
    color("red")
    speed(0)
    fill(1)
    for i in range(4):
        circle(50,90)
        right(90)
        forward(30)
        right(90)
    color("yellow")
    fill(0)
    color("red")
    left(90)
    up(); forward(30); down(); # setshape(1)

##    tri = turtles()[0]
    turtle=Pen()
##    turtle.setshape(1)
####    turtle.mode("logo")
    turtle.reset()
    turtle.left(90)
    turtle.speed(2)
    turtle.up()
    turtle.goto(280,40)
    turtle.left(24)
    turtle.down()
    turtle.speed(2)
    turtle.color("blue")
    turtle.width(2)
    speed(4)
##    setheading(towards(*turtle.position()))  ## for simple towards
    setheading(towards(turtle))
    while ( abs(position()[0]-turtle.position()[0])>4 or
            abs(position()[1]-turtle.position()[1])>4):
        turtle.forward(3.5)
        turtle.left(0.6)
##        setheading(towards(*turtle.position()))
        setheading(towards(turtle))
        forward(4)
    write("CAUGHT! ", move=True)


demo1()
demo2()

#mainloop()
## NT - Die neue Turtle-Grafik
##
#######################################
## Nfilltest.py  ---
## urspruenglich ein Testprogramm in NT.py
#######################################
##
## Autor: Gregor Lingl
## Datum: 16. 3. 2006


from turtlenew2 import Pen
from Tkinter import mainloop    
    
t = Pen()
t.left(90)
t.speed(1)

l = 210
t.up()
t.backward(20)
t.down()

## 1. triangle

t.right(30)
t.width(3)

t.fill(True)
for i in 1,2,3:
    t.color("red")
    t.forward(l/3.)
    t.color("green")
    t.forward(l/3.)
    t.color("blue")
    t.forward(l/3.)
    t.left(120)
t.color(.8,.8,1)
t.fill(False)

t.left(30)

## 2. triangle

t.left(60)

t.color("blue")
t.fill(True)
t.width(10)

for i in 1,2,3:
    t.forward(l)
    t.left(120)
t.color("red")
t.fill(False)

t.left(30)

## 3. triangle

t.left(60)
t.up()
t.fill(True)
for i in 1,2,3:
    t.forward(l)
    t.left(120)
t.color(0.7,0,0.7)
t.fill(False)
t.down()
t.left(30)

## Change screencolor

# t.screen.screencolor("yellow")

## 4. triangle    

t.left(60)

t.speed(1)
t.color("green")
t.fill(True)
for i in 1,2,3:
    #if i==2: t.hideturtle()
    t.width(2+3*i)
    t.forward(l/3.0)
    t.up()
    t.left(60)
    t.forward(l/6.0)
    t.right(120)
    t.forward(l/3.0)
    t.left(120)
    t.forward(l/6.0)
    t.right(60)
    t.down()
    t.forward(l/3.0)
    # if i==2: t.showturtle()
    t.left(120)
t.color("red")
t.fill(True)

t.left(30)

## original heading

t.left(90)
t.speed(2)
t.up()
t.forward(l/3**0.5)
#mainloop()
# Autor: Rudolf Zeidler
# Datum: 01.12.2004
# radioaktiv.py: Zeichnet ein radioaktiv-Gefahrensymbol

# doesn't use the color-capabilities of Xturtle in order
# to work also with turtle.py


# NOTE:  In the first import statement
# replace Xturtle by turtle to see, how
# (buggy) the turtle acts here, when trying to
# fill sectors

from turtlenew import *
from Tkinter import mainloop

def quadrat(laenge):
    for i in range(4):
        forward(laenge)
        left(90)

def kreisSektor(radius, winkel):
    forward(radius)
    left(90)
    circle(radius, winkel)
    left(90)
    forward(radius)
    left(120)

def move(x, y):
    up()
    forward(x)
    left(90)
    forward(y)
    left(-90)
    down()

def radioaktiv(radius1, radius2, seite, winkel = 60, randFarbe = "black", 
fuellFarbe = "yellow"):
    color(randFarbe)
    move(-(seite / 2) , -(seite / 2))
    
    fill(1)
    quadrat(seite)
    color(fuellFarbe)
    fill(0)
    move((seite / 2), (seite / 2))
    color(randFarbe)
    right(90 + winkel / 2)

    for i in range(3):
        fill(1)
        kreisSektor(radius1,winkel)
        left((360 - 3 * winkel)/3 + 60)
        color(randFarbe)
        fill(0)

    up()
    forward(radius2)
    left(90)
    down()

    color(fuellFarbe)
    fill(1)
    circle(radius2)
    color(randFarbe)
    fill(0)

    up()
    left(90)
    forward(radius2)
    width(1)

reset()
width(5)
radioaktiv(80, 15, 200) 
#mainloop()




#Gregor Lingl
#14.12.2005
#sierpinski_dreieck.py

from turtlenew2 import *
from Tkinter import mainloop

class Vec3(tuple):

    def __new__(cls, x, y, z):
        return tuple.__new__(cls, (x, y, z))
    def __add__(self, other):
        return Vec3(self[0]+other[0], self[1]+other[1], self[2]+other[2])
    def __mul__(self, other):
        return Vec3(self[0]*other, self[1]*other, self[2]*other)
    def __rmul__(self, other):
        return Vec3(self[0]*other, self[1]*other, self[2]*other)
    def __sub__(self, other):
        return Vec3(self[0]-other[0], self[1]-other[1], self[2]-other[2])
    def __div__(self, other):
        other = float(other)
        return Vec3(self[0]/other, self[1]/other, self[2]/other)
    def __neg__(self):
        return Vec3(-self[0], -self[1], -self[2])
    def __repr__(self):
        return "(%.2f,%.2f,%.2f)" % self 


  
def dreieck(laenge, stufe, f1, f2, f3):  # f1, f2, f3 Farben der Ecken
    if stufe == 0:
        color((f1+f2+f3)/3)
        down()
        fill(1)
        for i in range(3):
            forward(laenge)
            left(120)
        fill(0)
        up()
    else:
        c12 = (f1+f2)/2
        c13 = (f1+f3)/2
        c23 = (f2+f3)/2
        dreieck(laenge / 2, stufe - 1, f1, c12, c13)
        forward(laenge)
        left(120)
        dreieck(laenge / 2, stufe - 1, f2, c23, c12)
        forward(laenge)
        left(120)
        dreieck(laenge / 2, stufe - 1, f3, c13, c23)
        forward(laenge)
        left(120)

reset()
speed(0)
up()
backward(240)
left(90)
backward(200)
right(90)
down()
tracer(1)
speed(4)
dreieck(480, 5, Vec3(1.0,0,0), Vec3(0,1.0,0), Vec3(0,0,1.0))
#mainloop()
# LogoMation-like turtle graphics

from math import * # Also for export
import Tkinter

class Error(Exception):
    pass

_delay = 10      # default delay for drawing

class RawPen:

    def __init__(self, canvas):
        self._canvas = canvas
        self._items = []
        self._tracing = 1
        self._arrow = 0
        self._delay = _delay
        self.degrees()
        self.reset()

    def degrees(self, fullcircle=360.0):
        self._fullcircle = fullcircle
        self._invradian = pi / (fullcircle * 0.5)

    def radians(self):
        self.degrees(2.0*pi)

    def reset(self):
        canvas = self._canvas
        self._canvas.update()
        width = canvas.winfo_width()
        height = canvas.winfo_height()
        if width <= 1:
            width = canvas['width']
        if height <= 1:
            height = canvas['height']
        self._origin = float(width)/2.0, float(height)/2.0
        self._position = self._origin
        self._angle = 0.0
        self._drawing = 1
        self._width = 1
        self._color = "black"
        self._filling = 0
        self._path = []
        self._tofill = []
        self.clear()
        canvas._root().tkraise()

    def clear(self):
        self.fill(0)
        canvas = self._canvas
        items = self._items
        self._items = []
        for item in items:
            canvas.delete(item)
        self._delete_turtle()
        self._draw_turtle()

    def tracer(self, flag):
        self._tracing = flag
        if not self._tracing:
            self._delete_turtle()
        self._draw_turtle()

    def forward(self, distance):
        x0, y0 = start = self._position
        x1 = x0 + distance * cos(self._angle*self._invradian)
        y1 = y0 - distance * sin(self._angle*self._invradian)
        self._goto(x1, y1)

    def backward(self, distance):
        self.forward(-distance)

    def left(self, angle):
        self._angle = (self._angle + angle) % self._fullcircle
        self._draw_turtle()

    def right(self, angle):
        self.left(-angle)

    def up(self):
        self._drawing = 0

    def down(self):
        self._drawing = 1

    def width(self, width):
        self._width = float(width)

    def color(self, *args):
        if not args:
            raise Error, "no color arguments"
        if len(args) == 1:
            color = args[0]
            if type(color) == type(""):
                # Test the color first
                try:
                    id = self._canvas.create_line(0, 0, 0, 0, fill=color)
                except Tkinter.TclError:
                    raise Error, "bad color string: %r" % (color,)
                self._set_color(color)
                return
            try:
                r, g, b = color
            except:
                raise Error, "bad color sequence: %r" % (color,)
        else:
            try:
                r, g, b = args
            except:
                raise Error, "bad color arguments: %r" % (args,)
        assert 0 <= r <= 1
        assert 0 <= g <= 1
        assert 0 <= b <= 1
        x = 255.0
        y = 0.5
        self._set_color("#%02x%02x%02x" % (int(r*x+y), int(g*x+y), int(b*x+y)))

    def _set_color(self,color):
        self._color = color
        self._draw_turtle()

    def write(self, arg, move=0):
        x, y = start = self._position
        x = x-1 # correction -- calibrated for Windows
        item = self._canvas.create_text(x, y,
                                        text=str(arg), anchor="sw",
                                        fill=self._color)
        self._items.append(item)
        if move:
            x0, y0, x1, y1 = self._canvas.bbox(item)
            self._goto(x1, y1)
        self._draw_turtle()

    def fill(self, flag):
        if self._filling:
            path = tuple(self._path)
            smooth = self._filling < 0
            if len(path) > 2:
                item = self._canvas._create('polygon', path,
                                            {'fill': self._color,
                                             'smooth': smooth})
                self._items.append(item)
                if self._tofill:
                    for item in self._tofill:
                        self._canvas.itemconfigure(item, fill=self._color)
                        self._items.append(item)
        self._path = []
        self._tofill = []
        self._filling = flag
        if flag:
            self._path.append(self._position)
        self.forward(0)

    def circle(self, radius, extent=None):
        if extent is None:
            extent = self._fullcircle
        x0, y0 = self._position
        xc = x0 - radius * sin(self._angle * self._invradian)
        yc = y0 - radius * cos(self._angle * self._invradian)
        if radius >= 0.0:
            start = self._angle - 90.0
        else:
            start = self._angle + 90.0
            extent = -extent
        if self._filling:
            if abs(extent) >= self._fullcircle:
                item = self._canvas.create_oval(xc-radius, yc-radius,
                                                xc+radius, yc+radius,
                                                width=self._width,
                                                outline="")
                self._tofill.append(item)
            item = self._canvas.create_arc(xc-radius, yc-radius,
                                           xc+radius, yc+radius,
                                           style="chord",
                                           start=start,
                                           extent=extent,
                                           width=self._width,
                                           outline="")
            self._tofill.append(item)
        if self._drawing:
            if abs(extent) >= self._fullcircle:
                item = self._canvas.create_oval(xc-radius, yc-radius,
                                                xc+radius, yc+radius,
                                                width=self._width,
                                                outline=self._color)
                self._items.append(item)
            item = self._canvas.create_arc(xc-radius, yc-radius,
                                           xc+radius, yc+radius,
                                           style="arc",
                                           start=start,
                                           extent=extent,
                                           width=self._width,
                                           outline=self._color)
            self._items.append(item)
        angle = start + extent
        x1 = xc + abs(radius) * cos(angle * self._invradian)
        y1 = yc - abs(radius) * sin(angle * self._invradian)
        self._angle = (self._angle + extent) % self._fullcircle
        self._position = x1, y1
        if self._filling:
            self._path.append(self._position)
        self._draw_turtle()

    def heading(self):
        return self._angle

    def setheading(self, angle):
        self._angle = angle
        self._draw_turtle()

    def window_width(self):
        width = self._canvas.winfo_width()
        if width <= 1:  # the window isn't managed by a geometry manager
            width = self._canvas['width']
        return width

    def window_height(self):
        height = self._canvas.winfo_height()
        if height <= 1: # the window isn't managed by a geometry manager
            height = self._canvas['height']
        return height

    def position(self):
        x0, y0 = self._origin
        x1, y1 = self._position
        return [x1-x0, -y1+y0]

    def setx(self, xpos):
        x0, y0 = self._origin
        x1, y1 = self._position
        self._goto(x0+xpos, y1)

    def sety(self, ypos):
        x0, y0 = self._origin
        x1, y1 = self._position
        self._goto(x1, y0-ypos)

    def towards(self, *args):
        """returns the angle, which corresponds to the line
        from turtle-position to point (x,y).
        Argument can be two coordinates or one pair of coordinates
        or a RawPen/Pen instance. 
        """
        if len(args) == 2:
            x, y = args
        else:
            arg = args[0]
            if isinstance(arg, RawPen):
                x, y = arg.position()
            else:
                x, y = arg
        x0, y0 = self.position()
        dx = x - x0
        dy = y - y0
        return (atan2(dy,dx) / self._invradian) % self._fullcircle 

    def goto(self, *args):
        if len(args) == 1:
            try:
                x, y = args[0]
            except:
                raise Error, "bad point argument: %r" % (args[0],)
        else:
            try:
                x, y = args
            except:
                raise Error, "bad coordinates: %r" % (args[0],)
        x0, y0 = self._origin
        self._goto(x0+x, y0-y)

    def _goto(self, x1, y1):
        x0, y0 = start = self._position
        self._position = map(float, (x1, y1))
        if self._filling:
            self._path.append(self._position)
        if self._drawing:
            if self._tracing:
                dx = float(x1 - x0)
                dy = float(y1 - y0)
                distance = hypot(dx, dy)
                nhops = int(distance)
                item = self._canvas.create_line(x0, y0, x0, y0,
                                                width=self._width,
                                                capstyle="round",
                                                fill=self._color)
                try:
                    for i in range(1, 1+nhops):
                        x, y = x0 + dx*i/nhops, y0 + dy*i/nhops
                        self._canvas.coords(item, x0, y0, x, y)
                        self._draw_turtle((x,y))
                        self._canvas.update()
                        self._canvas.after(self._delay)
                    # in case nhops==0
                    self._canvas.coords(item, x0, y0, x1, y1)
                    self._canvas.itemconfigure(item, arrow="none")
                except Tkinter.TclError:
                    # Probably the window was closed!
                    return
            else:
                item = self._canvas.create_line(x0, y0, x1, y1,
                                                width=self._width,
                                                capstyle="round",
                                                fill=self._color)
            self._items.append(item)
        self._draw_turtle()

    def speed(self, speed=2):
        """ maps a speed in 4 to 0 to delay given _canvas.after() in
            _goto()

            4 is fastests (0 ms delay)
            2 is default  (10 ms delay)
            0 is slowest (20 ms delay)"""

##        if speed >=0 and speed <=4:    ## more elegantly:
        if 0 <= speed <=4:    
            self._delay = 20 - (speed * 5)

    def _draw_turtle(self,position=[]):
        if not self._tracing:
            return
        if position == []:
            position = self._position
        x,y = position
        distance = 8
        dx = distance * cos(self._angle*self._invradian)
        dy = distance * sin(self._angle*self._invradian)
        self._delete_turtle()
        self._arrow = self._canvas.create_line(x-dx,y+dy,x,y,
                                          width=self._width,
                                          arrow="last",
                                          capstyle="round",
                                          fill=self._color)
        self._canvas.update()

    def _delete_turtle(self):
        if self._arrow != 0:
            self._canvas.delete(self._arrow)
        self._arrow = 0


_root = None
_canvas = None
_pen = None
_width = 0.50                  # 50% of window for width
_height = 0.75                 # 75% of window for height
_startx = 0                    # start at upper left corner
_starty = 0
_title = "Turtle Graphics"     # default title

class Pen(RawPen):

    def __init__(self):
        global _root, _canvas, _width, _height
        if _root is None:
            _root = Tkinter.Tk()
            _root.wm_protocol("WM_DELETE_WINDOW", self._destroy)
            _root.title(_title)
            if _width <= 1:
                _width = _root.winfo_screenwidth() * _width
            if _height <= 1:
                _height = _root.winfo_screenheight() * _height
            _root.geometry("%dx%d+%d+%d" % (_width, _height,
                                            _startx, _starty))
        if _canvas is None:
            # XXX Should have scroll bars
            _canvas = Tkinter.Canvas(_root, background="white")
            _canvas.pack(expand=1, fill="both")
        RawPen.__init__(self, _canvas)

    def _destroy(self):
        global _root, _canvas, _pen
        root = self._canvas._root()
        if root is _root:
            _pen = None
            _root = None
            _canvas = None
        root.destroy()

def _getpen():
    global _pen
    if not _pen:
        _pen = Pen()
    return _pen

class Turtle(Pen):
    pass

def degrees(): _getpen().degrees()
def radians(): _getpen().radians()
def reset(): _getpen().reset()
def clear(): _getpen().clear()
def tracer(flag): _getpen().tracer(flag)
def forward(distance): _getpen().forward(distance)
def backward(distance): _getpen().backward(distance)
def left(angle): _getpen().left(angle)
def right(angle): _getpen().right(angle)
def up(): _getpen().up()
def down(): _getpen().down()
def width(width): _getpen().width(width)
def color(*args): _getpen().color(*args)
def write(arg, move=0): _getpen().write(arg, move)
def fill(flag): _getpen().fill(flag)
def circle(radius, extent=None): _getpen().circle(radius, extent)
def goto(*args): _getpen().goto(*args)
def heading(): return _getpen().heading()
def setheading(angle): _getpen().setheading(angle)
def position(): return _getpen().position()
def window_width(): return _getpen().window_width()
def window_height(): return _getpen().window_height()
def setx(xpos): _getpen().setx(xpos)
def sety(ypos): _getpen().sety(ypos)
def towards(*args): return _getpen().towards(*args)
def done(): _root.mainloop()
def speed(speed=2): _getpen().speed(speed)
def setup(geometry=()):
    global _width, _height, _startx, _starty
    if len(geometry) == 4:
        _width, _height, _startx, _starty = geometry
def title(title):
    global _title
    _title = title

def demo():
    reset()
    tracer(1)
    up()
    backward(100)
    down()
    # draw 3 squares; the last filled
    width(3)
    for i in range(3):
        if i == 2:
            fill(1)
        for j in range(4):
            forward(20)
            left(90)
        if i == 2:
            color("maroon")
            fill(0)
        up()
        forward(30)
        down()
    width(1)
    color("black")
    # move out of the way
    tracer(0)
    up()
    right(90)
    forward(100)
    right(90)
    forward(100)
    right(180)
    down()
    # some text
    write("startstart", 1)
    write("start", 1)
    color("red")
    # staircase
    for i in range(5):
        forward(20)
        left(90)
        forward(20)
        right(90)
    # filled staircase
    fill(1)
    for i in range(5):
        forward(20)
        left(90)
        forward(20)
        right(90)
    fill(0)
    # more text
    write("end")
    if __name__ == '__main__':
        _root.mainloop()

if __name__ == '__main__':
    demo()

Reply via email to