如何使用jtable标题在pdf上保存jtable

我可以在pdf上保存jtable,但是没有标题的表请帮助我:

Document document = new Document(PageSize.A4, 50.0f, 50.0f, 10.0f, 50.0f); PdfWriter writer = PdfWriter.getInstance((Document)document, (OutputStream)new FileOutputStream(this.file + ".pdf")); document.open(); PdfContentByte cb1 = writer.getDirectContent(); // modules table PdfTemplate template = cb1.createTemplate(2480.0f, 3500.0f); Graphics2D g1 = template.createGraphics((float)this.jTable_Modules2.getWidth(), (float)this.jTable_Modules2.getHeight()); // this.jTable_Modules2.getViewport().setBackground(Color.WHITE); this.jTable_Modules2.print(g1); g1.dispose(); com.itextpdf.text.Image image = com.itextpdf.text.Image.getInstance((PdfTemplate)template); image.scalePercent(60.0f); image.setAbsolutePosition(80.0f, 458.0f); document.add((Element)image); document.close(); JOptionPane.showMessageDialog(null, "Transcript successfully generated"); 

如本回答所示,您可以创建一个新的JTable并将其作为组件传递给getImageFromComponent(...)并将其传递给头部appart:

在此处输入图像描述

 java.awt.Image img = getImageFromComponent(table.getTableHeader()); addImageToDocument(img); img = getImageFromComponent(table); addImageToDocument(img); 

如果你没有将JTable添加到JScrollPane ,如果你这样做,那么你发送JScrollPane ,例如:

在此处输入图像描述

 java.awt.Image img = getImageFromComponent(scrollPane); addImageToDocument(img); 

这取决于你如何添加表…我更喜欢scrollPane版本:)


另一种方法是迭代JTable的数据并使用PdfPTable

