Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Reportlab error: 'Table' object has no attribute '_colpositions'

I'm trying to teach myself reportlab from the user guide. The document I need to create is just formatted text that needs to go in specific places on the page. In the following snippets, table_data is a list containing 3 strings. I imported Table as pdfTable because my application has a Table class.

First, I tried this:

top_row = pdfTable(table_data, colWidths=(3*inch, 3*inch, inch))

That gave me this error:

Traceback:
File "C:\Python33\lib\site-packages\django\core\handlers\base.py" in get_response
  114.                     response = wrapped_callback(request, *callback_args, **callback_kwargs)
File "C:/Users/Phoenix/PycharmProjects/gamecon\gameconapp\views\utilities.py" in splash_page
  86.                generate_signup_sheets()
File "C:/Users/Phoenix/PycharmProjects/gamecon\gameconapp\views\utilities.py" in generate_signup_sheets
  354.         top_row = pdfTable(table_data, colWidths=(3*inch, 3*inch, inch))
File "C:\Python33\lib\site-packages\reportlab-3.0-py3.3-win-amd64.egg\reportlab\platypus\tables.py" in __init__
  253.                 raise ValueError("%s data error - %d columns in data but %d in column widths" % (self.identity(),ncols, len(colWidths)))
File "C:\Python33\lib\site-packages\reportlab-3.0-py3.3-win-amd64.egg\reportlab\platypus\tables.py" in identity
  332.                     v = cv[i][j]

Exception Type: IndexError at /index.html
Exception Value: list index out of range

Since it looked like the problem was the column widths, and the docs say that colWidths is optional, I tried this:

top_row = pdfTable(table_data)

Which caused this error:

Traceback:
File "C:\Python33\lib\site-packages\django\core\handlers\base.py" in get_response
  114.                     response = wrapped_callback(request, *callback_args, **callback_kwargs)
File "C:/Users/Phoenix/PycharmProjects/gamecon\gameconapp\views\utilities.py" in splash_page
  86.                generate_signup_sheets()
File "C:/Users/Phoenix/PycharmProjects/gamecon\gameconapp\views\utilities.py" in generate_signup_sheets
  355.         top_row.drawOn(p, 0.75*inch, 0.5*inch)
File "C:\Python33\lib\site-packages\reportlab-3.0-py3.3-win-amd64.egg\reportlab\platypus\flowables.py" in drawOn
  110.         self._drawOn(canvas)
File "C:\Python33\lib\site-packages\reportlab-3.0-py3.3-win-amd64.egg\reportlab\platypus\flowables.py" in _drawOn
  91.         self.draw()#this is the bit you overload
File "C:\Python33\lib\site-packages\reportlab-3.0-py3.3-win-amd64.egg\reportlab\platypus\tables.py" in draw
  1363.         self._drawBkgrnd()
File "C:\Python33\lib\site-packages\reportlab-3.0-py3.3-win-amd64.egg\reportlab\platypus\tables.py" in _drawBkgrnd
  1386.         colpositions = self._colpositions

Exception Type: AttributeError at /index.html
Exception Value: 'Table' object has no attribute '_colpositions'

None of the examples in the reportlab documentation show Table actually being used.

Thanks in advance for any help.

Edited to add executable code that's still failing:

import os
from reportlab.pdfgen import canvas
from reportlab.lib.units import inch
from reportlab.platypus import Table as pdfTable

filename = os.path.join(BASE_DIR, 'pdf_test_%s.pdf' %
                        ( datetime.now().strftime('%d-%b-%Y %H-%M')))

p = canvas.Canvas(filename, pagesize=letter, bottomup=1)
table_data = [['a', 'b', 'c'], ['d', 'e', 'f']]
top_row = pdfTable([table_data])    #, colWidths=(3*inch, 3*inch, inch))
top_row.drawOn(p, 0.75*inch, 0.5*inch)
p.showPage()
p.save()
like image 467
Beverly Block Avatar asked Mar 15 '14 06:03

Beverly Block


1 Answers

I think the problem is that your just passing a list. Table wants to have a list of lists e.g. a 2D-Array. From the user-guide:

The data argument is a sequence of sequences of cell values each of which should be convertible to a string value using the str function or should be a Flowable instance (such as a Paragraph) or a list (or tuple) of such instances.

If you just have one row, encapsulate that row into another list and pass that to Table. If this doesn't work, please post a minimal and also executable code example.

P.S. On page 77 of the user guide is a straightforward example of the Table-class

UPDATE Now i see. You are using a Flowable which is normally supposed to go through platypus layout-engine by using it in combination with a DocTemplate. This is explained in detail in Chapter 5. You are using the manual way by drawing directly to a canvas, so you also have to code your "own" layout-engine. In this case you first have to use the wrapOn method of your Table. I don't really know why, but it doesn't seem to matter what sizes you pass as arguments. If it doesn't work, try to play with the values. Here is my adjusted version of your code:

from reportlab.pdfgen import canvas
from reportlab.lib.units import inch
from reportlab.platypus import Table as pdfTable

filename = 'pdf_test.pdf'
p = canvas.Canvas(filename)
table_data = [['a', 'b', 'c'], ['d', 'e', 'f']]
top_row = pdfTable(table_data)
w, h = top_row.wrapOn(p, 0, 0)
top_row.drawOn(p, 0.75*inch, 0.5*inch)
p.showPage()
p.save()
like image 140
Fookatchu Avatar answered Nov 14 '22 21:11

Fookatchu