Placing graphics & text on printed page - jan06call.jpg (0/1)

eric.howland eric.howland at gmail.com
Sun Jan 29 05:00:02 CET 2006


Michael Galvin wrote:
> I am trying to use Python to send to the printer a calender filled
> with a mix of text and simple graphics.  I want to draw on the printed
> page something like a table with 6 rows and 7 columns to represent a
> calendar.  I want to place text precisely within those boxes on the
> printed page. I am using Python 2.4 on Windows XP
>
> I was  in the past able to do this within Visual Basic using its
> printer object.  Visual Basic's printer object uses a coordinate
> system to allow you to draw lines and to place text on the printed
> page precisely. I have attached a file "jan06call.jpg" to this message
> to illustrate what I am trying to do.
>
> Does Python have a module which would help me do this?
>
> To put it another way, can Python control the placement of text and
> graphics precisely on the printed page?
>
> I have scoured my Python programming texts,  python.org, and this
> usenet group without success.  Mark Lutz's wonderful book "Programming
> Python"  has not one reference to the word "printer" in its index.
> Surely, I must be overlooking something or thinking about this wrong.
>
> Michael Galvin
> Muskegon, MI

This does something like you want using piddle. It is designed to make
a pdf of a calendar on a sheet of paper that has times blocked out (the
add_data and print_action methods).

import sys, os, string, re, calendar, time, datetime, copy
from optparse import OptionParser
from piddlePDF import *

class output_pdf:

   setup = { #constants to use for spacing
       "upperleftx": 0.75*72,
       "upperlefty": 1*72,
       "rowoffset": 2.0 * 72,
       "coloffset": 1.0 * 72,
       "vert_margin": 25,
       "horz_margin": 25,
       }

   canvas = PDFCanvas()     # backend you want to test
   def __init__(self, year, month, title ):
###     global canvas
       self.printcal( year, month, title)



   def printcal(self, year, month, label):
       """ prints the days, and times and outside boxes for each day.
           sets up a dictionary with the x and y offset for each day.
       """
       global calpos
       calpos = {}

       wkdaytxt = ['Sun', 'Mon', 'Tues', 'Wed', 'Thurs', 'Fri', 'Sat']
       calendar.setfirstweekday(calendar.SUNDAY)

       # use calendar to figure out  days for dates (a list of lists)
       month_cal=  calendar.monthcalendar( year, month)
       #figure out how many weeks and days
       daywk1st, days=  calendar.monthrange( year, month)

       if len(month_cal) == 6: self.setup["rowoffset"] = 1.8*72

       self.canvas.drawString(label,
                       10,
                       self.setup["upperlefty"]- 40,
                       Font(face="sansserif",size=16,bold=1),
color=green)


       for row, wk in enumerate(month_cal):
           topy = self.setup["upperlefty"]+ row*self.setup["rowoffset"]
           self.canvas.drawString('00:00', 10, topy+4,
                           Font(face="sansserif",size=8,bold=1),
color=darkorange)
           self.canvas.drawString('12:00', 10,
topy+4+(self.setup["rowoffset"]-self.setup["vert_margin"])*.5 ,
                           Font(face="sansserif",size=8,bold=1),
color=darkorange)
           self.canvas.drawLine( self.setup["upperleftx"]-10,

topy+(self.setup["rowoffset"]-self.setup["vert_margin"])*.5,
                           self.setup["upperleftx"]+
7*self.setup["coloffset"],

topy+(self.setup["rowoffset"]-self.setup["vert_margin"])*.5,
                           color=darkorange, width=1 )
           self.canvas.drawString('08:00', 10,
topy+4+(self.setup["rowoffset"]-self.setup["vert_margin"])*(8/24.0) ,
                           Font(face="sansserif",size=6,bold=1),
color=darkorange)
           self.canvas.drawLine( self.setup["upperleftx"]-10,

topy+(self.setup["rowoffset"]-self.setup["vert_margin"])*(8/24.0),
                           self.setup["upperleftx"]+
7*self.setup["coloffset"],

topy+(self.setup["rowoffset"]-self.setup["vert_margin"])*(8/24.0),
                           color=darkorange, width=1 )
           self.canvas.drawString('17:00', 10,
topy+4+(self.setup["rowoffset"]-self.setup["vert_margin"])*(17/24.0) ,
                           Font(face="sansserif",size=6,bold=1),
color=darkorange)
           self.canvas.drawLine( self.setup["upperleftx"]-10,

topy+(self.setup["rowoffset"]-self.setup["vert_margin"])*(17/24.0),
                           self.setup["upperleftx"]+
7*self.setup["coloffset"],

topy+(self.setup["rowoffset"]-self.setup["vert_margin"])*(17/24.0),
                           color=darkorange, width=1 )
           self.canvas.drawString('24:00', 10,
topy+4+(self.setup["rowoffset"]-self.setup["vert_margin"]) ,
                           Font(face="sansserif",size=8,bold=1),
color=darkorange)

           for col, date in enumerate(wk):
               topx = self.setup["upperleftx"]+
