Printing contents of a JList?
Hey, all. I've got an application here that adds a ton of items into a DefaultListModel for a JList. I'm now trying to print a report containing the entire contents of the list - not just the visible part of it in the JScrollPane.
I tried creating a subclass of JList which was a Printable, and I was getting the first page of values, stretched beyond the limits of the page horizontally. I never got a second page; I should have at least 20 pages.
Is there any easy way to achieve this? Bear in mind, I'm a neophyte to the Java printing API.
I'm affraid the print API is pretty nasty.
You need to write a Printable which prints a page from the list. I'd start by creating a separate JList from the same model (since you are going to muck it about and if you're also displaying it you'll mess that up).
The printable is passed a page index, bear in mind it can be asked for the same page multiple times and won't necessarilly be asked for every page.
What it needs to do is to determine the slice of the JList it needs to print for the page requested, then either set the y value on the JList so the bit you want starts at zero, or use a translate on the graphics context. Set a clip too, so you get just the rows that fit on the page.
Sounds great... Could I ask that to be rephrased in the form of a code sample? Sorry... this stuff just makes no sense to me at all. Why couldn't they just have created a subclass of Graphics2D which draws to the printer?
> Sounds great... Could I ask that to be rephrased in
> the form of a code sample? Sorry... this stuff just
> makes no sense to me at all. Why couldn't they just
> have created a subclass of Graphics2D which draws to
> the printer?
They have. That's what your Printable object gets passed, but it gets passed a graphics context for each page to be printed. The messey bit is that you have to do your own pagination.
I agree it's pretty nasty, and I've burried the worst of it under my own print libraries.
Actually, it might be simpler for you to use a single column JTable instead of a JList, because there iare rudimentary faclitities built into JTable to print it on multiple pages.
I don't have any code for JLists.
What you need to do is to write a class implementing Printable. This is given a page index, you need to decide which rows from the JList belong on that page. Annoyingly there's no getRowHeight() in JList but you could use locationToIndex to work out which row to break on, then indexToLocation to decide what "window" on the list to print on a particular page. The window will consist of a y and a height value. You can use tranlate() on the graphics context to move to the appropriate part of the list and setClip() to select just the part you want.
You need to print any auxilliary stuff like page headers and footers as well. I find JLabels very usefull here. You can simply position a JLabel on you page and call it's print() method.
OK... To simplify things, is there an easy way to just dump the contents to text (using each element in the list model's toString() or some such), and then print out a StringBuffer or something in a way that will give me the pagination for free?
> OK... To simplify things, is there an easy way to
> just dump the contents to text (using each element in
> the list model's toString() or some such), and then
> print out a StringBuffer or something in a way that
> will give me the pagination for free?
Printing straight text isn't particularly easy - the java.awt.print classes are designed to be used via a Graphics2D object.
You least coding solution is probably to use a single-column JTable for the printing.
JTable has a method which will construct a simple Printable.