whats the best way to embedded a java GUI component such as JPanel to pdf using PDFBox?
Im currently using this code:
PDDocument doc = null;
PDPage page = null;
PDXObjectImage ximage = null;
try {
doc = new PDDocument();
page = new PDPage(PDPage.PAGE_SIZE_A4);
doc.addPage(page);
PDPageContentStream content = new PDPageContentStream(doc, page);
BufferedImage image = new BufferedImage((int)PDPage.PAGE_SIZE_A4.getWidth()*2,(int)PDPage.PAGE_SIZE_A4.getHeight()*2, BufferedImage.TYPE_4BYTE_ABGR);
Graphics2D g = image.createGraphics();
g.setRenderingHint(RenderingHints.KEY_ALPHA_INTERPOLATION,RenderingHints.VALUE_ALPHA_INTERPOLATION_QUALITY);
g.setRenderingHint(RenderingHints.KEY_RENDERING,RenderingHints.VALUE_RENDER_QUALITY);
g.setRenderingHint(RenderingHints.KEY_ANTIALIASING,RenderingHints.VALUE_ANTIALIAS_ON);
g.setRenderingHint(RenderingHints.KEY_FRACTIONALMETRICS, RenderingHints.VALUE_FRACTIONALMETRICS_ON);
g.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
panel.setBounds(0, 0,(int)PDPage.PAGE_SIZE_A4.getWidth()*2,(int)PDPage.PAGE_SIZE_A4.getHeight()*2);
panel.doLayout();
panel.validate();
panel.paint(g);
g.dispose();
ximage = new PDPixelMap(doc, image);
content.drawXObject(ximage, 0 , 0 ,(int)PDPage.PAGE_SIZE_A4.getWidth(),(int)PDPage.PAGE_SIZE_A4.getHeight() );
content.close();
if (path==null || path.equals(""))
doc.print();
else
doc.save(path);
doc.close();
} catch(Exception ie) {
ie.printStackTrace();
}
but two problems that i got with it is 1. sometimes i am getting a blank pdf for some reason, and 2. when it works the PDF looks pixelated.
is there a better way?
PS: i am not allowed to use iText in my project
Because you add the (vector) panel graphics to the PDF page through a PDFPixelMap, the panel graphics will always be pixelated (converted to a raster).
If you want to prevent rasterization, you would have to use the vector drawing commands such as drawLine, stroke, drawText, etc. instead.
Related
I've been trying to figure out how to flip a pdf for a while, but haven't figured out yet.
I've only found how to flip image using Graphics2D:
// Flip the image vertically
AffineTransform tx = AffineTransform.getScaleInstance(1, -1);
tx.translate(0, -image.getHeight(null));
AffineTransformOp op = new AffineTransformOp(tx, AffineTransformOp.TYPE_NEAREST_NEIGHBOR);
image = op.filter(image, null);
Could you please help me to get it with PDFbox?
Thanks!!
With PDFBox 2.*, you need to prepend it to the page content stream. Optionally save and restore graphics state, useful for further modifications. (All based on this answer)
PDPage page = doc.getPage(0);
try (PDPageContentStream cs = new PDPageContentStream(doc, page, PDPageContentStream.AppendMode.PREPEND, true))
{
cs.saveGraphicsState();
cs.transform(Matrix.getScaleInstance(1, -1));
cs.transform(Matrix.getTranslateInstance(0, -page.getCropBox().getHeight()));
cs.saveGraphicsState();
}
try (PDPageContentStream cs = new PDPageContentStream(doc, page, PDPageContentStream.AppendMode.APPEND, true))
{
cs.restoreGraphicsState();
cs.restoreGraphicsState();
}
PDFBox offer functions to render a entire page, but no way to render only a specific rectangle of the page.
This code is working for me. But as mentioned above it renders the whole page and I need a method to render a little area of the pdf file:
File file = new File("package.pdf");
PDDocument document = PDDocument.load(file);
PDFRenderer renderer = new PDFRenderer(document);
BufferedImage image = renderer.renderImageWithDPI(0, 400);
ImageIO.write(image, "PNG", new File("C:/package1.png"));
document.close();
I would be very happy about a solution, since I have not found a solution for hours
I have found a soulution by myself. CropBox was the deciding keyword i did not know about.
File file = new File("package.pdf");
PDDocument document = PDDocument.load(file);
PDPage page = document.getPage(0);
page.setCropBox(new PDRectangle(133f, 150f, 100f, 100f)); // Here you draw a rectangle around the area you want to specify
PDFRenderer renderer = new PDFRenderer(document);
BufferedImage image = renderer.renderImageWithDPI(0, 400);
ImageIO.write(image, "PNG", new File("C:/fatihabi.png"));
document.close();
I am trying to make text selectable at PDF reading application made on JavaFX. I have PDF files that contain screenshots with text and OCR layer. So I need the text to be selectable like at regular viewer. I set up getting image from page and now trying to figure out how to highlight text.
I tried following:
InputStream is = this.getClass().getResourceAsStream(currentPdf);
Image convertedImage;
try {
PDDocument document = PDDocument.load(is);
List<PDPage> list = document.getDocumentCatalog().getAllPages();
PDPage page = list.get(pageNum);
List annotations = page.getAnnotations();
PDAnnotationTextMarkup markup = new PDAnnotationTextMarkup(PDAnnotationTextMarkup.SUB_TYPE_HIGHLIGHT);
markup.setRectangle(new PDRectangle(600, 600));
markup.setQuadPoints(new float[]{100, 100, 200, 100, 100, 500, 200, 500});
annotations.add(markup);
page.setAnnotations(annotations);
BufferedImage image = page.convertToImage(BufferedImage.TYPE_INT_RGB, 128);
convertedImage = SwingFXUtils.toFXImage(image, null);
document.close();
imageView.setImage(convertedImage);
} catch (Exception e) {
throw new RuntimeException(e);
}
but that results in image without any highlights.
I also tried to find information at stack overflow or other resources, but haven't found anything.
Would appreciate some Java code sample which enables text highlighting with mouse.
I used ICEpdf and did the following:
question.getSelectedBounds()
.stream()
.map(Shape::getBounds)
.forEach(bounds -> {
SquareAnnotation squareAnnotation = (SquareAnnotation)
AnnotationFactory.buildAnnotation(
pdfController.getPageTree().getLibrary(),
Annotation.SUBTYPE_SQUARE,
bounds);
squareAnnotation.setFillColor(true);
squareAnnotation.setFillColor(new Color(255, 250, 57, 120));
squareAnnotation.setRectangle(bounds);
squareAnnotation.setBBox(bounds);
squareAnnotation.resetAppearanceStream(null);
AbstractAnnotationComponent annotationComponent = AnnotationComponentFactory
.buildAnnotationComponent(squareAnnotation, pdfController.getDocumentViewController(),
pageViewComponent, pdfController.getDocumentViewController().getDocumentViewModel());
pageViewComponent.addAnnotation(annotationComponent);
});
I'm trying to convert a TIFF to a PDF using Apache Imaging and PDFBox. Everything I've tried results in a blank (but non-zero-byte) pdf.
There are some examples in other SO questions like Add BufferedImage to PDFBox document and PDFBox draw black image from BufferedImage which I've tried.
I know the buffered image that I'm reading from the TIFF is valid because I can display it and see it in a JFrame.
I've also tried a PDFJpeg instead of a PDFPixelMap, and contentStream.drawImage() instead of .drawXObject(), the result is always the same.
I also tried creating the PDXObjectImage before the content stream and writing multiple images as recommended in Can't add an image to a pdf using PDFBox, the result is still the same. The output file is larger when I write the image multiple times, so it's doing "something" but I don't know what it is.
How can I write a BufferedImage to a page on a PDF using PDFBox?
try(PDDocument document = new PDDocument();ByteArrayOutputStream outputStream = new ByteArrayOutputStream())
{
PDPage blankPage = new PDPage();
document.addPage( blankPage );
// PDXObjectImage pdImage = new PDJpeg(document, image);
PDXObjectImage pdImage = new PDPixelMap(document, image);
// contentStream.drawImage(pdImage, 5, 300);
PDPageContentStream contentStream = new PDPageContentStream(document, blankPage);
contentStream.drawXObject(pdImage, 5, 5, 100, 100);
document.save("test.pdf");
contentStream.close();
}
catch(COSVisitorException ex) {
throw new IOException(ex);
}
Why does the JPEG image inflate when it is added to a PDF using Apache PDFBox?
The image size is bigger. I search but found nothing to help me.
I am using BufferedImage. How can I fix it so that the image is same size once I added to the PDF?
Here's my code:
PDPage page = null;
PDXObjectImage image = null;
doc = new PDDocument();
page = new PDPage();
doc.addPage(page);
PDPageContentStream content = new PDPageContentStream(doc, page);
BufferedImage bImg = null;
bImg = ImageIO.read(new File("picture.jpg"));
image = new PDJpeg(doc, bImg);
content.drawImage(image, 100, 500);
content.close();
doc.save("test.pdf");