Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 4 years ago.
I'm using Python and Qt 4.4 and I have to print some pages. Initially I thought I'd use HTML with CSS to produce those pages. But HTML has some limitations.
Now the question is: is there anything that's better than HTML but just (or almost) as easy to use? Additionally, it should be GPL-compatible.
Edit:
kdgregory & Mark G: The most obvious limitation is that I can't specify the printer margins. There is another problem: How do I add page numbers?
Jeremy French: One thing I have to print is a list of all the products someone ordered which can spread over a few pages.
I have been fighting with printed (or PDF) output from Python for 8 years now and so far I came across the following approaches (in order of personal preference):
- Using JasperReports via pyJasper (written by me) or JasperServer. You can use the WYSIWYG design tool iReport to define your layout. Your Python code will contact the Java based Jasper engine via HTTP and make it render a PDF (pyJasper handles that). We use that for a few thousand pages a day.
- Use plain text output. You can't get any faster. We use that for a few hundred pages per day.
- Use XSLT-FO. You also have to call a Java based rendering engine like FOB. Might result in performance issues but can be mitigated by having a long running Java server process - same approach than with Jasper. We use that for a few hundred pages per day but writing XSLT-FO documents made my head hurt. Not used for new code.
- Generate LaTeX source and use a latex software package to render to PDF. Getting LaTeX to look like you like is quite difficult. But as long as you go with the provided LaTeX styles, you are fine. Not used in production at my shop.
- PDF generation with the ReportLab Toolkit. Somewhat low level. Even more low level: FPDF. We use FPDF-Ruby for a few hundred pages a day. Took a lot of fiddeling to get the layout we wanted.
- Directly generate Postscript. Strange but you nearly can't get more in terms of speed and control. We used that to generate contact sheets with a few hundred thousand Jpegs per day. Takes fiddling but is fun.
- use troff/groff to generate Postscript/PDF. Very low level bute nice to do simple, high volume things. Never used it thus in production.
For orders, invoices and the like I highly recommend JasperReports. The ability to use a visual editor to define the layout is a huge time saver.
There's LaTeX. Not sure if that falls into the "as easy to use as html" category, but it's not hard.
By print do you mean a printer? If so, check ReportLab's PDF tools.
from reportlab.pdfgen import canvas
from reportlab.lib.units import cm
c = canvas.Canvas("hello.pdf")
c.drawString(9*cm, 22*cm, "Hello World!")
c.showPage()
c.save()
Have you seen http://www.w3.org/TR/css3-page/ ? The print media is highly customizable.
In my new project I'm going to replace PDF generator by this one.
XSL Formatting Objects (part of the The Extensible Stylesheet Language Family (XSL)) if you need total control over printed documents.
Then, you'll need a Formatting Objects processor, like FOP or Antenna house, to transform the XSL-FO document into PDF, or PostScript.
You might consider Sphinx, a package that translates reStructuredText files into various output formats, including HTML, and LaTeX, for printable PDF. It's licensed under BSD and is now the official Python documentation tool.
What's wrong with just using Qt's native printing?
Or if you're on a mac, you could check out quartz bindings for Python, but it's obviously not GPL.
I came to like asciidoc. Basically you produce plain text. This can be enhanced a lot by using a templating system like Django templates, or Jinja2. This is in principal a lot like the XSLT-FO thingy described by mdorseif (you use a toolchain to produce docbook and then anything you like), but not so much of a headache. There is allready a nice toolchain wrapper that makes most things easy.
JasperReports has already been mentioned, but we use it in our Python-Qt applications WITHOUT a server or servlet (that is, without needing JasperServer or pyJasper).
So basically, instead of the server/servlet, you install the Jasper Reports Library. Then you need to create a little Java program that uses the Jasper Reports Library to generate a PDF report from serialized input, such as XML. There should be plenty of examples of this if you do a web search, and you only need to write this one time. Then you compile this Java program, with all the required libraries, into a JAR file.
At this point you can install the JasperSoft Studio and create a Jasper report template. Then in Python you can use JPype (or any other Python-to-Java library) to start a JVM, load your JAR file, call your Java function, pass it your serialized data, and specify which report template you want.
All of this is not trivial, but it's pretty straightforward. We like this solution because it provides a drag-and-drop form editor in the Qt Designer/Creator, a drag-and-drop JasperReports report designer, and the ability to generate a PDF report directly from data collected in Python. All of this uses well-supported tools and libraries, so it's unlikely this solution will fall apart in the foreseeable future.