col*self.setup["coloffset"]
               self.canvas.drawString(wkdaytxt[col],
                               topx,
                               self.setup["upperlefty"]*.7,
                               Font(face="sansserif",size=16,bold=1),
color=green)
               topx = self.setup["upperleftx"]+
col*self.setup["coloffset"]
               topy = self.setup["upperlefty"]+
row*self.setup["rowoffset"]
               calpos[date] = (topx, topy)


       for i in range(days):
           topx, topy = calpos[i+1]

           self.canvas.drawRect( topx, topy,

(topx+(self.setup["coloffset"]-self.setup["horz_margin"])),

(topy+(self.setup["rowoffset"]-self.setup["vert_margin"])),
                           edgeColor=black, edgeWidth=2,
fillColor=transparent)
           self.canvas.drawString('%d'%(i+1), topx, topy-2 ,
                           Font(face="sansserif",size=12,bold=1),
color=red)



   def date_str2value(self,intime):
       tuple_names = ["tm_year", "tm_mon", "tm_mday", "tm_hour",
"tm_min", "tm_sec", "tm_wday", "tm_yday", "tm_isdst"]
       t_tuple = time.localtime(intime)
       t_dict = {}
       for i, name in enumerate(tuple_names):
           t_dict[name] = t_tuple[i]
       floattime = (float(t_dict['tm_hour'])*60 +
float(t_dict['tm_min']))/float(24*60)

       return t_dict, floattime

   def print_action(self,year,month, action):
       ##action_list = re.split(r'\t', action)
       ##starttime = action_list[1]
       ##endtime = action_list[2]
       client = action['destination']

       s_dict, s_time = self.date_str2value(action['start_sec'])
       e_dict, e_time = self.date_str2value(action['stop_sec'])
       ##print s_dict, s_time, ":-:", e_dict, e_time
       if (s_dict['tm_mday'] == e_dict['tm_mday'] and
           s_dict['tm_mon'] == int(month) and
           s_dict['tm_year'] == int(year)):
           topx, topy = calpos[s_dict['tm_mday']]
           ypos_start = topy + (s_time *
(self.setup["rowoffset"]-self.setup["vert_margin"]))
           ypos_end = topy + (e_time *
(self.setup["rowoffset"]-self.setup["vert_margin"]))
           right_side = topx +
(self.setup["coloffset"]-self.setup["horz_margin"])

           self.canvas.drawRect( topx, ypos_start,
                            right_side, ypos_end,
                           edgeColor=black, edgeWidth=1,
fillColor=skyblue)
           self.canvas.drawString(client, topx+2, ypos_start+5,
                   Font(face="sansserif",size=5,bold=0),
color=darkorchid)

   def add_data(self, year, month, data):
       for action in data:
           #print "adding data", action
           self.print_action(year, month, action)

   def save(self, filename):
       self.canvas.flush()
       self.canvas.save(filename)




More information about the Python-list mailing list