根据这个答案你可以得到这样的东西:

 import java.awt.BorderLayout; import java.awt.Color; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.io.FileNotFoundException; import java.io.FileOutputStream; import javax.swing.BorderFactory; import javax.swing.JButton; import javax.swing.JFrame; import javax.swing.JScrollPane; import javax.swing.JTable; import javax.swing.SwingUtilities; import com.itextpdf.text.Document; import com.itextpdf.text.DocumentException; import com.itextpdf.text.PageSize; import com.itextpdf.text.Paragraph; import com.itextpdf.text.pdf.GrayColor; import com.itextpdf.text.pdf.PdfPCell; import com.itextpdf.text.pdf.PdfPTable; import com.itextpdf.text.pdf.PdfWriter; public class JTableToPdf { private JFrame frame; private JTable table; private JButton button; private Document document; private PdfWriter writer; private JScrollPane scrollPane; public static void main(String[] args) { SwingUtilities.invokeLater(new Runnable() { @Override public void run() { new JTableToPdf().createAndShowGui(); } }); } public void openPdf() throws FileNotFoundException, DocumentException { document = new Document(PageSize.A4, 30, 30, 30, 30); writer = PdfWriter.getInstance(document, new FileOutputStream("myFile2.pdf")); document.open(); } public void closePdf() { document.close(); } public void addData(PdfPTable pdfTable) throws DocumentException { pdfTable.setHeaderRows(1); PdfPCell cell = new PdfPCell(new Paragraph(table.getColumnName(0))); cell.setBackgroundColor(new GrayColor(0.7f)); pdfTable.addCell(cell); cell = new PdfPCell(new Paragraph(table.getColumnName(1))); cell.setBackgroundColor(new GrayColor(0.7f)); pdfTable.addCell(cell); cell = new PdfPCell(new Paragraph(table.getColumnName(2))); cell.setBackgroundColor(new GrayColor(0.7f)); pdfTable.addCell(cell); for (int i = 0; i < table.getRowCount(); i++) { for (int j = 0; j < table.getColumnCount(); j++) { pdfTable.addCell(table.getModel().getValueAt(i, j).toString()); } } document.add(pdfTable); } public void createAndShowGui() { frame = new JFrame("PDF creator"); int rows = 100; int cols = 3; String data [][] = new String[rows][cols]; for (int i = 0; i < rows; i++) { for (int j = 0; j < cols; j++) { data[i][j] = i + "-" + j; } } table = new JTable(data, new String []{"A", "B", "C"}); table.setBorder(BorderFactory.createLineBorder(Color.RED)); button = new JButton("Create PDF"); scrollPane = new JScrollPane(table); button.addActionListener(new ActionListener() { @Override public void actionPerformed(ActionEvent e) { try { PdfPTable pdfTable = new PdfPTable(table.getColumnCount()); openPdf(); addData(pdfTable); closePdf(); } catch (FileNotFoundException e1) { e1.printStackTrace(); } catch (DocumentException e1) { e1.printStackTrace(); } } }); // frame.add(table.getTableHeader(), BorderLayout.NORTH); frame.add(scrollPane, BorderLayout.CENTER); frame.add(button, BorderLayout.SOUTH); frame.pack(); frame.setVisible(true); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); } } 

在此处输入图像描述 在此处输入图像描述

如果您不希望在每个页面上重复标题,只需删除addData(...)方法上for循环之前的行。


第三种方法可能是使用JTableprintable方法,但我这里没有打印机,我稍后会处理这个样本,因为我现在没有太多时间,我不知道如何将它与iText集成,所以我必须搜索一下......


唷! 我花了一段时间来创建这个结果,但我觉得它很好用(虽然你需要在创建PDF后恢复JTable )。

看看代码注释,告诉我这是否有帮助。 我结合使用PDFPTable和图像方法来实现这种新方法:

 import java.awt.BorderLayout; import java.awt.Color; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.image.BufferedImage; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import javax.swing.BorderFactory; import javax.swing.JButton; import javax.swing.JComponent; import javax.swing.JFrame; import javax.swing.JScrollPane; import javax.swing.JTable; import javax.swing.SwingUtilities; import javax.swing.table.DefaultTableModel; import com.itextpdf.text.Document; import com.itextpdf.text.DocumentException; import com.itextpdf.text.Image; import com.itextpdf.text.PageSize; import com.itextpdf.text.pdf.PdfPCell; import com.itextpdf.text.pdf.PdfPTable; import com.itextpdf.text.pdf.PdfWriter; public class JTable2Pdf { private JFrame frame; private JTable table; private JButton button; private JScrollPane scrollPane; private DefaultTableModel model; private DefaultTableModel restoreModel; public static void main(String[] args) { SwingUtilities.invokeLater(new Runnable() { @Override public void run() { new JTable2Pdf().createAndShowGui(); } }); } public void restoreTableView() { table.setModel(restoreModel); frame.revalidate(); frame.repaint(); } public void createAndShowGui() { frame = new JFrame("PDF creator"); int rows = 130; int cols = 3; String data[][] = new String[rows][cols]; for (int i = 0; i < rows; i++) { for (int j = 0; j < cols; j++) { data[i][j] = i + "-" + j; } } model = new DefaultTableModel(data, new String[] { "A", "B", "C" }); restoreModel = new DefaultTableModel(data, new String[] { "A", "B", "C" }); table = new JTable(model); //Just some borders for the table and its header table.setBorder(BorderFactory.createLineBorder(Color.RED)); table.getTableHeader().setBorder(BorderFactory.createLineBorder(Color.RED)); scrollPane = new JScrollPane(table); button = new JButton("Create PDF"); button.addActionListener(new ActionListener() { @Override public void actionPerformed(ActionEvent e) { try { //We create an instance of pdfCreator and pass our JTable as instance PdfCreator pdfCreator = new PdfCreator(table); //We open the pdf and say we want to repeat the header for each page pdfCreator.openPdf(true); //Then we add the header (if we don't add it first, then the 1st row of the table will be the one repeating over the pages pdfCreator.addImageToTable(pdfCreator.getImageFromComponent(table.getTableHeader())); //Then we add the rows to the PDF pdfCreator.getRowsImage(); //Finally we close the PDF pdfCreator.closePdf(); //And last we restore the table restoreTableView(); } catch (DocumentException e1) { e1.printStackTrace(); } catch (FileNotFoundException e1) { e1.printStackTrace(); } catch (IOException e1) { e1.printStackTrace(); } } }); frame.add(scrollPane, BorderLayout.CENTER); frame.add(button, BorderLayout.SOUTH); frame.pack(); frame.setVisible(true); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); } } class PdfCreator { private JTable table; private Document document; private PdfWriter writer; private boolean isNewPage; private PdfPTable pdfTable; public PdfCreator(JTable table) { this.table = table; } //This method opens the PDF, repeatHeader if true, adds the header to each page, otherwise it only adds it to the 1st one public void openPdf(boolean repeatHeader) throws FileNotFoundException, DocumentException { document = new Document(PageSize.A4, 30, 30, 30, 30); writer = PdfWriter.getInstance(document, new FileOutputStream("myFile.pdf")); pdfTable = new PdfPTable(1); if (repeatHeader) { pdfTable.setHeaderRows(1); } pdfTable.getDefaultCell().setBorder(PdfPCell.NO_BORDER); pdfTable.getDefaultCell().setPadding(0); document.open(); } //This method closes the document public void closePdf() { document.close(); } //This method gets the image for each row recursively //As this method gets the graphics for the table from 0, 0 to the width and length determined, we need to remove the 1st row of the table //each time we go through it and that's why we need to restore the table model later in the code public void getRowsImage() throws DocumentException, IOException { if (table.getRowCount() > 0) { int width = table.getCellRect(0, 0, true).width + table.getCellRect(0, 1, true).width + table.getCellRect(0, 2, true).width; int height = table.getCellRect(0, 0, true).height; BufferedImage img = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB); table.paint(img.getGraphics()); DefaultTableModel dtm = (DefaultTableModel) table.getModel(); System.out.println(table.getRowCount() + " - " + isNewPage); dtm.removeRow(0); addImageToTable(img); getRowsImage(); } else { document.add(pdfTable); } } //This gets the image for the table header and / or any other components you need to add to the PDF public java.awt.Image getImageFromComponent(JComponent component) throws DocumentException { int width = component.getWidth(); int height = component.getHeight(); BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB); component.paint(image.getGraphics()); return image; } //This method add the image to a PDFPTable which will be added later to the document public void addImageToTable(java.awt.Image img) throws IOException, DocumentException { Image image = Image.getInstance(writer, img, 1); image.scalePercent(100); pdfTable.addCell(image); System.out.println("printed!"); } } 

这些是输出:

第一页有边框和重复标题 在此处输入图像描述 带边框和重复标题的第2页 在此处输入图像描述

带边框的第2页,不重复标题 在此处输入图像描述

第一页没有边框,没有重复标题 在此处输入图像描述 第二页没有边框,没有重复标题 在此处输入图像描述


我能够通过移动而不是删除行来更改上面的代码,这会产生相同的结果并且它仍然工作相同,但你不再需要restoreTableView()方法......只需更改getRowsImage()方法,如下所示:

 public void getRowsImage() throws DocumentException, IOException { if (movedRows < table.getRowCount()) { int width = table.getCellRect(0, 0, true).width + table.getCellRect(0, 1, true).width + table.getCellRect(0, 2, true).width; int height = table.getCellRect(0, 0, true).height; BufferedImage img = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB); table.paint(img.getGraphics()); DefaultTableModel dtm = (DefaultTableModel) table.getModel(); System.out.println(table.getRowCount() + " - " + isNewPage); dtm.moveRow(0, 0, table.getRowCount() - 1); movedRows++; addImageToTable(img); getRowsImage(); } else { document.add(pdfTable); } } 

并声明一个变量movedRows = 0作为PdfCreator类的类成员:)