I am trying to add a QrCode to my PDF using Reportlab but I am getting an IOerror. I have successfully appended my barcode before but the QrCode seems to be a bit trickier.
This is my QrCode Code:
def get_QRcode(self,inventory):
receipt = str(inventory.identifier)
qr_code = qr.QrCodeWidget(receipt)
bounds = qr_code.getBounds()
width = bounds[2] - bounds[1]
height = bounds[3] - bounds[1]
d = Drawing(45,45, transform = [45./width,0,0,45./height,0,0])
d.add(qr_code)
filename = tempfile.mkstemp()[1] + '.png'
d.save(filename)
return filename
Here is my append of QrCode:
parts.append(Image(self.qrCode, width=.15* 0.35 *inch, height=.2*.25*inch))
After trying to run this I get :
IOError at /inventories/download_tag/2525/
Cannot open resource "/tmp/tmpUf7ASf.png"
fileName='/tmp/tmpUf7ASf.png' identity=[ImageReader@0x7f6665819490 filename='/tmp/tmpUf7ASf.png']
Any help is appreciated! Thank you
EDIT: Here is a snippet that appends my barcode and currently attempting to append a QRCode
def get_pdf_flows(self):
sku = self.sku_name
sku = sku + " ({0})".format(self.num_cases) if self.num_cases else sku
sku = Paragraph(sku, self.sku_style)
grower_detail = self.get_grower_detail()
col1, col2 = self.get_table_rows()
parts = []
parts.append(Spacer(1, 30))
parts.append(sku)
parts.append(Spacer(1, 5))
parts.append(Image(self.barcode_file, width=.15* 0.35 *inch, height=.2*.25*inch))
parts.append(self.qrCode)
parts.append(grower_detail)
parts.append(Spacer(1, 5))
t1 = Table(col1,colWidths='*')
t2 = Table(col2,colWidths='*')
data = [[t1, t2]]
if self.foodhub.company_name== "Harvest Santa Barbara":
parts.append(Table(data, colWidths=(1.75*inch, 2.25*inch)))
return parts
def get_doc(self):
buff = StringIO.StringIO()
doc = SimpleDocTemplate(buff, pagesize=(4*inch, 3*inch), rightMargin=0, leftMargin=0, topMargin=1*mm, bottomMargin=0)
return doc, buff
I can share how I have done it, but my implementation is to draw it directly on the canvas, then I add it in the footnote on the document template. Your method is to create a png and then add it (I do a similar thing with a graph object, but then I use pdfrw, which is a nice addin, I struggled a bit with write-access to folders when I started out). See if below works out for you.
from reportlab.lib.units import mm, cm
from reportlab.lib.pagesizes import A4
from reportlab.graphics.barcode import qr, code128
from reportlab.graphics.shapes import Drawing
from reportlab.platypus import Table, TableStyle
from reportlab.platypus import SimpleDocTemplate
from reportlab.lib import colors
def func(canvas, doc):
canvas.saveState()
# draw a QR code
receipt = str(f'hello')
qr_code = qr.QrCodeWidget(f'{receipt}')
bounds = qr_code.getBounds()
width = bounds[2] - bounds[0]
height = bounds[3] - bounds[1]
d = Drawing(60, 60, transform=[60. / width, 0, 0, 60. / height, 0, 0])
d.add(qr_code)
d.drawOn(canvas, 1.77 * cm, 259.55 * mm)
#Draw Bar code
canvas.setFillColor(colors.black)
barcode = code128.Code128(receipt, barWidth=0.17 * mm, barHeight=5 * mm, ratio=2.75, humanReadable=1)
barcode.drawOn(canvas, 5.95 * cm, 259.55 * mm)
canvas.restoreState()
return func
#
def create_pdf():
story = []
data = [['Data1', 'Data2', 'Data3', 'Data4', 'Data5', 'Data6'],
['0.2', '-0.1', '0', '0', '-0.5', '0.6']]
colwidths = (50)
rowheights = (10)
t = Table(data, colwidths, rowheights)
GRID_STYLE = TableStyle(
[('FONTSIZE', (0, 0), (-1, -1), 5),
('GRID', (0, 0), (-1, -1), 0.5, colors.black),
('ALIGN', (0, 0), (-1, -1), 'CENTER'),
('LEFTPADDING', (0, 0), (-1, -1), 0),
('RIGHTPADDING', (0, 0), (-1, -1), 0),
('TOPPADDING', (0, 0), (-1, -1), 0),
('BOTTOMPADDING', (0, 0), (-1, -1), 0),
('FONTNAME', (0, 0), (-1, -1), 'Helvetica'),
('SIZE', (0, 0), (-1, -1), 7),
('LEADING', (0, 0), (-1, -1), 8.2),
]
)
t.setStyle(GRID_STYLE)
story.append(t)
doc = SimpleDocTemplate('mydoc.pdf', pagesize=A4, topMargin=50)
doc.build(story, onFirstPage=func)
# ----------------------------------------------------------------------
if __name__ == "__main__":
create_pdf() # Printing the pdf