简体   繁体   English

itext7-自动调整图像大小

[英]Itext7 - Auto resize image

I use iText (Version 7.1.1) to convert html to pdf using HtmlConverter (html2pdf version 2.0.1) : 我使用iText(7.1.1版)使用HtmlConverter(html2pdf 2.0.1版)将html转换为pdf:

public static ByteArrayOutputStream htmlToPDFStream(String htmlBody)
        throws DocumentException, IOException {
ConverterProperties props = new ConverterProperties();

FontProvider fp = new DefaultFontProvider(true, false, false);
for (String font : FONTS) {
    FontProgram fontProgram = FontProgramFactory.createFont(font);
    fp.addFont(fontProgram);
}

props.setFontProvider(fp);

com.itextpdf.kernel.pdf.PdfWriter writer = new com.itextpdf.kernel.pdf.PdfWriter(outputStream);
PdfDocument pdf = new PdfDocument(writer);
Document document = new Document(pdf);

List<IElement> elements = HtmlConverter.convertToElements(new ByteArrayInputStream(htmlBody.getBytes(StandardCharsets.UTF_8)), props);
for (IElement element : elements) {
    document.add((IBlockElement)element);
}
document.close();
return  outputStream;
}

It works good if the HTML string has small images (smaller than default page size A4). 如果HTML字符串中的图像较小(小于默认页面大小A4),则效果很好。 But if I have an image bigger than default page width, the result will be cropped image in pdf. 但是,如果我的图像大于默认页面宽度,则结果将以pdf格式裁剪图像。

Is there any way to tell iText to make auto resizing if the image is bigger than default pdf page size to be fit? 如果图像大于适合的默认pdf页面大小,是否有任何方法告诉iText自动调整大小?

Images in layout have autoscale property which should result in desired behavior. 布局中的图像具有自动缩放属性,这将导致所需的行为。 You would need to define a custom ITagWorker to actually add this property to the produced image elements. 您将需要定义一个自定义ITagWorker以将该属性实际添加到生成的图像元素中。

You would also have to define a custom ITagWorkerFactory to use new ITagWorker for images. 您还必须定义一个自定义ITagWorkerFactory才能将新的ITagWorker用于图像。

The code is very simple, you just have to tie everything together carefully: 代码非常简单,您只需要仔细地将所有内容捆绑在一起即可:

class CustomImageWorker extends ImgTagWorker {
    public CustomImageWorker(IElementNode element, ProcessorContext context) {
        super(element, context);
    }

    @Override
    public IPropertyContainer getElementResult() {
        return ((Image)super.getElementResult()).setAutoScale(true);
    }
}

ITagWorkerFactory customFactory = new DefaultTagWorkerFactory() {
    @Override
    public ITagWorker getCustomTagWorker(IElementNode tag, ProcessorContext context) {
        if (TagConstants.IMG.equals(tag.name())) {
            return new CustomImageWorker(tag, context);
        } else {
            return null;
        }
    }
};

After that, just set your tag factory to the props: props.setTagWorkerFactory(customFactory); 之后,只需将标签工厂设置为props: props.setTagWorkerFactory(customFactory);

Another solution at the CSS level would be to specify different image widths and heights depending on the media device settings, such as device width and height. CSS级别的另一种解决方案是根据媒体设备设置(例如设备的宽度和高度)指定不同的图像宽度和高度。 See @media CSS rule documentation. 请参阅@media CSS规则文档。

UPD If you don't have any width or height CSS properties defined for images, you can compare their sizes to page sizes directly, but keep in mind px to pt conversion rate. UPD如果您没有为图像定义任何widthheight CSS属性,则可以直接将它们的大小与页面大小进行比较,但要记住px到pt的转换率。 Example: 例:

@Override
public IPropertyContainer getElementResult() {
    Image result = ((Image)super.getElementResult());
    if (!processed) {
        float imageWidth = result.getImageScaledWidth();
        float pageMargin = 36 * 2;
        float maxWidth = PageSize.A4.getWidth() - pageMargin;
        float maxHeight = PageSize.A4.getHeight() - pageMargin;
        if (imageWidth * 0.75 > maxWidth) {
            result.scaleToFit(maxWidth / 0.75f, maxHeight / 0.75f);
        }
        processed = true;
    }
    return result;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM