""" gdraw.py: mini-graphics package: Simple TK graphics for Python. (c) Boley SIMPLE PYTHON INTERFACE TO THE TK GRAPHICS TOOLBOX. - Copyright 2005 by Boley version 2.2 of 11/26/05 (port of gdraw.stk to python) These are a simple set of graphics functions based on the "Tkinter" interface to the Tk toolbox. The coordinate system starts with the origin in the upper left corner and extends 500 pixels across in the x and down in the y directions (actually the extent can be adjusted by using a call of the form: set-width(0,600,600) ). This version of the file is for interactive sessions: python -i FILE.py To run without an interactive session, put the following two lines at the end of your script: from gdraw import CanvasWindow ## unless you have already imported from gdraw CanvasWindow.mainloop() See the beginning of the source file for further explanation. See the companion sample test driver for a simple example: testgdraw.py """ gdraw_version="mini-graphics package for python (version 2.2 11/26/05) ready." ## this version has been updated to work with TK v 8.3.1 ## [the main place this needed adapting is handling fonts] ## this version also has a new dragging interface (to be documented) #The following are the main functions intended for the user: # # draw_line(x1,y1,x2,y2) draws a line from (x1,y1) to (x2,y2). # draw_oval(x1,y1,x2,y2) draws an oval from (x1,y1) to (x2,y2). # fill_oval(x1,y1,x2,y2) draws a filled oval from (x1,y1) to (x2,y2). # draw_rectangle(x1,y1,x2,y2) draws a rectangle from (x1,y1) to (x2,y2). # fill_rectangle(x1,y1,x2,y2) draws a filled rectangle. # draw_text(string,x,y,options)puts text string at (x,y), centered. # The only option available is 'corner to # anchor the text at the lower left corner. # clear_canvas() [clears graphics window # delete(ID) delete an item on the canvas # stall(.,optional_prompt) updates display. If prompt is supplied # then wait for user to hit a key, which is # returned as the result. # print_canvas(filename,.,opt) create a postscript copy of the canvas. [NEW] # #For the TK interface, the "draw" and "fill" functions above return a positive #numerical ID affiliated with the object just created. By referring to that #numerical ID, one can modify many properties of that object using the #following functions, of which the first three are the principal ones. #Using ID = 0 refers to the underlying canvas. # # get_binding(ID) get binding for item # ID # set_binding(ID,THUNK) set binding for item # ID (see below) # get_mouse_coords()[ get the current mouse coordinates #[the binding is a procedure called whenever the mouse is clicked while # over the object (or canvas if ID=0). Besides mouse clicks, other events # can be bound. See some examples at end of file.] # ## The following functions access more of the TK interface, but you should ## not have to used these for most simple things. # # get_coords(ID) get coordinates for item # ID # [for ID=0 gives absolute position # of upper left corner] # set_coords(ID,CoordinateList) set coordinates for item # ID # [ID must be positive] # get_text(ID) get text appearing for item # ID # set_text(ID,new_text) set text appearing for item # ID # get_color(ID) get color for item. # set_color(ID,color) set color for item (see colors listed below). #Sample legal colors: red white green blue black yellow cyan magenta orange #purple magenta brown pink ; the empty string "" clears the color. # get_width(ID) get width (or thickness) for item # set_width(ID,new_width) set width for item # [for ID=0, gives 2D dimensions of canvas] # get_font_size(ID) get font size for text item # set_font_size(ID,new_size) set font size for text item. # raise(ID) raise item above all other items # lower(ID) lower item below all other items # get_motion_binding(ID) get motion binding for item # set_motion_binding(ID,thunk) set motion binding for item (see below) # get_release_binding(ID) get release binding for item # set_release_binding(ID,thunk) set release binding for item (see below) # endow_with_drag(ID,[d],[c]) allow item to be dragged by the mouse # d & c are optional procedures to carry out the dragging. # the defaults are drag-obj and clr-drag-obj. # get_type(ID) get type of item # get_IDs()[ get list of all existing IDs # #In each of the above, use the "get" fcn to see the format for the #new value to be used in the corresponding "set" fcn. #In some cases, the format depends on the type of the item. #All IDs are positive integers returned by the "draw" function that #created the item. ID=0 refers to the whole canvas. import sys import Tkinter print "=== ",gdraw_version," ===" print "=== Simple Python interface to Tk graphics toolkit. ===" def draw_line(x1,y1,x2,y2): "draws a line from (x1,y1) to (x2,y2)" return _dw.create_line(x1,y1,x2,y2) def draw_text(string,x,y,*options): "draws text at (x,y)" if "corner" in options: return _dw.create_text(x,y,text=string,anchor='sw') else: return _dw.create_text(x,y,text=string) def draw_oval(x1,y1,x2,y2): "draws an oval from (x1,y1) to (x2,y2)" return _dw.create_oval(x1,y1,x2,y2) def fill_oval(x1,y1,x2,y2,*color): "fills an oval from (x1,y1) to (x2,y2)" if color: color=color[0] else: color="black" ID=_dw.create_oval(x1,y1,x2,y2) set_color(ID,color) return ID def draw_rectangle(x1,y1,x2,y2): "draws an rectangle from (x1,y1) to (x2,y2)" return _dw.create_rectangle(x1,y1,x2,y2) def fill_rectangle(x1,y1,x2,y2,*color): "fills an rectangle from (x1,y1) to (x2,y2)" if color: color=color[0] else: color="black" ID=_dw.create_rectangle(x1,y1,x2,y2) set_color(ID,color) return ID def clear_canvas(): "Clears the canvas (synonym: clear_graphics)." for i in _dw.find('all'): _dw.delete(i) clear_graphics = clear_canvas def stall(*msg): sys.stdout.flush() _dw.update() if msg: raw_input(msg[0]); def print_canvas(filename,**options): """ ; save a postscript image of the canvas ; options: ; colormap varName ; colormode "color" | "grey" | "mono" ; file fileName e.g. "all.ps" ; fontmap varName ; height size e.g. "8i" ; pageanchor anchor ; pageheight size e.g. "8i" ; pagewidth size e.g. "8i" ; pagex position ; pagey position ; rotate boolean ; width size e.g. "8i" ; x position ; y position """ options['file']=filename if not options.has_key('colormode'): options['colormode']='color' apply(_dw.postscript,(),options) def get_color(ID): "get color for item." if ID>0: temp=_dw.itemconfigure(ID,'fill') else: temp=_dw.configure(ID,'background') return temp[-1] def set_color(ID,color): "set color for item." if ID>0: temp=_dw.itemconfig(ID,fill=color) else: temp=_dw.config(background=color) def get_text(ID): "get text for item." if ID>0: return _dw.itemconfigure(ID,'text')[-1] else: return "" def set_text(ID,new_text): "set text for item." if ID>0: _dw.itemconfig(ID,text=new_text) def get_width(ID): "get width for item. For ID=0, retrieves window size." if ID>0: return int(_dw.itemconfigure(ID,'width')[-1]) else: return (int(_dw.configure('height')[-1]),int(_dw.configure('width')[-1])) def set_width(ID,new_width,*more): """set width for item. for ID=0, sets window size. accepts either 2 numbers or a tuple of 2 numbers""" if ID>0: _dw.itemconfigure(ID,width=new_width) else: if more: _dw.configure(height=new_width,width=more) else: _dw.configure(height=new_width[0],width=new_width[1]) def get_font_info(ID): "retrieve font info for a text object." return _dw.itemconfig(ID,'font')[-1] def get_font_size(ID): "retrieve font size (a number) for a text object." f=_dw.itemconfig(ID,'font')[-1] return -(int(f[1])) def set_font_size(ID,fontsize): "set font size (a number) for ID, which should be a text object." f=list(_dw.itemconfig(ID,'font')[-1]) f[1]=-fontsize _dw.itemconfig(ID,font=tuple(f)) def get_coords(ID): "get X-Y coordinates of item, [left,top,right,bottom]" if ID>0: return _dw.coords(ID) else: return (_dw.winfo_height(),_dw.winfo_width()) def set_coords(ID,coords,*more): """set X-Y coordinates of item, [left,top,right,bottom]. accepts either individual numbers or a single list of numbers.""" if more: c=_cons(ID,_cons(coords,more)) else: c=_cons(ID,coords) if ID>0: apply(_dw.coords,c) else: _errmsg("Use set_width to change the shape of the canvas") def tkraise(ID): # would have used 'raise' except it's a reserved word "raise object, making it visible over all other objects." if ID>0: _dw.tkraise(ID) def lower(ID): "lower object, hiding behind other objects." if ID>0: _dw.lower(ID) bindings={} def get_binding(ID,button="